Vue项目中的虚拟滚动:提升页面渲染性能的最佳实践

简介: 本文介绍虚拟滚动技术及其在Vue项目中的应用,通过vue-virtual-scroller实现大数据量下长列表的高性能渲染,提升页面流畅度与用户体验,适用于地图轨迹等业务场景。

目录

前言

在现代 Web前端开发中,性能优化一直是个重要话题。尤其在数据量较大的情况下,页面的渲染性能会直接影响用户体验。使用虚拟滚动技术,可以有效解决大数据量下的渲染性能问题。本篇文章将带你深入了解虚拟滚动的应用,帮助你在Vue项目中优化页面渲染性能。

什么是虚拟滚动

虚拟滚动(Virtual Scrolling)是一种高效的渲染技术,主要用于处理大量数据的长列表或表格。其基本原理是只渲染当前视口内可见的元素,而对不可见的部分仅保留占位符。这种方法大幅减少了DOM节点的数量,从而提升了渲染性能和滚动流畅度。

虚拟滚动的核心有以下 4 点:

  • 渲染可见元素:虚拟滚动只会渲染当前视口内的元素,而不是整个列表或表格。比方说,假设视口中只能显示10个元素,那么虚拟滚动技术只会渲染这10个元素,即使总数据量有上万个。
  • 动态更新视口内容:当用户进行滚动操作 时,使用虚拟滚动技术可以动态更新可视区域内的内容。新进入视口的元素会被渲染,而离开视口的元素会被销毁,从而保持视口内元素的数量相对稳定。
  • 减少DOM操作:由于只渲染了可视区域内的元素,虚拟滚动大幅减少了DOM操作的频率。这不仅提高了渲染速度,还减小了内存占用,从而提升了整体性能。
  • 占位元素:为了确保滚动条的正确性,虚拟滚动技术通常会使用一个高度为所有元素总高度的占位元素。这种占位元素会占据整个列表的高度,从而使滚动条的行为与渲染所有元素时相同。

业务案例

我接到过一个需求,就是某个页面,需要展示多个人的地图行为轨迹,这个人数比较多,可能有上千人,由于后端限制,不能做成分页的形式,只能做成一个很长的、可以滚动的列表。如果数据少,一次性渲染也还好,数据多了,页面操作必然会有些卡顿的,这对页面性能消耗比较大。选择虚拟滚动,就能很好的解决这个问题。

实现方式

由于我这里是 Vue的项目,这里推荐一个很好用的第三方库:vue-virtual-scroller。

在 GitHub 上,可以看到针对 Vue2 或者 Vue3 的使用说明。

这里介绍下 Vue2 的使用方法:

通过 npm安装

npm install vue-virtual-scroller

main.js引入

import { RecycleScroller } from 'vue-virtual-scroller' // 虚拟滚动插件
import 'vue-virtual-scroller/dist/vue-virtual-scroller.css'
Vue.component('RecycleScroller', RecycleScroller)

这里我用的是RecycleScroller,适用于列表每一项大小固定的情况。如果你的每一项的高度不固定,你可以使用DynamicScrollerDynamicScrollerItem来实现虚拟滚动。

在Vue页面中使用

template 部分

<div class="table-box">
  <RecycleScroller class="scroller" :items="pointsData" :item-size="80" key-field="name" v-slot="{ item }">
    <div class="scroller-item">
      <img src="/avatar2.jpg" alt="" />
      <div class="scroller-item-content">
        <div>{
  { item.name }}</div>
        <div>编号:{
  { item.equipmentCoding }}</div>
      </div>
      <div class="scroller-item-btn" @click="viewingTrajectories(item)">查看轨迹</div>
    </div>
  </RecycleScroller>
</div>

css 部分:

