Vue之过渡动画(一)

简介: 3.1、进入/离开 & 列表过渡1. OverviewVue provides a variety of ways to apply transition effects when items are inserted, updated, or removed from the DOM.On this page, we’ll only cover **entering, leaving, **and list transitions, but you can see the next section for managing state transitions.DOM操作时的过渡效果,

Vue之过渡动画(一)



3.1、进入/离开 & 列表过渡


1. Overview


Vue provides a variety of ways to apply transition effects when items are inserted, updated, or removed from the DOM.

On this page, we’ll only cover **entering, leaving, **and list transitions, but you can see the next section for managing state transitions.

DOM操作时的过渡效果,让页面更丝滑。


2. 单元素/组件的过渡


先来个demo开开胃,完整代码


<style>
  .fade-enter-active, .fade-leave-active {
    transition: opacity .5s;
  }
  .fade-enter, .fade-leave-to /* .fade-leave-active below version 2.1.8 */ {
    opacity: 0;
  }
</style>
<div id="demo">
    <button v-on:click="show = !show">
        Toggle
    </button>
    <transition name="fade">
        <p v-if="show">hello</p>
    </transition>
</div>
<script>
    new Vue({
        el: '#demo',
        data: {
            show: true
        }
    })
</script>


2.1 过渡的类名(Transition Classes)


There are six classes applied for enter/leave transitions.


enter/leave过渡中,会有6个class切换


v-enter

v-enter-active

v-enter-to (2.1.8+)

v-leave

v-leave-active

v-leave-to (2.1.8+)


aHR0cHM6Ly9jZG4ubmxhcmsuY29tL3l1cXVlLzAvMjAyMC9wbmcvMTAzNTgyLzE1OTM2NTM2MzI5MDYtM2FmNTExOTctNTBlNS00NjcyLWIyYTMtODA3NzdiMDRmYWQwLnBuZw.png


2.2 CSS过渡


即给上面例子中的 .fade-enter-active, .fade-leave-active 这些类名应用的CSS样式


2.3 CSS动画


写法差不多,就是把transition换成animation 完整代码


<style>
  .bounce-enter-active {
    animation: bounce-in .5s;
  }
  .bounce-leave-active {
    animation: bounce-in .5s reverse;
  }
  @keyframes bounce-in {
    0% {
      transform: scale(0);
    }
    50% {
      transform: scale(1.5);
    }
    100% {
      transform: scale(1);
    }
  }
</style>
<div id="example-2">
  <button @click="show = !show">Toggle show</button>
  <transition name="bounce">
    <p v-if="show">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Mauris facilisis enim libero, at lacinia diam fermentum id. Pellentesque habitant morbi tristique senectus et netus.</p>
  </transition>
</div>
<script>
    new Vue({
        el: '#example-2',
        data: {
            show: true
        }
    })
</script>


2.4 自定义过渡的类名


我们可以通过以下 attribute 来自定义过渡类名:


enter-class

enter-active-class

enter-to-class (2.1.8+)

leave-class

leave-active-class

leave-to-class (2.1.8+)

如下与 Animate.css的结合使用:完整代码


<link href="https://cdn.jsdelivr.net/npm/animate.css@3.5.1" rel="stylesheet" type="text/css">
<div id="example-3">
  <button @click="show = !show">
    Toggle render
  </button>
  <transition
    name="custom-classes-transition"
    enter-active-class="animated tada"
    leave-active-class="animated bounceOutRight"
  >
    <p v-if="show">hello</p>
  </transition>
</div>
<script>
  new Vue({
    el: '#example-3',
    data: {
      show: true
    }
  })
</script>


2.5 同时使用过渡和动画


要同时使用过渡和动画,要用type属性指明类型:animation or transition


2.6 指定过渡的时间


<transition :duration="1000">...</transition>
<transition :duration="{ enter: 500, leave: 800 }">...</transition>


2.7 JavaScript钩子(JavaScript Hooks)


