前言
效果
基本思路
代码
前言el-dialog
是一个十分好用的弹窗组件,但是出场动画比较单调,于是决定自定义一个出场动画,本文记叙一下思路。
详见上面动图。
基本思路将.el-body
分为两个部分,一个弹窗真正要展示的内容,一个出现、关闭时动画的图片展示(不一定是图片,本项目刚好是图片而已),在出场动画的过程中,图片逐渐消失,真正的内容发逐渐展现,看起来就像是原本那张图片通过旋转之后,变成了弹窗。
首先,写一个常规的el-dialog
,里面el-body
分为两个部分,真正需要展示的内容和执行动画的图片:
<el-dialog
:visible.sync="visible"
top='0' // 设置为零,方便后续的居中处理
title="详情弹窗"
>
<div class="show-info-facce">
<!-- 真正展示的内容 -->
</div>
<!-- 执行动画的图片 -->
<div class="animation-face">
<el-image v-if="showInfo.img" :src="showInfo.img" :fit="'contain'" class="show-img" />
</div>
</el-dialog>
然后,对.el-dialog
元素的样式进行更改,主要是定位和居中处理,方便后续从某个位置逐渐旋转位移到屏幕中间:
.el-dialog {
position: absolute;
// 根据项目中弹窗的大小设定的居中,用其他方式实现居中也行
left: calc(50% - 400px);
top: calc(50% - 242px);
overflow: hidden;
// 设置过渡,出现与消失的动画是靠过渡实现的
transition: all 1s;
}
这个时候,得到了一个居中与屏幕的弹窗,当然,别忘取消原来el-dialog
的出现和消失动画:
.el-dialog__wrapper {
transition-duration: 0.1s;
}
.el-dialog__wrapper.dialog-fade-enter-active,
.el-dialog__wrapper.dialog-fade-leave-active {
animation: none !important;
}
这个时候就会得到一个没有动画的弹窗:
接下来,就是主要的动画部分了,在这个项目中,可以看到弹窗是在点击之后出现的,而这个点击实际上会操作一个控制弹窗是否出现的变量visible
,来控制弹窗是否出现,本人把这个操作封装成一个函数show()
,这个函数还接受展示内容的信息info
:
/**
* @param { Object } info
*/
show(info) {
this.showInfo = info
this.visible = true
}
到这个步骤为止,是大部分el-dialog
的常规使用流程;从封面的动图可以看到,el-dialog
是从被点击的图片位置出现的,而且弹窗出现后,原本的图片消失了。
这使得需要在show()
获取被点击元素target
来实现,这个不难获取,然后就是得到target
的位置和大小,将el-dialog
设为和target
一样,接着使用上面用于执行动画的.animation-face
元素来模拟原来的target
,然后将target
的不透明度opacity
设为零,整体代码如下:
/**
* @param { HTMLElement } target 被点击的元素
* @param { Object } info 展示的内容
*/
show (target, info) {
// 记录target
this.targetEl = target
// 获取target的位置和大小
const position = target.getClientRects()[0]
// 获取.el-dialog元素,将其设为和`target`一样的大小和位置
const dialog = this.$el.querySelector('.el-dialog')
dialog.style.width = position.width + 'px'
dialog.style.height = position.height + 'px'
dialog.style.top = position.top + 'px'
dialog.style.left = position.left + 'px'
// 记录展示信息
this.showInfo = info
this.$nextTick(() => {
this.visible = true
// 原本的target设为透明
target.style.opacity = 0
})
}
已经得到了初步的效果了,接下来就是让弹窗旋转变大居中,这些都比较好实现的,可以通过设定行内样式或者添加class
就行,因为前面已经在.el-dialog
上设置好了过渡属性,只要某个属性发生变化,就会触发。
个人是通过添加class
的方式,因为关闭的时候,弹窗还得回到原来target
的位置上,到时候只要去除这个class
就能实现,比较方便,变化的样式如下:
.dialog-finally {
// 设定好最终展示的宽高
width: 800px !important;
height: 484px !important;
// 最终展示的位置
left: calc(50% - 400px) !important;
top: calc(50% - 242px) !important;
// 加点旋转
transform: rotateY(360deg);
// 执行动画的图片透明度设置为零,隐藏起来,显示出真正要展示的内容
div.animation-face {
opacity: 0;
}
}
然后在show
函数中,给.el-dialog
元素添加这个class
,需要注意的是,直接添加会被vue2
合并成一次更改,直接展示最终的样式,不会触发过渡效果,所以延时一会再把展示的class
添加上去,完整的show()
代码如下:
/**
* @param { HTMLElement } target
* @param { Object } info
*/
show (target, info) {
// 记录target
this.targetEl = target
// 获取target的位置和大小
const position = target.getClientRects()[0]
// 获取.el-dialog元素,将其设为和`target`一样的大小和位置
const dialog = this.$el.querySelector('.el-dialog')
dialog.style.width = position.width + 'px'
dialog.style.height = position.height + 'px'
dialog.style.top = position.top + 'px'
dialog.style.left = position.left + 'px'
// 记录展示信息
this.showInfo = info
// 渲染初始位置
this.$nextTick(() => {
this.visible = true
// 延时添加最终样式
setTimeout(() => {
// 原本的target设为透明
target.style.opacity = 0
// 添加展示的class
dialog.classList.add('dialog-finally')
}, 50)
})
}
效果:
至此,出现的效果处理完成,接下来就是弹窗消失的效果,因为上面是使用class
来添加展示的位置和样式的,所以关闭时,移除那个class
就能让.el-dialog
回到target
的位置,那么需要使用el-dialog
关闭之前的钩子before-close
,该钩子接受一个函数,如下:
<el-dialog
:visible.sync="visible"
top='0' // 设置为零,方便后续的居中处理
title="详情弹窗"
:before-close="handleAnimateClose" // 使用关闭之前的钩子
>
<div class="show-info-facce">
<!-- 真正展示的内容 -->
</div>
<!-- 执行动画的图片 -->
<div class="animation-face">
<el-image v-if="showInfo.img" :src="showInfo.img" :fit="'contain'" class="show-img" />
</div>
</el-dialog>
handleAnimateClose
函数就是在关闭之前先移除展示的class
,等弹窗回到target
原本的位置之后,target
的不透明度设置为1
,关闭弹窗,代码如下:
/** 执行关闭动画 */
handleAnimateClose (done) {
// 获取`.el-dialog`元素
const dialog = this.$el.querySelector('.el-dialog')
// 移除展示的class
dialog.classList.remove('dialog-finally')
// 使用延时,等弹窗回到`target`原本的位置,再关闭弹窗
setTimeout(() => {
// 关闭弹窗
done()
// target不透明度设为1
this.targetEl.style.opacity = 1
}, 1000)
}
效果:
至此,就完成了。
到此这篇关于vue2中如何更改el-dialog出场动画的文章就介绍到这了,更多相关vue2 el-dialog出场动画内容请搜索软件开发网以前的文章或继续浏览下面的相关文章希望大家以后多多支持软件开发网!