CSS、JS之仿网易云音乐轮播图

效果演示

图片

实现了一个全屏滑动轮播图的效果,包括一个背景图片的模糊效果和多张图片的轮播。用户可以通过点击左右箭头或者点击下方的小圆点来切换图片。同时,这段代码还实现了响应式布局,在屏幕宽度小于1620px时,左右箭头的位置会发生变化。

Code

HTML
<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>仿网易云音乐轮播图</title>
    <link href="https://cdn.bootcdn.net/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css" rel="stylesheet">
    <link rel="stylesheet" href="./27-仿网易云音乐轮播图.css">
</head>

<body>
    <div class="swipe" id="swipe">
        <div class="bg" id="swipe_bg"></div>
        <section>
            <div class="img-box" id="swipe_img_box">
                <a href="#" class="link" id="swipe_link">
                    <img src="./images/1.jpg" alt="" class="img" id="swipe_img">
                </a>
            </div>
            <div class="select" id="swipe_select">
            </div>
            <div class="btn left" id="swipe_btn_left">
                <i class="fa fa-angle-left" aria-hidden="true"></i>
            </div>
            <div class="btn right" id="swipe_btn_right">
                <i class="fa fa-angle-right" aria-hidden="true"></i>
            </div>
        </section>
    </div>
</body>
<script src="./27-仿网易云音乐轮播图.js"></script>

</html>
CSS
* {
    margin: 0;
    padding: 0;
}

body {
    height: 100vh;
    display: flex;
    justify-content: center;
    align-items: center;
    background-color: #333;
}

.swipe {
    position: relative;
    width: 100%;
    overflow: hidden;
}

.swipe .bg {
    position: absolute;
    width: 500%;
    height: 100%;
    z-index: 1;
    background-image: url("../images/cloud_music/1.jpg");
    background-size: 6000px;
    background-position: center center;
    filter: blur(140px);
}

.swipe section {
    position: relative;
    z-index: 2;
    width: 100%;
    max-width: 1500px;
    height: 600px;
    margin: 0 auto;
}

.swipe .img-box {
    width: 100%;
    height: 100%;
}

.swipe .img-box .img {
    width: 100%;
    height: 100%;
    object-fit: cover;
}

.swipe .select {
    position: absolute;
    width: 100%;
    height: 30px;
    line-height: 30px;
    bottom: 20px;
    text-align: center;
}

.swipe .select .item {
    display: inline-block;
    width: 10px;
    height: 10px;
    background-color: #fff;
    border-radius: 50%;
    margin: 0 10px;
    box-shadow: 0 2px 5px rgba(0, 0, 0, 0.4);
}

.swipe .select .item:hover {
    background-color: #ff4400;
}

.swipe .select .item.checked {
    background-color: #ff4400;
}

.swipe .btn {
    width: 40px;
    height: 100px;
    color: #fff;
    position: absolute;
    top: 50%;
    transform: translateY(-50%);
    font-size: 50px;
    background-color: rgba(0, 0, 0, 0.05);
    display: flex;
    justify-content: center;
    align-items: center;
    z-index: 3;
    cursor: pointer;
    transition: 0.3s;
}

.swipe .btn.left {
    left: -60px;
}

.swipe .btn.right {
    right: -60px;
}

.swipe .btn:hover {
    background-color: rgba(0, 0, 0, 0.2);
}

