标签:listener start 转换 tle extc absolute 轮播图片 hang round
先上效果
https://rencoo.github.io/webproject/images/3DchangImg/index.html
完成目标
CODE部分
<!DOCTYPE html> <html lang="en" dir="ltr"> <head> <meta charset="utf-8"> <title>3D图片轮播图</title> <link rel="stylesheet" href="change.css"> </head> <body> <div id="my-slider"> <!-- 轮播图结构 --> <div class="slider-list"> <ul> <li class="p1"><img src="img/1.png" alt="" /></li> <li class="p2"><img src="img/2.png" alt="" /></li> <li class="p3-selected"><img src="img/3.jpg" alt="" /></li> <li class="p4"><img src="img/4.png" alt="" /></li> <li class="p5"><img src="img/5.jpg" alt="" /></li> <li class="p6"><img src="img/6.jpg" alt="" /></li> <li class="p7"><img src="img/7.jpg" alt="" /></li> </ul> </div> <!-- 控制流 UI --> <div class="slider-control"> <!-- 使用两个<span>的说明:由于里面按钮ui效果厚度需要很小,在窗口里不好点击到(触发事件);因此在外面套了一个<span>,用于绑定鼠标点击事件--> <span><span></span></span> <span><span></span></span> <span class="btn-selected"><span></span></span> <span><span></span></span> <span><span></span></span> <span><span></span></span> <span><span></span></span> </div> <span class="prev btn"><</span> <span class="next btn">></span> </div> <!-- 在组件外,也能灵活调用 API --> <div id="sliderState"><p>当前第 3 页</p></div> </body> <script src="change.js"></script> </html>
* { margin: 0; padding: 0; } #my-slider { position: relative; width: 100%; height: 340px; margin-top: 100px; } #my-slider>.slider-list{ position: absolute; left: 50%; width: 1200px; height: 300px; margin-left: -600px; overflow: hidden; } li { position: absolute; top: 0; left: 0; width: 750px; height: 300px; list-style: none; opacity: 0; transition: all 0.3s ease-in-out; } li>img { position: absolute; top: 0; left: 0; width: 100%; height: 100%; cursor: pointer; } .p1 { transform:translate3d(-224px,0,0) scale(0.81); } .p2 { transform:translate3d(0px,0,0) scale(0.81); transform-origin:0 50%; z-index: 2; opacity: 0.8; } .p3-selected { transform:translate3d(224px,0,0) scale(1); z-index: 3; opacity: 1; } .p4 { transform:translate3d(448px,0,0) scale(0.81); transform-origin:100% 50%; z-index: 2; opacity: 0.8; } .p5 { transform:translate3d(672px,0,0) scale(0.81); } .p6 { transform:translate3d(896px,0,0) scale(0.81); } .p7 { transform:translate3d(1120px,0,0) scale(0.81); } .btn { position: absolute; top: 50%; width: 60px; height: 100px; margin-top: -50px; background: black; opacity: 0.2; line-height: 100px; font-size: 30px; color: white; text-decoration: none; text-align: center; cursor: pointer; } .next{ right: 0; } .slider-control { position: absolute; bottom: 0; left: 50%; width: 1200px; height: 30px; margin-left: -600px; text-align: center; padding-top: 10px; } .slider-control>span { display: inline-block; width: 35px; height: 100%; cursor: pointer; } .slider-control>span>span { position: relative; top: 30%; display: block; width: 100%; height: 1px; background: red; } .slider-control>.btn-selected>span { background: blue; } #sliderState { position: absolute; top: 440px; width: 100%; text-align: center; }
class Slider { constructor(id, cycle=3000){ this.container = document.getElementById(id); this.items= this.container.querySelectorAll(‘.slider-list li‘); this.cycle = cycle; // 回调函数队列; this.slideHandlers = []; // UI 控制流部分 // 鼠标移入组件时清除定时器 this.container.addEventListener(‘mouseover‘, ()=>{ this.stop(); }) // 鼠标移出组件时开始定时器 this.container.addEventListener(‘mouseout‘, ()=>{ this.start(); }) // 鼠标点击图片,触发上一张和下一张 this.container.addEventListener(‘click‘, evt=>{ console.log(‘picclicked‘); console.log(evt.target.parentElement); if (evt.target.parentElement.className != ‘p2‘ && evt.target.parentElement.className != ‘p4‘ ) return; else if (evt.target.parentElement.className == ‘p2‘) { console.log(‘前一张‘); this.prevImg(); } else { console.log(‘下一张‘); this.nextImg(); } }) // 鼠标点击上一张 和 下一张 按钮进行触发 上一张和下一张 let nextBtn = this.container.querySelector(‘.next‘); if(nextBtn) { nextBtn.addEventListener(‘click‘, () => this.nextImg()); } let prevBtn = this.container.querySelector(‘.prev‘); if(prevBtn) { prevBtn.addEventListener(‘click‘, () => this.prevImg()); } // 鼠标点击底下slider控制按钮进行图片切换 let controller = this.container.querySelector(‘.slider-control‘); if (controller) { // 加了这个判断之后,整体删除组件的控制部分,程序也能正常运行 let btns = this.container.querySelectorAll(‘.slider-control>span‘); controller.addEventListener(‘click‘, evt=>{ var idx = Array.from(btns).indexOf(evt.target); if(idx >= 0) this.slideTo(idx); }); // 往回调函数队列中增加 "改变底下当前选中按钮的背景色" 的回调函数 this.addSlideListener(function(idx) { let selected = controller.querySelector(‘.btn-selected‘); if(selected) selected.className = ‘‘; btns[idx].className = ‘btn-selected‘; // 次数 褚className 不用加点 }); } } // API 部分 // 获取照片CSS布局定位的 class // ["p1", "p2", "p3-selected", "p4", "p5", "p6", "p7"]; getLiClasses(){ let liClasses = []; Array.from(this.items).forEach(li=>{ liClasses.push(li.className); }) return liClasses; } // 获取当前展示的图片 getSelectedItem() { let selected = this.container.querySelector(‘.p3-selected‘); return selected; } // 获取当前展示的图片的编号 getSelectedItemIndex() { return Array.from(this.items).indexOf(this.getSelectedItem()); } // 跳到要展示的目标图片(核心API) slideTo(idx) { let currentIdx = this.getSelectedItemIndex(); let liClasses = this.getLiClasses(); let item = this.items[idx]; if(item){ if(idx == currentIdx) { return; } else if(idx < currentIdx){ Array.from(this.items).forEach((item, i) => { item.className = ‘‘; item.className = liClasses[(i + (currentIdx - idx)) % liClasses.length]; }) } else if(idx > currentIdx){ Array.from(this.items).forEach((item, i)=>{ item.className = ‘‘; item.className = liClasses[(i + liClasses.length -(idx - currentIdx)) % liClasses.length]; }) } } // 执行回调函数队列里的函数: // 1. 改变底下按钮中当前选中按钮的背景色 // 2. 显示当前第几页 this.slideHandlers.forEach(handler=>{ handler(idx); }); } // 下一张图片 nextImg() { let currentIdx = this.getSelectedItemIndex(); let nextIdx = (currentIdx + 1) % this.items.length; this.slideTo(nextIdx); } // 上一张图片 prevImg() { let currentIdx = this.getSelectedItemIndex(); let prevIdx = (currentIdx + this.items.length - 1) % this.items.length; this.slideTo(prevIdx); } // 启动计时器 start() { this.stop(); this._sliderTimer = setInterval(() => { this.nextImg(); }, this.cycle); } // 清除计时器 stop() { clearInterval(this._sliderTimer); } // 高级API; 用于收集回调函数 addSlideListener(handler) { this.slideHandlers.push(handler); } } // 调用 const slider = new Slider(‘my-slider‘); // 启动定时器 slider.start(); // 在组件外部往 回调函数队列 添加函数 slider.addSlideListener(function(idx){ sliderState.textContent = `当前第 ${idx + 1} 页`; });
webProject demo-2 Images/3DchangeImg
标签:listener start 转换 tle extc absolute 轮播图片 hang round
原文地址:https://www.cnblogs.com/rencoo/p/9381499.html