前言
轮播图案例是一个比较重要的案例,能够在实现功能的过程中掌握大部分js代码的知识点。也是一个比较复杂的案例。涉及到的功能是比较的多,大家要一步步看才能明白哦!我也是学了好几个小时才搞明白的,当然在实际开发中都会直接用模板套。但和你自己一个字母一个字母打出来的感觉和掌握程度是有很大差别的。我感觉自己打一遍源码才是最好的效果。不多说了,直接开整。。。
一、案例实现功能描述
要实现淘宝轮播图,首先要做的是分析它的结构和功能。这里我把淘宝轮播图拿来大家一起分析。
分析结构
分析结构主要是为了写html+css 这个比较好分析,相信大家比较轻松。
1.一个大盒子放里面的内容。
2.左中和右中2个箭头。
3.把轮播的图放到ul li里。
4.ol li 实现小圆圈。
分析功能
大家看图能发现有什么功能吗?我给大家列出来看看和你的想法一样不!
1.鼠标放上去会出现左中和右中的2个箭头。
2.鼠标离开箭头也会随之消失。
3.鼠标点击箭头会出现图片轮播效果,点左箭头图片向左移动一个图片。反之也是一样的。
4.鼠标点击箭头后下方小圆圈的实心圆就会变色,展示的是对应的图片。
5.鼠标放上去后图片将不会再进行自动轮播效果。
6.鼠标离开后图片就会在间隔时间内实现自动的轮播图片。
二、html代码讲解
第一章已经把结构和功能都介绍了,现在开始整代码,先实现html布局。下述代码和分析的一样。
1.我们需要大盒子focus_f1。
2.2个箭头按钮用a标签。那个href写的是javascript:;这样点击域名栏不会跳转。
3.滚动图片区域用ul li。
4.ol 没有设置li ,因为我们要用js动态生成。是不是很高级,下面js再讲它的好处。
<!-- 轮播图 -->
<div class="focus_f1">
<!-- 左按钮 -->
<a href="javascript:;" class="arrow-l"> <</a>
<!-- 右按钮 -->
<a href="javascript:;" class="arrow-r">></a>
<!-- 滚动图片区域 -->
<ul >
<li>
<a href="#"><img src="./image/p6img/p6img1.png" ></a>
</li>
<li>
<a href="#"><img src="./image/p6img/p6img2.jpg" ></a>
</li>
<li>
<a href="#"><img src="./image/p6img/p6img3.webp" ></a>
</li>
<li>
<a href="#"><img src="./image/p6img/p6img4.jpg" ></a>
</li>
<li>
<a href="#"><img src="./image/p6img/p6img5.webp" ></a>
</li>
<li>
<a href="#"><img src="./image/p6img/p6img6.jpg" ></a>
</li>
</ul>
<ol class="circle" >
<!-- 用js添加li -->
</ol>
</div>
三、css代码讲解
到了布局样式了,html比较简单,这里就开始慢慢变难了,提醒仔细看代码哦。
下面代码就是css布局和样式的全部代码。要注意的是在没写js之前要把overflow注释掉哦。这样在写js条代码时才会很方便。还有就是大盒子一定要有相对定位。因为后边图片要轮播必须该ul的left属性值才能实现轮播效果。
/* 轮播图盒子修饰 */
.focus_f1 {
position: relative;
width: 520px;
height: 280px;
left: 0px;
top: 0px;
display: inline-block;
/* border: 1px solid #ff557f; */
overflow: hidden;
}
/* 轮播图左按钮 */
.focus_f1 .arrow-l {
position: absolute;
left: 0px;
top: 125px;
color: #FF0000;
z-index: 2;
display: none;
}
/* 轮播图右按钮 */
.focus_f1 .arrow-r {
position: absolute;
top: 125px;
left: 506px;
color: #FF0000;
z-index: 2;
display: none;
}
/* 轮播图片列表 */
.focus_f1 ul {
position: absolute;
top: 0px;
left: 0px;
list-style: none;
width: 3640px;
}
/* 每个图平铺 */
.focus_f1 ul li {
float: left;
}
/* 小圆点 ol样式 */
.focus_f1 .circle {
position: absolute;
left: 206px;
top: 250px;
width: 200px;
list-style-type: circle;
}
/* 每个li平铺 */
.focus_f1 .circle li {
width: 20px;
float: left;
color: #ffffff;
}
/* 选中的li小圆圈变色 */
.focus_f1 .circle .current {
color: #ff00ff;
}
四、js实现功能及代码讲解
html+css已经全部打出来了,但是他还不会实现轮播等鼠标监听事件的功能。所以说该我们的大哥js出马了。
首先我们要实现一个图片缓动动画的实现。把这个功能封装起来。封装成animate文件。方便我们调用。animate(移动对象,移动距离,执行的函数)三个参数。
进函数先让上一次的停止再开始执行函数代码:
clearInterval(obj.timer);
缓动的实现代码,每隔15毫秒执行移动的距离就会减少:
var step = (target - obj.offsetLeft) / 10;
缓动可能出现小数,这里我们把他取整,如果为2.1就变为3.如果为-1.1就变为-2代码。
step = step > 0 ? Math.ceil(step) : Math.floor(step);
直到等于了传过来的target就会让它停止代码,最后一个参数可以写也可以不写,写的话就执行:
if (obj.offsetLeft == target) {
clearInterval(obj.timer);
// 回调函数
if (callback) {
callback();
}
}
最后把ul li 的left值变化代码:
obj.style.left = obj.offsetLeft + step + 'px';
分开每一步都讲完了,完整的封装代码展示:
function animate(obj, target, callback) {
clearInterval(obj.timer);
obj.timer = setInterval(function() {
// var step=Math.ceil((target-obj.offsetLeft)/10);
var step = (target - obj.offsetLeft) / 10;
step = step > 0 ? Math.ceil(step) : Math.floor(step);
if (obj.offsetLeft == target) {
clearInterval(obj.timer);
// 回调函数
if (callback) {
callback();
}
}
obj.style.left = obj.offsetLeft + step + 'px';
}, 15);
}
下面我们就开始写js核心代码
创建一个lb.js文件然后获取元素代码,把要操作的元素都获取过来:
window.addEventListener('load',function(){
var arrow_l=document.querySelector('.arrow-l');
var arrow_r=document.querySelector('.arrow-r');
var focus=document.querySelector('.focus_f1');
var ul=focus.querySelector('ul');
var ol=focus.querySelector('.circle');
})
实现第一个功能鼠标放上去和离开实现箭头的显示和消失代码,加注释的下面会讲。先别着急,看不懂也没关系:
// 鼠标经过
focus.addEventListener('mouseenter',function(){
arrow_l.style.display='block';
arrow_r.style.display='block';
// 鼠标经过停止定时器
clearInterval(timer);
// 清除定时器变量
timer=null;
})
// 鼠标离开
focus.addEventListener('mouseleave',function(){
arrow_l.style.display='none';
arrow_r.style.display='none';
// 开启定时器
timer=setInterval(function(){
// 每2秒自动调用点击事件
arrow_r.click();
},2000);
})
每次图片移动都移动一个盒子的宽度,所以我们获取盒子宽度代码:
var focusWidth=focus.offsetWidth;
下面我们要动态创建ol li并且点击小圆圈就会变色并且实现图片移动过去代码,注释也都写在代码里了,这里就简单描述了,直接看代码:
for(var i=0;i<ul.children.length;i++){
// 创建li
var li=document.createElement('li');
// 记录小圆圈的索引号 自定义属性
li.setAttribute('index',i);
// 把创建li添加到ol里
ol.appendChild(li);
// 绑定点击事件
li.addEventListener('click',function(){
// 把所有li清除
for(var i=0;i<ol.children.length;i++){
ol.children[i].className='';
}
this.className='current';
// 当前li的索引号
var index=this.getAttribute('index');
// 当前小圆点的位置给num控制图片下一张播放
num=index;
// 当前小圆点的位置给小圆点,下一个移动小圆点才会正常
circle=index;
// 点击小圆圈移动图片
animate(ul,-focusWidth*index);
})
}
下面我们克隆一张图片放到ul最后面,实现走到最后一张后跳到第一张。并且把第一个ol li的小圆圈设置为默认点击样式代码:
// 把第一个小li设置类名current
ol.children[0].className='current';
// 克隆第一张图片 放到ul最后面
var first=ul.children[0].cloneNode(true);
ul.appendChild(first);
这里需要用排他思想来让点击的小圆圈变样式,其余的小圆圈都要变为默认样式代码:
function circleChange(){
// 重置小圆圈样式 排它思想
for(var i=0;i<ol.children.length;i++){
ol.children[i].className='';
}
ol.children[circle].className='current';
}
下面实现点击左右箭头后移动图片实现轮播效果代码:
// 右侧按钮
var num=0;
// 控制小圆圈的变化
var circle=0;
// 控制函数执行 防止点击过快
var flag=true;
arrow_r.addEventListener('click',function(){
if(flag){
// 有函数执行关闭 函数执行完后打开
flag=false;
// 走到了最后复制的图片 left改为0
if(num==ul.children.length-1){
ul.style.left=0+'px';
num=0;
}
num++;
animate(ul,-num*focusWidth,function(){
flag=true;
});
circle++;
if(circle==ol.children.length){
circle=0;
}
// 调用函数
circleChange();
}
})
arrow_l.addEventListener('click',function(){
if(flag){
flag=false;
// 走到了最后复制的图片 left改为0
if(num==0){
num=ul.children.length-1;
ul.style.left=-num*focusWidth+'px';
}
num--;
animate(ul,-num*focusWidth,function(){
flag=true;
});
circle--;
// if(circle<0){
// circle=ol.children.length-1;
// }
circle=circle<0 ? ol.children.length-1 :circle;
// 调用函数
circleChange();
}
})
最后就是自动2秒实现一次轮播效果的代码了:
// 自动播放定时器
var timer=setInterval(function(){
// 每2秒自动调用点击事件
arrow_r.click();
},2000);
lb.js全部代码展示
分块讲述完了代码,现在组合起来看看吧:
window.addEventListener('load',function(){
var arrow_l=document.querySelector('.arrow-l');
var arrow_r=document.querySelector('.arrow-r');
var focus=document.querySelector('.focus_f1');
// 鼠标经过
focus.addEventListener('mouseenter',function(){
arrow_l.style.display='block';
arrow_r.style.display='block';
// 鼠标经过停止定时器
clearInterval(timer);
// 清除定时器变量
timer=null;
})
// 鼠标离开
focus.addEventListener('mouseleave',function(){
arrow_l.style.display='none';
arrow_r.style.display='none';
// 开启定时器
timer=setInterval(function(){
// 每2秒自动调用点击事件
arrow_r.click();
},2000);
})
var ul=focus.querySelector('ul');
var ol=focus.querySelector('.circle');
var focusWidth=focus.offsetWidth;
for(var i=0;i<ul.children.length;i++){
// 创建li
var li=document.createElement('li');
// 记录小圆圈的索引号 自定义属性
li.setAttribute('index',i);
// 把创建li添加到ol里
ol.appendChild(li);
// 绑定点击事件
li.addEventListener('click',function(){
// 把所有li清除
for(var i=0;i<ol.children.length;i++){
ol.children[i].className='';
}
this.className='current';
// 当前li的索引号
var index=this.getAttribute('index');
// 当前小圆点的位置给num控制图片下一张播放
num=index;
// 当前小圆点的位置给小圆点,下一个移动小圆点才会正常
circle=index;
// 点击小圆圈移动图片
animate(ul,-focusWidth*index);
})
}
// 把第一个小li设置类名current
ol.children[0].className='current';
// 克隆第一张图片 放到ul最后面
var first=ul.children[0].cloneNode(true);
ul.appendChild(first);
// 右侧按钮
var num=0;
// 控制小圆圈的变化
var circle=0;
// 控制函数执行 防止点击过快
var flag=true;
arrow_r.addEventListener('click',function(){
if(flag){
// 有函数执行关闭 函数执行完后打开
flag=false;
// 走到了最后复制的图片 left改为0
if(num==ul.children.length-1){
ul.style.left=0+'px';
num=0;
}
num++;
animate(ul,-num*focusWidth,function(){
flag=true;
});
circle++;
if(circle==ol.children.length){
circle=0;
}
// 调用函数
circleChange();
}
})
arrow_l.addEventListener('click',function(){
if(flag){
flag=false;
// 走到了最后复制的图片 left改为0
if(num==0){
num=ul.children.length-1;
ul.style.left=-num*focusWidth+'px';
}
num--;
animate(ul,-num*focusWidth,function(){
flag=true;
});
circle--;
// if(circle<0){
// circle=ol.children.length-1;
// }
circle=circle<0 ? ol.children.length-1 :circle;
// 调用函数
circleChange();
}
})
function circleChange(){
// 重置小圆圈样式 排它思想
for(var i=0;i<ol.children.length;i++){
ol.children[i].className='';
}
ol.children[circle].className='current';
}
// 自动播放定时器
var timer=setInterval(function(){
// 每2秒自动调用点击事件
arrow_r.click();
},2000);
})
五、效果图
总结
这里也是讲完了,不知道你们能不能看的懂。我的语言描述能力比较差,看不懂的下去自己思考思考,何尝不是一种学习呢!轮播图是BOM中做的案例里计较麻烦的一个,我也就写这一遍啊,下次我直接打开我的博客看我的笔记了。希望大家也能自己动手实现一遍。对知识的掌握更牢固。这篇内容写了好久,看到这里的动动你们可爱的小手指点个赞呗。这也是我创作最大的动力哦!
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/114672.html