溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

如何利用Javascript簡單實(shí)現(xiàn)星空連線效果

發(fā)布時(shí)間:2022-01-07 17:44:05 來源:億速云 閱讀:190 作者:iii 欄目:web開發(fā)

這篇文章主要講解了“如何利用Javascript簡單實(shí)現(xiàn)星空連線效果”,文中的講解內(nèi)容簡單清晰,易于學(xué)習(xí)與理解,下面請(qǐng)大家跟著小編的思路慢慢深入,一起來研究和學(xué)習(xí)“如何利用Javascript簡單實(shí)現(xiàn)星空連線效果”吧!

如何利用Javascript簡單實(shí)現(xiàn)星空連線效果

Javascript 星空連線效果的簡單實(shí)現(xiàn)

之前有見過非常炫酷的粒子連線的效果,這篇文章主要是實(shí)現(xiàn)一個(gè)簡單的星空連線的效果。

先貼一下大概的效果圖。

如何利用Javascript簡單實(shí)現(xiàn)星空連線效果

這個(gè)主要是用到了Html5中的canvas繪圖,關(guān)于canvas的基本使用這里就不展開介紹了,大家可以自行去了解。

然后采用的是requestAnimationFrame來進(jìn)行動(dòng)畫的繪制,而沒有采用定時(shí)器。

一、實(shí)現(xiàn)的效果

  • 星星自動(dòng)生成,且星星的顏色,初始位置,移動(dòng)方向都是隨機(jī)的。

  • 當(dāng)星星之間的距離小于給定值之后,會(huì)在星星之間生成連線。

  • 鼠標(biāo)指針和星星之間的距離小于給定值之后,也會(huì)在星星和鼠標(biāo)指針之間生成連線。

二、實(shí)現(xiàn)的方法

通過canvas繪圖實(shí)現(xiàn)

定義星星類Star, 包括位置,半徑,顏色,移速等屬性與繪制和移動(dòng)等方法。

繪制星星,實(shí)現(xiàn)隨機(jī)移動(dòng)的效果。

在繪制星星之后計(jì)算每個(gè)星星之間的距離,在符合要求的星星之間繪制連線。

計(jì)算鼠標(biāo)指針和星星之間的距離,在符合要求的星星之間繪制連線。

繪制采用requestAnimationFrame

在主函數(shù)中執(zhí)行4,5的函數(shù)繼續(xù)進(jìn)行繪制

三、具體的實(shí)現(xiàn)

Html + Css

基本的文檔結(jié)構(gòu)非常簡單,創(chuàng)建一個(gè)canvas容器就可以了。

<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>星空連線</title>
    <style type="text/css">
        * {
            margin: 0;
            padding: 0;
        }
        body,
        html {
            width: 100%;
            height: 100%;
            overflow: hidden;
        }
        #starry {
            position: absolute;
            background-color: #000000;
        }
    </style>
</head>
<body>
    <canvas id="starry"></canvas>
</html>

定義星星類Star, 包括位置,半徑,顏色,移速等屬性與繪制和移動(dòng)等方法。

      class Star {
            constructor() {
                this.x = randNum(3, canvas.width - 3);
                this.y = randNum(3, canvas.height - 3);
                this.r = randNum(1, 3);
                this.color = randColor();
                this.speedX = randNum(-2, 2) * 0.2;
                this.speedY = randNum(-3, 3) * 0.2;
            }
            // 繪制每個(gè)星點(diǎn)
            draw() {
                //新建一條路徑
                ctx.beginPath();
                //調(diào)整透明度
                ctx.globalAlpha = 1;
                // 填充顏色
                ctx.fillStyle = this.color;
                // 繪制圓弧
                ctx.arc(this.x, this.y, this.r, 0, Math.PI * 2);
                // 填充
                ctx.fill();
            }
            // 星星移動(dòng)
            move() {
                this.x += this.speedX;
                this.y += this.speedY;
                //設(shè)置極限值
                if (this.x <= 3 || this.x >= canvas.width - 3) this.speedX *= -1;
                if (this.y <= 3 || this.y >= canvas.height - 3) this.speedY *= -1;
            }
        }
        // 存儲(chǔ)小球
        let stars = [];
        for (let i = 0; i < 150; i++) {
            let star = new Star();
            // 存入數(shù)組
            stars.push(star);
        }