用js代码操作动画

如下使用了Velocity.js动画库,完整代码


<script src="https://cdnjs.cloudflare.com/ajax/libs/velocity/1.2.3/velocity.min.js"></script>
<div id="example-4">
  <button @click="show = !show">
    Toggle
  </button>
  <transition
    v-on:before-enter="beforeEnter"
    v-on:enter="enter"
    v-on:leave="leave"
    v-bind:css="false"
  >
    <p v-if="show">
      Demo
    </p>
  </transition>
</div>
<script>
    new Vue({
        el: '#example-4',
        data: {
            show: false
        },
        methods: {
            beforeEnter: function (el) {
                el.style.opacity = 0
                el.style.transformOrigin = 'left'
            },
            enter: function (el, done) {
                Velocity(el, {opacity: 1, fontSize: '1.4em'}, {duration: 300})
                Velocity(el, {fontSize: '1em'}, {complete: done})
            },
            leave: function (el, done) {
                Velocity(el, {translateX: '15px', rotateZ: '50deg'}, {duration: 600})
                Velocity(el, {rotateZ: '100deg'}, {loop: 2})
                Velocity(el, {
                    rotateZ: '45deg',
                    translateY: '30px',
                    translateX: '30px',
                    opacity: 0
                }, {complete: done})
            }
        }
    })
</script>


3. 初始渲染的过渡(Transitions on Initial Render)


If you also want to apply a transition on the initial render of a node, you can add the appear attribute:

一个DOM节点初始化渲染到页面时可以引用过渡效果


<transition appear>
  <!-- ... -->
</transition>
// 【还自定义class】
<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>
// 【也可以自定义js钩子】
<transition
  appear
  v-on:before-appear="customBeforeAppearHook"
  v-on:appear="customAppearHook"
  v-on:after-appear="customAfterAppearHook"
  v-on:appear-cancelled="customAppearCancelledHook"
>
  <!-- ... -->
</transition>


4. 多个元素之间的过渡(Transitioning Between Elements)


一个常见的场景就是:渲染列表元素时,如果列表是空的,则渲染一个代表空列表的元素


<transition>
  <table v-if="items.length > 0">
    <!-- ... -->
  </table>
  <p v-else>Sorry, no items found.</p>
</transition>


需要注意:如果两个tag名一样的元素之间做过渡时,要加key demo如下:


<style>
  .bounce-enter-active {
    animation: bounce-in .5s;
  }
  .bounce-leave-active {
    animation: bounce-in .5s reverse;
  }
  @keyframes bounce-in {
    0% {
      transform: scale(0);
    }
    50% {
      transform: scale(1.5);
    }
    100% {
      transform: scale(1);
    }
  }
</style>
<div id="app">
    <transition name="bounce">
        <button v-bind:key="docState">
            {{ buttonMessage }}
        </button>
    </transition>
    <button @click="savebutton">切换按钮</button>
</div>
<script>
    new Vue({
        el: '#app',
        data: {
            docState: 'saved'
        },
        computed:{
            buttonMessage: function () {
                switch (this.docState) {
                    case 'saved': return 'Edit'
                    case 'edited': return 'Save'
                }
            }
        },
        methods: {
            savebutton:function () {
                if(this.docState == 'edited'){
                    this.docState = 'saved'
                }else {
                    this.docState = 'edited'
                }
            }
        }
    })
</script>


4.1 过渡模式

可以设置两种过渡模式:


in-out: New element transitions in first, then when complete, the current element transitions out.


out-in: Current element transitions out first, then when complete, the new element transitions in.


我们来对比下设置了out-in模式和不设置的区别吧:给上面例子上的transition加上mode属性为out-in


<transition name="bounce" mode="out-in">
   <button v-bind:key="docState">
     {{ buttonMessage }}
   </button>
 </transition>


加之前:


