
关于vue实现无缝滚动--数据大屏可能用的多一点
没有过渡动画;
·
不注重动画的基于transition-group实现的方式:
没有过渡动画;
<template>
<div class="scroll-container">
<transition-group tag="div" name="slide" class="scroll-list">
<div class="scroll-item" v-for="(item, index) in items" :key="item.key">
{{ item.text }}
</div>
</transition-group>
</div>
</template>
<script>
export default {
data() {
return {
items: [], // 您的数据数组
maxVisibleItems: 5, // 可视区域最多显示的条目数
};
},
mounted() {
this.initializeItems();
this.startSeamlessScroll();
},
methods: {
initializeItems() {
// 初始化数据,确保有足够的条目来填充滚动列表
for (let i = 1; i <= 10; i++) {
this.items.push({ text: `条目${i}`, key: i });
}
},
startSeamlessScroll() {
// 设置定时器来更新列表,实现无缝滚动
setInterval(() => {
const firstItem = this.items.shift(); // 移除第一个元素
this.items.push(firstItem); // 将第一个元素添加到列表末尾
}, 2000); // 每2秒滚动一次
},
},
};
</script>
<style>
.scroll-container {
overflow: hidden;
height: 250px; /* 根据您的项目高度调整 */
}
.scroll-item {
height: 50px; /* 根据您的项目高度调整 */
}
.scroll-list {
display: flex;
flex-direction: column;
}
.slide-enter-active,
.slide-leave-active {
transition: all 0.5s ease;
}
.slide-enter,
.slide-leave-to {
transform: translateY(100%);
opacity: 0;
}
</style>
效果图:
有动画的基于transition-group的实现的方式:
有过渡动画;
<template>
<div class="scroll-view" @mouseenter="stopScroll" @mouseleave="startScroll">
<transition-group name="list" tag="div" class="list-container">
<div
class="list-item"
v-for="(item, index) in displayItems"
:key="item.key"
>
{{ item.text }}
</div>
</transition-group>
</div>
</template>
<script>
export default {
data() {
return {
items: [], // 这个数组会填入全部数据
displayItems: [], // 这个数组用于展示可见的数据
scrollInterval: null,
pauseTime: 2000,
};
},
created() {
// 初始化 items,添加 key 用作 transition-group 的唯一标识
this.items = Array.from({ length: 10 }, (v, k) => ({
text: `Item ${k + 1}`,
key: k,
}));
// 填充 displayItems 数组
this.displayItems = [...this.items];
},
mounted() {
this.startScroll();
},
methods: {
scroll() {
const firstItem = this.displayItems.shift(); // 移除数组的第一个元素
this.displayItems.push(firstItem); // 将其添加到数组的末尾(无缝滚动的关键)
// 如果我们到达列表的末尾,我们会重置按键以创建无缝体验 TODO 一开始因为vue的diff算法涉及到key,想着去更新dom,但实际这里会阻塞页面的渲染
// if (this.displayItems[0].key === 0) {
// this.resetKeys();
// }
},
startScroll() {
// TODO 不想停留的话,去掉这些
this.scrollInterval = setInterval(() => {
this.scroll();
}, this.pauseTime);
},
stopScroll() {
clearInterval(this.scrollInterval);
},
resetKeys() {
this.displayItems.forEach((item, index) => {
item.key = index;
});
console.log("重置", this.displayItems);
},
},
beforeDestroy() {
this.stopScroll();
},
};
</script>
<style scoped>
.scroll-view {
overflow: hidden;
height: 250px; /* Assumes each item is 50px in height and we show 5 items */
}
.list-container {
padding: 0;
}
.list-item {
height: 50px;
display: flex;
align-items: center;
justify-content: left;
transition: transform 0.8s ease;
}
/* Animation for each list item */
.list-move {
transition: transform 2s ease;
}
/* Set the distance each item has to move (should be the height of 1 item) */
.list-enter-active,
.list-leave-active {
transition-duration: 0.8s;
}
.list-enter,
.list-leave-to /* <- this is the new Vue 2.1.8+ syntax for v-leave */ {
transform: translateY(50px);
}
</style>
效果图:
其他的可以参考借鉴的例子:
https://codesandbox.io/p/sandbox/vue-template-pt5oz?file=%2Fsrc%2FApp.vue%3A11%2C1
更多推荐
所有评论(0)