实现下图效果:
一、动态组件
在不同组件之间进行动态切换。
通过 Vue 的 <component>
元素加一个特殊的 is
attribute 来实现:
<!-- 组件会在 `currentTabComponent` 改变时改变 -->
<component v-bind:is="currentTabComponent"></component>
例:
<div class="login-tab">
<a href="" @click="view= 'WechatLogin'">微信登录</a>
<a href="" @click="view= 'PassLogin'">密码登录</a>
</div>
<div class="login-view">
<!-- view 是当前显示的组件名 -->
<component :is="view"></component>
</div>
import PassLogin from "./PassLogin.vue";
import WechatLogin from "./WechatLogin.vue";
......
data() {
return {
view: "WechatLogin",
};
},
components: {
PassLogin,
WechatLogin,
},
当在组件之间切换时,想保持这些组件的状态,以避免反复重新渲染导致的性能问题。
需要有<keep-alive>
将其包裹。
<!-- 失活的(即切换走的)组件会被缓存!-->
<keep-alive>
<component v-bind:is="currentTabComponent"></component>
</keep-alive>
二、动态组件的tab切换高亮效果
<div class="login-tab">
<!-- 动态组件切换效果 -->
<a
href="#none"
v-for="(item, index) in tabArr"
:key="index"
@click="
currentIndex = index;
view = item.componentId;
"
:class="{ highLight: currentIndex == index }"
>{{ item.componentName }}</a
>
</div>
<div class="login-view">
<component :is="view"></component>
</div>
import PassLogin from "./PassLogin.vue";
import WechatLogin from "./WechatLogin.vue";
export default {
name: "Login",
data() {
return {
view: "WechatLogin",
currentIndex: 0,
tabArr: [
{
componentName: "微信登录",
componentId: "WechatLogin",
},
{
componentName: "密码登录",
componentId: "PassLogin",
},
],
};
},
methods: {},
components: {
PassLogin,
WechatLogin,
},
};
// 设置动态组件切换高亮
.highLight {
background-color: @mainColor!important;
color: #fff!important;
}
三、多个组件间过渡效果
<!-- 动态组件过渡 -->
<transition name="component-fade" mode="out-in">
<component :is="view"></component>
</transition>
.component-fade-enter-active,
.component-fade-leave-active {
transition: opacity 0.2s ease;
}
.component-fade-enter, .component-fade-leave-to
opacity: 0;
}
实现图上的最终代码:
<div class="login-box">
<div class="login-tab">
<!-- 动态组件切换效果 -->
<a
href="#none"
v-for="(item, index) in tabArr"
:key="index"
@click="
currentIndex = index;
view = item.componentId;
"
:class="{ highLight: currentIndex == index }"
>{{ item.componentName }}</a
>
</div>
<div class="login-view">
<keep-alive>
<!-- 动态组件过渡 -->
<transition name="component-fade" mode="out-in">
<component :is="view"></component>
</transition>
</keep-alive>
</div>
<script>
import PassLogin from "./PassLogin.vue";
import WechatLogin from "./WechatLogin.vue";
export default {
name: "Login",
data() {
return {
view: "WechatLogin",
currentIndex: 0,
tabArr: [
{
componentName: "微信登录",
componentId: "WechatLogin",
},
{
componentName: "密码登录",
componentId: "PassLogin",
},
],
};
},
methods: {},
components: {
PassLogin,
WechatLogin,
},
};
</script>
// 设置动态组件切换高亮
.highLight {
background-color: @mainColor!important;
color: #fff!important;
}
.component-fade-enter-active,
.component-fade-leave-active {
transition: opacity 0.3s ease;
}
.component-fade-enter, .component-fade-leave-to
{
opacity: 0;
}