@media screen and (max-width: 1620px) {
    .swipe .btn.left {
        left: 20px;
    }

    .swipe .btn.right {
        right: 20px;
    }
}
JavaScript
let current_index = -1;
let swipe_timer = null;
let links = [
  {'image': './images/1.jpg', 'target': '#1'},
  {'image': './images/2.jpg', 'target': '#2'},
  {'image': './images/3.jpg', 'target': '#3'},
  {'image': './images/4.jpg', 'target': '#4'},
  {'image': './images/5.jpg', 'target': '#5'},
  {'image': './images/6.jpg', 'target': '#6'}
];
let swipe = document.getElementById('swipe');
let swipe_bg = document.getElementById('swipe_bg');
let swipe_img_box = document.getElementById('swipe_img_box');
let swipe_link = document.getElementById('swipe_link');
let swipe_img = document.getElementById('swipe_img');
let swipe_select = document.getElementById('swipe_select');
let swipe_btn_left = document.getElementById('swipe_btn_left');
let swipe_btn_right = document.getElementById('swipe_btn_right');
let select = (index) => {
  stop();
  index = Number(index);
  if (index >= links.length) {
    return;
  }
  if (current_index == index) {
    return;
  }
  if (current_index > -1) {
    swipe_select.children[current_index].classList.remove('checked');
  }
  current_index = index;
  let current_link = links[current_index];
  swipe_bg.style.backgroundImage = 'url(' + current_link.image + ')';
  swipe_img.setAttribute('src', current_link.image);
  swipe_link.setAttribute('href', current_link.target);
  swipe_select.children[current_index].classList.add('checked');
};
let autoSelect = (index) => {
  index = Number(index);
  if (index >= links.length) {
    return;
  }
  if (current_index == index) {
    return;
  }
  swipe_select.children[current_index].classList.remove('checked');
  current_index = index;
  let current_link = links[current_index];
  swipe_img.style.transition = 'opacity 0.5s ease-in 0s';
  swipe_img.style.opacity = 0.2;
  setTimeout(() => {
    swipe_bg.style.backgroundImage = 'url(' + current_link.image + ')';
    swipe_img.setAttribute('src', current_link.image);
    swipe_link.setAttribute('href', current_link.target);
    swipe_img.style.transition = 'opacity 0.7s ease-out 0s';
    swipe_img.style.opacity = 1;
    if (!document.querySelector('.swipe .checked')) {
      swipe_select.children[current_index].style.transition = 'background-color 0.5s';
      swipe_select.children[current_index].classList.add('checked');
    }
  }, 500);
};
let play = () => {
  swipe_timer = setInterval(() => {
    let index = current_index + 1;
    if (index >= links.length) {
      index = 0;
    }
    autoSelect(index);
  }, 3000);
};
let stop = () => {
  if (swipe_timer) {
    clearInterval(swipe_timer);
    swipe_timer = null;
  }
};
let init = () => {
  for (let i = 0; i < links.length; i++) {
    let item = document.createElement('a');
    item.setAttribute('class', 'item');
    item.setAttribute('href', '#');
    item.setAttribute('data-index', i);
    swipe_select.appendChild(item);
    }
    select(0);
    bind();
    play();
};
let bind = () => {
    swipe_btn_left.addEventListener('click', () => {
        let index = current_index - 1;
        if (index < 0) {
            index = links.length - 1;
        }
        select(index);
    });
    swipe_btn_right.addEventListener('click', () => {
        let index = current_index + 1;
        if (index >= links.length) {
            index = 0;
        }
        select(index);
    });
    for (const key in swipe_select.children) {
        if (swipe_select.children.hasOwnProperty(key)) {
            const element = swipe_select.children[key];
            element.addEventListener('click', (e) => {
                e.preventDefault();
                select(e.target.dataset.index);
            });
        }
    }
    swipe.addEventListener('mouseover', (e) => {
        if (e.relatedTarget && swipe.compareDocumentPosition(e.relatedTarget) == 10) {
            stop();
        }
    });
    swipe.addEventListener('mouseout', (e) => {
        if (e.relatedTarget && swipe.compareDocumentPosition(e.relatedTarget) == 10) {
            play();
        }
    });
    swipe.addEventListener('mousemove', (e) => {
        stop();
    });
};
window.addEventListener('load', () => {
    init();
})

实现思路拆分

* {
  margin: 0;
  padding: 0;
}

这段代码是设置所有元素的外边距和内边距为0,这是为了避免不同浏览器的默认样式对页面造成影响。

body {
  height: 100vh;
  display: flex;
  justify-content: center;
  align-items: center;
  background-color: #333;
}

这段代码设置了body元素的高度为100vh,即占据整个视口的高度。同时,使用flex布局使得body元素的子元素在水平和垂直方向上都居中对齐。背景颜色为#333。

.swipe {
  position: relative;
  width: 100%;
  overflow: hidden;
}

