如何用纯CSS&JS将 testimonial 滑块改为每行显示3条?
纯CSS+JS实现每行3条的滑动Testimonial板块改造方案
核心布局思路
- 外层容器设为
overflow: hidden,负责裁切超出视口的内容 - 内部滑动容器用flex布局横向排列所有 testimonial 项,通过
transform实现平移切换 - 单个 testimonial 项宽度设为
calc((100% - 2*间隙值)/3),确保每行刚好显示3条,同时保留间隙
CSS代码修改示例
/* 外层裁切容器 */ .testimonial-wrap { overflow: hidden; position: relative; width: 90%; margin: 0 auto; padding: 0 10px; } /* 滑动容器:承载所有testimonial项 */ .testimonial-slider { display: flex; gap: 20px; /* 项之间的水平间隙 */ transition: transform 0.4s cubic-bezier(0.25, 0.46, 0.45, 0.94); /* 平滑过渡动画 */ width: fit-content; /* 由子项总宽度自动撑开 */ } /* 单个testimonial项:每行3条的宽度计算 */ .testimonial-card { flex-shrink: 0; /* 禁止压缩,保证宽度稳定 */ width: calc((100% - 40px)/3); /* 减去两个gap的宽度,均分3份 */ padding: 24px; background: #ffffff; border-radius: 12px; box-shadow: 0 3px 12px rgba(0,0,0,0.08); } /* 响应式适配:移动端自动切换为每行1条 */ @media (max-width: 768px) { .testimonial-card { width: 100%; } }
JS滑动逻辑实现
// 获取DOM元素 const slider = document.querySelector('.testimonial-slider'); const prevBtn = document.querySelector('.testimonial-prev'); const nextBtn = document.querySelector('.testimonial-next'); // 计算基础参数 let cardWidth = document.querySelector('.testimonial-card').offsetWidth + 20; // 单条宽度+gap let currentSlide = 0; // 最大可滑动次数:总条数除以3取整,再减1(从0开始计数) const maxSlides = Math.floor(slider.children.length / 3) - 1; // 滑动核心函数 function updateSliderPosition() { slider.style.transform = `translateX(-${currentSlide * cardWidth * 3}px)`; } // 下一页按钮事件 nextBtn.addEventListener('click', () => { if (currentSlide < maxSlides) { currentSlide++; updateSliderPosition(); } }); // 上一页按钮事件 prevBtn.addEventListener('click', () => { if (currentSlide > 0) { currentSlide--; updateSliderPosition(); } }); // 窗口 resize 时重新计算宽度,避免布局错乱 window.addEventListener('resize', () => { cardWidth = document.querySelector('.testimonial-card').offsetWidth + 20; updateSliderPosition(); });
对应HTML结构调整
<div class="testimonial-wrap"> <div class="testimonial-slider"> <div class="testimonial-card"> <p>用户评价内容1</p> <span>—— 用户A</span> </div> <div class="testimonial-card"> <p>用户评价内容2</p> <span>—— 用户B</span> </div> <div class="testimonial-card"> <p>用户评价内容3</p> <span>—— 用户C</span> </div> <div class="testimonial-card"> <p>用户评价内容4</p> <span>—— 用户D</span> </div> <div class="testimonial-card"> <p>用户评价内容5</p> <span>—— 用户E</span> </div> <div class="testimonial-card"> <p>用户评价内容6</p> <span>—— 用户F</span> </div> </div> <!-- 切换按钮 --> <button class="testimonial-prev">←</button> <button class="testimonial-next">→</button> </div>
关键细节提示
- 如果 testimonial 总条数不是3的倍数,最后一行可以通过给滑动容器添加
padding-right或者调整maxSlides的计算逻辑,避免滑动后出现空白区域 - 可以给切换按钮添加禁用状态(比如当前是第一页时,禁用上一页按钮),提升交互体验
- 过渡动画的
cubic-bezier曲线可以根据需求调整,让滑动更贴合产品风格
内容的提问来源于stack exchange,提问作者Web Zaintech
相关产品推荐
相关产品推荐

