作者 RuoYi

系统布局配置支持动态标题开关

  1 +# 页面标题
  2 +VUE_APP_TITLE = 若依管理系统
  3 +
1 # 开发环境配置 4 # 开发环境配置
2 ENV = 'development' 5 ENV = 'development'
3 6
  1 +# 页面标题
  2 +VUE_APP_TITLE = 若依管理系统
  3 +
1 # 生产环境配置 4 # 生产环境配置
2 ENV = 'production' 5 ENV = 'production'
3 6
  1 +# 页面标题
  2 +VUE_APP_TITLE = 若依管理系统
  3 +
1 NODE_ENV = production 4 NODE_ENV = production
2 5
3 # 测试环境配置 6 # 测试环境配置
@@ -55,6 +55,7 @@ @@ -55,6 +55,7 @@
55 "vue": "2.6.12", 55 "vue": "2.6.12",
56 "vue-count-to": "1.0.13", 56 "vue-count-to": "1.0.13",
57 "vue-cropper": "0.5.5", 57 "vue-cropper": "0.5.5",
  58 + "vue-meta": "^2.4.0",
58 "vue-router": "3.4.9", 59 "vue-router": "3.4.9",
59 "vuedraggable": "2.24.3", 60 "vuedraggable": "2.24.3",
60 "vuex": "3.6.0" 61 "vuex": "3.6.0"
@@ -6,6 +6,14 @@ @@ -6,6 +6,14 @@
6 6
7 <script> 7 <script>
8 export default { 8 export default {
9 - name: 'App' 9 + name: 'App',
  10 + metaInfo() {
  11 + return {
  12 + title: this.$store.state.settings.dynamicTitle && this.$store.state.settings.title,
  13 + titleTemplate: title => {
  14 + return title ? `${title} - ${process.env.VUE_APP_TITLE}` : process.env.VUE_APP_TITLE
  15 + }
  16 + }
  17 + }
10 } 18 }
11 </script> 19 </script>
@@ -62,6 +62,11 @@ @@ -62,6 +62,11 @@
62 <el-switch v-model="sidebarLogo" class="drawer-switch" /> 62 <el-switch v-model="sidebarLogo" class="drawer-switch" />
63 </div> 63 </div>
64 64
  65 + <div class="drawer-item">
  66 + <span>动态标题</span>
  67 + <el-switch v-model="dynamicTitle" class="drawer-switch" />
  68 + </div>
  69 +
65 <el-divider/> 70 <el-divider/>
66 71
67 <el-button size="small" type="primary" plain icon="el-icon-document-add" @click="saveSetting">保存配置</el-button> 72 <el-button size="small" type="primary" plain icon="el-icon-document-add" @click="saveSetting">保存配置</el-button>
@@ -129,6 +134,17 @@ export default { @@ -129,6 +134,17 @@ export default {
129 }) 134 })
130 } 135 }
131 }, 136 },
  137 + dynamicTitle: {
  138 + get() {
  139 + return this.$store.state.settings.dynamicTitle
  140 + },
  141 + set(val) {
  142 + this.$store.dispatch('settings/changeSetting', {
  143 + key: 'dynamicTitle',
  144 + value: val
  145 + })
  146 + }
  147 + },
