vue实现虚拟列表功能的代码


Posted in Javascript onJuly 28, 2020

当数据量较大(此处设定为10w),而且要用列表的形式展现给用户,如果我们不做处理的话,在浏览器中渲染10w dom节点,是极其耗费时间的,那我的Macbook air举例,10w条数据渲染出来到能看到页面,需要13秒多(实际应该是10秒左右),如果是用户的话肯定是不会等一个网页十几秒的

vue实现虚拟列表功能的代码

我们可以用虚拟列表解决这个问题
一步步来
首先看一下效果

vue实现虚拟列表功能的代码

这是data中的数据

data() {
  return {
   list: [], // 贼大的数组
   li: {
    // 列表项信息
    height: 50,
   },
   container: {
    // 容器信息
    height: 500,
   },
   pos: 1, // 第一排显示的元素的下标
   MAX_NUM: 1, // 在容器内最多显示几个列表项
   timer: null, // 定时器
   carriedOut: true, // 能不能执行操作
  };
 },

然后在mounted中创建一个贼大的数组,在调用test方法计算第一次的虚拟列表中有哪些

mounted() {
  // 创建一个贼大的数据数组
  for (let i = 0; i < 100000; i++) {
   this.list.push(i);
  }
  this.test();
 },

test方法

test() {
   // 节流
   if (this.carriedOut) {
    // 容器跟里面的列表项
    const { container, li } = this;
    // 计算可视区域最多能显示多少个li
    this.MAX_NUM = Math.ceil(container.height / li.height);
    // 获取 overflow:scroll 的元素已滚动的高度
    let scrollTop = this.$refs.container.scrollTop;
    // 计算当前处于第一排的元素的下标
    this.pos = Math.round(scrollTop / li.height);
    // 下方节流操作
    this.carriedOut = false;
    this.timer = setTimeout(() => {
     this.carriedOut = true;
     clearTimeout(this.timer);
    }, 50);
   }
  },

然后是computed

computed: {
  // 用于渲染在页面上的数组
  showList() {
   // 根据计算出来的 第一排元素的下标,和最多显示多少个 用slice实现截取数组
   let arr = this.list.slice(this.pos, this.pos + this.MAX_NUM);
   return arr;
  },
 },

这是html,注意监听了div的scroll事件,并且调用的是test方法

<div class="virtual-list">
  <h1>虚拟列表</h1>
  <div class="container" ref="container" :style="`height:${container.height}px`" @scroll="test">
   <ul :style="`height:${li.height*list.length}px;padding-top:${li.height*pos}px`">
    <li :style="`height:${li.height}px`" v-for="item in 100000" :key="item">{{item}}</li>
   </ul>
  </div>
 </div>

完整源代码

<template>
 <div class="virtual-list">
  <h1>虚拟列表</h1>
  <div class="container" ref="container" :style="`height:${container.height}px`" @scroll="test">
   <ul :style="`height:${li.height*list.length}px;padding-top:${li.height*pos}px`">
    <li :style="`height:${li.height}px`" v-for="item of showList" :key="item">{{item}}</li>
   </ul>
  </div>
 </div>
</template>

<script>
export default {
 data() {
  return {
   list: [], // 贼大的数组
   li: {
    // 列表项信息
    height: 50,
   },
   container: {
    // 容器信息
    height: 500,
   },
   pos: 1, // 第一排显示的元素的下标
   MAX_NUM: 1, // 在容器内最多显示几个列表项
   timer: null, // 定时器
   carriedOut: true, // 能不能执行操作
  };
 },
 mounted() {
  // 创建一个贼大的数据数组
  for (let i = 0; i < 1000; i++) {
   this.list.push(i);
  }
  this.test();
 },
 computed: {
  // 用于渲染在页面上的数组
  showList() {
   // 根据计算出来的 第一排元素的下标,和最多显示多少个 用slice实现截取数组
   let arr = this.list.slice(this.pos, this.pos + this.MAX_NUM);
   return arr;
  },
 },
 methods: {
  test() {
   // 节流
   if (this.carriedOut) {
    // 容器跟里面的列表项
    const { container, li } = this;
    // 计算可视区域最多能显示多少个li
    this.MAX_NUM = Math.ceil(container.height / li.height);
    // 获取 overflow:scroll 的元素已滚动的高度
    let scrollTop = this.$refs.container.scrollTop;
    // 计算当前处于第一排的元素的下标
    this.pos = Math.round(scrollTop / li.height);
    // 下方节流操作
    this.carriedOut = false;
    this.timer = setTimeout(() => {
     this.carriedOut = true;
     clearTimeout(this.timer);
    }, 50);
   }
  },
 },
};
</script>

