charsandrew
2017-05-30 02:40
根据老师的实现我自己写了一段代码,跟老师的不太一样,但是动画过程中有一定几率出现bug。代码如下:
<script>
window.onload=function(){
var myDiv=document.getElementById('box1');
var timer=null;
myDiv.onmouseover=function(event){
timer=setTimeout(move,30);
function move(){
clearTimeout(timer);
if(myDiv.offsetLeft>=0) return;
else{
myDiv.style.left = myDiv.offsetLeft + 5 +'px';
setTimeout(move,30);
}
}
}
myDiv.onmouseout=function(event){
timer=setTimeout(move,30);
function move(){
clearTimeout(timer);
if(myDiv.offsetLeft<=-600) return;
else{
myDiv.style.left = myDiv.offsetLeft -5 +'px';
setTimeout(move,30);
}
}
}
}
</script>我把div的宽度设置为600px,left值也为-600px,然后执行代码,在动画过程中反复触发鼠标事件。或者直接触摸span标签。有时候动画就一直执行,闪来闪去,不会停止。
我的分析是mouseover的结束条件是left>=0,mouseout的结束条件是left<=-600,当在动画过程中,即mouseover未结束时,又触发了mouseout事件。left的值就可能永远位于-600到0之间。动画就不会停止。
请问大神这样分析对不?有什么方法解除这种bug?
另外如果要实现无论是否在动画执行过程中,鼠标over上时,left就增加,鼠标移开,马上left减小这样的效果,有什么方法?
又看了下代码: 发现了其实主要是没能有效的清除定时器的问题,把代码改成下面这样就可以运行。
<script>
window.onload=function(){
var myDiv=document.getElementById('box1');
var timer=null;
myDiv.onmouseover=function(event){
move();
function move(){
clearTimeout(timer);
if(myDiv.offsetLeft>=0) return;
else{
myDiv.style.left = myDiv.offsetLeft + 5 +'px';
timer = setTimeout(move,100);
}
}
}
myDiv.onmouseout=function(event){
move();
function move(){
clearTimeout(timer);
if(myDiv.offsetLeft<=-600) return;
else{
myDiv.style.left = myDiv.offsetLeft -5 +'px';
timer = setTimeout(move,100);
}
}
}
}
</script>将函数提出来放到事件外面定义效率更高,再将两个move函数合并在一起代码会更简洁。
为了让问题更清晰,我把代码copy下来,大家可以自己试下效果。 这动画执行过程中多次快速触发鼠标事件,有惊喜哦!!
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
body{margin: 0;padding: 0;}
#box1{
width: 600px;
height: 100px;
background-color: #f00;
left: -600px;
position: relative;
}
#box1 span{
width: 20px;
height: 50px;
background-color: #00f;
position: absolute;
left: 600px;
top: 25px;
}
</style>
</head>
<body>
<div id="box1">
<span id="share">分享</span>
</div>
<script>
window.onload=function(){
var myDiv=document.getElementById('box1');
var timer=null;
myDiv.onmouseover=function(event){
timer=setTimeout(move,100);
function move(){
clearTimeout(timer);
if(myDiv.offsetLeft>=0) return;
else{
myDiv.style.left = myDiv.offsetLeft + 5 +'px';
setTimeout(move,100);
}
}
}
myDiv.onmouseout=function(event){
timer=setTimeout(move,100);
function move(){
clearTimeout(timer);
if(myDiv.offsetLeft<=-600) return;
else{
myDiv.style.left = myDiv.offsetLeft -5 +'px';
setTimeout(move,100);
}
}
}
}
实际上只需要把onmouseover和onmouseout改成onmouseenter和onmouseleave就行了,over和out指代的是鼠标经过和移出,实际上你从div移动到span中按道理来说还是在div内,但是因为涉及了span的移入移出则会出现事件冒泡。换成enter和leave(穿入穿出)后不会触发span事件,所以不会出问题,你可以试试
把你的计时器settimeout换成setInterval看看,虽然两个方法都是延时加载,但是作用有所不同
JS动画效果
113910 学习 · 1502 问题
相似问题