无缝轮播图(自动轮播+点击轮播+拖拽轮播)

废话不多说,直接上代码(注:js部分代码会有截图对其解释)

一、HTML

html 复制代码
    <div class="bigBox">
        <!-- 轮播主体 -->
        <div class="box">
            <div class="littleBox">1</div>
            <div class="littleBox">2</div>
            <div class="littleBox">3</div>
        </div>
        <!-- 底部小点 -->
        <div class="point">
            <div class="active"></div>
            <div></div>
            <div></div>
        </div>
        <!-- 上一页 -->
        <div class="prev"></div>
        <!-- 下一页 -->
        <div class="next"></div>
    </div>

二、CSS

css 复制代码
* {
    margin: 0;
    padding: 0;
}

.bigBox {
    width: 300px;
    height: 180px;
    border: 2px solid black;
    overflow: hidden;
    margin: 100px auto;
    position: relative;
}

/* 轮播主体 */
.box {
    width: 900px;
    display: flex;
    transition: all .6s;
}

.littleBox {
    text-align: center;
    line-height: 180px;
    width: 300px;
    height: 180px;
}

.littleBox:nth-of-type(1) {
    background-color: skyblue;
}

.littleBox:nth-of-type(2) {
    background-color: pink;
}

.littleBox:nth-of-type(3) {
    background-color: yellow;
}

/* 小点 */
.point {
    position: absolute;
    width: 50px;
    height: 10px;
    bottom: 10px;
    left: 50%;
    transform: translateX(-50%);
    display: flex;
    justify-content: space-evenly;
    cursor: pointer;
}

.point div {
    width: 10px;
    height: 10px;
    background-color: rgb(151, 151, 151);
    border-radius: 10px;
}

.point .active {
    background-color: white;
}

/* 上一页/下一页 */
.prev::after,
.next::after {
    position: absolute;
    width: 20px;
    height: 30px;
    top: 50%;
    transform: translateY(-50%);
    background-color: aliceblue;
    line-height: 30px;
    text-align: center;
    cursor: pointer;
}

/* 上一页 */
.prev::after {
    content: '<';
    left: 0;
    border-top-right-radius: 15px;
    border-bottom-right-radius: 15px;
}

/* 下一页 */
.next::after {
    content: '>';
    right: 0;
    border-top-left-radius: 15px;
    border-bottom-left-radius: 15px;
}

三、JS以及解释截图

javascript 复制代码
// dom元素
const doms = {
    box: document.querySelector('.box'),
    point: document.querySelectorAll('.point div'),
    prev: document.querySelector('.prev'),
    next: document.querySelector('.next')
}

// 当前所在页面(从0开始)
let currentIndex = 0

// 切换页面
function moved(index) {
    currentIndex = index
    const x = -300 * index
    doms.point.forEach((item, i) => {
        item.classList.remove('active')
    })
    doms.point[index].classList.add('active')
    doms.box.style.transform = `translateX(${x}px)`
}

// 上一页点击事件
function changePrev() {
    currentIndex === 0 ? currentIndex = 2 : currentIndex--
    moved(currentIndex)
}
doms.prev.addEventListener('click', changePrev)

// 下一页点击事件
function changeNext() {
    currentIndex === 2 ? currentIndex = 0 : currentIndex++
    moved(currentIndex)
}
doms.next.addEventListener('click', changeNext)

// 小点点击事件
doms.point.forEach((item, i) => {
    item.addEventListener('click', function () {
        moved(i)
    })
})

// 自动轮播
let timer = setInterval(changeNext, 2000)

// 鼠标移入后清除自动轮播
doms.box.addEventListener('mouseenter', function () {
    clearInterval(timer)
})

// box元素相对视口的位置
const boxPosition = {
    x: Math.floor(doms.box.getBoundingClientRect().x),
    y: Math.floor(doms.box.getBoundingClientRect().y)
}

// 鼠标最初位置
let mouseX = 0

// box移动的位置
let transformX = 0
let x = 0

// 手动拖拽
function onMoueseDown(e) {
    mouseX = e.clientX - boxPosition.x
    doms.box.addEventListener('mousemove', onMoueseMove)
}

function onMoueseMove(e) {
    e.preventDefault()
    x = transformX + -1 * (mouseX - (e.clientX - boxPosition.x));
    doms.box.style.transform = `translateX(${x}px)`
}

function onMoueseUp() {
    // 判断当前页数
    if (Math.round(-1 * x / 300) < 0) {
        currentIndex = 2
    } else if (Math.round(-1 * x / 300) > 2) {
        currentIndex = 0
    } else {
        currentIndex = Math.round(-1 * x / 300)
    }
    transformX = currentIndex * -300
    moved(currentIndex)
    // 移出监听
    doms.box.removeEventListener('mousemove', onMoueseMove)
}


function onMoueseLeave() {
    // 移出监听
    doms.box.removeEventListener('mousemove', onMoueseMove)
    // 添加自动轮播
    timer = setInterval(changeNext, 2000)
}
// 鼠标按下添加拖拽
doms.box.addEventListener('mousedown', onMoueseDown)

// 鼠标抬起移除事件
doms.box.addEventListener('mouseup', onMoueseUp)
// 鼠标移出后添加自动轮播以及移出事件
doms.box.addEventListener('mouseleave', onMoueseLeave)

解释截图(最左侧为可视窗口最左侧):

相关推荐
meilindehuzi_a5 小时前
从零理解并实现 RAG:用 LangChain.js 构建语义检索问答系统
开发语言·javascript·langchain
世界哪有真情6 小时前
拿人类意识卡 AI?等于用 bug 验收正式产品
前端·人工智能·后端
鱼樱前端6 小时前
别再自己拼凑了!这款 Vue 3.5+ 严肃产品级组件库,把 AI 对话、工作流和复杂数据全包了!
javascript·vue.js·github
Listen·Rain7 小时前
Vue3:setup详解
前端·javascript·vue.js
Patrick_Wilson8 小时前
修好 bug 只是开始:一次由监控需求反向重构日志结构的复盘
前端·监控·数据可视化
kyriewen8 小时前
面试官让我优化一个卡死的表格,我打开 Claude 五秒重写,他放下咖啡问我要不要来当组长
前端·javascript·面试
‘’林花谢了春红‘’8 小时前
小玩意 生日快乐
css·html·css3
小粉粉hhh9 小时前
React(二)——dom、组件间通信、useEffect
前端·javascript·react.js
Csvn9 小时前
🤖 AI 生成前端代码的 5 个典型翻车现场及修复指南
前端
IT_陈寒10 小时前
SpringBoot自动装配坑了我一天,原来问题出在这
前端·人工智能·后端