一、transition过度/动画
transition可以在vue更新,插入,隐藏,删除dom的时候提供一个过渡的效果
<transition name="fade">
<div v-if="show">hello</div>
</transition>
上面代码中trancition 标签中的name属性决定了css选择器的名字,如上面name=“fade”,那么样式选择器使用.fade-enter{ },如果是"fade1"则为.fade1-enter,根据当前使用情况命名
.fade-enter{ } 进入过渡的开始状态,元素被插入时生效,只应用一帧后立即删除。(运动的初始状态)
.fade-enter-to{} 定义进入过渡的结束状态。(2.1.8版及以上)
.fade-enter-active{ } 定义进入过渡生效时的状态。在整个进入过渡的阶段中应用,在元素被插入之前生效,在过渡/动画完成之后移除这个类可以被用来定义进入过渡的过程时间,延迟和曲线函数。
.fade-leave{ } 离开过渡的开始状态,元素被删除时触发,只应用一帧后立即删除;
.fade-leave-to{} 定义离开过渡的结束状态。(2.1.8版及以上)
.fade-leave-active{ } 定义离开过渡生效时的状态。在整个离开过渡的阶段中应用,在离开过渡被触发时立刻生效,在过渡/动画完成之后移除。这个类可以被用来定义离开过渡的过程时间,延迟和曲线函数。
.fade-enter{ } 到 .fade-enter-active{ } 是从无到有的过程
.fade-leave{ } 到 .fade-leave-active{ } 是从有到无的过程
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>过渡/动画</title>
<link rel="stylesheet" href="animate.css">
<style>
[v-cloak] {
display: none;
}
.box {
width: 100px;
height: 100px;
position: absolute;
top: 0;
left: 100px;
background-color: indianred;
}
.fade-enter,
.fade-leave-to {
opacity: 0;
}
.fade-enter-active,
.fade-leave-active {
transition: opacity 1s;
}
</style>
</head>
<body>
<div id="app" v-cloak></div>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.10/dist/vue.js"></script>
<script>
new Vue({
el: "#app",
template: `<div>
<transition name="fade">
<div class="box" v-show="isShow"></div>
</transition>
<button @click="isShow = !isShow">change</button>
</div>`,
data() {
return {
isShow: false
}
}
})
</script>
</body>
</html>
可以配合使用第三方 CSS 动画库,如 Animate.css
Animate.css官网:https://animate.style/
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>过渡/动画</title>
<link rel="stylesheet" href="animate.css">
<style>
[v-cloak] {
display: none;
}
</style>
</head>
<body>
<div id="app" v-cloak></div>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.10/dist/vue.js"></script>
<script>
new Vue({
el: "#app",
template: `<div>
// 配合使用animate.css
<transition name="fade" enter-active-class="animated bounceInRight" leave-active-class="animated fadeOutDownBig">
<div class="box" v-show="isShow"></div>
</transition>
<button @click="isShow = !isShow">change</button>
</div>`,
data() {
return {
isShow: false
}
}
})
</script>
</body>
</html>
实现幻灯片
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>过渡/动画</title>
<!-- <link rel="stylesheet" href="animate.css"> -->
<style>
[v-cloak] {
display: none;
}
.banner-box {
width: 300px;
height: 170px;
}
.banner {
width: 300px;
height: 170px;
display: flex;
}
.control {
width: 300px;
position: absolute;
top: 150px;
left: 120px;
}
.control div {
width: 14px;
height: 14px;
border-radius: 7px;
border: 1px solid #000;
margin-right: 5px;
float: left;
}
.active {
background-color: #000;
}
.list-enter-active,
.list-leave-active {
transition: all 1s;
position: absolute;
}
.list-enter-to,
.list-leave {
opacity: 1;
}
.list-enter,
.list-leave-to {
opacity: 0;
}
</style>
</head>
<body>
<div id="app" v-cloak></div>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.10/dist/vue.js"></script>
<script>
new Vue({
el: "#app",
template: `<div>
<transition-group name="list">
<div v-for="(item, index) in list" class="banner" :style="{backgroundColor: item.color}" key="index" v-show="item.isShow"></div>
</transition-group>
<div class="control">
<div v-for="(item, index) in list" :key="index" :class="{active: item.isShow}" @click="controlBanner(item)"> </div>
</div>
</div>`,
data() {
return {
isShow: false,
list: [{
color: 'green',
isShow: false,
}, {
color: 'pink',
isShow: true,
}, {
color: 'yellow',
isShow: false
}]
}
},
methods: {
// 根据点击的点控制当前的幻灯片显示或者隐藏
controlBanner(item) {
console.log(item)
if (item.isShow) {
return
} else {
for (let i = 0; i < this.list.length; i++) {
if (this.list[i].isShow) {
this.list[i].isShow = false
break;
}
}
item.isShow = true
}
}
},
})
</script>
</body>
</html>
二、Mixins混入
Mixins混入包含了组件内的配置,当混入组件的时候会跟组件内的配置合并,当于merge一下,如果发生冲突以组件数据优先,混入对象的钩子将在组件自身钩子之前调用。
作用:
可以把操作类似的组件相同部分提取出来,放到Mixins里面,比如需要大量引入可视化图表的项目,使用mixins可以少很多代码,让项目轻减许多
使用:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>mixins</title>
<style>
[v-cloak] {
display: none;
}
</style>
</head>
<body>
<div id="app" v-cloak></div>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.10/dist/vue.js"></script>
<script>
// mixins混入
let mixin = {
mounted() {
console.log('mixin') // 混入组件mixin会比组件内钩子先执行
},
methods: {
mixinFun() {
console.log('mixins方法')
}
}
}
new Vue({
el: "#app",
template: `<div>
<button @click="mixinFun">点击</button>
</div>`,
mixins: [mixin],
mounted() {
console.log('组件')
},
methods: {
mixinFun() {
console.log('组件内方法') // 方法冲突的时候组件内方法优先级高
}
}
})
</script>
</body>
</html>
打印结果:
三、自定义指令
相当于获取dom的另一个途径,然后在里面写需要对dom进行的一系列操作程序
全局自定义指令
下面代码来自vue官网:https://cn.vuejs.org/v2/guide/custom-directive.html
// 注册一个全局自定义指令 `v-focus`
Vue.directive('focus', {
// 当被绑定的元素插入到 DOM 中时……
inserted: function (el) {
// 聚焦元素
el.focus()
}
})
局部自定义指令
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>自定义指令</title>
<style>
[v-cloak] {
display: none;
}
</style>
</head>
<body>
<div id="app" v-cloak></div>
<script src="https://cdn.jsdelivr.net/npm/vue@2.6.10/dist/vue.js"></script>
<script>
let Home = {
template: `<div>
<div v-style:width="100" v-style:height="100"></div>
</div>`,
data() {
return {
date: '2020-9-15'
}
},
directives: {
style: (el, binding) => {
console.log(binding) // 打印出我们需要的参数
el.style.backgroundColor = 'pink'
el.style[binding.arg] = binding.value + 'px'
}
}
}
new Vue({
el: '#app',
template: `<div>
<Home/>
</div>`,
components: {
Home
}
})
</script>
</body>
</html>
binding打印结果如图: