赞
踩
项目中需要做一个全局换肤(主题色)以及多语言的需求,在通用页更改,全局生效。
我们都知道,vue是MVVM模式,即模型-视图-视图模型,视图更新,数据会跟着更新,反之也一样。但是仅仅在当前组件生效,那么:
如何在一处修改数据就能触发全局视图的更新呢?
答案就是vuex状态管理。
有了状态管理,如何将主题色,语言数据等注入每一个组件呢?
我们可以用mixin(混入),单组件混入或全局混入都可,可以根据需要权衡是否使用全局混入,全局混入意味着每一个new出来的组件,都会拥有混入的方法和数据,并且优先级是组件内部所声明的数据或方法>混入的
下面我们就来进入正题,以uni-app为例
首先,在项目根路径下新建store文件夹,并在store目录下新建module文件夹,添加主题色theme.js和多语言lang.js的配置文件
lang.js
- let userLang , lang = {};
- try {
- // 1. 分析用户已经选择的语言
- userLang = uni.getStorageSync("userLang");
-
- // 2. 如果用户没有选择过则设置默认语言
- if(!userLang){
- userLang = 'zh'
- }
-
- switch(userLang.substring(0, 2)) {
- case 'zh':
- lang = require('../../lang/zh.js');
- break;
- case 'en':
- lang = require('../../lang/en.js');
- break;
- case 'ja':
- lang = require('../../lang/ja.js');
- break;
- default:
- lang = require('../../lang/zh.js');
- }
- } catch (e) {
- // error
- }
-
- const state = {
- lang : lang
- }
-
- const mutations={
- changeLang(state, lang) {
- state.lang = lang;
- }
- }
-
- const actions = {
- changeLang: function(context){
- let lang = {};
-
- uni.showActionSheet({
- itemList:['简体中文', 'English', '日本語'],
- success: function(e){
- try {
- if (e.tapIndex == 0) {
- uni.setStorageSync('userLang', 'zh');
- lang = require('../../lang/zh.js');
- } else if (e.tapIndex == 1){
- uni.setStorageSync('userLang', 'en');
- lang = require('../../lang/en.js');
- } else {
- uni.setStorageSync('userLang', 'ja');
- lang = require('../../lang/ja.js');
- }
- } catch (e) {
- // error
- }
-
- context.commit('changeLang', lang);
- }
- });
- }
- }
-
- export default {
- namespaced: true, // 当你需要在别的文件里面使用( mapGetters、mapActions)时
- state,
- actions,
- mutations
- }
theme.js
- let defaultColor;
-
- try {
- // 获取用户已设置的主题色
- defaultColor = uni.getStorageSync("themeColor");
-
- // 如果没有,设置默认色
- if(!defaultColor){
- defaultColor = '#40aee2';
- }
- } catch (e) {
- // error
- }
-
- const state = {
- themeColor: defaultColor, // 初始化为配置的主题色
- };
-
- const mutations = {
- setThemeColor(state, color) {
- state.themeColor = color;
- }
- };
-
- const actions = {
- setThemeColor(context, color) { // 触发mutations里面的setThemeColor ,传入数据形参color
- let themeColor = '';
-
- uni.showActionSheet({
- itemList: ['红色', '橙色'],
- success: function(e) {
- if (e.tapIndex == 0) {
- themeColor = '#f25762';
- } else {
- themeColor = '#ff6600';
- }
-
- uni.setStorageSync('themeColor', themeColor);
- context.commit('setThemeColor', themeColor);
- }
- });
- }
- };
-
- export default {
- namespaced: true, // 当你需要在别的文件里面使用( mapGetters、mapActions)时
- state,
- actions,
- mutations
- }
store/index.js
- import Vue from 'vue'
- import Vuex from 'vuex'
- import themeColor from './modules/theme'
- import lang from './modules/lang'
-
- Vue.use(Vuex)
- const debug = process.env.NODE_ENV !== 'production'
-
- export default new Vuex.Store({
- modules: {
- themeColor,
- lang
- },
- //在严格模式下,无论何时发生了状态变更且不是由 mutation 函数引起的,将会抛出错误。这能保证所有的状态变更都能被调试工具跟踪到。
- strict: debug
- })
然后在项目入口文件中引入并挂载
main.js
- import Vue from 'vue'
- import App from './App'
- import store from "./store"
- import { mapState } from 'vuex'
-
- // 全局混入主题色,多语言
- Vue.mixin({
- computed: {
- ...mapState('lang', {
- lang: 'lang'
- }),
- ...mapState('themeColor', {
- themeColor: 'themeColor'
- })
- }
- })
-
- Vue.config.productionTip = false
- Vue.prototype.$store = store
-
- App.mpType = 'app'
-
- const app = new Vue({
- store,
- ...App
- })
- app.$mount()
在index.vue中使用
- <template>
- <view class="content">
- <image class="logo" src="/static/logo.png"></image>
- <view class="text-area">
- <text class="title">{{lang.hello}}</text>
- </view>
- <navigator open-type="navigate" url="./test">
- <button class="button" :style="{background: themeColor}">去更换主题色和语言</button>
- </navigator>
- </view>
- </template>
-
- <script>
- export default {
- data() {
- return {}
- }
- }
- </script>
在test.js中设置
- <template>
- <view>
- <view class="list">
- <view class="items" @tap="changeLang">
- <view class="body">
- <view class="title">多语言<text>跟随系统</text></view>
- </view>
- </view>
- <view class="items" @tap="setThemeColor">
- <view class="body">
- <view class="title">使用默认皮肤<text>选择皮肤</text></view>
- </view>
- </view>
- </view>
- </view>
- </template>
- <script>
- import {mapActions} from 'vuex';
-
- export default {
- methods: {
- ...mapActions('lang', {
- 'changeLang': 'changeLang'
- }),
-
- ...mapActions('themeColor', {
- 'setThemeColor': 'setThemeColor'
- })
- }
- }
- </script>
以上只是提供一个简单的示例,具体的实现细节可以自己修改。
其他文件:
lang/zh.js
- module.exports = {
- hello: '你好'
- }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。