【一】、 React-用swiper实现多行交错、同速、跑马灯效果的弹幕式轮播(总)
一、实现效果
数据轮播(三行交错、同速、跑马灯效果),动图如下:
二、配置swiper
react-swiper8
1、安装swiper8
npm i swiper@8
或者
yarn add swiper@8
2、在app.jsx全局引入
app.jsx
// swiper【Autoplay:自动播放 ,Pagination:分页 ,Navigation:标记页数】
import SwiperCore, { Autoplay, Pagination, Navigation } from 'swiper';
SwiperCore.use([Autoplay, Pagination, Navigation])
三、实现代码
1、先封装一个swiper写的弹幕item组件 —— swiperComponent ⭐️
swiperComponent.jsx
【关键点】 实现跑马灯效果的关键点用【关键】标注出来了~
/**
* swiper写的弹幕item组件
*/
'use strict';
import React from 'react';
import { observer } from 'mobx-react';
import { Swiper, SwiperSlide } from "swiper/react"; // 引入swiper,实现轮播
import 'style-loader!css-loader!swiper/swiper-bundle.css'; // 引入swiper的css
import './swiperComponent.less';
@observer
class SwiperComponent extends React.Component {
constructor(props) {
super(props);
}
// 【非常重要】fixed: 多行swiper情况下,第一次进入页面时,某一行 出现 先快后慢、滑动一轮后才和其余几行达成一致 的步调
componentDidMount() {
this.carouselSwiper?.autoplay.stop(); // 关闭自动切换
// 加个延时
setTimeout(() => {
this.carouselSwiper?.autoplay.start(); // 开启自动切换
},500)
}
// TODO: 根据自己需求对下方两个数据进行调整(可以把autoplay关闭后慢慢调)
firstContainerSlidesPerView = 1.25; // 第一个swiper-container的slidesPerView
SecondSlidePaddingLeft = 0.8; // 第二个swiper-slide的paddingLeft值(第一个的值为0)
render() {
const {
// 索引值
index,
// 当前轮播信息
carouselInfo,
} = this.props;
return (
{
carouselInfo?.length > 0 &&
className="barrage" // 设置slider容器能够同时显示的slides数量(carousel模式) slidesPerView={this.firstContainerSlidesPerView - index * 0.15} //【关键】匀速时间 speed={3000} //【关键】设置为true则变为free模式 freeMode={true} // 设置为true 则开启loop(无限循环)模式 loop={true} // 自动播放 autoplay={{ delay: 0, //【关键】自动切换的时间间隔,单位ms }} onSwiper={swiper => { this.carouselSwiper = swiper; }} style={{ paddingLeft: `${index * this.SecondSlidePaddingLeft}rem` }} > { carouselInfo?.map((item, index) => { return ( {/* slide背景图 */}
{/* slide内容 */}
)
})
}
}
}
}
export default SwiperComponent;
swiperComponent.less
【关键点】 给.swiper-wrapper增加样式transition-timing-function: linear;实现swiper匀速轮播~
.barrageInner {
width: 100%;
height: 100%;
/** 相当于swiper-container */
.barrage {
width: 100%;
height: 100%;
box-sizing: border-box;
/**【关键】swiper实现匀速轮播 */
&>.swiper-wrapper {
-webkit-transition-timing-function: linear; /*之前是ease-out*/
-moz-transition-timing-function: linear;
-ms-transition-timing-function: linear;
-o-transition-timing-function: linear;
transition-timing-function: linear;
}
/** 相当于swiper-slide */
.barrageItem {
position: relative;
/** 不需要写宽度,用swiper-slide的默认宽度 */
height: 62px;
.barrageItemBg, .barrageText {
/** slide背景图和slide内容的宽度 */
width: 467px;
height: 100%;
position: absolute;
left: 0;
top: 0;
}
/** slide背景 */
.barrageItemBg {
opacity: .4;
background: url("../../assets/startPage/danmuBg.png") no-repeat center/cover;
}
/** slide内容 */
.barrageText {
padding: 0 10px;
box-sizing: border-box;
font-size: 26px;
color: #4478a0;
text-align: center;
line-height: 62px;
}
/** 文字展示固定宽度,超出省略号展示 */
.text-hidden-ellipsis {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
/** 设置文字方向:从左往右 */
direction: ltr;
}
}
}
}
2、调用该组件 ⭐️
homePage.jsx
【注意】多行交错、同速、跑马灯效果的弹幕式轮播 里的 行数 修改方法如下哦:
小萝卜儿们凌,想实现好多行,就将如下代码里state的devideNum修改成对应理想行数即可哦~
/**
* 活动首页
*/
'use strict';
import React from 'react';
import { observer } from 'mobx-react';
import SwiperComponent from "@src/components/swiperComponent/swiperComponent"; // 引入弹幕item组件
import './homePage.less';
@observer
class HomePage extends React.Component {
constructor(props) {
super(props);
this.state = {
/** 弹幕信息 */
fakeCarouselData: [],
/** 需划分的swiper份数 */
devideNum: 3,
}
}
// 测试数据
carouselInfo = ['嘻嘻嘻1', '啦啦啦啦1', '嘻嘻嘻2', '哈哈哈2', '嘻嘻嘻3'];
componentDidMount() {
const result = this.cut(this.state.devideNum, this.carouselInfo);
console.log('result', result); // [['嘻嘻嘻1', '啦啦啦啦1'],['嘻嘻嘻2', '哈哈哈2'],['嘻嘻嘻3']]
this.setState({
fakeCarouselData: result,
})
}
/*
将一个含未知个数内容的数组,划分成num份
* num {Int} 需划分的份数
* arr {Array} 数据源
*/
cut = (num, arr) => {
if (num < 2) {
console.error("参数不合法");
}
const length = arr.length;
if (length == 0) {
return [];
}
const step = Math.ceil(length / num);
const list = [];
for (let i = 0; i < num; i++) {
const start = i * step;
const end = length - i * step > step ? (i + 1) * step : length;
const part = arr.slice(start, end);
list.push(part);
}
return list;
}
// 在组件卸载及销毁之前 清空掉swiper里的数据【数据为动态数据时,一定要加这步哦:https://blog.csdn.net/weixin_48850734/article/details/127509051?spm=1001.2014.3001.5501】
componentWillUnmount() {
this.carouselInfo = [];
}
render() {
const { fakeCarouselData } = this.state;
return (
{/* 弹幕区域【swiper-no-swiping: 禁止手动滑动】*/}
{/* 遍历fakeCarouselData数组 */}
{
fakeCarouselData.map((item, index) => {
return (
)
})
}
);
}
}
export default HomePage;
homePage.less
.homePage {
width: 750px;
height: 100%;
position: absolute;
/** swiper实现的弹幕区域 */
.barrageContent {
width: 750px;
height: 264px;
position: absolute;
left: 0;
top: 1106px;
/** 轮播的swiper */
.barrageOuter {
width: 100%;
height: 62px;
&:not(:last-child) {
margin-bottom: 39px;
}
}
}
}
【二】、JS-将一个含未知个数内容的数组,划分成num份
/*
将一个含未知个数内容的数组,划分成num份
* @param {Int} num 需划分的份数
* @param {Array} arr 数据源
* @return {Array}
*/
function cut(num, arr) {
if (num < 2) {
console.error("参数不合法");
}
const length = arr.length;
if (length == 0) {
return [];
}
const step = Math.ceil(length / num);
const list = [];
for (let i = 0; i < num; i++) {
const start = i * step;
const end = length - i * step > step ? (i + 1) * step : length;
const part = arr.slice(start, end);
list.push(part);
}
return list;
}
cut(3,['嘻嘻嘻1', '啦啦啦啦1', '嘻嘻嘻2', '哈哈哈2', '嘻嘻嘻3']); // [['嘻嘻嘻1', '啦啦啦啦1'], ['嘻嘻嘻2', '哈哈哈2'], ['嘻嘻嘻3']]
推荐文章
发表评论