如何用原生javascript实现一个轮播功能呢?
我们先实现简易版v1.0:
首先是HTML部分,用一个#wrap容器将我们的内容都包裹起来,内容包括:5张定宽定高的图片、下部5个对应的数字标识、左右两侧的点击翻页按钮。
<
CSS主要逻辑是:首先让5张宽高大小一样的<img>重叠在一起相对其父容器div#wrap定位于起始处(left:0;top:0;) ,且先隐藏所有图片(display:none),
代码如下:
*
然后是js逻辑:定义一个函数run,其内部逻辑是每运行一次函数则计数标记count增加1(增到5时又置零),遍历所有图片使其样式变为display:none;即不可见,再将这一轮的第count张图片样式置为可见(display:none), 定义一个每隔一秒执行一次run函数的定时器来保证run函数的持续运行。这样,一个最简易的“轮播”便在效果上实现了。
var
接下来我们完善功能,即加上下方对应鼠标和左右侧翻页按钮的逻辑:
#
接着改造run函数:除了每一秒展示不同的图片外,这次还要加上其对应的序号数字标识标红,非对应的置灰
+
然后用户点击右侧翻页按钮能翻到“下一页”:
+
点击左侧翻页按钮回到“上一页”比较复杂,需要新建一个函数来支持:
+
再附加一个鼠标悬停的功能,基本原理其实就是打碎持续运行run函数的定时器:
+
最后再补全下方数标的功能——点击对应鼠标能切换到对应图片:
for
现在我们就完成了最简易的“轮播”啦,v1.0体验版请见:https://jsbin.com/xikijafina/edit?css,js,output
其实简易版依靠切换display为none或block的这种原理虽能勉强实现“轮播”的效果,但体验上没有动画般舒缓流畅的感官效果所以略显粗暴。第二章节我们便来优化一下:
HTML部分如下:(注意5张图片最后一张后面多放来一张图1/第一张图片前面多放了一张图5)
首先定义一个包裹内容的外容器div#wrap,其宽600高400超出部分不可见(overflow:hidden;),然后内部再放一个内容器div#list其宽4200高400 (600x(5+2)=4200),然后初始位置是将div#list相对于div#wrap左移位600(-600) 放置是为了抵消掉特意多放在图1前的图5,使网页刚加载就呈现在用户眼前的是此时实际位于第二位的图1 。
<
CSS部分如下:
#
初步效果图如下:
然后是JS部分:
function
其原理就是:当div#list容器盒子左位移逼近3600(600x6)时即已经到达图5,则立即给div#list重置为-600位移,这样就使得用户眼前看起来最后一张图5与第一张图1无缝对接。
V2.0版本效果如:https://jsbin.com/kaceyonoge/edit?html,css,js,output
假如现在有个新需求需要多张图片一起轮播每次只走一小步呢? 咱们来写V2.1的版本:
5张宽200高200的图片装在滚动容器div#list里,宽12张图的div#list盒子初始时在其宽800(200X4)高200 父容器div#wrap的左侧200px处,每隔1秒左移200直到逼近左1200前又立即重置为左200。
<!DOCTYPE html>
CSS部分:
#
JS部分:
var
V2.1版本预览:https://jsbin.com/tuxicimofu/2/edit?html,css,js,output
第二版的方法过于依赖图片宽高来计算位移,倘若图片宽度或尺寸日后变更则js逻辑需要更改很多处,这样很不稳定不适合生产环境。所以我们开始开发第三版V3.0:
<!DOCTYPE html>
CSS部分:不管原图片宽高多少我们都统一设置为宽400高200,宽5张图宽的父盒子div#list在容器div#wrap里放着,超出部分hidden。
#
JS部分:父盒子div#list每秒相对于容器div#wrap左移400,直到左移到1600就立即重置为0无缝衔接。
var
V3.0效果预览:https://output.jsbin.com/gigizutomu
我们将第三版的下方标识优化为对应数字,请看V3.1版:
<!DOCTYPE html>
CSS部分:
#
JS部分:
var
V3.1版预览:https://jsbin.com/wukobecefa/edit?html,css,js,output
再在第三版的基础上加上底部标识导航和左右翻页,优化得V3.2:
<!DOCTYPE html>
CSS部分:
#
JS部分:
var
V3.2预览见: https://jsbin.com/rotepopeka/edit?html,css,js,output
最后,让我们用面向对象来重写以上代码:
<!DOCTYPE html>
JS部分:
function
面向对象版本的V4.0预览见:https://jsbin.com/zitakuceja/edit?html,css,js,output
当然,你也可以选择向swiper这样的成熟包来直接借用轮播效果,如这种类似途家APP首页的划动层叠轮播: