<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>淘宝js运动</title> <style type="text/css"> * { padding: 0; margin: 0; } #move { width: 240px; margin: 10px auto; background-color: #f5f4f4; border: 1px solid #ccc; overflow: hidden; } #move a { float: left; display: inline-block; width: 58px; height: 25px; border: 1px solid #ddd; border-radius: 3px; background: #fff; text-align: center; margin: 10px 10px; position: relative; padding-top: 40px; color: #9c9c9c; font-size: 12px; text-decoration: none; line-height: 25px; overflow: hidden; } #move a i { position: absolute; top: 20px; left: 0; display: inline-block; width: 100%; text-align: center; opacity: 1; filter: alpha(opacity=100); } #move a:hover { color: #f00; } #move img { border: none; } </style> <script type="text/javascript" src="../move.js"></script> <script> window.onload=function(){ var oMove=document.getElementById('move'), aList=oMove.getElementsByTagName('a'); for(var i=0;i<aList.length;i++){ //onmouseenter不会影响子元素,不会引发事件冒泡 aList[i].onmouseenter=function(){ var _this=this.getElementsByTagName('i')[0]; startMove(_this,{top:-25,opacity:0},function(){ _this.style.top=30+'px'; startMove(_this,{top:20,opacity:100}); }); } } } </script> </head> <body> <div id='move'> <a href='#'><i><img src="images/tickets.png"></i><p>彩票</p></a> <a href='#'><i><img src="images/film.png"></i><p>电影</p></a> <a href='#'><i><img src="images/fork.png"></i><p>外卖</p></a> <a href='#'><i><img src="images/fly.png"></i><p>缴费</p></a> <a href='#'><i><img src="images/game.png"></i><p>游戏</p></a> <a href='#'><i><img src="images/protection.png"></i><p>理财</p></a> </div> </body>
//完美运动框架 //获取css属性 function getStyle(obj, attr) { if (obj.currentStyle) { //针对IE8获取元素某项css属性 return obj.currentStyle[attr]; } else { //针对其他浏览器,false为伪类选项 return getComputedStyle(obj, false)[attr]; } } //若传入fn(用于函数回调)执行链式运动 //startMove(obj,{attr1,iTarget1,attr2,iTarget2}, fn) function startMove(obj, json, fn) { clearInterval(obj.timer); obj.timer = setInterval(function() { var flag = true; //每次循环初始化flag值,否则flag无法为true,定时器无法真正结束 //for()in遍历循环,将json中以attr属性循环,json[attr]为它的对应值 for (var attr in json) { //1.取当前值 var iCur = 0;//初始化 if (attr == 'opacity') { iCur = Math.round(parseFloat(getStyle(obj, attr)) * 100); } else { iCur = parseInt(getStyle(obj, attr)); } //2.算速度 var speed = (json[attr] - iCur) / 5; //speed类整数变量需要判断取整 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); //3.检测停止 //只要有一个运动目标没有完成,则flag为false,未完成运动继续执行 //已达到的运动目标会因为speed最终等于0而“停止”,没有实际停止定时器 if (iCur != json[attr]) { flag = false; } if (attr == 'opacity') { obj.style.filter = 'alpha(opacity:' + (iCur + speed) + ')'; obj.style.opacity = (iCur + speed) / 100; } else { //用style[]追加变量,因为attr传入的是字符所以不能用style.xxx obj.style[attr] = iCur + speed + 'px'; } } //如果flag成立,即所有运动目标完成,则停止定时器,判断是否有回调函数存在 if (flag) { clearInterval(obj.timer); if (fn) { //为了不让fn()在回调时指向window,用call()改变this指向 //var that=this也可以 fn.call(obj); } } }, 10)//时间间隔,变更达到增减动画速度 }
转发:JS动画框架及案例链接 https://blog.csdn.net/qq_15096707/article/details/50571021