我被困在一个关于javascript中的雪动画的项目中

时间:2019-10-27 18:53:28

标签: javascript

我必须创建一个脚本来模拟javascript中雪的动画(如果可能,我希望不使用画布)。我被困在这一点上,我不知道错误在哪里。当我运行程序谷歌浏览器崩溃且控制台没有给我错误时,我认为该错误是由于循环或某些不正确的语句所致,我附上了代码,希望对您有所帮助!

    var direction=true; //true=right false =left
    var active=true;     //if true run the cycle,false stops the cycle
    function startSnow() {

var _snowflakes = new Array(30);    
var wid=50;                       //distance from a snowflake to another
var counterX;                     //var for editing the x position
var counterY;                     //var for editing the y position
for (var i=0; i< 30; i++)         //cycle that initializes snowflakes
{
    _snowflakes[i] = document.createElement("img");   
    _snowflakes[i].setAttribute("src","snowflake.png"); // setting the image
    _snowflakes[i].setAttribute("class", "snowflake"); //setting the css style
    _snowflakes[i].style.visibility ="inherit";       //when the function is running snowflakes have to be visible, when it finishes they have to be invisible
    _snowflakes[i].style.right = (wid*i)+"px";        //set the distance from the left margin
    _snowflakes[i].style.top = "30px";           // set the distance from the top
    document.getElementById("background").appendChild(_snowflakes[i]);
}
while(active)
{
        move();
}
function move()  //function that moves the snowflake
        {
            for(;;)
        {
            if(counterY>=600)   //when the snowflake reaches 600px from the top the function has to stop and hide snowflakes
            {
                for(var i=0;i<30;i++)
                    _snowflakes[i].style.visibility = "hidden";
                active=false;
                break;
            }                
             else
            {
                if ((counterY%50)==0)
                    {
                        direction=!direction   //every 50 Y pixels the snoflake change direction
                    }
                counterY++;
                for(var i=0;i<30;i++)
                    {
                        _snowflakes[i].style.top = counterY+"px";       //Y movement     
                        if (direction==true)
                            {
                                _snowflakes[i].style.right = (_snowflakes[i].offsetLeft+counterX) + "px";      //x right movement
                                counterX++;
                            }
                        else
                            {
                                _snowflakes[i].style.right = (_snowflakes[i].offsetLeft+counterX) + "px";      //x left movement
                                counterX--;
                            }
                    }
            }
        }
    }

}

1 个答案:

答案 0 :(得分:1)

实际上,由于变量counterY没有初始化,因此它的值为undefined,因此代码进入了无限循环。在undefined中添加一个将得到NaN,因此您永远不会遇到该break语句。

但更重要的是,您需要一种不同的方法,因为即使您解决了此问题,也永远不会看到动画的发生。为了实际观看动画,您需要给浏览器一些时间来更新显示。因此,whilefor(;;)循环是不可能的。

请一次调用move,然后在该函数内的else块中调用requestAnimationFrame(move)。这将使浏览器有时间在move被称为增益之前重新绘制。删除for(;;)循环,然后删除break

水平移动也存在逻辑错误。当您阅读当前的offsetLeft时,增加counterX毫无意义,因为这会导致向右(或向左)跳跃(相对)跳跃。取而代之的是,您只需要在offsetLeft上加上(或减去)1即可取消counterX。另外,请勿将其分配给style.right,而应分配给style.left

因此,所有内容放在一起(请参见有更改的注释):

var direction=true;
var active=true;

function startSnow() {    
    var _snowflakes = new Array(30);    
    var wid=50;
    // var counterX = 0; -- not used.
    var counterY = 0; // Need to initialise!
    for (var i=0; i< 30; i++) {
        _snowflakes[i] = document.createElement("img");   
        _snowflakes[i].setAttribute("src", "snowflake.png");
        _snowflakes[i].setAttribute("alt", "❄"); // added for when image not found
        _snowflakes[i].setAttribute("class", "snowflake");
        _snowflakes[i].style.visibility = "inherit";
        _snowflakes[i].style.left = (wid*i)+"px"; // assign to style.left
        _snowflakes[i].style.top = "30px";
        document.getElementById("background").appendChild(_snowflakes[i]);
    }

    // No while loop. Just call move    
    move();
    
    function move() {
        //No for (;;) loop
        if (counterY>=600) {
            for (var i=0;i<30;i++) {
                _snowflakes[i].style.visibility = "hidden"; // you forgot the underscore
            }
            active=false;
            // No break -- function will just return
        } else {
            if ((counterY%50)==0) {
                direction=!direction
            }
            counterY++;
            for (var i=0;i<30;i++) {
                _snowflakes[i].style.top = counterY+"px";
                if (direction==true) {
                    // assign to style.left, 
                    _snowflakes[i].style.left = (_snowflakes[i].offsetLeft+1) + "px"; // add 1
                } else {
                    _snowflakes[i].style.left = (_snowflakes[i].offsetLeft-1) + "px"; // sub 1
                }
            }
            requestAnimationFrame(move); // schedule next run of this function
        }
    }
}
 
startSnow(); // Need to start it!
#background { width: 800px; height: 800px }
.snowflake { position: absolute; font-size: 40px }
<div id="background">
</div>