繪制星星,實(shí)現(xiàn)隨機(jī)移動(dòng)的效果。

我們可以先實(shí)現(xiàn)星星的繪制,先暫時(shí)不管連線的效果。

        function drawLine() {
            for (var i = 0; i < stars.length; i++) {
                stars[i].draw();
                stars[i].move();
            }
        }

在繪制星星之后計(jì)算每個(gè)星星之間的距離,在符合要求的星星之間繪制連線。

其實(shí)只要在上一步的函數(shù)中添加距離判斷和繪制連線的代碼就可以了。

        function drawLine() {
            for (var i = 0; i < stars.length; i++) {
                stars[i].draw();
                stars[i].move();
                for (var j = 0; j < stars.length; j++) {
                    if (i != j) {
                        if (Math.sqrt(Math.pow((stars[i].x - stars[j].x), 2) + Math.pow((stars[i].y - stars[j].y), 2)) < 80) {
                            ctx.beginPath();
                            ctx.moveTo(stars[i].x, stars[i].y);
                            ctx.lineTo(stars[j].x, stars[j].y);
                            ctx.strokeStyle = "white";
                            ctx.globalAlpha = 0.2;
                            ctx.stroke();
                        }
                    }
                }
            }
        }

計(jì)算鼠標(biāo)指針和星星之間的距離,在符合要求的星星之間繪制連線。

和繪制星星的方法差不多。

      function mouseLine() {
            for (var i = 0; i < stars.length; i++) {
                if (Math.sqrt(Math.pow((stars[i].x - mouseX), 2) + Math.pow((stars[i].y - mouseY), 2)) < 120) {
                    ctx.beginPath();
                    ctx.moveTo(stars[i].x, stars[i].y);
                    ctx.lineTo(mouseX, mouseY);
                    ctx.strokeStyle = "white";
                    ctx.globalAlpha = 0.8;
                    ctx.stroke();
                }
            }
        }

主函數(shù)進(jìn)行繪制

      function main() {
            // 清除矩形區(qū)域
            ctx.clearRect(0, 0, canvas.width, canvas.height);
            //鼠標(biāo)移動(dòng)繪制連線
            mouseLine();
            // 小球之間自動(dòng)連線
            drawLine();
            // 不斷重新執(zhí)行main(繪制和清除)
            window.requestAnimationFrame(main);
        }

一些輔助隨機(jī)函數(shù)

      // 隨機(jī)函數(shù)
        function randNum(m, n) {
            return Math.floor(Math.random() * (n - m + 1) + m);
        }
        // 隨機(jī)顏色
        function randColor() {
            return 'rgb(' + randNum(0, 255) + ',' + randNum(0, 255) + ',' + randNum(0, 255) + ')';
        }

完整的代碼

<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>星空連線</title>
    <style type="text/css">
        * {
            margin: 0;
            padding: 0;
        }
        body,
        html {
            width: 100%;
            height: 100%;
            overflow: hidden;
        }
        #starry {
            position: absolute;
            background-color: #000000;
        }
    </style>
