在日常网页开发中,我们会经常接触或加入一些动画效果,而其中一些网页动画特效是可以通过一个统一的动画函数来调用完成的。今天就给大家分享一下之前学习到的动画函数,并利用该函数实现侧边伸缩栏效果。
1、动画函数封装
先上代码:
function animate(obj, target, callback) {
// 先清除以前的定时器,只保留当前的一个定时器执行
clearInterval(obj.timer);
obj.timer = setInterval(function () {
//console.log(obj.offsetLeft);
// 动态获取步长值,步长值的获取需写到定时器里面,且需改为整数(以便能达到需要达到的距离)
var step = (target - obj.offsetLeft) / 10;
// 若step>0,则向上取整,若step<0,则向下取整
step = step > 0 ? Math.ceil(step) : Math.floor(step);
if (obj.offsetLeft == target) {
clearInterval(obj.timer);
// 若有回调函数,则调用,否则跳过
// if (callback) {
// callback();
// }
callback && callback();
}
obj.style.left = obj.offsetLeft + step + 'px';
}, 15)
}
这里创建了一个 animate(obj, target, callback) 函数,其中参数'obj'代表调用该动画函数的元素,参数'target'代表元素移动的目标距离,'callback'为可选参数,代表回调函数。
我们可看到 animate() 函数来实现指定元素 'obj' 的移动是通过定时器函数来实现的,这里我们每隔15ms调用一次定时器,每次调用都在指定元素的原来位置加上不断变化的步长值:'step' 距离,直至元素移动到指定位置时就清除定时器。
注意点:
(1)step的取值:
这里 step = (target - obj.offsetLeft) / 10; 其中 'obj.offsetLeft' 代表移动元素相对于父元素左边缘的距离。因为 'obj.offsetLeft' 会随着元素的移动而不断变化,因此 'step' 的取值也是不断变化的,且step的取值是先大后小,因此元素的移动也是先快后慢的过程。
step = step > 0 ? Math.ceil(step) : Math.floor(step); 这句代码是对 'step' 进行取整处理,对step取整时为了确保元素能移动到指定位置,且取整的数值必须要大于原数值(即step>0时,向上取整,step<0时,向下取整)。
(2)定时器的清除:
每次调用 animate() 函数时,第一步都须加入 clearInterval(obj.timer); 这句代码来清除之前的定时器,这是为防止当同一个元素多次调用 animate() 函数时,存在多个正在进行的定时器的情况。
2、利用动画函数实现侧边伸缩栏
博主利用动画函数实现侧边伸缩栏的思路为:先设定好侧边栏的盒子宽高,再设置css属性将盒子‘隐藏’在可视区域外,最后利用动画函数实现侧边栏盒子的移动,从而实现伸缩效果。这里通过代码进行解释。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>侧边伸缩栏</title>
<style>
* {
margin: 0;
padding: 0;
}
.expansionField {
position: absolute;
left: -250px;
width: 250px;
height: 100vh;
background-color: skyblue;
opacity: 0.6;
}
.flexBtn {
position: absolute;
top: 100px;
width: 20px;
height: 100px;
background-color: skyblue;
cursor: pointer;
}
</style>
</head>
<body>
<!-- 侧边伸缩栏 -->
<div class="expansionField"></div>
<!-- 展开侧边栏的按钮 -->
<div class="flexBtn"></div>
<!-- 引用动画函数 -->
<script src="./animate.js"></script>
<script>
// 声明一个变量flag,用于区分按钮的点击事件
var flag = 0;
// 获取元素
var flexBtn = document.querySelector('.flexBtn');
var expansionField = document.querySelector('.expansionField');
// 绑定事件
flexBtn.addEventListener('click', move);
function move() {
if (flag == 0) {
animate(expansionField, 0);
animate(flexBtn, 250);
flag = 1;
} else {
animate(expansionField, -250);
animate(flexBtn, 0);
flag = 0;
}
}
</script>
</body>
</html>
这里设置的侧边栏盒子宽度为250px,我们首先用绝对定位(left:-250px)将侧边栏盒子全部‘隐藏’在浏览器可视区域外部,并设置了一个按钮:flexBtn 来控制侧边栏盒子的移动。
js部分我们声明了一个变量‘flag’来区分‘flexBtn’按钮的点击事件,当 flag=0代表侧边栏展开,flag=1代表侧边栏收回,flag取值的变化在‘flexBtn’按钮绑定的事件函数move()中进行改变。
侧边栏展开时的移动距离和目标位置分析如下:
在展开前,侧边栏的offsetLeft = -250,展开后的offsetLeft = 0,因此侧边栏展开时的目标移动位置为0,即调用动画函数animate(expansionField, 0); 而伸缩栏按钮flexBtn在展开前的offsetLeft = 0,展开后offsetLeft = 250,即伸缩栏按钮控制侧边栏展开时的目标移动位置为250px,所以调用动画函数animate(flexBtn, 250); 侧边栏收回情况可同理推得。
上述代码的运行结果如下(视频上传不了,大家看一下gif图,或者自己运行一下代码):
上面只是实现了一个很简易的侧边栏伸缩功能,具体的伸缩栏界面或样式大家可以自己去添加修改和扩展。动画函数可应用于很多网页动态特效,大家可积极尝试实现。