Vue.js学习笔记:过渡效果(含列表过渡)

Vue 提供了 transition 的封装组件,在下列情形中,可以给任何元素和组件添加 entering/leaving 过渡

  • 条件渲染 (使用 v-if
  • 条件展示 (使用 v-show
  • 动态组件
  • 组件根节点

 

 

一、单元素过渡

  1. 一般需要过渡的元素要放在<transition> <transition>组件中 ,过渡有四个状态 
    ①. enter 元素进入时第一帧的状态 
    ②. enter-active 元素从进入第一帧后到完成过渡的这一过程的状态 
    ③. leave 元素离开时的第一帧状态 
    ④. leave-active 元素离开第一帧后到完成过渡的这一过程的状态 
    列如: 
    2 . css过渡

 

html

 

<button v-on:click="show = !show">Toggle</button>
	<transition name="fade">
	  	<p v-if="show">hello,看我渐渐地消失。</p>
	</transition>

css

.fade-enter-active, .fade-leave-active {
  transition: opacity .5s
}
.fade-enter, .fade-leave-to {
  opacity: 0
}

js

new Vue({
	  el: '#demo',
	  data: {
	    show: true
	  }
	})


注意:

     对于这些在 enter/leave 过渡中切换的类名,v- 是这些类名的前缀(也就是例子中的fade,这个是可以自定义的)。使用 <transition name="fade"> 可以重置前缀,比如 v-enter 替换为 fade-enter。下面会介绍

 

1. v-enter :定义 进入过渡的开始状态 。在元素被插入之前生效,在元素被插入之后的下一帧移 除。
 
.fade-enter { opacity : 0 ; }
 
2. v-enter-active :定义 进入过渡生效时的状态 。在元素被插入之前生效,在过渡 / 动画完成之后移 除。
 
.fade-enter-active { transition: opacity .5s; }
 
3. v-enter-to : 定义 进入过渡的结束状态 。在元素被插入之后下一帧生效 ( 与此同时 v-enter 被移 除) ,在过渡 / 动画完成之后移除。
 
.fade-enter-to { opacity: 1; }
 
4. v-leave : 定义 离开过渡的开始状态 。在离开过渡被触发时立刻生效,下一帧被移除。
 
.fade-leave { opacity: 1; }
 
5. v-leave-active :定义 离开过渡生效时的状态 。在整个离开过渡的阶段中应用,在离开过渡被触 发时立刻生效,在过渡/ 动画完成之后移除。这个类可以被用来定义离开过渡的过程时间,延迟和 曲线函数。
 
.fade-leave-active { transition: opacity .5s; }
 
6. v-leave-to : 定义 离开过渡的结束状态 。在离开过渡被触发之后下一帧生效 ( 与此同时 v-leave 被 删除) ,在过渡 / 动画完成之后移除。
 
.fade-leave-to { opacity: 0; }

 

二.自定义过渡类名

自定义过渡类就不需要 中的name属性了。类名可以是自己随意起,也可引入第三方动画库animate.css【<link href="https://cdn.jsdelivr.net/npm/animate.css@3.5.1" rel="stylesheet" type="text/css">】, 但是需要在 加入一些添加类名的属性

  • enter-class=类名 
  • enter-active-class=类名 (常用) 
  • leave-class=类名 
  • leave-active-class=类名 (常用)

在引入第三方动画库 animate.css 时 以上属性要先添加 animated 类, 在添加 动画类名,例如: 
enter-class=”animated tada “

 


<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
    <link rel="stylesheet" type="text/css" href="css/animate.min.css">
</head>
<body>
<div id="demo">
	<button @click="show = !show">看我</button>
	<transition 
	enter-active-class="lookshow"
	leave-active-class="animated tada"
	>
		<p v-if="show">hello</p>
	</transition>
</div>
<script type="text/javascript" src='js/vue.js'></script>
<script type="text/javascript">
	new Vue({
	  el: '#demo',
	  data: {
	    show: true
	  }
	})
</script>
</body>
</html>

注意:这里要加上 animated 才会有效果 (第一个是我自己写的类名,不用加,但是引入animate.css 需要在前面加animate)

同时使用 Transitions 和 Animations

Vue 为了知道过渡的完成,必须设置相应的事件监听器。它可以是 transitionend 或animationend ,这取决于给元素应用的 CSS 规则。如果你使用其中任何一种,Vue 能自动识别类型并设置监听。

但是,在一些场景中,你需要给同一个元素同时设置两种过渡动效,比如 animation 很快的被触发并完成了,而 transition 效果还没结束。在这种情况中,你就需要使用type 特性并设置 animation 或 transition 来明确声明你需要 Vue 监听的类型。

 

三.JavaScript 钩子

 

<transition 
    v-on:before-enter="beforeEnter" // 动画开始前,设置初始状态 
    v-on:enter="enter" // 执行动画 
    v-on:after-enter="afterEnter" // 动画结束,清理工作 
    v-on:enter-cancelled="enterCancelled" // 取消动画  在 v-show 中应用
    v-on:before-leave="beforeLeave" 
    v-on:leave="leave"
    v-on:after-leave="afterLeave" 
    v-on:leave-cancelled="leaveCancelled" // 在 v-show 中应用
>
</transition>

       这些钩子函数可以结合 CSS transitions/animations 使用,也可以单独使用。

      当只用 JavaScript 过渡的时候, 在 enter 和 leave 中,回调函数 done 是必须的 。 
否则,它们会被同步调用,过渡会立即完成。

案例查看官网

四.初始渲染的过渡

可以通过 appear 特性设置节点的在初始渲染的过渡

 

<transition appear>
  <!-- ... -->
</transition>

这里默认和进入和离开过渡一样,同样也可以自定义 CSS 类名。

 


<transition
  appear
  appear-class="custom-appear-class"
  appear-to-class="custom-appear-to-class" (2.1.8+)
  appear-active-class="custom-appear-active-class"
>
  <!-- ... -->
</transition>

自定义 JavaScript 钩子:

<transition
  appear
  v-on:before-appear="customBeforeAppearHook"
  v-on:appear="customAppearHook"
  v-on:after-appear="customAfterAppearHook"
  v-on:appear-cancelled="customAppearCancelledHook"
>
  <!-- ... -->
</transition>

 

 

 

五.多元素过渡

1.实现多个元素过渡用 
① v-if 和 v-else 或 v-else-if (两个相邻元素要求不一样)
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
    <style type="text/css">
    	.fade-enter-active, .fade-leave-active {
		  transition: opacity .5s
		}
		.fade-enter, .fade-leave-to /* .fade-leave-active in below version 2.1.8 */ {
		  opacity: 0
		}
    </style>
</head>
<body>
<div id="demo">
	<button @click="show = !show">点击查看变化</button>
	<transition name="fade">      
		<div v-if="show">
		    请看我的变化div
		</div>
		<p v-else="fade">我也会变化pppp</p>
	</transition>
</div>
<script type="text/javascript" src='js/vue.js'></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/velocity/1.2.3/velocity.min.js"></script>
<script type="text/javascript">
new Vue({
    el : "#demo",
    data : {
        show : true
    }
})
</script>
</body>
</html>

② 利用 属性 key (推荐)
 
当有相同标签名的元素切换时,需要通过key 特性设置唯一的值来标记以让 Vue 区分它们否则 Vue 为了效率只会替换相同标签内部的内容。即使在技术上没有必要,给在 <transition> 组件中的多个元素设置 key 是一个更好的实践。
 
③ v-if 和 key属性 混合使用
 <style type="text/css">
    	.fade-enter-active, .fade-leave-active {
		  transition: opacity .5s
		}
		.fade-enter, .fade-leave-to /* .fade-leave-active in below version 2.1.8 */ {
		  opacity: 0
		}
    </style>

<div id="demo">
 <!-- v-if 、v-show 和 key 配合切换更多元素-->
      <button @click="showa">点击查看变化</button>
      <transition name="fade">      
        <div v-if="show == 'one'" key="one">
            oneoneoneone
        </div>
        <div v-if="show == 'two'" key="two">
           twotwotwotwo
        </div>
        <div v-if="show == 'three'" key="three">
           threethreethree
        </div>
      </transition>
</div>

<script type="text/javascript">
new Vue({
    el : "#demo",
    data : {
        show : true
    },
    methods:{
        showa:function (){
			if(this.show == 'one'){
				return this.show = 'two';
			}else if(this.show == 'two'){
				return this.show = 'three';
			}else{
				return this.show = 'one';
			}
        }
    }
    
})
</script>
 

2.过渡模式 
在多个元素过渡时,这些元素会同时出发,vue 提供了两个属性,在 中加入 mode 属性,它有两个值

A.in-out: 新元素先进行过渡,完成之后当前元素过渡离开。 

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
    <style type="text/css">

	.no-mode-translate-demo-wrapper {
	  position: relative;
	  height: 18px;
	}
	.no-mode-translate-demo-wrapper button {
	  position: absolute;
	}
	.no-mode-translate-fade-enter-active, .no-mode-translate-fade-leave-active {
	  transition: all 1s;
	}
	.no-mode-translate-fade-enter, .no-mode-translate-fade-leave-active {
	  opacity: 0;
	}
	.no-mode-translate-fade-enter {
	  transform: translateX(31px);
	}
	.no-mode-translate-fade-leave-active {
	  transform: translateX(-31px);
	}

    </style>
</head>
<body>
<div id="app">
    <div id="no-mode-demo" class="no-mode-translate-demo-wrapper ">
        <transition name="no-mode-translate-fade" mode="in-out">
            <button v-if="on" key="on" @click="on = false">on</button>
            <button v-else="" key="off" @click="on = true">off</button>
        </transition>
    </div>
</div>
<script type="text/javascript" src='js/vue.js'></script>
<script type="text/javascript">
	new Vue({
        el: '#no-mode-demo',
        data: {
            on: false
        }
    })
</script>
</script>
</body>
</html>


B.out-in: 当前元素先进行过渡,完成之后新元素过渡进入。

 

当把上面例子中<transition name="no-mode-translate-fade" mode="in-out">mode="in-out"

改为mode="out-in"时,效果是不一样。
 

六.多组件过渡

 
多个组件的过渡简单很多 - 我们不需要使用 key 特性。相反,我们只需要使用动态组件component
1.多组件过渡,利用 is 属性
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
    <style type="text/css">
.fade-enter-active,.fade-leave-active {
 transition: all 1s linear;
}
.fade-enter,.fade-leave-active {
  opacity: 0;
  transform:translateX(50px);
}
    </style>
</head>
<body>
<div id="app">
	<button @click="show">点击查看变化</button>
	<transition name="fade" mode = "out-in">      
	    <component v-bind:is="view"></component>    
	    <!-- 组件替换用 is属性 -->
	</transition>
</div>
<script type="text/javascript" src='js/vue.js'></script>
<script type="text/javascript">
new Vue({
	el: '#app',
	data:{
        view:"a-view",
    },
    components: {
		"a-view":{
			template:"<div>我是第一个模板</div>"
		},
		"b-view":{
			template:"<div>我是第二个模板</div>"
		}
    },
    methods:{
        show:function(){
            this.view = this.view == "a-view"?"b-view":"a-view";
        }
    }
})
</script>
</body>
</html>

 

 

七.列表过渡

列表的过渡需要用 v-for 和 <transition-group> </transition-group> 组件 
注意: 
① 列表 <transition-group> </transition-group> 在页面渲染出来是个 span 标签, 如果你想更改它用 tag 属性。例如 <transition-group tag="div"> </transition-group>渲染出来就是div 

② 列表在循环时 要给每一个列表项添加唯一的key 属性值。这样列表才会有过渡效果

 

1. FLIP 简单的动画队列(使用 transforms 将元素从之前的位置平滑过渡新的位置)

列表的位移过渡(<transition-group> 组件还有一个特殊之处。不仅可以进入和离开动画,还可以改变定位。

只需了解新增的 v-move 特性:v-move 对于设置过渡的切换时机和过渡曲线非常有用。

如:

需要注意的是使用 FLIP 过渡的元素不能设置为 display: inline 。作为替代方案,可以设置为 display: inline-block 或者放置于 flex 中

引入lodash.min.js 实现随机排序

 

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
    <link rel="stylesheet" type="text/css" href="css/animate.min.css">
    <style type="text/css">
		span{
		    display:inline-block;
		    padding:10px;
		}
		.position{position: absolute;} 
		.list-complete-item{transition:all .3s linear;}
    </style>
</head>
<body>
<div id="myDiv">
	<button @click="add">随机增加数字</button>
	<button @click="remvoed">随机删除数字</button>
	<button @click="suffle">随机排序</button>
	<transition-group tag="div" 
	 name="flip-list"
	 enter-active-class="animated bounceInUp position"
	 leave-active-class="animated bounceOutDown position">     
	 	<span v-for="item in list" :key="item" class="list-complete-item">{{item}}</span>
	</transition-group>
</div>
<script type="text/javascript" src='js/vue.js'></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.14.1/lodash.min.js"></script>
<script type="text/javascript">
new Vue({
	el:"#myDiv",
    data:{ //这里写代码片
        list:[1,2,3,4,5],
        addNumber:5
    },
    methods:{
        randomIndex:function(){ //随机插入的位置
            return Math.floor(Math.random()*this.list.length);
        },
        add:function(){
            this.list.splice(this.randomIndex(),0,++this.addNumber)
        },
        remvoed:function(){
            this.list.splice(this.randomIndex(),1);
        },
        suffle:function(){
            this.list = _.shuffle(this.list)
        }
    }
})
</script>
</body>
</html>

 

注意:FLIP 动画不仅可以实现单列过渡,多维网格的过渡也同样简单:

 

2.列表的渐进过渡

通过 data 属性与 JavaScript 通信 ,就可以实现列表的渐进过渡

 

3.可复用的过渡

要创建一个可复用过渡组件,你需要做的就是将 <transition> 或者 <transition-group> 作为根组件,然后将任何子组件放置在其中就可以了。

 

4.动态过渡

动态过渡最基本的例子是通过 name 特性来绑定动态值。

 

 
<transition v-bind:name="transitionName">
<!-- ... -->
</transition>
 

 

 
  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值