</head>
<body>
    <canvas id="starry"></canvas>
    <script type="text/javascript">
        // 獲取canvas容器
        let canvas = document.getElementById('starry');
        // 獲取屏幕的寬高
        canvas.width = document.documentElement.clientWidth;
        canvas.height = document.documentElement.clientHeight;
        // 設(shè)置繪制模式為2d
        let ctx = canvas.getContext('2d');
        class Star {
            constructor() {
                this.x = randNum(3, canvas.width - 3);
                this.y = randNum(3, canvas.height - 3);
                this.r = randNum(1, 3);
                this.color = 'pink';
                this.color = randColor();
                this.speedX = randNum(-2, 2) * 0.2;
                this.speedY = randNum(-3, 3) * 0.2;
            }
            // 繪制每個(gè)星點(diǎn)
            draw() {
                //新建一條路徑
                ctx.beginPath();
                //調(diào)整透明度
                ctx.globalAlpha = 1;
                // 填充顏色
                ctx.fillStyle = this.color;
                // 繪制圓弧
                ctx.arc(this.x, this.y, this.r, 0, Math.PI * 2);
                // 填充
                ctx.fill();
            }
            // 小球移動(dòng)
            move() {
                this.x += this.speedX;
                this.y += this.speedY;
                //設(shè)置極限值
                if (this.x <= 3 || this.x >= canvas.width - 3) this.speedX *= -1;
                if (this.y <= 3 || this.y >= canvas.height - 3) this.speedY *= -1;
            }
        }
        // 存儲(chǔ)小球
        let stars = [];
        for (let i = 0; i < 150; i++) {
            let star = new Star();
            // 存入數(shù)組
            stars.push(star);
        }
        let mouseX; let mouseY;
        canvas.onmousemove = function (e) {
            var e = event || e;
            mouseX = e.offsetX;
            mouseY = e.offsetY;
            // console.log(mouseX+','+mouseY);
        }
        // 主要事件
        main();
        function mouseLine() {
            for (var i = 0; i < stars.length; i++) {
                if (Math.sqrt(Math.pow((stars[i].x - mouseX), 2) + Math.pow((stars[i].y - mouseY), 2)) < 120) {
                    ctx.beginPath();
                    ctx.moveTo(stars[i].x, stars[i].y);
                    ctx.lineTo(mouseX, mouseY);
                    ctx.strokeStyle = "white";
                    ctx.globalAlpha = 0.8;
                    ctx.stroke();
                }
            }
        }
        // 在一定范圍內(nèi)劃線
        function drawLine() {
            for (var i = 0; i < stars.length; i++) {
                stars[i].draw();
                stars[i].move();
                // for (var j = 0; j < stars.length; j++) {
                //     if (i != j) {
                //         if (Math.sqrt(Math.pow((stars[i].x - stars[j].x), 2) + Math.pow((stars[i].y - stars[j].y), 2)) < 80) {
                //             ctx.beginPath();
                //             ctx.moveTo(stars[i].x, stars[i].y);
                //             ctx.lineTo(stars[j].x, stars[j].y);
                //             ctx.strokeStyle = "white";
                //             ctx.globalAlpha = 0.2;
                //             ctx.stroke();
                //         }
                //     }
                // }
            }
        }
        function main() {
            // 清除矩形區(qū)域
            ctx.clearRect(0, 0, canvas.width, canvas.height);
            //鼠標(biāo)移動(dòng)繪制連線
            mouseLine();
            // 小球之間自動(dòng)連線
            drawLine();
            // 不斷重新執(zhí)行main(繪制和清除)
            window.requestAnimationFrame(main);
        }
        // 隨機(jī)函數(shù)
        function randNum(m, n) {
            return Math.floor(Math.random() * (n - m + 1) + m);
        }
        // 隨機(jī)顏色
        function randColor() {
            return 'rgb(' + randNum(0, 255) + ',' + randNum(0, 255) + ',' + randNum(0, 255) + ')';
        }
    </script>
</body>
</html>

結(jié)果如下:

如何利用Javascript簡單實(shí)現(xiàn)星空連線效果

感謝各位的閱讀,以上就是“如何利用Javascript簡單實(shí)現(xiàn)星空連線效果”的內(nèi)容了,經(jīng)過本文的學(xué)習(xí)后,相信大家對(duì)如何利用Javascript簡單實(shí)現(xiàn)星空連線效果這一問題有了更深刻的體會(huì),具體使用情況還需要大家實(shí)踐驗(yàn)證。這里是億速云,小編將為大家推送更多相關(guān)知識(shí)點(diǎn)的文章,歡迎關(guān)注!

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI