スクロールメソッドで実装
Vue3 では、ref
フックonMounted
関数を使用してコンテナ要素を取得し、スクロール イベントをリッスンしてコンテンツが一番下までスクロールしたかどうかを判断し、新しいデータの読み込みをトリガーできます。
簡単なコード例を次に示します。
<template>
<div class="container" ref="container" @scroll="handleScroll">
<ul>
<li v-for="item in items" :key="item.id">{
{ item.title }}</li>
<li v-if="loading">Loading...</li>
</ul>
</div>
</template>
<script>
import { ref, onMounted } from 'vue'
export default {
setup() {
const containerRef = ref(null)
const items = ref([])
const loading = ref(false)
const page = ref(1)
const handleScroll = () => {
const container = containerRef.value
if (container.scrollTop + container.clientHeight >= container.scrollHeight) {
loadMore()
console.log('到底了');
}
}
const loadMore = () => {
if (loading.value) return
loading.value = true
// 发送请求加载新数据
fetchData(page.value)
.then(newData => {
items.value = [...items.value, ...newData]
loading.value = false
page.value++
})
}
onMounted(() => {
// 初始化加载数据
loadMore()
})
return {
containerRef,
items,
loading,
handleScroll
}
}
}
</script>
上記の例では、コンテナ要素は
containerRef
を使用して取得され、リスト データはを使用して定義され、新しいデータがロードされているかどうかを示し、現在のページ番号を示します。ref
items
ref
loading
page
handleScroll
この関数はスクロールイベントの処理関数で、まずコンテナ要素を取得し、その合計が等しいかどうかでコンテンツが一番下までスクロールしたかどうかを判定し、等しい場合には新規データの読み込みをトリガーscrollTop
します。clientHeight
scrollHeight
loadMore
loadMore
この関数は、まずデータがロードされているかどうかを判断し、ロードされている場合は直接戻ります。そうでない場合は に設定され、新しいデータをロードするリクエストを送信しloading
、true
新しいデータと古いデータを結合して を更新し、items
増加した値loading
に設定します。。false
page
最後に、
onMounted
フック関数で読み込みデータを初期化します。
コンポーネントアプローチ
vue-infinite-loading
プラグインを使用すると、コンテナのコンテンツが一番下までスクロールしたときに新しいデータを自動的にロードできます。
次のように進めます。
プラグインをインストールしvue-infinite-loading
、Vue プロジェクトに導入します。
npm install vue-infinite-loading
import InfiniteLoading from 'vue-infinite-loading';
スクロール読み込みを実装する必要があるコンポーネントをコンテナに追加しますinfinite-loading
。
<template>
<div class="container" ref="container">
<div v-for="(item, index) in items" :key="index">{
{ item }}</div>
<infinite-loading @infinite="loadMore" />
</div>
</template>
コンテナーが配置されているコンポーネントにメソッドを追加してloadMore
、新しいデータをロードします。
import axios from 'axios';
export default {
data() {
return {
items: [],
page: 1, // 当前页码
limit: 10, // 每页数据量
};
},
methods: {
async loadMore($state) {
const res = await axios.get(`/api/data?page=${this.page}&limit=${this.limit}`);
this.items.push(...res.data);
this.page++;
$state.loaded(); // 通知插件已加载完成
},
},
mounted() {
// 监听滚动事件,当滚动到底部时触发加载更多数据
this.$refs.container.addEventListener('scroll', () => {
if (this.$refs.container.scrollTop + this.$refs.container.clientHeight === this.$refs.container.scrollHeight) {
this.$refs.infiniteLoading.$emit('$InfiniteLoading:infinite');
}
});
},
};
上記の手順により、コンテナのコンテンツが一番下までスクロールしたときに新しいデータを自動的にロードできます。データのロードが完了したら、ロードが完了したことをプラグインに手動で通知する、つまり$state.loaded()
メソッドを呼び出す必要があります。