• JavaScript动画实例:运动的字母特效


          已知圆的坐标方程为:

              X=R*SIN(θ)

              Y=R*COS(θ)     (0≤θ≤2π)

          给定初始坐标位置(X,Y),按照圆的坐标方程,从角度angle = 0开始,每间隔angleSpeed = 0.2求得一个坐标值(x,y),将这个坐标值作为偏移变化量,分别加到初始坐标位置上,即在(X+x,Y+y)处填充字母A。填充15个字母后,清除画布,重新从初始坐标位置开始动画过程。

    编写如下的HTML代码。

    <html>

    <head>

    <title>旋转的字母(一)</title>

    </head>

    <body>

    <canvas id="myCanvas" width="600" height="600" style="border:3px double #996633;background:black;"></canvas>

    <script>

        var canvas = document.getElementById('myCanvas');

        var ctx = canvas.getContext('2d');

        var w2 = Math.floor(canvas.width/ 2);

        var h2 = Math.floor(canvas.height/ 2);

        var pi2 = Math.PI * 2;

        ctx.font = "36px Impact";

        ctx.translate(w2, h2);

        var char = "A";

        var x =0;

        var y =0;

        var radius = 30;

        var angle = 0;

        var angleSpeed = 0.2;

        var color='rgba(0,255,255,0.9)';

        var age = 0;

        function animate()

        {

            ctx.fillStyle=color;

            ctx.fillText(char, x, y);

            x += Math.cos(angle) * radius;

            y += Math.sin(angle) * radius;

            angle += angleSpeed;

            age++;

            if (age >= 15)

            {

               ctx.clearRect(-canvas.width,-canvas.height,2*canvas.width,2*canvas.height);

               x = 0;

               y = 0;

               angle = 0;

               age=0;

            }

        }

        setInterval('animate()',100);

    </script>

    </body>

    </html>

          在浏览器中打开包含这段HTML代码的html文件,可以看到在浏览器窗口中呈现出如图1所示的动画效果。

     

    图1  angleSpeed = 0.2的字母运动效果

          若将上面程序中的语句“var angleSpeed = 0.2;”改写为“var angleSpeed = 0.45;”,其余部分保持不变,则在浏览器窗口中呈现出如图2所示的动画效果。

     

    图2  angleSpeed = 0.45的字母运动效果

          由图1和图2看出,输出的字母A看起来沿着一个圆周线,但字母均是朝向正上方,能否让字母朝着圆周线的方向呢?这需要在输出字母的时候适当旋转坐标。将程序中的语句

                ctx.fillText(char, x, y);

          改写为:

            ctx.translate(x, y);

            ctx.rotate(angle + pi2 / 4);

            ctx.fillText(char, -13,10);

            ctx.rotate(-angle-pi2 / 4);

            ctx.translate(-x, -y);

          其余部分保持不变,则在浏览器窗口中呈现出如图3所示的动画效果。

     

    图3  沿着圆周线运动的字母

          由图3看出,字母A的运动轨迹是确定的。若在角度angle的变化中加入随机因素会怎样呢?编写如下的HTML文件。

    <html>

    <head>

    <title>旋转的字母(二)</title>

    </head>

    <body>

    <canvas id="myCanvas" width="600" height="600" style="border:3px double #996633;background:black;"></canvas>

    <script>

        var canvas = document.getElementById('myCanvas');

        var ctx = canvas.getContext('2d');

        var w2 = Math.floor(canvas.width/ 2);

        var h2 = Math.floor(canvas.height/ 2);

        var pi2 = Math.PI * 2;

        ctx.font = "36px Impact";

        ctx.translate(w2, h2);

        var char = "A";

        var x =0;

        var y =0;

        var radius = 30;

        var angle = pi2*0.05;

        var angleSpeed = 0.2;

        var color='rgba(0,255,255,0.9)';

        var age = 0;

        function animate()

        {

            ctx.fillStyle=color;

            ctx.translate(x, y);

            ctx.rotate(angle + pi2 / 4);

            ctx.fillText(char, -13, 10);

            ctx.rotate(-angle-pi2 / 4);

            ctx.translate(-x, -y);

            x += Math.cos(angle) * radius;

            y += Math.sin(angle) * radius;

            angle += angleSpeed;

            age++;

            if (Math.random() > 0.75)    // 加入随机变化

            {

                 angleSpeed *= -1;

            }

            if (age >= 15)

            {

               ctx.clearRect(-canvas.width,-canvas.height,2*canvas.width,2*canvas.height);

               x = 0;

               y = 0;

               angle = pi2*0.05;

               angleSpeed = 0.2;

               age=0;

            }

        }

        setInterval('animate()',100);

    </script>

    </body>

    </html>

          在浏览器中打开包含这段HTML代码的html文件,可以看到在浏览器窗口中呈现出如图4所示的动画效果。此时字母的运动轨迹就随机变化着了。

     

    图4  有着随机变化的沿着圆周线运动的字母

          进一步我们考虑,能否将图4的字母轨迹按一个圆周相似地绘制5条呢?采用一个循环加上适当的坐标旋转即可。编写如下的HTML文件。

    <html>

    <head>

    <title>旋转的字母(三)</title>

    </head>

    <body>

    <canvas id="myCanvas" width="600" height="600" style="border:3px double #996633;background:black;"></canvas>

    <script>

        var canvas = document.getElementById('myCanvas');

        var ctx = canvas.getContext('2d');

        var w2 = Math.floor(canvas.width/ 2);

        var h2 = Math.floor(canvas.height/ 2);

        var pi2 = Math.PI * 2;

        ctx.font = "36px Impact";

        ctx.translate(w2, h2);

        var char = "A";

        var x =30;

        var y =30;

        var radius = 30;

        var angle = pi2*0.05;

        var angleSpeed = 0.2;

        color='rgba(0,255,255,0.9)';

        age = 0;

        symmetry =5;

        function animate()

        {

            for (i = 0;i<symmetry; i++)

            {

                ctx.fillStyle=color;

                ctx.translate(x, y);

                ctx.rotate(angle + pi2 / 4);

                ctx.fillText(char, -13, 10);

                ctx.rotate(-angle-pi2 / 4);

                ctx.translate(-x, -y);

                ctx.rotate(pi2 / symmetry);

            }

            x += Math.cos(angle) * radius;

            y += Math.sin(angle) * radius;

            angle += angleSpeed;

            age++;

            if (Math.random() > 0.75)

            {

                 angleSpeed *= -1;

            }

            if (age >= 15)

            {

               ctx.clearRect(-canvas.width,-canvas.height,2*canvas.width,2*canvas.height);

               x = 30;

               y = 30;

               angle = pi2*0.05;

               angleSpeed = 0.2;

               age=0;

            }

        }

        setInterval('animate()',100);

    </script>

    </body>

    </html>

          在浏览器中打开包含这段HTML代码的html文件,可以看到在浏览器窗口中呈现出如图5所示的动画效果。

     

    图5  字母A的5条相似运动轨迹

          更进一步,我们将上面程序中的初始坐标位置(x,y)、初始角度angle、角度变化量angleSpeed、字母填充颜色color和相似轨迹条数symmetry均采用随机数的方式确定初值,例如:

           x = rand(-w2/2,w2/2);

           y = rand(-h2/2,h2/2);

           angle = Math.random() * pi2;

           angleSpeed = Math.random() * 1 - 0.5;

           color='rgba('+rand(0,255)+','+rand(0,255)+','+rand(0,255)+',0.9)';

           symmetry =rand(3,10);

    编写如下的HTML代码。

    <html>

    <head>

    <title>旋转的字母(四)</title>

    </head>

    <body>

    <canvas id="myCanvas" width="600" height="600" style="border:3px double #996633;background:black;"></canvas>

    <script>

        var canvas = document.getElementById('myCanvas');

        var ctx = canvas.getContext('2d');

        var w2 = Math.floor(canvas.width/ 2);

        var h2 = Math.floor(canvas.height/ 2);

        var pi2 = Math.PI * 2;

        ctx.font = "36px Impact";

        ctx.translate(w2, h2);

        function rand(min,max)

        {

            return Math.floor(Math.random()*(max-min)+min)

        }  

        var char = "A";

        var x,y,radius,angle,angleSpeed,color,age,symmetry;

        function reset()

        {

           x = rand(-w2/2,w2/2);

           y = rand(-h2/2,h2/2);

           radius = 30;

           angle = Math.random() * pi2;

           angleSpeed = Math.random() * 1 - 0.5;

           color='rgba('+rand(0,255)+','+rand(0,255)+','+rand(0,255)+',0.9)';

           age = 0;

           symmetry =rand(3,10);

        }

        reset();

        function animate()

        {

            for (i = 0;i<symmetry; i++)

            {

                ctx.fillStyle=color;

                ctx.translate(x, y);

                ctx.rotate(angle + pi2 / 4);

                ctx.fillText(char, -13, 10);

                ctx.rotate(-angle-pi2 / 4);

                ctx.translate(-x, -y);

                ctx.rotate(pi2 / symmetry);

            }

            x += Math.cos(angle) * radius;

            y += Math.sin(angle) * radius;

            angle += angleSpeed;

            age++;

            if (Math.random() > 0.75)

            {

                 angleSpeed *= -1;

            }

            if (age >= 18)

            {

              ctx.clearRect(-canvas.width,-canvas.height,2*canvas.width,2*canvas.height);

              reset();

            }

        }

        setInterval('animate()',50);

    </script>

    </body>

    </html>

          在浏览器中打开包含这段HTML代码的html文件,可以看到在浏览器窗口中呈现出如图6所示的动画效果。

     

    图6   字母A的随机运动

          最后,我们在图6的基础上考虑,能否搞多个字母有周期地组合进行运动,以此得到字母的运动特效呢?编写如下的HTML文件。

    <html>

    <head>

    <title>旋转的字母(五)</title>

    </head>

    <body>

    <canvas id="myCanvas" width="600" height="600" style="border:3px double #996633;background:black;"></canvas>

    <script>

        var canvas = document.getElementById('myCanvas');

        var ctx = canvas.getContext('2d');

        var w2 = Math.floor(canvas.width/ 2);

        var h2 = Math.floor(canvas.height/ 2);

        var pi2 = Math.PI * 2;

        ctx.font = "36px Impact";

        ctx.translate(w2, h2);

        var srcChar =["A","B","C","D","E","F"];

        var particles = [];

        var eIndex = 0;

        var rCnt=0;

        function rand(min,max)

        {

            return Math.floor(Math.random()*(max-min)+min)

        }  

        function resetPart(part)

        {

           part.char = srcChar[eIndex++];

           if (eIndex>=srcChar.length)

           {

               eIndex=0;

           }

           part.x = rand(-w2/2,w2/2);

           part.y = rand(-h2/2,h2/2);

           part.radius = 30;

           part.angle = Math.random() * pi2;

           part.angleSpeed = Math.random() * 1 - 0.5;

           part.color='rgba('+rand(0,255)+','+rand(0,255)+','+rand(0,255)+',0.9)';

           part.age = 0;

           part.symmetry =rand(3,10);

        }

        var count=2;

        for (var i=0;i<count;i++)

        {

            var part;

            part = {};

            resetPart(part);

            rCnt++;

            particles.push(part);

        }

        function animate()

        {

           for (i =0;i<particles.length; i++)

           {

              part = particles[i];

              for (j = 0;j<part.symmetry; j++)

              {

                  ctx.fillStyle=part.color;

                  ctx.translate(part.x, part.y);

                  ctx.rotate(part.angle + pi2 / 4);

                  ctx.fillText(part.char, -13, 10);

                  ctx.rotate(-part.angle-pi2 / 4);

                  ctx.translate(-part.x, -part.y);

                  ctx.rotate(pi2 / part.symmetry);

              }

              part.x += Math.cos(part.angle) * part.radius;

              part.y += Math.sin(part.angle) * part.radius;

              part.angle += part.angleSpeed;

              part.age++;

              if (Math.random() > 0.75)

              {

                  part.angleSpeed *= -1;

              }

              if (part.age >= 18)

              {

                 resetPart(part);

                 rCnt++;

                 if (rCnt==6)

                 {

                    rCnt=0;

                    ctx.clearRect(-canvas.width,-canvas.height,2*canvas.width,2*canvas.height);

                 }

              }

           }

        }

        setInterval('animate()',50);

    </script>

    </body>

    </html>

          在浏览器中打开包含这段HTML代码的html文件,可以看到在浏览器窗口中呈现出如图7所示的动画效果。

     

    图7  字母的运动特效

  • 相关阅读:
    链式前向星啊
    并 查 集 ! ! !
    看似很水的题--找画笔
    tarjan
    动态内存分配
    C++ 基础中的基础 ---- 引用
    STL 补档
    错题笔记和易错点提醒
    题解 P2253 【好一个一中腰鼓!】
    PAT-A1003
  • 原文地址:https://www.cnblogs.com/cs-whut/p/13413820.html
Copyright © 2020-2023  润新知