Blogger Information
Blog 37
fans 1
comment 0
visits 32509
Popular Tutorials
More>
Latest Downloads
More>
Web Effects
Website Source Code
Website Materials
Front End Template
原生js实现选项卡和轮播图
Jason Pu?
Original
988 people have browsed it

一:前置知识

1.事件代理:
事件绑定者:ev.currentTarget
事件触发者:ev.target
思维:给母元素添加事件,通过ev.target解发事件的元素

2.dataset对象:自定义属性
dataset对象专用于访问自定义的标签属性,在自定义属性前面加上data-,便可以用“dataset.自定义标签名”,进行访问,如果自定义的标签是两个单词组成且中间有加”-“,访问时要省略掉”-“,并把第二个单词首字母进行大写

二:JS实战选项卡

思维:定义3个dataset,分别放在对应的主题和内容区标签里,利用事件绑定给相同的dataset自定义属性的classList添加active
html部分:

  1. <div class="box">
  2. <ul class="nav">
  3. <li data-index="1" class="active">财经</li>
  4. <li data-index="2">股票</li>
  5. <li data-index="3">理财</li>
  6. </ul>
  7. <ul data-index="1" class="content active">
  8. <li><a href="">道歉变自夸 全棉时代忘了本</a></li>
  9. <li><a href="">拉夏贝尔内斗激烈 一年五换总裁</a></li>
  10. <li><a href="">深圳华强北6亿缉私震荡波</a></li>
  11. </ul>
  12. <ul data-index="2" class="content">
  13. <li><a href="">[美股]小摩:价值股即将咸鱼翻身</a></li>
  14. <li><a href="">[港股]百度回港上市AB面</a></li>
  15. <li><a href="">猪肉价格浮沉启示 A股需坚守信仰</a></li>
  16. </ul>
  17. <ul data-index="3" class="content">
  18. <li><a href="">极致行情虐惨量化对冲基金</a></li>
  19. <li><a href="">数字人民币在上海扩大试点 已实现“双离线”支付</a></li>
  20. <li><a href="">[黄金] 国债收益率上攻叠加美指反弹 黄金出现急跌</a></li>
  21. </ul>
  22. </div>

css部分:

  1. *{
  2. margin: 0;
  3. padding: 0;
  4. box-sizing: border-box;
  5. list-style: none;
  6. text-decoration: none;
  7. }
  8. .box{
  9. margin: 30px;
  10. }
  11. a{
  12. color: #666;
  13. }
  14. a:hover{
  15. text-decoration: underline;
  16. color: red;
  17. }
  18. .box{
  19. width: 300px;
  20. height: 300px;
  21. margin: 30px;
  22. border-color: #F7F7F7;
  23. display: flex;
  24. flex-direction: column;
  25. }
  26. .nav{
  27. height: 36px;
  28. display: flex;
  29. border-left: 1px solid #DBDEE1;
  30. border-top: 1px solid #DBDEE1;
  31. border-right: 1px solid #DBDEE1;
  32. }
  33. .nav li{
  34. flex: auto;
  35. text-align: center;
  36. line-height: 36px;
  37. background-color: #F8F8F8;
  38. border-bottom: 1px solid #DBDEE1;
  39. border-left: 1px solid #DBDEE1;
  40. }
  41. .nav li:hover{
  42. border-bottom: none;
  43. background-color: white;
  44. }
  45. /* 默认所有选项卡只能显示active*/
  46. .content{
  47. padding: 20px;
  48. display: none;
  49. }
  50. .content.active{
  51. display: block;
  52. }

js实现:

  1. const nav = document.querySelector(".nav");
  2. const content=document.querySelectorAll(".content");
  3. nav.onmouseover = ev =>{
  4. Array.from(nav.children).forEach(lis=>lis.classList.remove("active"));
  5. ev.target.classList.add("active");
  6. // 根据自定义属性data-index找到对应的content并显示
  7. content.forEach(lis=>lis.classList.remove("active"));
  8. //filter方法虽然只返回了一个结果,但还是数组,所以要加[0]:
  9. let result = Array.from(content).filter(lis=>lis.dataset.index===ev.target.dataset.index)[0];
  10. result.classList.add("active");
  11. }

效果如下:
before:

onmouseover:

三.js事件代理实现轮播图,并实现自动播放,鼠标移入停止播放功能

html部分:

  1. <div class="container">
  2. <!-- 1. 图片组 -->
  3. <nav class="imgs">
  4. <a href="#"
  5. ><img src="banner/banner1.jpg" alt="" data-index="1" class="active"
  6. /></a>
  7. <a href="#"><img src="banner/banner2.jpg" alt="" data-index="2" /></a>
  8. <a href="#"><img src="banner/banner3.jpg" alt="" data-index="3" /></a>
  9. <a href="#"><img src="banner/banner4.jpg" alt="" data-index="4" /></a>
  10. </nav>
  11. <!-- 2. 与图片组对应的按钮组(一个个独立的,数量与图片数量是相同的) -->
  12. <nav class="btns">
  13. <!-- 这些小按钮应该是js根据图片数量动态来创建 -->
  14. <!-- <a href="#" data-index="1" class="active"></a>
  15. <a href="#" data-index="2"></a>
  16. <a href="#" data-index="3"></a>
  17. <a href="#" data-index="4"></a> -->
  18. </nav>
  19. <!-- 3. 翻页按钮(只有二个,分别在左右) -->
  20. <nav class="skip">
  21. <!-- &lt;: 实体符号 -->
  22. <a href="#" class="prev">&lt;</a>
  23. <a href="#" class="next">&gt;</a>
  24. </nav>
  25. </div>

