如何利用vue實(shí)現(xiàn)css過渡和動畫
一、過渡和動畫的區(qū)別
過渡:通常用來表示元素上屬性狀態(tài)的變化。
動畫:通常用來表示元素運(yùn)動的情況。
二、使用Vue實(shí)現(xiàn)基礎(chǔ)得css過渡與動畫
1. 動畫
/* css */
@keyframes leftToRight {
0% {
transform: translateX(-100px);
}
50% {
transform: translateX(-50px);
}
100% {
transform: translateX(0);
}
}
.animation {
animation: leftToRight 3s;
}
// js
const app = Vue.createApp({
data() {
return {
animate: {
animation: true
}
}
},
methods: {
handleClick(){
this.animate.animation = !this.animate.animation
}
},
template: `
<div :class='animate'>hello</div>
<button @click='handleClick'>切換</button>
`
});

2. 過渡
/* css */
.transition {
transition: background-color 3s linear 0s;
}
.gold {
background-color: gold;
}
.cyan {
background-color: cyan;
}
// js
const app = Vue.createApp({
data() {
return {
animate: {
transition: true,
gold: true,
cyan: false
}
}
},
methods: {
handleClick() {
this.animate.gold = !this.animate.gold;
this.animate.cyan = !this.animate.cyan;
}
},
template: `
<div :class='animate'>hello</div>
<button @click='handleClick'>切換</button>
`
});

以上是通過設(shè)置class屬性實(shí)現(xiàn)的,同樣通過設(shè)置style屬性也可以實(shí)現(xiàn):
/* css */
.transition {
transition: background-color 3s linear 0s;
}
// js
data() {
return {
transition: 'transition',
styleObject: {
backgroundColor: 'gold'
}
}
},
methods: {
handleClick() {
if(this.styleObject.backgroundColor === 'gold'){
this.styleObject.backgroundColor = 'cyan';
}else{
this.styleObject.backgroundColor = 'gold';
}
}
},
template: `
<div :class='transition' :style='styleObject'>hello</div>
<button @click='handleClick'>切換</button>
`
三、使用transition標(biāo)簽實(shí)現(xiàn)單元素/組件的過渡和動畫效果
1. transition 的基本介紹
- <transition>?元素作為單個(gè)元素/組件的過渡效果。
- <transition>?只會把過渡效果應(yīng)用到其包裹的內(nèi)容上,而不會額外渲染 DOM 元素,也不會出現(xiàn)在可被檢查的組件層級中。
2. transition 的過渡class
在進(jìn)入/離開的過渡中,會有 6 個(gè) class 切換:
- v-enter-from:定義進(jìn)入過渡的開始狀態(tài)。在元素被插入之前生效,在元素被插入之后的下一幀移除。
- v-enter-active:定義進(jìn)入過渡生效時(shí)的狀態(tài)。在整個(gè)進(jìn)入過渡的階段中應(yīng)用,在元素被插入之前生效,在過渡/動畫完成之后移除。這個(gè)類可以被用來定義進(jìn)入過渡的過程時(shí)間,延遲和曲線函數(shù)。
- v-enter-to:定義進(jìn)入過渡的結(jié)束狀態(tài)。在元素被插入之后下一幀生效 (與此同時(shí) v-enter-from 被移除),在過渡/動畫完成之后移除。
- v-leave-from:定義離開過渡的開始狀態(tài)。在離開過渡被觸發(fā)時(shí)立刻生效,下一幀被移除。
- v-leave-active:定義離開過渡生效時(shí)的狀態(tài)。在整個(gè)離開過渡的階段中應(yīng)用,在離開過渡被觸發(fā)時(shí)立刻生效,在過渡/動畫完成之后移除。這個(gè)類可以被用來定義離開過渡的過程時(shí)間,延遲和曲線函數(shù)。
- v-leave-to:離開過渡的結(jié)束狀態(tài)。在離開過渡被觸發(fā)之后下一幀生效 (與此同時(shí) v-leave-from 被刪除),在過渡/動畫完成之后移除。

