前言
很多同学在第一次搭建后台管理系统时,会遇到一个问题,layout组件该放哪里?如何使用?路由又该如何设计?
这边会讲一下我的思考过程和最后的结果,大家可以参考一下,希望大家看完能有所收获。
文章目录
一、为什么需要layout组件?
1. Container 布局容器
我用的是
element-plus
的组件,所以这里以这个ui库作为例子讲哦。
这里先引入一个组件,<contaienr>
用于布局的容器组件,方便快速搭建页面的基本结构。
<el-container>
:外层容器。 当子元素中包含<el-header>
或<el-footer>
时,全部子元素会垂直上下排列, 否则会水平左右排列。
常见且实用的布局呢,大概是一下这几个:
2. Header 顶栏容器
<el-header>
:顶栏容器。一般会单独写个组件,组件内部大概是以下这些部分:
1) 页头组件<el-page-header>
在组件中可以展示很多区块,大家可以自行去了解哈。如果不清楚自己要怎么设计,就直接用这个组件就好啦!在这个组件里放东西就ok~(这是链接)。
2)自己写的组件
- 控制侧边栏收缩和展开的icon,可以用
<el-icon><Fold /></el-icon>
,记得添加相对应的事件。 - 面包屑组件,用来展示当前
<Main>
中正在展示的路由路径。可以用
el-breadcrumb
组件
3)<el-aside>
侧边栏容器
可以使用<el-menu>
菜单组件,这边一般是通过循环 menu数组(大型项目都会涉及到权限配置,里面就会有一个菜单栏配置,这边就是动态加载的啦)。有同学不会我再放代码吧。
4) <el-main>
主要区域容器。
上面说啦~展示我们的路由们
5)<el-footer>
底栏容器。
一般写个备案的时间呀、公司邮箱呀、公司信息呀什么的。聪明的你!灵活使用吧!
二、怎么写一个layout组件?
好啦,几个要素都了解了,接下来需要我们的脑子和手配合。将它们组成一个完整的layout组件。我分享一下简单的layout组件在项目中的结构长啥样哈,如图:
这里放一下index.vue的代码
<template>
<div class="common-layout">
<el-container>
<el-aside><MyAside /></el-aside>
<el-container>
<el-header class="header"><MyHeader /></el-header>
<el-main>
<!-- 这里是会被缓存的视图组件 -->
<router-view v-slot="{ Component }">
<keep-alive>
<component :is="Component" :key="$route.name" v-if="$route.meta.keepAlive" />
</keep-alive>
<component :is="Component" :key="$route.name" v-if="!$route.meta.keepAlive" />
</router-view>
</el-main>
</el-container>
</el-container>
</div>
</template>
三、怎么使用layout组件呢?
这里有点小可爱不知道咋用@,请转到我的另一篇文章:
【vite好用的配置】自动导入组件、vue中的hook、路径解析、打包配置、本地运行反向代理配置
1. 先在路由配置里定义基础路由,同时设置children路由。
// router/index.js
import { createRouter, createWebHistory } from 'vue-router'
const routes = [
{
path: '/',
name: 'Layout',
component: () => import('@/layout/index.vue'),
children: [
{
path: '',
name: 'Dashboard',
component: () => import('@/views/Dashboard.vue')
},
{
path: '/users',
name: 'Users',
component: () => import('@/views/Users.vue')
}
]
},
{
path: '/login',
name: 'Login',
component: () => import('@/views/Login.vue')
}
]
const router = createRouter({
history: createWebHistory(),
routes
})
export default router
2.动态 Layout 组件(基于路由元信息)
通过路由配置中的meta字段指定使用的 Layout 组件,实现更灵活的布局切换。实现步骤:
1)路由配置:在路由中添加meta.layout字段指定布局组件。
// router/index.js
const routes = [
{
path: '/',
name: 'Dashboard',
component: () => import('@/views/Dashboard.vue'),
meta: { layout: 'AdminLayout' }
},
{
path: '/login',
name: 'Login',
component: () => import('@/views/Login.vue'),
meta: { layout: 'AuthLayout' }
}
]
2)创建 Layout 组件:准备多个 Layout 组件(如AdminLayout.vue、AuthLayout.vue)。
3)动态渲染 Layout:在根组件中根据当前路由的meta.layout动态加载布局。
<!-- App.vue -->
<template>
<component :is="currentLayout">
<router-view />
</component>
</template>
<script>
import { computed, onMounted, ref } from 'vue'
import { useRouter } from 'vue-router'
export default {
setup() {
const router = useRouter()
const layouts = {
AdminLayout: () => import('@/layouts/AdminLayout.vue'),
AuthLayout: () => import('@/layouts/AuthLayout.vue'),
DefaultLayout: () => import('@/layouts/DefaultLayout.vue')
}
const currentLayout = computed(() => {
const layout = router.currentRoute.value.meta.layout || 'DefaultLayout'
return layouts[layout]
})
return {
currentLayout
}
}
}
</script>
优点:
更灵活的布局切换,同一层级路由可使用不同 Layout。
避免深层嵌套路由,路由配置更简洁。
缺点:
需要在每个路由中手动指定 layout,维护成本较高。
3.组合式 API + 插件方式
通过创建自定义插件,将 Layout 逻辑封装,减少重复代码。实现步骤:
1)创建 Layout 插件:注册全局组件并处理布局逻辑。
// plugins/layout.js
import AdminLayout from '@/layouts/AdminLayout.vue'
import AuthLayout from '@/layouts/AuthLayout.vue'
export default {
install(app) {
app.component('AdminLayout', AdminLayout)
app.component('AuthLayout', AuthLayout)
}
}
2)定义 Layout 组件:使用插槽机制实现灵活布局。
3)在路由中使用:通过插件提供的组件包裹视图
<!-- 路由组件示例 -->
<template>
<AdminLayout>
<template #header>
<h1>Custom Header</h1>
</template>
<template #content>
<router-view />
</template>
<template #footer>
<p>Custom Footer</p>
</template>
</AdminLayout>
</template>
优点:
高度可定制,通过插槽传递内容更灵活。
布局逻辑集中管理,便于维护。
缺点:
需要额外的插件配置,适合大型项目。
4. 更多&总结
当然还有其他办法啦,这里就差不多列举出来,不仔细说了哈,感兴趣的同学,可以自己去研究一下。
- 基础嵌套路由:适合中小型项目,布局结构固定。
- 动态 Layout:适合需要灵活切换布局的场景。
- 插件方式:适合大型项目,需要统一管理布局逻辑。
- 权限布局:适合需要根据用户角色展示不同布局的系统。
- 多层嵌套 Layout:适合超复杂系统(如 IDE、设计工具等)。