aHR0cHM6Ly9jZG4ubmxhcmsuY29tL3l1cXVlLzAvMjAyMC9naWYvMTAzNTgyLzE1OTM2NzY5NDg3NjUtYjZjMmQ2NmEtNGM5MC00MjBkLWFhMzctOTNlMzAwNTFkMzQwLmdpZg.gif


加之后:效果棒棒哒


aHR0cHM6Ly9jZG4ubmxhcmsuY29tL3l1cXVlLzAvMjAyMC9naWYvMTAzNTgyLzE1OTM2NzY5NjcxMTAtMWY4MTgyMzgtNWFhZS00Mzk1LThhNDQtZmQ0NTlkZmQ4ZjgwLmdpZg.gif


5. 多个组件之间的过渡


组件之间的过渡更加简单,写法和元素一样,不需要加key:


<style>
  .component-fade-enter-active, .component-fade-leave-active {
    transition: opacity .3s ease;
  }
  .component-fade-enter, .component-fade-leave-to
  /* .component-fade-leave-active below version 2.1.8 */ {
    opacity: 0;
  }
</style>
<div id="app">
    <input type="radio" value="v-a" id="a" name="view" @change="view='v-a'">
    <label for="a">A</label>
    <input type="radio" value="v-b" id="b" name="view" @change="view='v-b'">
    <label for="b">B</label>
    <transition name="component-fade" mode="out-in">
        <component v-bind:is="view"></component>
    </transition>
</div>
<script>
    new Vue({
        el: '#app',
        data: {
            view: 'v-a'
        },
        components: {
            'v-a': {
                template: '<div>Component A</div>'
            },
            'v-b': {
                template: '<div>Component B</div>'
            }
        }
    })
</script>


6. 列表过渡(List Transitions)


列表的Entering/Leaving过渡、Move Transitions移动过渡,用<transition-group>

有几个注意点:


渲染时会转换为实际元素,默认为span,可以加tag标签指定,如下例子中指定为 tag='p'

的内部元素上要加key

css过渡类是应用在内部元素上的,而不是 group/container itself.


6.1 List Entering/Leaving Transitions


<style>
  .list-complete-item {
    transition: all 1s;
    display: inline-block;
    margin-right: 10px;
  }
  .list-complete-enter, .list-complete-leave-to
  /* .list-complete-leave-active below version 2.1.8 */ {
    opacity: 0;
    transform: translateY(30px);
  }
  .list-complete-leave-active {
    position: absolute;
  }
</style>
<div id="list-demo">
    <button v-on:click="shuffle">Shuffle</button>
    <button v-on:click="add">Add</button>
    <button v-on:click="remove">Remove</button>
    <transition-group name="list-complete" tag="p">
    <span v-for="item in items" v-bind:key="item" class="list-complete-item">
      {{ item }}
    </span>
    </transition-group>
</div>
<script>
    new Vue({
        el: '#list-demo',
        data: {
            items: [1, 2, 3, 4, 5, 6, 7, 8, 9],
            nextNum: 10
        },
        methods: {
            randomIndex: function () {
                return Math.floor(Math.random() * this.items.length)
            },
            add: function () {
                this.items.splice(this.randomIndex(), 0, this.nextNum++)
            },
            remove: function () {
                this.items.splice(this.randomIndex(), 1)
            },
            shuffle: function () {
                this.items = _.shuffle(this.items)
            }
        }
    })
</script>


6.2 List Move Transitions


上面演示了列表内元素进入/离开时的过渡效果,

为了列表中元素移动时的过渡效果,vue引入了v-move过渡类名,如下的:.flip-list-move


<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.14.1/lodash.min.js"></script>
<style>
  .flip-list-move {
    transition: transform 1s;
  }
</style>
<div id="flip-list-demo" class="demo">
  <button v-on:click="shuffle">Shuffle</button>
  <transition-group name="flip-list" tag="ul">
    <li v-for="item in items" v-bind:key="item">
      {{ item }}
    </li>
  </transition-group>
