如何在Vue中根据视口宽度调整显示的条目数量?
动态根据视口调整Vue列表显示条数的最优方案
方案一:计算属性 + window.matchMedia(Vue 2/3通用)
这种方式直接利用浏览器原生的媒体查询监听API,比手动监听resize事件更精准,代码简洁且无需自己处理宽度判断逻辑:
<template> <div> <!-- 直接使用计算后的列表 --> <div v-for="item in displayedItems" :key="item.id">{{ item.content }}</div> </div> </template> <script> export default { data() { return { items: [], // 你的数据源 displayCount: 10, mediaQuery: null }; }, computed: { displayedItems() { // 统一通过displayCount控制截取数量 return this.items.slice(0, this.displayCount); } }, mounted() { // 定义移动端分界的媒体查询(可根据需求修改断点) this.mediaQuery = window.matchMedia('(max-width: 768px)'); // 初始化显示数量 this.displayCount = this.mediaQuery.matches ? 5 : 10; // 监听媒体查询变化 this.mediaQuery.addEventListener('change', this.handleMediaChange); }, beforeUnmount() { // 组件销毁前移除监听,避免内存泄漏 this.mediaQuery?.removeEventListener('change', this.handleMediaChange); }, methods: { handleMediaChange(e) { // 根据视口切换显示数量 this.displayCount = e.matches ? 5 : 10; } } }; </script>
方案二:Vue 3组合式API + 可复用组合函数(推荐)
如果使用Vue 3,把逻辑封装成组合式函数,可在多个组件中复用,扩展性更强:
第一步:封装组合式函数
// composables/useMediaDisplayCount.js import { ref, onMounted, onUnmounted } from 'vue'; export function useMediaDisplayCount( breakpoint = '(max-width: 768px)', mobileCount = 5, desktopCount = 10 ) { const displayCount = ref(desktopCount); const handleMediaChange = (e) => { displayCount.value = e.matches ? mobileCount : desktopCount; }; onMounted(() => { const mediaQuery = window.matchMedia(breakpoint); displayCount.value = mediaQuery.matches ? mobileCount : desktopCount; mediaQuery.addEventListener('change', handleMediaChange); // 临时存储实例用于销毁 window.__mediaQueryInstance__ = mediaQuery; }); onUnmounted(() => { window.__mediaQueryInstance__?.removeEventListener('change', handleMediaChange); delete window.__mediaQueryInstance__; }); return displayCount; }
第二步:在组件中使用
<template> <div> <div v-for="item in displayedItems" :key="item.id">{{ item.content }}</div> </div> </template> <script setup> import { ref, computed } from 'vue'; import { useMediaDisplayCount } from '@/composables/useMediaDisplayCount'; const items = ref([]); // 你的数据源 // 调用组合函数,可自定义断点和显示数量 const displayCount = useMediaDisplayCount('(max-width: 768px)', 5, 10); const displayedItems = computed(() => { return items.value.slice(0, displayCount.value); }); </script>
为什么这些方案更好?
- 避免了重复编写两个列表的冗余代码,所有逻辑统一通过
displayCount变量控制 - 原生
matchMediaAPI比手动监听resize更高效,只会在视口跨越断点时触发回调,而非每次 resize 都执行 - 组合式函数的方式支持多组件复用,后续修改断点或显示数量只需调整参数,扩展性拉满
内容的提问来源于stack exchange,提问作者hnrd
相关产品推荐
相关产品推荐