3. 過渡示例
將需要過渡的元素使用transition標(biāo)簽包裹。設(shè)置過渡需要的class,可從以上六種class中選擇。
/* css */
/* .v-enter-from {
opacity: 0;
}
.v-enter-active {
transition: opacity 1s ease;
}
.v-enter-to {
opacity: 1;
}
.v-leave-from {
opacity: 1;
}
.v-leave-active {
transition: opacity 1s ease;
}
.v-leave-to {
opacity: 0;
} */
/* 簡寫 */
.v-enter-from, .v-leave-to{
opacity: 0;
}
.v-enter-active, .v-leave-active{
transition: opacity 1s ease;
}
// js
const app = Vue.createApp({
data() {
return {
show: true
}
},
methods: {
handleClick() {
this.show = !this.show;
}
},
template: `
<transition>
<div v-if='show'>hello</div>
</transition>
<button @click='handleClick'>切換</button>
`
});

4. 動畫示例
使用動畫效果只需要修改css部分,js部分功能不變。
/* css */
@keyframes shake-in {
0% {
transform: translateX(-50px);
}
50% {
transform: translateX(50px);
}
100% {
transform: translateX(0px);
}
}
@keyframes shake-out {
0% {
transform: translateX(50px);
}
50% {
transform: translateX(-50px);
}
100% {
transform: translateX(0px);
}
}
.v-enter-active{
animation: shake-in 1s ease-in;
}
.v-leave-active{
animation: shake-out 1s ease-in-out;
}

5. transition的name屬性
- name?-?string?:用于自動生成 CSS 過渡類名,不寫默認(rèn)是v。
- name設(shè)置為hy,對應(yīng)的class名稱也要改為hy開頭。
// js
<transition name='hy'>
<div v-if='show'>hello</div>
</transition>
/* css */
.hy-enter-from, .hy-leave-to{
opacity: 0;
}
.hy-enter-active, .hy-leave-active{
transition: opacity 1s ease;
}
6. 自定義過渡類名
我們可以通過以下 attribute 來自定義過渡類名:
- enter-from-class
- enter-active-class
- enter-to-class
- leave-from-class
- leave-active-class
- leave-to-class
他們的優(yōu)先級高于普通的類名,這對于 Vue 的過渡系統(tǒng)和其他第三方 CSS 動畫庫,如?Animate.css. 結(jié)合使用十分有用。
// 首先引入樣式文件
<link rel="stylesheet" rel="external nofollow" />
const app = Vue.createApp({
data() {
return {
show: true
}
},
methods: {
handleClick() {
this.show = !this.show;
}
},
// 以自定義過渡類名的方式去添加動畫樣式
template: `
<transition name='hy'
enter-active-class='animate__animated animate__bounce'
leave-active-class='animate__animated animate__bounce'>
<div v-if='show'>hello</div>
</transition>
<button @click='handleClick'>切換</button>
`
});
7. 同時(shí)設(shè)置過渡和動畫
- 在一些場景中,你需要給同一個(gè)元素同時(shí)設(shè)置過渡和動畫,比如 animation 很快的被觸發(fā)并完成了,而 transition 效果還沒結(jié)束。
- 在這種情況中,你就需要使用?type?attribute 并設(shè)置?animation?或?transition?來明確聲明你需要 Vue 監(jiān)聽的類型。
- type?-?string。指定過渡事件類型,偵聽過渡何時(shí)結(jié)束。有效值為?"transition" 和?"animation"。默認(rèn) Vue.js 將自動檢測出持續(xù)時(shí)間長的為過渡事件類型。
在transition時(shí)間更長時(shí),使用type=‘transiton'的效果:
可以發(fā)現(xiàn)animation先完成,但transition并沒有終止會一致執(zhí)行完,元素才消失。
/* css */
@keyframes shake-in {
0% {
transform: translateX(-50px);
}
50% {
transform: translateX(50px);
}
100% {
transform: translateX(0px);
}
}
@keyframes shake-out {
0% {
transform: translateX(50px);
}
50% {
transform: translateX(-50px);
}
100% {
transform: translateX(0px);
}
}
.v-enter-from,
.v-leave-to {
color: red;
}
.v-enter-active {
animation: shake-in 1s ease-in;
transition: color 3s ease-in;
}
.v-enter-to, .v-leave-from {
color: green;
}
.v-leave-active {
animation: shake-out 1s ease-in-out;
transition: color 3s ease-in-out;
}
// js
const app = Vue.createApp({
data() {
return {
show: true
}
},
methods: {
handleClick() {
this.show = !this.show;
}
},
template: `
<transition type='transition'>
<div v-if='show'>hello</div>
</transition>
<button @click='handleClick'>切換</button>
`
});
?
在transition時(shí)間更長時(shí),使用type=‘a(chǎn)nimation'的效果:
- 可以發(fā)現(xiàn)animation完成后,transition也會立即終止,元素也消失了。
<transition type='animation'>
<div v-if='show'>hello</div>
</transition>