132 }, 148 },
133 methods: { 149 methods: {
134 themeChange(val) { 150 themeChange(val) {
@@ -160,6 +176,7 @@ export default { @@ -160,6 +176,7 @@ export default {
160 "tagsView":${this.tagsView}, 176 "tagsView":${this.tagsView},
161 "fixedHeader":${this.fixedHeader}, 177 "fixedHeader":${this.fixedHeader},
162 "sidebarLogo":${this.sidebarLogo}, 178 "sidebarLogo":${this.sidebarLogo},
  179 + "dynamicTitle":${this.dynamicTitle},
163 "sideTheme":"${this.sideTheme}", 180 "sideTheme":"${this.sideTheme}",
164 "theme":"${this.theme}" 181 "theme":"${this.theme}"
165 }` 182 }`
@@ -20,6 +20,8 @@ import { parseTime, resetForm, addDateRange, selectDictLabel, selectDictLabels, @@ -20,6 +20,8 @@ import { parseTime, resetForm, addDateRange, selectDictLabel, selectDictLabels,
20 import Pagination from "@/components/Pagination"; 20 import Pagination from "@/components/Pagination";
21 // 自定义表格工具扩展 21 // 自定义表格工具扩展
22 import RightToolbar from "@/components/RightToolbar" 22 import RightToolbar from "@/components/RightToolbar"
  23 +// 头部标签插件
  24 +import VueMeta from 'vue-meta'
23 25
24 // 全局方法挂载 26 // 全局方法挂载
25 Vue.prototype.getDicts = getDicts 27 Vue.prototype.getDicts = getDicts
@@ -49,6 +51,7 @@ Vue.component('Pagination', Pagination) @@ -49,6 +51,7 @@ Vue.component('Pagination', Pagination)
49 Vue.component('RightToolbar', RightToolbar) 51 Vue.component('RightToolbar', RightToolbar)
50 52
51 Vue.use(permission) 53 Vue.use(permission)
  54 +Vue.use(VueMeta)
52 55
53 /** 56 /**
54 * If you don't want to use mock-server 57 * If you don't want to use mock-server
@@ -12,6 +12,7 @@ const whiteList = ['/login', '/auth-redirect', '/bind', '/register'] @@ -12,6 +12,7 @@ const whiteList = ['/login', '/auth-redirect', '/bind', '/register']
12 router.beforeEach((to, from, next) => { 12 router.beforeEach((to, from, next) => {
13 NProgress.start() 13 NProgress.start()
14 if (getToken()) { 14 if (getToken()) {
  15 + to.meta.title && store.dispatch('settings/setTitle', to.meta.title)
15 /* has token*/ 16 /* has token*/
16 if (to.path === '/login') { 17 if (to.path === '/login') {
17 next({ path: '/' }) 18 next({ path: '/' })
1 module.exports = { 1 module.exports = {
2 - title: '若依管理系统',  
3 -  
4 /** 2 /**
5 * 侧边栏主题 深色主题theme-dark,浅色主题theme-light 3 * 侧边栏主题 深色主题theme-dark,浅色主题theme-light
6 */ 4 */
@@ -32,6 +30,11 @@ module.exports = { @@ -32,6 +30,11 @@ module.exports = {
32 sidebarLogo: true, 30 sidebarLogo: true,
33 31
34 /** 32 /**
  33 + * 是否显示动态标题
  34 + */
  35 + dynamicTitle: false,
  36 +
  37 + /**
35 * @type {string | array} 'production' | ['production', 'development'] 38 * @type {string | array} 'production' | ['production', 'development']
36 * @description Need show err logs component. 39 * @description Need show err logs component.
37 * The default is only used in the production env 40 * The default is only used in the production env
1 import variables from '@/assets/styles/element-variables.scss' 1 import variables from '@/assets/styles/element-variables.scss'
2 import defaultSettings from '@/settings' 2 import defaultSettings from '@/settings'
3 3
4 -const { sideTheme, showSettings, topNav, tagsView, fixedHeader, sidebarLogo } = defaultSettings 4 +const { sideTheme, showSettings, topNav, tagsView, fixedHeader, sidebarLogo, dynamicTitle } = defaultSettings
5 5
6 const storageSetting = JSON.parse(localStorage.getItem('layout-setting')) || '' 6 const storageSetting = JSON.parse(localStorage.getItem('layout-setting')) || ''
7 const state = { 7 const state = {
  8 + title: '',
8 theme: storageSetting.theme || variables.theme, 9 theme: storageSetting.theme || variables.theme,
9 sideTheme: storageSetting.sideTheme || sideTheme, 10 sideTheme: storageSetting.sideTheme || sideTheme,
10 showSettings: showSettings, 11 showSettings: showSettings,
11 topNav: storageSetting.topNav === undefined ? topNav : storageSetting.topNav, 12 topNav: storageSetting.topNav === undefined ? topNav : storageSetting.topNav,
12 tagsView: storageSetting.tagsView === undefined ? tagsView : storageSetting.tagsView, 13 tagsView: storageSetting.tagsView === undefined ? tagsView : storageSetting.tagsView,
13 fixedHeader: storageSetting.fixedHeader === undefined ? fixedHeader : storageSetting.fixedHeader, 14 fixedHeader: storageSetting.fixedHeader === undefined ? fixedHeader : storageSetting.fixedHeader,
14 - sidebarLogo: storageSetting.sidebarLogo === undefined ? sidebarLogo : storageSetting.sidebarLogo 15 + sidebarLogo: storageSetting.sidebarLogo === undefined ? sidebarLogo : storageSetting.sidebarLogo,
  16 + dynamicTitle: storageSetting.dynamicTitle === undefined ? dynamicTitle : storageSetting.dynamicTitle
15 } 17 }
16 const mutations = { 18 const mutations = {
17 CHANGE_SETTING: (state, { key, value }) => { 19 CHANGE_SETTING: (state, { key, value }) => {
@@ -22,8 +24,13 @@ const mutations = { @@ -22,8 +24,13 @@ const mutations = {
22 } 24 }
23 25
24 const actions = { 26 const actions = {
  27 + // 修改布局设置
25 changeSetting({ commit }, data) { 28 changeSetting({ commit }, data) {
26 commit('CHANGE_SETTING', data) 29 commit('CHANGE_SETTING', data)
  30 + },
  31 + // 设置网页标题
  32 + setTitle({ commit }, title) {
  33 + state.title = title
27 } 34 }
28 } 35 }
29 36
1 'use strict' 1 'use strict'
2 const path = require('path') 2 const path = require('path')
3 -const defaultSettings = require('./src/settings.js')  
4 3
5 function resolve(dir) { 4 function resolve(dir) {
6 return path.join(__dirname, dir) 5 return path.join(__dirname, dir)
7 } 6 }
8 7
9 -const name = defaultSettings.title || '若依管理系统' // 标题 8 +const name = process.env.VUE_APP_TITLE || '若依管理系统' // 网页标题
10 9
11 const port = process.env.port || process.env.npm_config_port || 80 // 端口 10 const port = process.env.port || process.env.npm_config_port || 80 // 端口
12 11