不同tab切换,内部的swiper自动轮播失效

简介

我们有个需求,就是不同功能中都有轮播,然后使用的是 swiper。

也就是切换 tab 标签,内部的 swiper 变开始自动轮播。

现在遇到的问题是:初始进来的那个 tab 的 swiper 能自动轮播,但切换了 tab 就不能轮播了。

解决方法

然后我就查询度娘,找到了一个博客,里面大致说的就是,切换了 tab,让每个 swiper 的父盒子(这个 tab 盒子添加了一个 display: “none”)

所以就造成了:swiper 轮播失效。

然后他说的就是,每次切换回来的时候重新初始化 swiper

所以,我的方案是:每次切换 tab 时,通过全局事件总线,来让子组件重新调用函数进行 swiper 的初始化。

代码

swiper 部分代码

<div class="swiper-container judge-swiper swiper-no-swiping swiper-container-setting">
<div class="swiper-wrapper">
<div class="swiper-slide" v-for="(item, index) in judgeDataList" :key="index">
<div class="judge-box"></div>
</div>
</div>
</div>

以前的代码

// eslint-disable-next-line no-unused-vars
let judgeSwiper

export default {
methods: {
_initJudgeSwiper () {
// eslint-disable-next-line no-new
judgeSwiper = new Swiper('.judge-swiper', {
loop: true,
autoplay: {
delay: 2000,
disableOnInteraction: false
},
speed: 3000,
slidesPerView: 4,
spaceBetween: 40,
preloadImages: true,
observer: true, // 修改 swiper 自己或子元素时,自动初始化 swiper 默认为 false
observeParents: false // 修改 swiper 的父元素时,自动初始化 swiper
})
},
},
activated () {
setTimeout(() => {
this._initJudgeSwiper()
}, 2000)
}
}

修改后的代码

父组件

<el-tabs v-model="defaultTab" style="margin-top: -15px" class="content-wrapper" @tab-click="tabClickHandle">
<el-tab-pane label="评委介绍页" name="judgeShow">
<keep-alive><ScreenJudgeShow @_submitJudgeData="_submitJudgeData" :judgeData="subcomponentData.judgeData"></ScreenJudgeShow></keep-alive>
</el-tabs>
</el-tab-pane>

methods: {
tabClickHandle (tab, event) {
// 当点击了这个 tab 后就告诉对应子组件: 我被点击了,你快点初始化 swiper 组件,让它动起来
this.$bus.$emit('initJudgeSwiper')
}
}

解释一下:

  • @tab-click="tabClickHandle": 父子组件之间的 $emit 通信(本次讲解的通信,使用的是事件委托,本来的 tab 标签较多,这里未展示完全)
  • @_submitJudgeData="_submitJudgeData": 父子组件之间的 $emit 通信(这个是另一个的通信,这里可以不管)
  • :judgeData="subcomponentData.judgeData": 父子组件之间的 props 通信

子组件


// eslint-disable-next-line no-unused-vars
let judgeSwiper

export default {
methods: {
_initJudgeSwiper () {
// eslint-disable-next-line no-new
judgeSwiper = new Swiper('.judge-swiper', {
loop: true,
autoplay: {
delay: 2000,
disableOnInteraction: false
},
speed: 3000,
slidesPerView: 4,
spaceBetween: 40,
preloadImages: true,
observer: true, // 修改 swiper 自己或子元素时,自动初始化 swiper 默认为 false
observeParents: false // 修改 swiper 的父元素时,自动初始化 swiper
})
},
},
activated () {
this.$nextTick(() => {
// 收到父组件传递的消息(我被点击了,你快点初始化 swiper 组件,让它动起来),开始对 swiper 进行初始化
this.$bus.$on('initJudgeSwiper', this._initJudgeSwiper)
})
}
}