<style lang="scss" scoped>
.virtual-list {
 text-align: center;
 .container {
  overflow: scroll;
  border: 1px solid red;
 }
}
</style>

到此这篇关于vue实现虚拟列表功能的代码的文章就介绍到这了,更多相关vue 虚拟列表内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Javascript 相关文章推荐
JQuery 绑定事件时传递参数的实现方法
Oct 13 Javascript
ExtJs Excel导出并下载IIS服务器端遇到的问题
Sep 16 Javascript
玩转jQuery按钮 请告诉我你最喜欢哪些?
Jan 08 Javascript
JavaScript实现重置表单(reset)的方法
Apr 02 Javascript
轻松实现javascript数据双向绑定
Nov 11 Javascript
使用Function.apply()的参数数组化来提高 JavaScript程序性能的技巧
Dec 23 Javascript
JS实现图片平面旋转的方法
Mar 01 Javascript
详解jQuery中的empty、remove和detach
Apr 11 Javascript
fullCalendar中文API官方文档
Feb 07 Javascript
AngularJS实现的简单拖拽功能示例
Jan 02 Javascript
简易Vue评论框架的实现(父组件的实现)
Jan 08 Javascript
JS+HTML5 canvas绘制验证码示例
Dec 05 Javascript
vue.js 解决v-model让select默认选中不生效的问题
Jul 28 #Javascript
Vue2.0 $set()的正确使用详解
Jul 28 #Javascript
JavaScript 监听组合按键思路及代码实现
Jul 28 #Javascript
JavaScript动画实例之粒子文本的实现方法详解
Jul 28 #Javascript
Vue $emit()不能触发父组件方法的原因及解决
Jul 28 #Javascript
vue 遮罩层阻止默认滚动事件操作
Jul 28 #Javascript
JavaScript实现沿五角星形线摆动的小圆实例详解
Jul 28 #Javascript
You might like
《心理测量者3》剧场版动画预告
2020/03/02 日漫
PHP4之COOKIE支持详解
2006/10/09 PHP
php 文章调用类代码
2011/08/11 PHP
redis+php实现微博(三)微博列表功能详解
2019/09/23 PHP
laravel框架中间件简单使用方法示例
2020/01/25 PHP
8个超棒的学习 jQuery 的网站 推荐收藏
2011/04/02 Javascript
Prototype源码浅析 Number部分
2012/01/16 Javascript
jQuery中 prop() attr()使用详解
2015/05/19 Javascript
javascript实现的字符串与十六进制表示字符串相互转换方法
2015/07/17 Javascript
JavaScript运行过程中的“预编译阶段”和“执行阶段”
2015/12/16 Javascript
如何利用JSHint减少JavaScript的错误
2016/08/23 Javascript
AngularJS中$injector、$rootScope和$scope的概念和关联关系深入分析
2017/01/19 Javascript
原生js实现类似fullpage的单页/全屏滚动
2017/01/22 Javascript
jquery+ajaxform+springboot控件实现数据更新功能
2018/01/22 jQuery
弱类型语言javascript中 a,b 的运算实例小结
2019/08/07 Javascript
vue data对象重新赋值无效(未更改)的解决方式
2020/07/24 Javascript
[03:04]2018年度DOTA2玩家最喜爱的主播-完美盛典
2018/12/16 DOTA
python使用win32com在百度空间插入html元素示例
2014/02/20 Python
Python中subprocess的简单使用示例
2015/07/28 Python
Python中functools模块函数解析
2017/03/12 Python
python3爬虫之设计签名小程序
2018/06/19 Python
Python跑循环时内存泄露的解决方法
2020/01/13 Python
Python pip使用超时问题解决方案
2020/08/03 Python
使用css实现android系统的loading加载动画
2019/07/25 HTML / CSS
WSDL的操作类型主要有几种
2013/07/19 面试题
护理职业生涯规划书
2014/01/24 职场文书
政治学求职信
2014/06/03 职场文书
小学生国庆节演讲稿
2014/09/05 职场文书
护士医德医风自我评价
2014/09/15 职场文书
民主评议党员个人总结
2015/02/13 职场文书
导游词之扬州大明寺
2019/10/09 职场文书
详细介绍python类及类的用法
2021/05/31 Python
Oracle创建只读账号的详细步骤
2021/06/07 Oracle
Python编解码问题及文本文件处理方法详解
2021/06/20 Python
教你怎么用Python selenium操作浏览器对象的基础API
2021/06/23 Python
MySQL七大JOIN的具体使用
2022/02/28 MySQL