</div>
<script>
  new Vue({
    el: '#flip-list-demo',
    data: {
      items: [1,2,3,4,5,6,7,8,9]
    },
    methods: {
      shuffle: function () {
        this.items = _.shuffle(this.items)
      }
    }
  })
</script>


6.3 列表使用Javascript钩子函数添加过渡效果


上面讲的都是列表用css进行过渡,列表也可以用js代码进行过渡,如下:


<script src="https://cdnjs.cloudflare.com/ajax/libs/velocity/1.2.3/velocity.min.js"></script>
<div id="staggered-list-demo">
    <input v-model="query">
    <transition-group
            name="staggered-fade"
            tag="ul"
            v-bind:css="false"
            v-on:before-enter="beforeEnter"
            v-on:enter="enter"
            v-on:leave="leave"
    >
        <li
                v-for="(item, index) in computedList"
                v-bind:key="item.msg"
                v-bind:data-index="index"
        >{{ item.msg }}
        </li>
    </transition-group>
</div>
<script>
    new Vue({
        el: '#staggered-list-demo',
        data: {
            query: '',
            list: [
                { msg: 'Bruce Lee' },
                { msg: 'Jackie Chan' },
                { msg: 'Chuck Norris' },
                { msg: 'Jet Li' },
                { msg: 'Kung Fury' }
            ]
        },
        computed: {
            computedList: function () {
                var vm = this
                return this.list.filter(function (item) {
                    return item.msg.toLowerCase().indexOf(vm.query.toLowerCase()) !== -1
                })
            }
        },
        methods: {
            beforeEnter: function (el) {
                el.style.opacity = 0
                el.style.height = 0
            },
            enter: function (el, done) {
                var delay = el.dataset.index * 150
                setTimeout(function () {
                    Velocity(
                        el,
                        { opacity: 1, height: '1.6em' },
                        { complete: done }
                    )
                }, delay)
            },
            leave: function (el, done) {
                var delay = el.dataset.index * 150
                setTimeout(function () {
                    Velocity(
                        el,
                        { opacity: 0, height: 0 },
                        { complete: done }
                    )
                }, delay)
            }
        }
    })
</script>


7. 可复用的过渡


To create a reusable transition, all you have to do is place a <transition> or <transition-group>


组件的过渡也也可以不用,相当于一个壳子,壳子上带着过渡效果,你可以复用到别的地方


8. 动态过渡


Yes, even transitions in Vue are data-driven! The most basic example of a dynamic transition binds the name attribute to a dynamic property.


由于过渡效果的实现都是在<transition> or <transition-group> 组件上添加属性,那么这些属性的属性值根据不同条件也可以被指定不同的动态值。

这就是动态过渡的由来。让过渡更加灵活和随心所欲



