vue-music实现轮播无缝滚动better-scroll

最近在写一个基于vue2.0的移动端音乐项目,昨天写到 了首页的轮播图部分,跟着视频教程写的,没想到最后却出现了一大堆错误,并且都是视频中所没有的,自己思考了很久,也不知道是怎么回事,今天早上开机之后,百度发现,原来是better-scroll的版本为题,视频中用的是老版本"better-scroll": "^0.1.15",而 我npm安装的是新版本"better-scroll": "^1.15.2",,顿时恍然大悟

接下来我主要发一些本次出错误的需要纠正新老版本的部分代码

slider.vue:

<<template>
  <div class="slider" ref="slider">
      <div class="slider-group" ref="sliderGroup">
          <slot>
              <!-- 外部引入一个插槽,slider包裹的dom会被引入到插槽部分 -->
          </slot>
      </div>
      <div class="dots">
          <span class="dot" v-for="(item,index) in dots" :class="{active: currentPageIndex === index}"></span>
      </div>
  </div>
</template>

recommend.vue:  

<<template>
   <div class="recommend">
     <div class="recommend-content">
       <div v-if="recommends.length" class="slider-wrapper">
         <slider>
           <div v-for="(item,index) in recommends">
             <a :href="item.linkUrl">
               <img :src="item.picUrl">
             </a>
           </div>
         </slider>
       </div>
       <div class="recommend-list">
         <h1 class="list-title">热门歌单推荐</h1>
         <ul>

         </ul>
       </div>
     </div>
   </div>
</template>

其中需要注意,这边需要控制显示的时机,是由于slider.vue中设置html的宽度等是在mounted (即已完成模板渲染后执行),而recommend.vue 当还未获取数据的时候,mounted 已经执行,为了确保元素的存在再渲染,所以添加判断。

slider.vue,设置图片的宽度以及总宽度:
 

 _setSliderWidth(isResize){
            this.children = this.$refs.sliderGroup.children
            //console.log(this.children.length)
            let width = 0
            let sliderWidth = this.$refs.slider.clientWidth
            for(let i = 0;i<this.children.length;i++){
                let child = this.children[i]
                addClass(child,'slider-item')   //为每一个子元素添加类名

                child.style.width = sliderWidth+'px'
                width += sliderWidth    //容器的总宽度
            }
            if (this.loop&&!isResize) {
                width += 2*sliderWidth  //如果轮播,左右会各增加一个,所以要加上两张图片的宽度
            }
            this.$refs.sliderGroup.style.width = width+'px'   //为元素设置容器的总宽度

        },

addClass :(添加类名)

//写一些dom相关操作的代码
export function addClass(el,className) {
    if (hasClass(el,className)) {
        return
    }
    let newClass = el.className.split(' ') //split() 将原本的className字符串按空格分割成数组
    newClass.push(className) //将新的className 添加到上面的数组中
    el.className = newClass.join(' ') //join() 以空格为连接符链接成class字符串
}
export function hasClass(el,className) {
    let reg = new RegExp('(^|\\s)'+className+'(\\s|$)')
    //创建一个正则,开头或者是空白字符,class字符跟空白字符,或者结束
    return reg.test(el.className)
}//判断是否有class方法

初始化 better-scroll时机,将那些函数在mounted  完成渲染后执行:(*一般初始化better-scroll不成功);

 并通过监听窗口改变事件,解决当窗口改变时,图片的宽度未发生改变的问题

 mounted(){
        setTimeout(() => {
            this._setSliderWidth()
            this._initDots()
            this._initSlider()

            if (this.autoPlay) {
              this._play() 
            }
        }, 20)

        window.addEventListener('resize',()=>{
            if (!this.slider) {
                return
            }
            this._setSliderWidth(true)
            this.slider.refresh()
        })
    },

初始化better-slider插件:

_initSlider(){
            //初始化slider
            this.slider = new BScroll(this.$refs.slider,{
                scrollX:true,//允许横向滚动
                scrollY:false,//不允许纵向滚动
                momentum:false,//关闭动量动画,能提升效能
                snap:{    //新版本将snap的属性都当成一个对象来书写
                    loop:this.loop,//循环
                    threshold:0.3,
                    speed:400,//轮播间隔
                }
                //click:true //允许点击
            })
            this.slider.on('scrollEnd',()=>{
                let pageIndex = this.slider.getCurrentPage().pageX

                console.log(pageIndex+1)
                // if (this.loop) {
                //    // pageIndex -= 1
                // }旧版本需要,新版本不需要
                this.currentPageIndex = pageIndex
                if(this.autoPlay){
                    clearTimeout(this.timer)
                   // pageIndex -= 1
                    this._play()
                } 
            })
        },

播放就可以采用更便捷的命令:

 _play(){
            //let pageIndex = this.currentPageIndex + 1
            // if (this.loop) {
            //     pageIndex += 1
            // }//旧版本需要计算增加的两张图片带来的影响
            this.timer = setTimeout(() => {
                // this.slider.goToPage(pageIndex,0,400)
                this.slider.next()
            }, this.interval);
        }
    },

优化: 

1.     及时关闭轮播,有利于内存的释放

  destroyed() {
    clearTimeout(this.timer)
  }

2.    app.vue中添加<keep-alive>,将DOM缓存到内存中,切换不会重新请求,并且没有一闪而过的画面

    <keep-alive>
      <router-view></router-view>
    </keep-alive>

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值