过渡路由
通过结合 Vue Router 中的 router-element 组件和过渡组件,我们可以轻松设置用户从一个 URL(路由)导航到另一个 URL(路由)时的过渡效果。
为了让您有更基本的理解,我们将在下一节中演示用户从网站主页重定向到网站上的 “关于” 页面的基本情况。
让我们用过渡包装 router-element 并添加 name="zoom"
属性:
<transition
name="zoom"
mode="out-in"
>
<router-view/>
</transition>
这里我们将使用 mode
属性来指示过渡模式。目前有两种模式可以设置:
-
in-out:新元素首先出现,只有在此之后当前元素才会从视图中消失。
-
out-in:当前元素先出去,然后新元素才会进来。我们将以此作为示例,它比前一个更常见。
然后,我们只需要像往常一样使用过渡类设置过渡 CSS 效果即可。就那么简单:
/**Zoom animation **/
.zoom-enter-active,
.zoom-leave-active {
animation-duration: 0.3s;
animation-fill-mode: both;
animation-name: zoom;
}
.zoom-leave-active {
animation-direction: reverse;
}
@keyframes zoom {
from {
opacity: 0;
transform: scale3d(0.4, 0.4, 0.4);
}
100% {
opacity: 1;
}
}
在本节中,我们研究了过渡路由。过渡效果是在路由渲染之间发生的动画,例如从一个页面导航到另一页面。在下一节中,我们将研究为应用程序中导航的每个路由创建过渡效果。
练习 7.03:为每条导航路由创建过渡效果
在本练习中,我们将使用 “过渡路由” 部分中的路由器元素来调整我们所学到的有关过渡的知识,以便为不同的路由创建不同的过渡效果。默认效果是淡入淡出(fade)。
要访问本练习的代码文件,请访问 https://packt.live/376DoXo :
在开始本练习之前,请运行 |
-
使用 Vue Router 创建一个简单的应用程序,并使用位于
src/views/
文件夹中的Messages.vue
视图添加消息路由。使用上一个练习中的代码并在App.vue
中添加指向此新创建的路由的链接。 -
接下来,我们在 App.vue 中用过渡组件包装 router-view 元素:
<transition :name="transition" :mode="mode"> <router-view/> </transition>
-
在 App.vue 的导出(export)部分中,确保 data 函数包含转换(transition)和模式(mode)的值,如下所示:
data() { return { transition: 'fade', mode: 'out-in', }; },
-
在 App.vue 中使用以下 CSS 添加淡入和淡出的 CSS 样式:
<style> .fade-enter, .fade-leave-to { opacity: 0; } .fade-enter-active, .fade-leave-active { transition: opacity 1s ease-in; } </style>
-
此时,所有页面都加载了淡入淡出(fade)效果,甚至
/messages
。但我们想让消息页面加载时具有不同的效果——缩放(zoom)效果。接下来,在同一样式(style)标签内添加缩放(zoom)动画的相关 CSS 代码:/**Zoom animation */ .zoom-enter-active, .zoom-leave-active { animation-duration: 0.5s; animation-fill-mode: both; animation-name: zoom; } .zoom-leave-active { animation-direction: reverse; } @keyframes zoom { from { opacity: 0; transform: scale3d(0.4, 0.4, 0.4); } 100% { opacity: 1; } }
-
现在,我们将借助以下代码为应用程序的默认布局添加一些标准 CSS 样式:
#app { font-family: 'Avenir', Helvetica, Arial, sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-align: center; color: #2c3e50; } #nav { padding: 30px; } #nav a { font-weight: bold; color: #2c3e50; } #nav a.router-link-exact-active { color: #42b983; }
-
现在我们需要用这个特定的转换效果来映射
/messages
路由,并且不影响其它路由。为此,我们需要在src/router/index.js
中的路由配置的元(meta)属性中添加一个名为transition
的字段:{ path: '/messages', name: 'messages', meta: { transition: 'zoom', }, component: () => import(/* webpackChunkName: "about" */'../views/Messages.vue') }
-
检查
routes
对象的代码以确认其与以下代码相同。在这里,我们将应用程序的每个 URL 与视图文件进行匹配:const routes = [ { path: '/', name: 'home', component: Home }, { path: '/about', name: 'about', component: () => import(/* webpackChunkName: "about" */'../views/About.vue') }, { path: '/messages', name: 'messages', meta: { transition: 'zoom', }, component: () => import(/* webpackChunkName: "messages" */'../views/Messages.vue') } ]
-
这不会在浏览器中显示,因为此转换声明尚未绑定到
App.vue
组件的data
字段,并且需要在视图开始加载之前绑定。为此,我们将利用第 6 章 “路由” 中提到的create
生命周期钩子和$router
全局的beforeEach
路由钩子。 -
让我们在 App.vue 中每次路由更改之前添加一个钩子。我们会检查目的地路由(to)是否有自定义的 transition 效果。如果是,我们会将 App 实例中的 transition 值映射到它;否则,我们将在继续导航之前使用后备默认值,如下所示:
created() { this.$router.beforeEach(( to, // The destination route from, //The source route next //The function to trigger to resolve the hook ) => { let transition = 'fade'; if (to.meta && to.meta.transition) { transition = to.meta.transition; } this.transition = transition; next(); }) }
-
使用以下命令运行应用程序:
yarn serve
-
现在,如果您在浏览器中打开 localhost:8080 并导航到 /messages,您应该会看到类似于图 7.11 的内容:

当导航到其它路由时,我们应该看到如图 7.12 所示的默认 transition:

本练习演示了如何通过组合正确的钩子和方法,以最少的努力轻松地在不同页面上设置不同的转换。您可以进一步尝试使用外部库,以使您的应用程序动画更流畅、更生动。