VueUse useInfiniteScroll在Vue3正常运行,为何在Nuxt3中失效?
Nuxt3中useInfiniteScroll无法触发加载的原因及解决办法
问题根源
在Nuxt3中,默认页面布局的滚动容器并非你绑定ref="el"的自定义div,而是外层的#__nuxt或#__layout容器。你的代码监听的是自定义div的滚动事件,但实际滚动发生在父容器上,导致useInfiniteScroll无法检测到滚动到底部的动作。而Vue3项目没有这种默认布局容器的层级问题,所以功能正常。
另外,你给自定义div设置的h-100类(假设使用Tailwind CSS)需要父元素也设置100%高度才能生效,否则该div不会占满视口高度,自然不会出现滚动条,滚动事件也就无从触发。
解决办法
办法1:监听window的滚动事件
直接将useInfiniteScroll的监听目标改为window,这样无论滚动容器是谁,都能正确检测滚动到底部的动作:
<script setup lang="ts"> import { useInfiniteScroll } from '@vueuse/core'; const data = ref([]); const total = ref(0); // 监听window的滚动 useInfiniteScroll(window, loadData, { distance: 10 }); loadData(); async function loadData() { if (data.value.length !== 0 && data.value.length >= total.value) return; const res = await fetch( `https://dummyjson.com/products/?limit=10&skip=${data.value.length}` ); const d = await res.json(); total.value = d.total; data.value = data.value.concat(d.products); } </script> <template> <div class="el"> <div v-for="item in data" class="card"> <img :src="item.thumbnail" alt="" /> <h3>{{ item.title }}</h3> <p>{{ item.description }}</p> </div> </div> </template>
办法2:让自定义div成为滚动容器
确保自定义div成为实际的滚动容器,需要调整样式使其占满视口并开启垂直滚动:
<script setup lang="ts"> import { useInfiniteScroll } from '@vueuse/core'; const el = ref<HTMLElement>(null); const data = ref([]); const total = ref(0); useInfiniteScroll(el, loadData, { distance: 10 }); loadData(); async function loadData() { if (data.value.length !== 0 && data.value.length >= total.value) return; const res = await fetch( `https://dummyjson.com/products/?limit=10&skip=${data.value.length}` ); const d = await res.json(); total.value = d.total; data.value = data.value.concat(d.products); } </script> <template> <div ref="el" class="el h-screen overflow-y-auto"> <div v-for="item in data" class="card"> <img :src="item.thumbnail" alt="" /> <h3>{{ item.title }}</h3> <p>{{ item.description }}</p> </div> </div> </template> <style> /* 确保根元素占满视口高度 */ html, body, #__nuxt, #__layout { height: 100%; margin: 0; padding: 0; } </style>
这里用h-screen替代h-100确保div占满整个视口高度,同时添加overflow-y-auto使其出现垂直滚动条,再通过全局样式让所有父容器都占满视口高度,保证自定义div成为滚动容器。
内容的提问来源于stack exchange,提问作者redshift
相关产品推荐
相关产品推荐

