实现内容:
类似于csdn个人博客,每篇文章都分成一个一个板块,我实现的功能是:随着浏览器滚动条往下滚动,每个文章div都以一个特效出现,并且每次刷新网页的特效都不同(仅限近两次,也就是连续两次不同,但是第一次和第三次可能相同)
环境:
<link rel="stylesheet" href="//cdn.bootcss.com/animate.css/3.5.1/animate.min.css">
<script src="https://cdn.bootcss.com/jquery-cookie/1.4.1/jquery.cookie.js"></script>
<script src="https://cdn.bootcss.com/jquery/3.3.1/jquery.js"></script>
思路来源:
诗酒趁年华 【有想开发自己博客的可以模仿一下他的博客,个人认为很好看】
第一次看他的博客觉得很好看,特别是特效特别震撼,以前接触过这种特效,但是不知道怎么实现的,于是也没太在意,最近在开发自己的博客,觉得自己的首页太过于单调,想加点特效,于是就好好研究了一下他是怎么实现的,终于功夫不负有心人,我在他网页源码上发现了这一行代码
<link href="//cdn.bootcss.com/animate.css/3.5.1/animate.min.css" rel="stylesheet">
bootcss上的CDN加速项目,于是百度了一下这个animate,原来是css3特效插件,来到官网逛了一圈,发现很多有趣的特效,解决了一大特效难题(对CSS没研究过,不太会自己写特效.....)
只需要导入相关css文件,并给div加入类名,即可实现动画播放动能
突破一、
在仔细研究一下他的效果,随着滚动条向下移动,每个div以一定的特效出现,应该是给滚动条增加监听
在jquery的API查了一下滚动监听(以前一直原生js...鬼知道我怎么想的...)
$(window).scroll(function(){
.....
})
思路就是,在滚动事件中监听每一个div到当前可视窗口最下边的距离,如果到一定的返回内,则设置div可见,并播放动画(通俗点说,等div马上要从底下出现的时候,就播放动画)
于是开始查找相关属性
- offset【获取匹配在当前视口的相对偏移。返回的对象包含两个整型属性:top 和 left,以像素计。此方法只对可见元素有效】
- scrollTop【获取匹配元素相对滚动条顶部的偏移。此方法对可见和隐藏元素均有效】
- height:【计算当前元素的高度值】
具体判断条件就是,首先判断当前滚动条向下滚动的值,如果这个值 > (当前元素相对于当前窗口的值 - 当前窗口高度)
但是有个问题就是(如果只是满足这个条件,会出现的问题就是元素的最顶部一出现或者还没出现,已经开始播放动画,可能你还没看到,动画已经播放完了,经过我的尝试,在条件的最后边加上15,就是div露出一块,在播放动画,效果比较好,大家可以自己测试一下)
则满足div播放动画的条件,播放动画
突破二、
还有一个需求就是每次刷新页面都出现不同的特效,思路比较简单,通过定义一个效果的数组,每次产生一个效果数组范围内的随机数,添加类名的时候,选择数组中的元素即可,因此现在的问题就是两次刷新网页产生不同的随机数,我目前能想到的思路是使用cookie,第一次在$(document).ready()函数中产生随机数,并通过cookie保存到浏览器,第二次在产生随机数时便与第一次进行比较,如果相同,则再次产生随机数,直到产生一个不同的随机数,在退出循环
核心代码:
/* 存放效果的数组 */
var effectArr = ["lightSpeedIn", "fadeInRight", "fadeInUp", "flipInX", "zoomIn", "rotateInDownRight", "rubberBand", "bounceIn", "bounceInUp", "fadeInDown", "rotateInDownLeft", "rotateInUpLeft", "rollIn"];
/* 随机数 */
var randomNum = generateRandomNum(effectArr.length);
/* 从cookie读取的随机数 */
var cookieNum = parseInt($.cookie("randomCookie"));
/**
* DOM加载完毕后,产生一个随机数,并将其存入cookie
* 通过while循环产生随机数,如果不同于cookie中读取出的,则退出循环,并将新数字存入cookie
*/
$(window).ready(function () {
while (true) {
/* 若两个数相同,则再次产生随机数,如果不同,则将新的数放入cookie,同时推出循环 */
if (randomNum === cookieNum) {
console.log("重新产生随机数中......");
randomNum = generateRandomNum(effectArr.length);
} else {
//将新产生的随机数存入cookie
$.cookie("randomCookie", randomNum);
break;
}
}
});
$(window).scroll(function () {
// 在scroll函数中,不断检测进度条滚动值与每一个div的位置关系,如果满足条件,则调用相关函数
$(".article").each(function () {
// 获取每一个div距离网页最顶端的距离,因此div需要设置relative定位
var above_top = $(this).offset().top;
// 获取当前窗口距离
var window_height = $(window).height();
// 获取滚动条滚动了多少
var scrollTop = $(window).scrollTop();
// var elemHeight = $(this).height();
// 如果滚动条滚动的高度大 > (元素距离顶部距离 - 当前窗口高度 + 15)
// 加15是为了让div露出一点在播放动画,所以最开始让div隐藏
if (scrollTop > (above_top - window_height + 15)) {
$(this).css({"visibility": "visible","opacity":"0.8"});
//添加animated属性
$(this).addClass("animated");
$(this).addClass(effectArr[randomNum]);
}
});
});
/**
* 根据传入数组的长度产生一个随机数,用于控制网页效果
* @param arrayLength
* @returns {number}
*/
function generateRandomNum(arrayLength) {
return parseInt(Math.random() * arrayLength);
}
html代码随便写了写,我的是jsp页面,,有点乱
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>animate</title>
<style>
.article {
visibility: hidden;
position: relative;
padding: 20px;
width: 100%;
background: #000;
border-bottom: 1px solid #ccc;
margin-bottom: 25px;
border-radius: 10px;
opacity: 0.8;
box-shadow: 3px 2px 8px rgba(0, 0, 0, 0.15);
line-height: 200%;
}
</style>
</head>
<body>
<div class="container">
<div class="article">
<p style="line-height:200px;color:#fff;text-align:center">随便写点啥撑起div</p>
</div>
<div class="article">
<p style="line-height:200px;color:#fff;text-align:center">随便写点啥撑起div</p>
</div>
<div class="article">
<p style="line-height:200px;color:#fff;text-align:center">随便写点啥撑起div</p>
</div>
<div class="article">
<p style="line-height:200px;color:#fff;text-align:center">随便写点啥撑起div</p>
</div>
</div>
</body>
</html>
做到这,兴高采烈的去测试我的代码,????各种bug
补充一、
由于我的动画是监听的滚动条,滚动条不滚动时,无法触发动画,也就是屏幕最初几个div无法播放动画,因此在加载完DOM节点后,判断哪些div在最初识的屏幕上,单独播放动画,实现衔接
也就是在$(window).ready()中兼容这一部分,于是对页面最上面几个元素进行了处理,处理完后,将滚动条滚动到最上面,刷新网页,果然最上面几个div成功播放动画,于是兴高采烈的将代码提交到git,出去玩耍
晚上又拿出来看我的网页,将滚动条移动到窗口某一地方,再次刷新页面.....问题又出现了,怎么在当前可视区域内不播放动画...有一个问题,真的是太脆弱了...经不住测试
补充二、
本来只考虑了,整个网页如果不滚动鼠标,无法触发动画,也就是网页最上边部分,无法播放动画于是单独考虑了上面部分单独播放动画,然后又出现了新的问题,如果网页已经移动到最后此时F5,发现,当前可视窗口仍然无法播放动画,于是调整思路如果当前元素距离顶部高度-滚动条滚动的距离 < 当前窗口的实际高度则证明当前元素在可视范围内,则播放动画,问题解决,实现所有区域衔接,尽情刷新吧...
附js全部代码
/**
* @description:
* 每次打开网页,文章切换效果均不同
* 通过将每次产生的随机数放入cookie中,再次打开后从cookie中读出该数字
* 并与新产生的数字进行比较,如果相同,则再次产生随机数,直到产生不同的随机数
* @author rambler
* @time 2019年3月10日16:32:14
*/
/* 存放效果的数组 */
var effectArr = ["lightSpeedIn", "fadeInRight", "fadeInUp", "flipInX", "zoomIn", "rotateInDownRight", "rubberBand", "bounceIn", "bounceInUp", "fadeInDown", "rotateInDownLeft", "rotateInUpLeft", "rollIn"];
/* 随机数 */
var randomNum = generateRandomNum(effectArr.length);
/* 从cookie读取的随机数 */
var cookieNum = parseInt($.cookie("randomCookie"));
/**
* DOM加载完毕后,产生一个随机数,并将其存入cookie
* 通过while循环产生随机数,如果不同于cookie中读取出的,则退出循环,并将新数字存入cookie
*/
$(window).ready(function () {
while (true) {
/* 若两个数相同,则再次产生随机数,如果不同,则将新的数放入cookie,同时推出循环 */
if (randomNum === cookieNum) {
console.log("重新产生随机数中......");
randomNum = generateRandomNum(effectArr.length);
} else {
//将新产生的随机数存入cookie
$.cookie("randomCookie", randomNum);
break;
}
}
/*
兼容处理
*/
$(".article").each(function(){
console.log($(this).offset().top);
console.log("高度"+$(window).height());
if(($(this).offset().top-$(window).scrollTop())<($(window).height())){
$(this).css("visibility", "visible");
$(this).addClass("animated");
$(this).addClass(effectArr[randomNum]);
}
else{
$(this).removeClass("animated");
$(this).removeClass(effectArr[randomNum]);
}
});
});
/**
* 监控滚动条事件,当超过一定距离,则触发相应函数
*/
$(window).scroll(function () {
// 在scroll函数中,不断检测进度条滚动值与每一个div的位置关系,如果满足条件,则调用相关函数
$(".article").each(function () {
// 获取每一个div距离网页最顶端的距离,因此div需要设置relative定位
var above_top = $(this).offset().top;
// 获取当前窗口距离
var window_height = $(window).height();
// 获取滚动条滚动了多少
var scrollTop = $(window).scrollTop();
// var elemHeight = $(this).height();
// 如果滚动条滚动的高度大 > (元素距离顶部距离 - 当前窗口高度 + 15)
// 加15是为了让div露出一点在播放动画,所以最开始让div隐藏
if (scrollTop > (above_top - window_height + 15)) {
$(this).css({"visibility": "visible","opacity":"0.8"});
//添加animated属性
$(this).addClass("animated");
$(this).addClass(effectArr[randomNum]);
}
});
});
/**
* 根据传入数组的长度产生一个随机数,用于控制网页效果
* @param arrayLength
* @returns {number}
*/
function generateRandomNum(arrayLength) {
return parseInt(Math.random() * arrayLength);
}
如果出现新的bug,请大家评论区走一走