基本js功能:

  1. //图片
  2. const imgs = document.querySelectorAll(".container > .imgs img");
  3. //按钮
  4. const btnList = document.querySelector(" .container > .btns");
  5. //小耳朵
  6. const skip = document.querySelector(".skip");
  7. //----------------------------生成小圆点-------------------------------------
  8. //生成和图片数量一致的小圆点:
  9. function antoCreateSpot(position,img){
  10. //使用文档片断:
  11. const frag = document.createDocumentFragment();
  12. for(let i=0;i<img.length;i++){
  13. const a = document.createElement("a");
  14. a.href="#";
  15. a.dataset.index = i+1;//data-index="i+1"
  16. if(i===0)a.classList.add("active");//为第一个添加active
  17. frag.appendChild(a);
  18. }
  19. position.appendChild(frag);
  20. };
  21. antoCreateSpot(btnList,imgs);//调用函数并实现生成小圆点
  22. // 获取一下生成的小圆点的所有元素:
  23. const spot=document.querySelectorAll(".container > .btns > *");

创建公共函数:

  1. //----------------------------公共函数区-------------------------------------
  2. //1.获取激活元素函数:
  3. function getActivedElement(elements){
  4. //contains():判断DOM元素的包含关系,返回布尔值
  5. let actived = [...elements].filter(img=>img.classList.contains("active"));
  6. return actived[0];//filter返回的是数组,所以要加[0]
  7. };
  8. //2.设置激活的元素:
  9. function setActiveElement(btnIndex){
  10. //同时遍历所有图片和按钮
  11. [imgs,spot].forEach(arr => {
  12. // 取消当前激活元素的状态:
  13. getActivedElement(arr).classList.remove("active");
  14. //根据当前用户点击的按钮的索引,重置应该激活的元素:
  15. arr.forEach(item =>{
  16. if(item.dataset.index === btnIndex){
  17. item.classList.add("active");
  18. }
  19. })
  20. });
  21. };

给小圆点添加事件:

  1. spot.forEach(btn=>
  2. btn.addEventListener("click",ev=>setActiveElement(ev.target.dataset.index))
  3. );

让两侧的小耳机变活:

  1. skip.addEventListener("click",skipImg);
  2. skip.children[1].addEventListener("click",skipImg);
  3. function skipImg(ev){
  4. // 获取当前被激活的图片:
  5. let currentImg = getActivedElement(imgs);
  6. //获取当前激活的图片包裹器的元素,因为图片包在a元素里面,所以要弄两次:
  7. let parentEle = currentImg.parentElement.parentElement;
  8. //获取当前激活元素的上一个兄弟节点:
  9. let preEle = currentImg.parentElement.previousElementSibling;
  10. //获取当前激活元素的下一个兄弟节点:
  11. let nextEle = currentImg.parentElement.nextElementSibling;
  12. //第一张图片:
  13. let firstImg = parentEle.firstElementChild.firstElementChild;
  14. //最后一张图片:
  15. let lastImg = parentEle.lastElementChild.lastElementChild;
  16. let activeImg = currentImg;
  17. //向前:
  18. if (ev.target.classList.contains("prev")){
  19. //向前图片使用完毕,自动到最后一张
  20. let activeImg=preEle !==null?preEle.firstElementChild:lastImg;
  21. setActiveElement(activeImg.dataset.index);//同步更新
  22. }
  23. //向后:
  24. if(ev.target.classList.contains("next")){
  25. //向后结束后自动到第一张:
  26. let activeImg=nextEle !==null?nextEle.firstElementChild:firstImg;
  27. setActiveElement(activeImg.dataset.index);
  28. }
  29. }

让轮播图自动动起来:

  1. let sk = null;
  2. const clickEvent = new Event("click");
  3. const box = document.querySelector(".container");
  4. const autonext = document.querySelector(".skip .next");
  5. box.addEventListener("mouseover",stop);
  6. box.addEventListener("mouseout",start);
  7. setTimeout(function (){
  8. start()},1000);
  9. function start(){
  10. sk = setInterval(function (){
  11. autonext.dispatchEvent(clickEvent)
  12. },2000);
  13. }
  14. function stop(){
  15. clearInterval(sk);
  16. }
Correcting teacher:天蓬老师天蓬老师

Correction status:qualified

Teacher's comments:是不是重复提交了
Statement of this Website
The copyright of this blog article belongs to the blogger. Please specify the address when reprinting! If there is any infringement or violation of the law, please contact admin@php.cn Report processing!
All comments Speak rationally on civilized internet, please comply with News Comment Service Agreement
0 comments
Author's latest blog post