vue的滚动条插件实现代码

这篇文章主要介绍了vue的滚动条插件实现代码,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下

效果如下

代码如下

<template>
  <div class="vue-scroll" ref="vueScrollW">
    <div class="vue-scroll-w" ref="vueScroll" >
      <div class="vue-scroll-c" :style="{width:cWidth}">
        <slot></slot>
      </div>
    </div>
    <div class="vue-scrollbar" v-if="rate < 1">
      <div class="vue-scrollbar-thumb"
      :style="{height:thumbH,top:thumbTop}"
      @mousedown="onmousedown"
      @mouseup="onmouseup"
      ></div>
    </div>
  </div>
</template>

<script>

export default {
  name:"vue-scroll",
  data(){
    return {
      thumb:0,
      top:0,
      rate:2,
      moveTop:null,
      isDrag:false,
      cw:10,
      observer:null
    }
  },
  computed:{
    thumbH(){
      return this.thumb + "px";
    },
    thumbTop(){
      return this.top + "px";
    },
    cWidth(){
      return this.cw + "%";
    }

  },
  updated(){
    if(!window.MutationObserver){
      this.refresh();
    }
  },
  mounted(){
    var me = this;
    me.$refs.vueScroll.addEventListener("scroll",me.onscroll.bind(me));
    window.addEventListener("mouseup",me.onmouseup.bind(me));
    window.addEventListener("mousemove",me.onmousemove.bind(me));

    if(window.MutationObserver){
      //MutationObserver 最低只兼容 ie11
      me.observer = new window.MutationObserver(me.mutationCallback.bind(me));
      me.observer.observe(me.$refs.vueScroll, {
        attributes: true,
        childList: true,
        subtree: true
      });
    }

    me.refresh();
  },
  methods:{
    mutationCallback(mutationsList){
      this.refresh();
    },
    onscroll(){
      this.top = this.$refs.vueScroll.scrollTop * this.rate; //计算滚动条所在的高度
      if(this.rate < 1){
        this.eventTrigger(this.top);
      }
    },
    refresh(){
      var me = this;
      var vueScroll = me.$refs.vueScroll;
      var rate = vueScroll.clientHeight / vueScroll.scrollHeight; //滚动条高度的比例,也是滚动条top位置的比例
      me.rate = rate;
      if(rate < 1){
        //需要出现滚动条,并计算滚动条的高度
        me.thumb = rate * vueScroll.clientHeight; //滚动条的 bar 的高度
        //计算出原生的滚动条的宽度
        var w = me.$refs.vueScrollW.clientWidth;
        //根据比例,转换为内容的百分比
        me.cw = w/vueScroll.clientWidth *100;
      }else{
        //不需要出现滚动条
         me.thumb = 0;
         me.cw = 10;
      }
    },

    onmousedown(){
      this.isDrag = true;
      this.moveTop = null;
    },
    onmouseup(){
      this.isDrag = false;
    },
    onmousemove(e){
      if(this.isDrag){
        if(this.moveTop !== null){
          var speed = e.screenY - this.moveTop;
          var top = this.top + speed;
          this.scrollThumb(top);
        }
        this.moveTop = e.screenY;
        e.preventDefault();
      }

    },
    scrollThumb(top){
      if(top < 0 ){
        top = 0;

      }
      if(top > this.$refs.vueScroll.clientHeight-this.thumb){
        top = this.$refs.vueScroll.clientHeight-this.thumb;

      }

      this.$refs.vueScroll.scrollTop = top/this.rate;
      this.top = top;
    },
    eventTrigger(top){
      if(top === 0){
        this.$emit("reachTop"); //到达顶部
      }
      if(top === this.$refs.vueScroll.clientHeight-this.thumb){
        this.$emit("reachBottom"); //到达底部与
      }
      this.$emit("vuescroll",this.$refs.vueScroll.scrollTop,this.top);//返回内容滚动的高度 和 滚动条所在的高度
    },
    scrollTo(scrollTop){
      //对外的api,滚动的内容的哪里
       this.$refs.vueScroll.scrollTop = scrollTop;
       this.$nextTick(()=>{
         this.onscroll();
       })
    }
  },
  destroyed(){
    var me = this;
    me.$refs.vueScroll && me.$refs.vueScroll.removeEventListener("scroll",me.onscroll.bind(me));
    window.removeEventListener("mouseup",me.onmouseup.bind(me));
    window.removeEventListener("mousemove",me.onmousemove.bind(me));
    me.observer&&me.observer.disconnect();
  }
}
</script>