.table-box {
  display: flex;
  gap: 10px;
  height: 400px;
  .scroller {
    width: 100%;
    height: 100%;
    .scroller-item {
      display: flex;
      justify-content: space-between;
      align-items: center;
      height: 70px;
      padding: 10px 16px;
      margin-bottom: 10px;
      border-radius: 15px;
      background: linear-gradient(180deg, #dee9ff 0%, #ffffff 100%);
      box-shadow: 1px 1px 6px 0px rgba(163, 190, 244, 0.67);
      border-radius: 4px 4px 4px 4px;
      border: 1px solid #fff;
      border-image: linear-gradient(180deg, rgba(255, 255, 255, 1), rgba(255, 255, 255, 0)) 1 1;
      &:nth-last-child(1){
        margin-bottom: 0;
      }
      > img {
        width: 40px;
        height: 40px;
        border-radius: 100px;
      }
      > .scroller-item-content {
        display: flex;
        flex-direction: column;
        justify-content: flex-start;
        align-items: flex-start;
        gap: 4px;
        font-size: 14px;
        margin-left: 16px;
        > div:nth-child(1) {
          font-weight: 500;
          color: #1d2129;
        }
        > div:nth-child(n + 2) {
          font-weight: 400;
          color: #86909c;
        }
      }
      > .scroller-item-btn {
        cursor: pointer;
        user-select: none;
        margin-left: auto;
        margin-top: auto;
        padding: 5px 16px;
        border-radius: 20px;
        border: 1px solid #0a57fe;
        font-weight: 400;
        font-size: 14px;
        color: #0a57fe;
      }
    }
  }
}

这里需要注意,如果你希望让子元素之间有间距,我设置了item-size="80",同时设置.scroller-item这个class 的样式的height 为 70px,以及设置它的margin-bottom:10px;,最后一个元素设置 margin-bottom: 0

效果预览

请在此添加图片描述

可以看到,无论是鼠标滚轮,还是拖动滚动滑块,都可以有很流畅的滚动效果。

总结

通过引入虚拟滚动技术,我们可以显著提升大数据量列表的渲染性能和用户滚动体验。虚拟滚动通过只渲染可视区域的内容,减少了DOM操作和内存占用,解决了传统大数据量渲染带来的性能瓶颈问题。目前 Vue3 相关的 UI 框架,大部分组件都支持了虚拟滚动,可以直接用,但 Vue2 旧项目相关的虚拟滚动相对较少,可能部分业务场景,需要自己手动实现,比方说下拉选择框、表格等。后面我会深入研究,用虚拟滚动技术,改造现有的组件。希望这篇文章可以对你有所帮助。

目录
相关文章
|
6天前
|
JavaScript 前端开发 开发工具
前端开发必备的 VSCode 插件推荐(第三期)
本文推荐两款提升Vue开发效率的VSCode插件:vue-helper,支持代码扩选、快速跳转与变量定位;别名路径跳转插件,解决@路径无法跳转问题。配置简单,实用高效,助力前端开发提速。
135 0
|
JavaScript 中间件 测试技术
Nest 框架:解锁企业级 Web 应用开发的秘密武器(上)
Nest 框架:解锁企业级 Web 应用开发的秘密武器(上)
Nest 框架:解锁企业级 Web 应用开发的秘密武器(上)
隐藏el-table-column过多的内容并进行浮窗展示
隐藏el-table-column过多的内容并进行浮窗展示
隐藏el-table-column过多的内容并进行浮窗展示
|
JavaScript
自行封装的tabs组件配合echarts而出现的bug以及解决
自行封装的tabs组件配合echarts而出现的bug以及解决
527 0
|
容器
layui框架实战案例(14):tabs选项卡切换时echarts拉伸变形无法正常显示的解决方案
layui框架实战案例(14):tabs选项卡切换时echarts拉伸变形无法正常显示的解决方案
508 0
|
6天前
|
前端开发 JavaScript API
CSS弹性盒子布局图标的展示效果优化技巧
本文介绍前端开发中一个弹性布局的优化问题:小屏幕下图标错位影响美观。通过媒体查询和ResizeObserver API两种方案,实现容器宽度不足时隐藏图标,提升响应式体验。重点讲解ResizeObserver对单个元素的精准监听与Vue中的实践应用,兼顾用户体验与代码性能。
26 0
CSS弹性盒子布局图标的展示效果优化技巧
|
6天前
|
存储 资源调度 前端开发
如何在Vue2项目中完美集成pnpm?
本文介绍如何在Vue2项目中使用pnpm包管理器,涵盖其快速安装、高效磁盘利用、严格依赖管理等优势,并详细说明Windows和Mac下的安装步骤及关键配置方法,如新建.npmrc文件解决兼容性问题,帮助开发者顺利迁移并提升项目维护效率。
38 0
Element UI【详解】el-scrollbar 滚动条组件 —— 监听滚动条的滚动,跟随页面一起滚动,获取滚动距离,隐藏水平滚动条等
Element UI【详解】el-scrollbar 滚动条组件 —— 监听滚动条的滚动,跟随页面一起滚动,获取滚动距离,隐藏水平滚动条等
2586 0
|
缓存 JavaScript 前端开发
Vue3升级版本引发的 npm ERR! code ERESOLVE npm ERR! ERESOLVE unable to resolve dependency tree
Vue3升级版本,引发的 npm ERR! code ERESOLVE npm ERR! ERESOLVE unable to resolve dependency tree
1778 0
Vue3升级版本引发的 npm ERR! code ERESOLVE npm ERR! ERESOLVE unable to resolve dependency tree