当前位置:首页 > VUE

vue无限滚动实现教程

2026-01-22 02:17:17VUE

Vue无限滚动实现方法

使用第三方库vue-infinite-loading

安装vue-infinite-loading库:

npm install vue-infinite-loading --save

在组件中引入并使用:

vue无限滚动实现教程

import InfiniteLoading from 'vue-infinite-loading';

export default {
  components: {
    InfiniteLoading
  },
  data() {
    return {
      items: [],
      page: 1
    };
  },
  methods: {
    loadMore($state) {
      axios.get(`/api/items?page=${this.page}`)
        .then(({ data }) => {
          if (data.length) {
            this.items.push(...data);
            this.page++;
            $state.loaded();
          } else {
            $state.complete();
          }
        });
    }
  }
}

模板部分:

<template>
  <div>
    <div v-for="item in items" :key="item.id">
      {{ item.content }}
    </div>
    <infinite-loading @infinite="loadMore"></infinite-loading>
  </div>
</template>

原生实现无限滚动

监听滚动事件实现:

vue无限滚动实现教程

export default {
  data() {
    return {
      items: [],
      isLoading: false,
      page: 1,
      hasMore: true
    };
  },
  mounted() {
    window.addEventListener('scroll', this.handleScroll);
    this.loadItems();
  },
  beforeDestroy() {
    window.removeEventListener('scroll', this.handleScroll);
  },
  methods: {
    handleScroll() {
      const scrollY = window.scrollY;
      const visible = window.innerHeight;
      const pageHeight = document.documentElement.scrollHeight;
      const bottomOfPage = visible + scrollY >= pageHeight - 200;

      if (bottomOfPage && !this.isLoading && this.hasMore) {
        this.loadItems();
      }
    },
    loadItems() {
      this.isLoading = true;
      axios.get(`/api/items?page=${this.page}`)
        .then(({ data }) => {
          if (data.length) {
            this.items = [...this.items, ...data];
            this.page++;
          } else {
            this.hasMore = false;
          }
          this.isLoading = false;
        });
    }
  }
}

使用Intersection Observer API

现代浏览器支持的更高效方式:

export default {
  data() {
    return {
      items: [],
      observer: null,
      page: 1
    };
  },
  mounted() {
    this.observer = new IntersectionObserver((entries) => {
      if (entries[0].isIntersecting) {
        this.loadMore();
      }
    });

    this.observer.observe(this.$refs.loader);
    this.loadMore();
  },
  methods: {
    loadMore() {
      axios.get(`/api/items?page=${this.page}`)
        .then(({ data }) => {
          if (data.length) {
            this.items = [...this.items, ...data];
            this.page++;
          }
        });
    }
  }
}

模板中添加触发元素:

<div ref="loader"></div>

注意事项

  • 确保API接口支持分页查询
  • 处理加载状态和错误情况
  • 移动端需要考虑滚动性能优化
  • 大量数据渲染时使用虚拟滚动技术提高性能
  • 清除事件监听和观察器避免内存泄漏

标签: 教程vue
分享给朋友:

相关文章

vue实现tab标签

vue实现tab标签

Vue 实现 Tab 标签的方法 使用动态组件和 v-for 渲染标签 通过 v-for 循环生成标签页标题,结合 v-bind:class 动态切换激活状态。使用 v-show 或动态组件 <…

vue怎么实现数据检测

vue怎么实现数据检测

Vue 数据检测的实现方式 Vue 通过响应式系统实现数据检测,核心机制基于 Object.defineProperty(Vue 2)或 Proxy(Vue 3)。以下是具体实现方法: 基于 Vu…

vue怎么实现文件树

vue怎么实现文件树

Vue 实现文件树的方法 使用递归组件 递归组件是处理嵌套数据结构的理想方式。文件树通常包含文件夹和文件的嵌套结构,适合用递归组件实现。 <template> <ul>…

vue实现倒计时抢券

vue实现倒计时抢券

Vue 实现倒计时抢券功能 核心逻辑 倒计时抢券功能需要结合时间计算、状态管理和界面交互。通过 Vue 的响应式特性和生命周期钩子,可以高效实现这一需求。 实现步骤 1. 数据准备 在 Vue 组…

vue实现缩放

vue实现缩放

Vue 实现缩放的方法 在 Vue 中实现缩放功能可以通过多种方式完成,以下是一些常见的方法: 使用 CSS transform 属性 通过 CSS 的 transform: scale() 属性…

vue 实现闪烁

vue 实现闪烁

Vue 实现闪烁效果的方法 方法一:使用 CSS 动画 在 Vue 组件中定义一个闪烁的 CSS 动画,通过绑定 class 或 style 来控制元素的闪烁效果。 <template&…