关于作者
还是大剑师兰特:曾是美国某知名大学计算机专业研究生,现为航空航海领域高级前端工程师;CSDN知名博主,GIS领域优质创作者,深耕openlayers、leaflet、mapbox、cesium,canvas,webgl,echarts等技术开发,欢迎加底部微信,一起交流。
No. | 推荐链接 |
---|---|
1 | Openlayers 【入门教程】 - 【源代码+图文 300+】 |
2 | Leaflet 【入门教程】 - 【源代码+图文示例 150+】 |
3 | Cesium 【入门教程】 - 【源代码+图文示例200+】 |
4 | MapboxGL【入门教程】 - 【源代码+图文示例150+】 |
5 | 前端就业宝典 【面试题+详细答案 1000+】 |
文章目录
- 一、项目需求
- 二、通常思路
- 三、示例效果图
- 四、示例源代码
一、项目需求
使用vue做项目的时候,碰到区块内公告信息间隔一定时间自动向上滚动的情形。demo图和代码如下。
二、通常思路
在Vue中实现文字向上滚动的原理通常涉及使用CSS动画和/或JavaScript来改变元素的位置。这里有几个关键的概念和步骤,可以帮助理解这一过程:
-
容器定位:
- 创建一个固定高度的容器,用于容纳滚动的文字。这个容器应该有
overflow: hidden
属性,这样超出的部分会被裁剪,不会显示在容器外。
- 创建一个固定高度的容器,用于容纳滚动的文字。这个容器应该有
-
文字排列:
- 文字需要被包裹在一个内部元素中,这个内部元素将被移动来模拟滚动效果。这个内部元素可以是
<div>
或其他任何块级元素。
- 文字需要被包裹在一个内部元素中,这个内部元素将被移动来模拟滚动效果。这个内部元素可以是
-
CSS动画或变换:
- 使用CSS动画或变换属性来向上移动内部元素,这通常是通过
transform: translateY()
实现的。 - 为了创建一个连续的滚动效果,内部元素可能需要包含多份文本内容,这样当文本滚动出视口时,下面的文本可以无缝地接上。
- 使用CSS动画或变换属性来向上移动内部元素,这通常是通过
-
定时器或动画循环:
- 可以使用JavaScript的
setInterval
函数来定期更新内部元素的位置,或者使用CSS的@keyframes
来定义动画循环。
- 可以使用JavaScript的
-
无缝滚动:
- 要实现无缝滚动,需要在动画结束时将内部元素的位置重置,同时避免视觉上的跳变。这通常通过将内部元素的副本放置在其下方并立即开始向上滚动来实现。
-
Vue的响应式处理:
- Vue的响应式系统可以用来在数据变化时重新计算元素的位置或触发动画,确保动画与数据同步。
三、示例效果图
四、示例源代码
/*
* @Author: 大剑师兰特(xiaozhuanlan),还是大剑师兰特(CSDN)
* @此源代码版权归大剑师兰特所有,可供学习或商业项目中借鉴,未经授权,不得重复地发表到博客、论坛,问答,git等公共空间或网站中。
* @Email: 2905222303@qq.com
* @weixin: gis-dajianshi
* @First published in CSDN
* @First published time: 2024-06-03
*/
<template>
<div class="djs-box">
<div class="topBox">
<h3>vue实现文字向上滚动效果</h3>
<div>大剑师兰特, 还是大剑师兰特,gis-dajianshi</div>
</div>
<div class="dajianshi">
<li v-for="item in list" ref="rollul" :class="{anim:animate==true}">
{{item.vname}} - {{item.vtime}} - {{item.pvname}}
</li>
</div>
</div>
</template>
<script>
export default {
data() {
return {
time:[],
animate: true,
list: [
{ "vname": "大剑师1", "pvname": "PIC-----1", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师2", "pvname": "PIC-----2", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师3", "pvname": "PIC-----3", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师4", "pvname": "PIC-----4", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师5", "pvname": "PIC-----5", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师6", "pvname": "PIC-----6", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师7", "pvname": "PIC-----7", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师8", "pvname": "PIC-----8", "vtime": "2024.05.12 11:12:23" },
{ "vname": "大剑师9", "pvname": "PIC-----9", "vtime": "2024.05.12 11:12:23" },
]
}
},
mounted() {
const timer = setInterval(this.goscroll,1000);
// 通过$once来监听定时器,在beforeDestroy钩子可以被清除。
this.$once('hook:beforeDestroy', () => {
clearInterval(timer);})
},
methods: {
goscroll() {
let con1 = this.$refs.rollul;
con1[0].style.marginTop = '30px';
this.animate = !this.animate;
var that = this; // 在异步函数中会出现this的偏移问题,此处一定要先保存好this的指向
setTimeout(function() {
that.list.push(that.list[0]);
that.list.shift();
con1[0].style.marginTop = '0px';
that.animate = !that.animate; // 这个地方如果不把animate 取反会出现消息回滚的现象,此时把ul 元素的过渡属性取消掉就可以完美实现无缝滚动的效果了
}, 0)
}
}
}
</script>
<style scoped>
.djs-box {
width: 1000px;
height: 650px;
margin: 50px auto;
border: 1px solid black;
}
.topBox {
margin: 0 auto 0px;
padding: 10px 0 20px;
background: black;
color: #fff;
}
.dajianshi {
width: 98%;
margin: 0 auto;
height: 520px;
padding-top:150px;
background-color: cde;
position: relative;
}
.dajianshi li {height: 30px; line-height: 30px; font-size: 20px; list-style: none; }
.anim {transition: all 0.5s; }
</style>