这段代码定义了一个名为swipe的类,设置其为相对定位,宽度为100%,并且隐藏超出部分。

.swipe .bg {
  position: absolute;
  width: 500%;
  height: 100%;
  z-index: 1;
  background-image: url("../images/cloud_music/1.jpg");
  background-size: 6000px;
  background-position: center center;
  filter: blur(140px);
}

这段代码定义了一个名为bg的类,设置其为绝对定位,宽度为500%,高度为100%,并且设置z-index为1,使其在其他元素之下。同时,设置背景图片、背景大小、背景位置和模糊效果。

.swipe section {
  position: relative;
  z-index: 2;
  width: 100%;
  max-width: 1500px;
  height: 600px;
  margin: 0 auto;
}

这段代码定义了一个名为section的类,设置其为相对定位,z-index为2,宽度为100%,最大宽度为1500px,高度为600px,并且水平居中对齐。

.swipe .img-box {
  width: 100%;
  height: 100%;
}

这段代码定义了一个名为img-box的类,设置其宽度和高度均为100%。

.swipe .img-box .img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

这段代码定义了一个名为img的类,设置其宽度和高度均为100%,并且使用object-fit属性使得图片按比例缩放并且填充整个容器。

.swipe .select {
  position: absolute;
  width: 100%;
  height: 30px;
  line-height: 30px;
  bottom: 20px;
  text-align: center;
}

这段代码定义了一个名为select的类,设置其为绝对定位,宽度为100%,高度为30px,行高为30px,底部距离为20px,并且文本居中对齐。

.swipe .select .item {
  display: inline-block;
  width: 10px;
  height: 10px;
  background-color: #fff;
  border-radius: 50%;
  margin: 0 10px;
  box-shadow: 0 2px 5px rgba(0, 0, 0, 0.4);
}

这段代码定义了一个名为item的类,设置其为内联块元素,宽度和高度均为10px,背景颜色为白色,边框半径为50%,左右间距为10px,阴影效果为0 2px 5px rgba(0, 0, 0, 0.4)。

.swipe .select .item:hover {
  background-color: #ff4400;
}

这段代码设置鼠标悬停在item元素上时的背景颜色为#ff4400。

.swipe .select .item.checked {
  background-color: #ff4400;
}

这段代码设置选中的item元素的背景颜色为#ff4400。

.swipe .btn {
  width: 40px;
  height: 100px;
  color: #fff;
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
  font-size: 50px;
  background-color: rgba(0, 0, 0, 0.05);
  display: flex;
  justify-content: center;
  align-items: center;
  z-index: 3;
  cursor: pointer;
  transition: 0.3s;
}

这段代码定义了一个名为btn的类,设置其宽度为40px,高度为100px,颜色为白色,绝对定位,顶部距离为50%,使用transform属性使其在垂直方向上居中对齐,字体大小为50px,背景颜色为rgba(0, 0, 0, 0.05),使用flex布局使得内容水平和垂直方向上都居中对齐,z-index为3,鼠标样式为手型,过渡效果为0.3秒。

.swipe .btn.left {
  left: -60px;
}

.swipe .btn.right {
  right: -60px;
}

这段代码设置左箭头的位置为左侧-60px,右箭头的位置为右侧-60px。

.swipe .btn:hover {
  background-color: rgba(0, 0, 0, 0.2);
}

这段代码设置鼠标悬停在btn元素上时的背景颜色为rgba(0, 0, 0, 0.2)。

@media screen and (max-width: 1620px) {
  .swipe .btn.left {
    left: 20px;
  }

  .swipe .btn.right {
    right: 20px;
  }
}

这段代码使用@media查询,当屏幕宽度小于等于1620px时,将左箭头的位置设置为左侧20px,右箭头的位置设置为右侧20px。这是为了适应不同屏幕尺寸的设备。

let current_index = -1;
let swipe_timer = null;
let links = [
  { 'image': './images/1.jpg', 'target': '#1' },
  { 'image': './images/2.jpg', 'target': '#2' },
  { 'image': './images/3.jpg', 'target': '#3' },
  { 'image': './images/4.jpg', 'target': '#4' },
  { 'image': './images/5.jpg', 'target': '#5' },
  { 'image': './images/6.jpg', 'target': '#6' }
];