8. duration 屬性
- duration?-?number | { enter: number, leave: number }:指定過渡的持續(xù)時(shí)間。
- 比css中設(shè)置的時(shí)間優(yōu)先級更高。
- 單位是:ms。
<transition :duration='100' >
<div v-if='show'>hello</div>
</transition >
你也可以定制進(jìn)入和移出的持續(xù)時(shí)間:
<transition :duration='{ enter: 1000, leave: 3000 }' >
<div v-if='show'>hello</div>
</transition >

9. 使用js實(shí)現(xiàn)動畫
- 當(dāng)只用 JavaScript 過渡的時(shí)候,在?enter?和?leave?鉤中必須使用?done?進(jìn)行回調(diào)。否則,它們將被同步調(diào)用,過渡會立即完成。
- 添加?:css="false",也會讓 Vue 會跳過 CSS 的檢測,除了性能略高之外,這可以避免過渡過程中 CSS 規(guī)則的影響。
想要用js實(shí)現(xiàn)動畫,可以在transition的 attribute 中聲明 JavaScript 鉤子:
| @before-enter="beforeEnter" | 進(jìn)入過渡前 |
| @enter="enter" | 進(jìn)入過渡時(shí) |
| @after-enter="afterEnter" | 進(jìn)入過渡后 |
| @enter-cancelled="enterCancelled" | 進(jìn)入過渡被打斷時(shí) |
| @before-leave="beforeLeave" | 離開過渡前 |
| @leave="leave" | 離開過渡時(shí) |
| @after-leave="afterLeave" | 離開過渡后 |
| @leave-cancelled="leaveCancelled" | 離開過渡被打斷時(shí) |
const app = Vue.createApp({
data() {
return {
show: true
}
},
methods: {
handleClick() {
this.show = !this.show;
},
handleBeforeEnter(el){
el.style.color = 'red';
},
handleEnter(el, done){
const timer = setInterval(()=>{
if(el.style.color === 'red'){
el.style.color = 'blue';
}else{
el.style.color = 'red';
}
}, 1000);
setTimeout(()=>{
clearInterval(timer);
// 動畫結(jié)束標(biāo)志
// 不執(zhí)行done()的話,handleAfterEnter不會執(zhí)行
done();
}, 3000)
},
handleAfterEnter(el){
console.log('success');;
}
},
template: `
<transition :css='false'
@before-enter='handleBeforeEnter'
@enter='handleEnter'
@after-enter='handleAfterEnter'
>
<div v-if='show'>hello</div>
</transition>
<button @click='handleClick'>切換</button>
`
});

// js
const app = Vue.createApp({
components: ['item-a', 'item-b'],
data() {
return {
component: 'item-a'
}
},
methods: {
handleClick() {
if (this.component === 'item-a') {
this.component = 'item-b';
} else {
this.component = 'item-a';
}
}
},
template: `
<transition mode='out-in' appear>
<component :is='component' />
</transition>
<button @click='handleClick'>切換</button>
`
});
app.component('item-a', {
template: `<div>hello</div>`
});
app.component('item-b', {
template: `<div>bye</div>`
});
四、組件和元素切換動畫的實(shí)現(xiàn)
- mode?-?string?控制離開/進(jìn)入過渡的時(shí)間序列。
- 有效的模式有?先出后進(jìn):?"out-in"?和 先進(jìn)后出:"in-out";默認(rèn)同時(shí)進(jìn)行。
- 可以通過?appear?attribute 設(shè)置節(jié)點(diǎn)在初始渲染的過渡。
/* css */
.v-enter-from,
.v-leave-to {
opacity: 0;
}
.v-enter-active,
.v-leave-active {
transition: opacity 1s ease-in;
}
.v-enter-to,
.v-leave-from {
opacity: 1;
}
// js
const app = Vue.createApp({
components: ['item-a', 'item-b'],
data() {
return {
component: 'item-a'
}
},
methods: {
handleClick() {
if (this.component === 'item-a') {
this.component = 'item-b';
} else {
this.component = 'item-a';
}
}
},
template: `
<transition mode='out-in' appear>
<component :is='component' />
</transition>
<button @click='handleClick'>切換</button>
`
});
app.component('item-a', {
template: `<div>hello</div>`
});
app.component('item-b', {
template: `<div>bye</div>`
});