<style lang="scss" scoped>
.vue-scroll{
  height: 100%;
  width: 100%;
  overflow: hidden;
  position: relative;
  .vue-scroll-w{
    width: 1000%;
    height: 100%;
    overflow: auto;
    .vue-scroll-c{
      position: relative;
      width: 10%;
    }
  }
  .vue-scrollbar{
    position: absolute;
    z-index: 1;
    right: 0;
    top: 0;
    width: 4px;
    height: 100%;
    background: #EEEEEE;
    opacity: 0.6;
    .vue-scrollbar-thumb{
      position: absolute;
      top: 0;
      right: 0;
      width: 4px;
      border-radius: 4px;
      background: #D3D3D3;
      &:hover{
        background: #bbb;
      }
      &:active{
        background: #aaa;
      }
    }
  }
}
</style>

使用

<template>
  <div class="scroll">
    <vueScroll>
      <ul>
        <li v-for="item in 60" :key="item">{{item}}</li>
      </ul>
    </vueScroll>
  </div>
</template>

<script>
import vueScroll from "@/components/vue-scroll.vue"
export default {
  data(){
    return {
      count:60
    }
  },
  components:{
    vueScroll
  },
  mounted(){

  }
}
</script>
<style lang="less" scoped>
.scroll{
  width: 400px;
  height: 600px;
  margin: 0 auto;
  border: 1px solid red;
  ul{
    li{
      line-height: 30px;
      border-bottom: 1px solid #ddd;
    }
  }
}
</style>

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • Vue 无限滚动加载指令实现方法

    也不存在什么加载咯, 就是一个判断滚动条是否到达浏览器底部了. 如果到了就触发事件,米到就不处理. 计算公式提简单的   底部等于(0) =  滚动条高度 - 滚动条顶部距离 - 可视高度.  反正结果就是0. 一.获取滚动条位置 class Scroll { static get top() { return Math.max(document.documentElement.scrollTop || document.body.scrollTop); } static get clientH

  • vue 实现滚动到底部翻页效果(pc端)

    pc端vue 滚动到底部翻页 效果,具体内容如下所示: html: <div class="list" ref="scrollTopList"> <div class="listsmall" v-for="(item,index) of list" :key="index" @click="getDeviceInfo(item.id)"> <span cla

  • vue中获取滚动table的可视页面宽度调整表头与列对齐(每列宽度不都相同)

    mounted() { // 在mounted中监听表格scroll事件 this.$refs.scrollTable.addEventListener( 'scroll',(event) => { this.adjustTable(event); }); }, ...... // target中的属性很多,可以通过控制台查看--clientWidth可以获取除滚动条外的可视区域宽度 adjustTable(event) { this.clientWidth = event.target.cli

  • Vue.js+cube-ui(Scroll组件)实现类似头条效果的横向滚动导航条

    本博主在一次个人移动端项目中,遇到这么一个需求:希望自己的项目中,头部导航条的效果可以像今日头条那样,横向滚动! 对于这样的效果,在各大移动端项目中几乎是随处可见,为什么呢? 我们都知道,对于移动端也就是手机上,我们页面的宽度并不像PC端那样大,可以显示很长的导航项,但对于我们移动端来说,由于功能的拓展,或者业务的细分,往往导航项也会随之增多,一旦超过移动端在一行的页面显示宽度,那便会出现导航项换行的现象,虽说也有这样布局,但一旦导航项增多到一定程度的时候,我们的页面(首页)将均被导航项霸占,这

  • vue使用keep-alive保持滚动条位置的实现方法

    前言 下班前,20分钟,发一篇... 简单介绍,使用keep-alive的时候,返回前一页,没有保持滚动条位置. 事实上,就算不使用keep-alive,位置也没有被记录. 但是,在不适用keep-alive的时候,页面内容会刷新,所以就随他去了--就是这么任性-- 思路 官方有推荐一个scrollBehavior,链接,但是上面标注,只在history.pushState的浏览器生效,不知道是不是只能开启history.pushState才可以使用,看了下实现,挺不友好的,还是自己搞一个吧..

  • vue滚动tab跟随切换效果

    分享一个我前几天做的移动端 tab滚动跟随的例子 随着滚动条的滚动,tab会对应进行切换 首先我们需要监听当前页面的滚动 mounted(){ //记录每个内容对用的dom数组 this.arrDom = document.getElementsByClassName("item-content"); window.addEventListener('scroll', this.handleScroll); }, destroyed(){ window.removeEventListe

  • 基于vue实现滚动条滚动到指定位置对应位置数字进行tween特效

    实现目标 浏览各大云平台,发现一个页面特效使用较为频繁,以"百度云"为例(https://cloud.baidu.com/),进入百度云后,当滚动条滚动至"更可靠的数据支持"模块时,页面数据将会开始滚动式增长特效.下面将会介绍我的解决方案,希望有同行更好的解决方案大家一起交流. 解决思路 主要的解决要点如下: 如何实现数字动画的效果 如何监听滚动条到指定的位置 分解要点寻找解决思路: 一.如何实现数字动画的效果 在vue的官方文档(https://cn.vuejs.

  • vue的滚动条插件实现代码

    这篇文章主要介绍了vue的滚动条插件实现代码,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 效果如下 代码如下 <template> <div class="vue-scroll" ref="vueScrollW"> <div class="vue-scroll-w" ref="vueScroll" > <div class=&quo

  • 在vue项目中使用codemirror插件实现代码编辑器功能

    在vue项目中使用codemirror插件实现代码编辑器功能(代码高亮显示及自动提示),具体内容如下所示: 1.使用npm安装依赖 npm install --save codemirror; 2.在页面中放入如下代码 <template> <textarea ref="mycode" class="codesql" v-model="code" style="height:200px;width:600px;&quo

  • vue利用Moment插件格式化时间的实例代码

    moment是一款多语言支持的日期处理类库, 在vue中如何使用呢?首先附上官网地址:http://momentjs.cn/, 毕竟查找api才是学习正途! 使用npm命令安装moment npm install moment --save 在main.js文件里引用moment // The Vue build version to load with the `import` command // (runtime-only or standalone) has been set in we

  • vue引入swiper插件的使用实例

    本文介绍了vue引入swiper插件,分享给大家,希望对大家有帮助 步骤一:安装vue, $ npm install vue 步骤二:创建vue项目 # 全局安装 vue-cli $ npm install -g vue-cli $ cd my-project $ npm install $ npm run dev 上面这些就是安装好vue项目,最主要的就是下面的步骤 步骤三:下载好swiper相关的js和css,js放在static目录下,css放在assets目录下. 步骤四:  安装run

  • vue调用高德地图实例代码

    一. vue-amap,一个基于 Vue 2.x 和高德地图的地图组件 https://elemefe.github.io/vue-amap/#/ 这个就不细说了,按照其文档,就能够安装下来. 二. 按照官方提供的方法引入 1.修改webpac.base.conf.js文件 externals: { 'AMap': 'AMap' } 2.引入sdk 引入有两种方式,一种是页面直接引入 复制代码 代码如下: <script type="text/javascript" src=&q

  • jquery滚动条插件slimScroll使用方法

    本文实例为大家总结了滚动条插件slimScroll的使用方法,供大家参考,具体内容如下 simScroll插件项目下载地址:https://github.com/rochal/jQuery-slimScroll TIP: 1.slimScroll在使用的时候要依赖JQ,所以首次使用的时候要引入JQ再引入simScroll插件 2.不支持resize的时候重新调用插件,不过有人已经修改过源码,这是修改过的版本的下载地址:https://github.com/kujian/jQuery-slimSc

  • jquery自定义滚动条插件示例分享

    复制代码 代码如下: <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html xmlns="http://www.w3.org/1999/xhtml"><head><meta http-equiv="

  • jQuery中Nicescroll滚动条插件的用法

    本篇文章主要介绍了jQuery中Nicescroll滚动条插件的用法,Nicescroll滚动条插件是一个非常强大的基于jQuery的滚动条插件,有需要的可以了解下. Nicescroll滚动条插件是一个非常强大的基于jQuery的滚动条插件,不需要增加额外的css,几乎全浏览器兼容.ie6+,实现只需要一段代码,侵入性非常小,样式可完全自定义,支持触摸事件,可在触摸屏上使用. Nicescroll官网地址:http://www.areaaperta.com/nicescroll/ 引入核心文件

  • 分享一则JavaScript滚动条插件源码

    这是过年的时候自己写的js滚动条插件的源码,做出的效果自己并不满意,正因为做的并不满意所以回头重新巩固和深入学习js,这个插件有如下几个不太满意的地方: 内容的过度效果,可以参阅QQ客户端最近会话列表里的滚动条,它的滚动非常的平滑,简单的说就是缺少动画过渡效果. 并不算完美的兼容性,在IE6.7下的style仍然有点缺憾. 样式的不完美,例如鼠标悬浮才显示滚动条,移除后隐藏这种效果都没有写. 内部结构的混乱,需要调整内容结构. 滚动条那个图片毕竟不是美工,自己切图切的真是恶心到爆了...囧 总体

  • jQuery leonaScroll 1.1 自定义滚动条插件(推荐)

    leonaScroll-1.1最新版 leonaScroll-1.1.js 欢迎使用leonaScroll-1.1.js,如您在使用过程中发现更多问题,欢迎指正! 更新:1.1版本 1.修复了前面初始版本中的一些bug,比如不能自适应用户的文本内容,css文件繁杂 2.用户只需调用一个方法即可使用该插件,无需按照原来的class类名去添加和定义你的滚动条文本域及外层元素,显得更为自由 3.增设了滚动条宽度.上下微调按钮高度,滚动文本区域的设置 4.增设了文本内容未超出时是否显示滚动条可选设置选项

随机推荐