这段代码定义了三个变量,current_index表示当前选中的图片的索引,swipe_timer表示轮播定时器,links是一个数组,包含了每张图片的路径和链接目标。

let swipe = document.getElementById('swipe');
let swipe_bg = document.getElementById('swipe_bg');
let swipe_img_box = document.getElementById('swipe_img_box');
let swipe_link = document.getElementById('swipe_link');
let swipe_img = document.getElementById('swipe_img');
let swipe_select = document.getElementById('swipe_select');
let swipe_btn_left = document.getElementById('swipe_btn_left');
let swipe_btn_right = document.getElementById('swipe_btn_right');

这段代码获取了页面中的各个元素,包括轮播图容器、背景图片、图片容器、链接、图片、小圆点、左箭头和右箭头。

let select = (index) => {
  stop();
  index = Number(index);
  if (index >= links.length) {
    return;
  }
  if (current_index == index) {
    return;
  }
  if (current_index > -1) {
    swipe_select.children[current_index].classList.remove('checked');
  }
  current_index = index;
  let current_link = links[current_index];
  swipe_bg.style.backgroundImage = 'url(' + current_link.image + ')';
  swipe_img.setAttribute('src', current_link.image);
  swipe_link.setAttribute('href', current_link.target);
  swipe_select.children[current_index].classList.add('checked');
};

这段代码定义了一个名为select的函数,用于切换图片。首先调用stop函数停止轮播,然后将传入的参数转换为数字类型,并且判断是否超出数组范围或者是否已经选中了该图片。如果当前已经选中了一张图片,则将其小圆点的样式去除。然后更新current_index的值,获取当前图片的路径和链接目标,并且更新背景图片、图片和链接的属性。最后将当前小圆点的样式添加上。

let autoSelect = (index) => {
  index = Number(index);
  if (index >= links.length) {
    return;
  }
  if (current_index == index) {
    return;
  }
  swipe_select.children[current_index].classList.remove('checked');
  current_index = index;
  let current_link = links[current_index];
  swipe_img.style.transition = 'opacity 0.5s ease-in 0s';
  swipe_img.style.opacity = 0.2;
  setTimeout(() => {
    swipe_bg.style.backgroundImage = 'url(' + current_link.image + ')';
    swipe_img.setAttribute('src', current_link.image);
    swipe_link.setAttribute('href', current_link.target);
    swipe_img.style.transition = 'opacity 0.7s ease-out 0s';
    swipe_img.style.opacity = 1;
    if (!document.querySelector('.swipe .checked')) {
      swipe_select.children[current_index].style.transition = 'background-color 0.5s';
      swipe_select.children[current_index].classList.add('checked');
    }
  }, 500);
};

这段代码定义了一个名为autoSelect的函数,用于自动切换图片。首先将传入的参数转换为数字类型,并且判断是否超出数组范围或者是否已经选中了该图片。然后将当前小圆点的样式去除,更新current_index的值,获取当前图片的路径和链接目标。接着设置图片的过渡效果和透明度,等待0.5秒后更新背景图片、图片和链接的属性,并且设置图片的过渡效果和透明度。最后判断是否存在选中的小圆点,如果不存在则添加当前小圆点的样式。

let play = () => {
  swipe_timer = setInterval(() => {
    let index = current_index + 1;
    if (index >= links.length) {
      index = 0;
    }
    autoSelect(index);
  }, 3000);
};

这段代码定义了一个名为play的函数,用于启动轮播。使用setInterval函数每隔3秒调用一次autoSelect函数,传入的参数为当前选中图片的索引加1,如果超出数组范围则从头开始。

let stop = () => {
  if (swipe_timer) {
    clearInterval(swipe_timer);
    swipe_timer = null;
  }
};

这段代码定义了一个名为stop的函数,用于停止轮播。如果swipe_timer存在,则清除定时器并且将其赋值为null。