五、列表動畫
- 使用 <transition-group> 組件,可以同時(shí)渲染整個(gè)列表。
- 內(nèi)部元素總是需要提供唯一的 key attribute 值。
- CSS 過渡的類將會應(yīng)用在內(nèi)部的元素中,而不是這個(gè)組/容器本身。
- <transition-group> 組件還有一個(gè)特殊之處。不僅可以進(jìn)入和離開動畫,還可以改變定位。要使用這個(gè)新功能只需使用新增的 v-move 類。
/* css */
.inline-block {
display: inline-block;
margin-right: 10px;
}
.v-enter-from,
.v-leave-to {
opacity: 0;
transform: translateY(30px);
}
.v-enter-active {
transition: all 1s ease;
}
.v-leave-active {
position: absolute;
}
.v-move {
transition: all 1s ease;
}

六、狀態(tài)動畫
對于數(shù)據(jù)元素本身而言,通過數(shù)字和運(yùn)算、顏色的顯示、SVG 節(jié)點(diǎn)的位置、元素的大小和其他的 property 這些屬性的變化,同樣可以實(shí)現(xiàn)動畫的效果。
數(shù)字變化示例:
const app = Vue.createApp({
data() {
return {
number: 1
}
},
methods: {
handleClick() {
const timer = setInterval(() => {
if (this.number >= 10) {
clearInterval(timer)
}else{
this.number++;
}
}, 100);
}
},
template: `
<div>{{number}}</div>
<button @click='handleClick'>增加</button>
`
});
?
總結(jié)
到此這篇關(guān)于如何利用vue實(shí)現(xiàn)css過渡和動畫的文章就介紹到這了,更多相關(guān)vue實(shí)現(xiàn)css過渡和動畫內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Vue+ElementUI使用vue-pdf實(shí)現(xiàn)預(yù)覽功能
這篇文章主要為大家詳細(xì)介紹了Vue+ElementUI使用vue-pdf實(shí)現(xiàn)預(yù)覽功能,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2019-11-11
vue+elementUI實(shí)現(xiàn)多文件上傳與預(yù)覽功能實(shí)戰(zhàn)記錄(word/PDF/圖片/docx/doc/xlxs/txt)
這篇文章主要給大家介紹了關(guān)于利用vue+elementUI實(shí)現(xiàn)多文件上傳與預(yù)覽功能的相關(guān)資料,包括word/PDF/圖片/docx/doc/xlxs/txt等格式文件上傳,文中通過實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下2022-08-08
使用vue-cli3新建一個(gè)項(xiàng)目并寫好基本配置(推薦)
這篇文章主要介紹了使用vue-cli3新建一個(gè)項(xiàng)目并寫好基本配置的實(shí)例代碼,代碼簡單易懂,非常不錯,具有一定的參考借鑒價(jià)值 ,需要的朋友可以參考下2019-04-04
Vue實(shí)現(xiàn)內(nèi)部組件輪播切換效果的示例代碼
這篇文章主要介紹了Vue實(shí)現(xiàn)內(nèi)部組件輪播切換效果的示例代碼,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2018-04-04
vue中如何動態(tài)綁定圖片,vue中通過data返回圖片路徑的方法
下面小編就為大家分享一篇vue中如何動態(tài)綁定圖片,vue中通過data返回圖片路徑的方法,具有很好的參考價(jià)值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-02-02
Vue+Element UI實(shí)現(xiàn)下拉菜單的封裝
這篇文章主要為大家詳細(xì)介紹了Vue+Element UI實(shí)現(xiàn)下拉菜單的封裝代碼,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2021-09-09