目录
打赏
0
0
0
0
1
分享
相关文章
Vue 中 key 属性的深入解析:改变 key 导致组件销毁与重建
Vue 中 key 属性的深入解析:改变 key 导致组件销毁与重建
178 0
Vue 自定义进度条组件封装及使用方法详解
这是一篇关于自定义进度条组件的使用指南和开发文档。文章详细介绍了如何在Vue项目中引入、注册并使用该组件,包括基础与高级示例。组件支持分段配置(如颜色、文本)、动画效果及超出进度提示等功能。同时提供了完整的代码实现,支持全局注册,并提出了优化建议,如主题支持、响应式设计等,帮助开发者更灵活地集成和定制进度条组件。资源链接已提供,适合前端开发者参考学习。
151 17
Vue 文件批量下载组件封装完整使用方法及优化方案解析
本文详细介绍了批量下载功能的技术实现与组件封装方案。主要包括两种实现方式:**前端打包方案(基于file-saver和jszip)** 和 **后端打包方案**。前者通过前端直接将文件打包为ZIP下载,适合小文件场景;后者由后端生成ZIP文件流返回,适用于大文件或大量文件下载。同时,提供了可复用的Vue组件`BatchDownload`,支持进度条、失败提示等功能。此外,还扩展了下载进度监控和断点续传等高级功能,并针对跨域、性能优化及用户体验改进提出了建议。可根据实际需求选择合适方案并快速集成到项目中。
177 17
Vue 手风琴实现的三种常用方式及长尾关键词解析
手风琴效果是Vue开发中常见的交互组件,可节省页面空间、提升用户体验。本文介绍三种实现方式:1) 原生Vue结合数据绑定与CSS动画;2) 使用Element UI等组件库快速构建;3) 自定义指令操作DOM实现独特效果。每种方式适用于不同场景,可根据项目需求选择。示例包括产品特性页、后台菜单及FAQ展示,灵活满足多样需求。附代码示例与资源链接,助你高效实现手风琴功能。
105 10
Vue 表情包输入组件的实现代码:支持自定义表情库、快捷键发送和输入框联动的聊天表情解决方案
本文详细介绍了在 Vue 项目中实现一个功能完善、交互友好的表情包输入组件的方法,并提供了具体的应用实例。组件设计包含表情分类展示、响应式布局、与输入框的交互及样式定制等功能。通过核心技术实现,如将表情插入输入框光标位置和点击外部关闭选择器,确保用户体验流畅。同时探讨了性能优化策略,如懒加载和虚拟滚动,以及扩展性方案,如自定义主题和国际化支持。最终,展示了如何在聊天界面中集成该组件,为用户提供丰富的表情输入体验。
129 8
Vue 表情包输入组件实现代码及详细开发流程解析
这是一篇关于 Vue 表情包输入组件的使用方法与封装指南的文章。通过安装依赖、全局注册和局部使用,可以快速集成表情包功能到 Vue 项目中。文章还详细介绍了组件的封装实现、高级配置(如自定义表情列表、主题定制、动画效果和懒加载)以及完整集成示例。开发者可根据需求扩展功能,例如 GIF 搜索或自定义表情上传,提升用户体验。资源链接提供进一步学习材料。
79 1
Vue框架中常见指令的应用概述。
通过以上的详细解析,你应该已经初窥Vue.js的指令的威力了。它们是Vue声明式编程模型的核心之一,无论是构建简单的静态网站还是复杂的单页面应用,你都会经常用到。记住,尽管Vue提供了大量预定义的指令,你还可以创建自定义指令以满足特定的需求。为你的Vue应用程序加上这些功能增强器,让编码变得更轻松、更愉快吧!
37 1
如何高效实现 vue 文件批量下载及相关操作技巧
在Vue项目中,实现文件批量下载是常见需求。例如文档管理系统或图片库应用中,用户可能需要一次性下载多个文件。本文介绍了三种技术方案:1) 使用`file-saver`和`jszip`插件在前端打包文件为ZIP并下载;2) 借助后端接口完成文件压缩与传输;3) 使用`StreamSaver`解决大文件下载问题。同时,通过在线教育平台的实例详细说明了前后端的具体实现步骤,帮助开发者根据项目需求选择合适方案。
99 0
Vue 项目中如何自定义实用的进度条组件
本文介绍了如何使用Vue.js创建一个灵活多样的自定义进度条组件。该组件可接受进度段数据数组作为输入,动态渲染进度段,支持动画效果和内容展示。当进度超出总长时,超出部分将以红色填充。文章详细描述了组件的设计目标、实现步骤(包括props定义、宽度计算、模板渲染、动画处理及超出部分的显示),并提供了使用示例。通过此组件,开发者可根据项目需求灵活展示进度情况,优化用户体验。资源地址:[https://pan.quark.cn/s/35324205c62b](https://pan.quark.cn/s/35324205c62b)。
45 0
AI助理

你好,我是AI助理

可以解答问题、推荐解决方案等

登录插画

登录以查看您的控制台资源

管理云资源
状态一览
快捷访问