let init = () => {
  for (let i = 0; i < links.length; i++) {
    let item = document.createElement('a');
    item.setAttribute('class', 'item');
    item.setAttribute('href', '#');
    item.setAttribute('data-index', i);
    swipe_select.appendChild(item);
  }
  select(0);
  bind();
  play();
};

这段代码定义了一个名为init的函数,用于初始化轮播图。首先使用for循环创建小圆点元素,并且设置其class、href和data-index属性。然后调用select函数选中第一张图片,调用bind函数绑定事件,最后调用play函数启动轮播。

let bind = () => {
  swipe_btn_left.addEventListener('click', () => {
    let index = current_index - 1;
    if (index < 0) {
      index = links.length - 1;
    }
    select(index);
  });
  swipe_btn_right.addEventListener('click', () => {
    let index = current_index + 1;
    if (index >= links.length) {
      index = 0;
    }
    select(index);
  });
  for (const key in swipe_select.children) {
    if (swipe_select.children.hasOwnProperty(key)) {
      const element = swipe_select.children[key];
      element.addEventListener('click', (e) => {
        e.preventDefault();
        select(e.target.dataset.index);
      });
    }
  }
  swipe.addEventListener('mouseover', (e) => {
    if (e.relatedTarget && swipe.compareDocumentPosition(e.relatedTarget) == 10) {
      stop();
    }
  });
  swipe.addEventListener('mouseout', (e) => {
    if (e.relatedTarget && swipe.compareDocumentPosition(e.relatedTarget) == 10) {
      play();
    }
  });
  swipe.addEventListener('mousemove', (e) => {
    stop();
  });
};

这段代码定义了一个名为bind的函数,用于绑定事件。首先为左箭头和右箭头添加点击事件,分别调用select函数切换图片。然后使用for循环为每个小圆点添加点击事件,调用select函数切换图片。接着为轮播图容器添加鼠标移入事件,调用stop函数停止轮播。为轮播图容器添加鼠标移出事件,调用play函数启动轮播。最后为轮播图容器添加鼠标移动事件,调用stop函数停止轮播。

window.addEventListener('load', () => {
  init();
})

这段代码为页面加载完成后调用init函数,初始化轮播图。

  • 3
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以下是使用JavaScript设计网易云音乐轮播图的效果的示例代码: HTML部分: ```html <div class="slider"> <ul class="slides"> <li><img src="image1.jpg"></li> <li><img src="image2.jpg"></li> <li><img src="image3.jpg"></li> <li><img src="image4.jpg"></li> <li><img src="image5.jpg"></li> </ul> </div> ``` CSS部分: ```css .slider { width: 100%; overflow: hidden; } .slides { display: flex; overflow-x: auto; scroll-snap-type: x mandatory; scroll-behavior: smooth; -webkit-overflow-scrolling: touch; } .slides::-webkit-scrollbar { width: 10px; height: 10px; } .slides::-webkit-scrollbar-track { background: #f1f1f1; } .slides::-webkit-scrollbar-thumb { background: #888; border-radius: 5px; } .slides li { scroll-snap-align: start; flex-shrink: 0; width: 100%; height: 400px; margin-right: 50px; position: relative; } .slides li:last-of-type { margin-right: 0; } .slides img { width: 100%; height: 100%; object-fit: cover; } ``` JavaScript部分: ```javascript const slides = document.querySelectorAll(".slides li"); let currentSlide = 0; const slideInterval = setInterval(nextSlide, 5000); function nextSlide() { slides[currentSlide].classList.remove("active"); currentSlide = (currentSlide + 1) % slides.length; slides[currentSlide].classList.add("active"); } ``` 以上代码中,HTML部分包括一个轮播图容器,其中包含一个无序列表,每个列表项都包含一个图片。CSS部分设置了轮播图容器和图片的样式,使用了Flex布局和滚动条样式。JavaScript部分通过获取轮播图容器中的所有列表项,并使用setInterval函数每5秒自动切换下一张图片。同时,定义了nextSlide函数,用于切换图片,并在当前图片上添加active类,以便在CSS中设置过渡效果。 总体来说,这段代码使用JavaScript实现了网易云音乐轮播图的效果,可以通过修改CSS样式和JavaScript代码来实现自定义的样式和功能。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值