vue3 数据可视化大屏 项目开发中,为了让项目页面更酷炫,会增加很多动画效果,今天使用 gsap补间动画 实现线条延伸动画效果。
线条延伸效果,是通过一条线将两个div进行连接,让线条的宽度从0延伸到自己想要的长度,达到一个线条延伸的效果。
上面的动画中有一个水柱上升的效果是通过gsap来实现的补间动画。通过css实现一个波浪的效果
列表组件
通过vue的列表渲染,渲染出列表,使用wow实现入场动画,通过依次增加data-wow-delay wowjs延迟时间,达到依次入场的效果,使用css定位将线条定位到div的指定位置,然后通过css3 rotateZ 设置div的旋转角度,然后通过补间动画让线条延伸连接到目标div上面。
<template>
<div class="list">
<div class="listItem wow fadeInRight" :data-wow-delay="0.15*index+'s'" :style="{marginLeft:item.left+'%'}"
v-for="(item,index) in list" :key="index">
<div class="listItemInner">
<p>{{ item.title }}</p></div>
<lines class="lineRight"
:style="{transform:'rotateZ('+item.rotateZ+'deg)',width:item.width+'%'}"></lines>
</div>
</div>
</template>
<script>
import WOW from "wow.js";
import lines from '@/components/line/index.vue'
export default {
name: "left",
data() {
return {
list: [{
title: '就业',
left: 55,
rotateZ: -190,
width: 120
},{
title: '教评',
left: 65,
rotateZ: -190,
width: 140
},{
title: '一卡通',
left: 65,
rotateZ: -170,
width: 140
},{
title: '医务',
left: 60,
rotateZ: -160,
width: 140
}]
}
},
components: {
lines,
},
mounted() {
var wow = new WOW({
boxClass: "wow", // animated element css class (default is wow)
animateClass: "animated", // animation css class (default is animated)
offset: 0, // distance to the element when triggering the animation (default is 0)
mobile: true, // trigger animations on mobile devices (default is true)
live: true, // act on asynchronously loaded content (default is true)
callback: function (box) {
// the callback is fired every time an animation is started
// the argument that is passed in is the DOM node being animated
},
scrollContainer: null, // optional scroll container selector, otherwise use window,
resetAnimation: true, // reset animation on end (default is true)
});
wow.init();
},
}
</script>
<style lang="scss" scoped>
.list {
position: absolute;
right: 100px;
width: 300px;
overflow: hidden;
height: 100%;
display: flex;
justify-content: flex-start;
align-items: center;
flex-wrap: nowrap;
flex-direction: column;
align-content: flex-start;
padding-top: 20%;
.listItem {
background: url("../../../../assets/home2/paopao.png") no-repeat;
width: 60px;
height: 60px;
background-size: 100% 100%;
position: relative;
right: 0px;
margin-bottom: 16px;
display: flex;
justify-content: center;
align-items: center;
flex-wrap: nowrap;
flex-direction: column;
align-content: flex-start;
font-size: 12px;
font-family: PingFang SC-Bold, PingFang SC;
font-weight: bold;
color: #FFFFFF;
.lineRight {
position: absolute;
left: 0px;
top: 40px;
transform-origin: 0% 0%;
transform: rotateZ(-90deg);
}
}
}
</style>
线条延伸组件
线条延伸需要两个div,最外层是预设宽度,内层是需要延伸的宽度,通过gsap实现让div从宽度0到100%的补间动画。
<template>
<div class="lineAnimation">
<div class="lineAnimationInner" ref="lineAnimationInner"></div>
</div>
</template>
<script>
import gsap from "gsap";
export default {
name: "lineAnimation",
props: {
delay: {
type: Number,
default() {
return 2;
}
}
},
mounted() {
gsap.to(this.$refs.lineAnimationInner, {
duration: 2, delay: this.delay, width: 100 + '%', onComplete: () => {
console.log('动画完成')
}
})
},
}
</script>
<style lang="scss" scoped>
.lineAnimation {
width: 120px;
height: 1px;
display: flex;
justify-content: flex-start;
align-items: center;
flex-wrap: nowrap;
flex-direction: row;
align-content: flex-start;
.lineAnimationInner {
width: 0;
height: 1px;
background: rgba(54, 167, 237, 1.00);
}
}
</style>