vue之使用vuex進(jìn)行狀態(tài)管理詳解
vuex進(jìn)行狀態(tài)管理
首先學(xué)習(xí)vuex必須先知道vue原理
Vue是一個(gè)典型的MVVM框架,模型(Model)只是普通的JavaScript對(duì)象,修改它則視圖(View)會(huì)自動(dòng)更新。這種設(shè)計(jì)讓狀態(tài)管理變得非常簡(jiǎn)單而直觀
Vue實(shí)現(xiàn)這種數(shù)據(jù)雙向綁定的效果,需要三大模塊:
Observer
:能夠?qū)?shù)據(jù)對(duì)象的所有屬性進(jìn)行監(jiān)聽(tīng),如有變動(dòng)可拿到最新值并通知訂閱者Compile
:對(duì)每個(gè)元素節(jié)點(diǎn)的指令進(jìn)行掃描和解析,根據(jù)指令模板替換數(shù)據(jù),以及綁定相應(yīng)的更新函數(shù)Watcher
:作為連接Observer和Compile的橋梁,能夠訂閱并收到每個(gè)屬性變動(dòng)的通知,執(zhí)行指令綁定的相應(yīng)回調(diào)函數(shù),從而更新視圖
大概分為這么幾類
vuex是什么呢
vuex是實(shí)現(xiàn)狀態(tài)管理的工具 可以用來(lái)管理大型項(xiàng)目的工具
下面是一個(gè)簡(jiǎn)單的vuex的結(jié)構(gòu)
index是主文件
//index// import Vue from 'vue' import Vuex from 'vuex' import * as getters from './getters' import * as actions from './actions' import * as mutations from './mutations' Vue.use(Vuex) const state = { username: '123' } const store = new Vuex.Store({ state, getters, actions, mutations }) export default store
進(jìn)行一個(gè)簡(jiǎn)單地賬戶管理
//actions文件 // 給action注冊(cè)事件處理函數(shù)。當(dāng)這個(gè)函數(shù)被觸發(fā)時(shí)候,將狀態(tài)提交到mutations中處理 export function modifyAName({commit}, name) { // commit 提交;name即為點(diǎn)擊后傳遞過(guò)來(lái)的參 return commit ('modifyAName', name) } // ES6精簡(jiǎn)寫法 //export const modifyAName = ({commit},name) => commit('modifyAName', name) //motations文件 // 提交 mutations是更改Vuex狀態(tài)的唯一合法方法 export const modifyAName = (state, name) => { // A組件點(diǎn)擊更改餐館名稱為 A餐館 state.resturantName = name // 把方法傳遞過(guò)來(lái)的參數(shù),賦值給state中的resturantName } //getters文件 // 獲取最終的狀態(tài)信息 export const resturantName = state => state.resturantName //組件A/methods函數(shù) sub(){ let log = document.querySelector("#log").value; let reg = document.querySelector("#reg").value; userapi("/users/userpsw",{name:log,psw:reg}, (mes) => { if(mes === 1){ console.log(log) this.$store.commit("modifyAName",log) // 賬戶名稱 console.log(this.$store.getters.resturantName) document.querySelector(".text").innerHTML = "登錄成功" this.$router.push({ path: '/my' }) }else{ document.querySelector(".text").innerHTML = "登錄失敗" } }) }, 組件B/computed computed:{ username(){//調(diào)用username即可 {{username}} return this.$store.getters.resturantName } },
vuex狀態(tài)管理基本使用
通過(guò)npm安裝vuex
npm install vuex --save
使用vuex
import Vuex from 'vuex' Vue.use(Vuex) //賦值給一個(gè)變量,然后引入 let store = new Vuex.Store({ ... }) //為了更好的維護(hù),且體現(xiàn)模塊化,可以寫在別的js文件中,然后導(dǎo)入 import store from './store' //創(chuàng)建一個(gè)store文件夾,默認(rèn)為文件夾下的index.js文件 new Vue({ ... store, ... })
使用vuex基本結(jié)構(gòu)
new Vuex.Store({ //狀態(tài) state: { count: 100 }, //將狀態(tài)裝飾,或刷選,以想要的結(jié)果輸出 getters: { hasUnit () { return this.state.count.filter(count => count + 1) } }, //可以理解為變更狀態(tài)的方法,第一個(gè)參數(shù)為state,可以再添加自定義參數(shù),注意:只能進(jìn)行同步 mutations: { increment (state) { state.count++ } }, //可控制的提交mutation事件,彌補(bǔ)mutation無(wú)法異步 actions: { increment (state) { setTimeout(() => state.commit('increment'), 30) } } })
為了更好的維護(hù),往往將store文件寫成以下結(jié)構(gòu) ,名字自定義,但是需要知道每個(gè)文件的作用
index.js
:主要作為導(dǎo)出store,作為匯總的文件state.js
:作為定義的變量集合,作為一個(gè)對(duì)象導(dǎo)出getters.js
:作為主要是獲取state中變量值的方法,return出state相應(yīng)的值,或者length等等的一些state變量的信息mutations-type.js
: 作為一些方法等命名的變量,防止書寫錯(cuò)誤
mutaintions.js
:存放修改state變量的同步方法,這里可以的方法名就是用了mutations-type.js中的變量命名,[object.value]這種方式是ES6中的語(yǔ)法
action.js
:存放修改state變量的異步方法
在組件中引用,不使用mapXXXXX輔助函數(shù)情況下
state和getter:直接在computed計(jì)算屬性中使用
computed: { count () { return this.$store.state.count }, hasUnit () { return this.$store.getters.hasUnit } }
mutations和actions則被作為事件調(diào)用,可以放在methods,watch等等,有事件調(diào)用的時(shí)候都可以
methods: { add () { this.$store.commit('increment') // mutations使用commit調(diào)用 }, asyncAdd () { this.$store.dispatch('increment') // actions使用dispatch調(diào)用 } }
通過(guò)mapXXXX輔助函數(shù)來(lái)引用
先確保組件中已導(dǎo)入vuex的相應(yīng)輔助函數(shù):用到哪個(gè)導(dǎo)入哪個(gè)
import { mapState } from 'vuex' import { mapGetters } from 'vuex' import { mapMutations } from 'vuex' import { mapActions } from 'vuex' //導(dǎo)入多個(gè):ES6模塊 import { mapState, mapGetters } from 'vuex'
然后根據(jù)你的需求使用對(duì)應(yīng)的輔助函數(shù),前提是已經(jīng)導(dǎo)入
computed: { ...mapState([ 'count' ]), ...mapGetters([ 'addUnit' ]) } //使用this.count, this.addUnit
methods: { ...mapMutations([ 'increment' ]), ...mapActions({ addNum: 'increment' }) add () { this.increment() } } //可以被當(dāng)做事件調(diào)用,為了避免命名沖突,可以使用重命名,需要使用{}而不是[]
模塊:Module
當(dāng)項(xiàng)目很大的時(shí)候,很多版塊在一起容易混淆,希望每個(gè)版塊的信息歸每個(gè)版塊下面,易于維護(hù)
//局部模塊引用的第一個(gè)參數(shù)state都是自己模塊里的 const moduleA = { state: { ... }, mutations: { ... }, actions: { ... }, getters: { ... } } const moduleB = { state: { ... }, mutations: { ... }, actions: { ... } } const store = new Vuex.Store({ modules: { a: moduleA, b: moduleB } })
以moduleA為例 ,可以新建一個(gè)JS文件,然后通過(guò)import導(dǎo)入到總的vuex管理中
const state = { count: 1 }; const getters = { get(state) { return state.count; } }; const mutations = { add(state) { state.count++; }, reduce(state) { state.count--; } }; const actions = { add: ({ commit }) => { commit("add"); }, reduce: ({ commit }) => { commit("reduce"); } }; export default { namespaced: true, // 使該模塊帶有命名空間,使它在命名上會(huì)按路徑進(jìn)行命名 如moduleA/state state, getters, mutations, actions };
在使用了模塊后,我們可以通過(guò)以下方式獲取,這里只用了輔助函數(shù)展示
computed: { ...mapState({ count: state => state.moduleA.count }), ...mapGetters({ get: "moduleB/get" }) }
methods: { ...mapMutations( 'moduleA', {addA:'add', reduceB:'reduce'} // 重命名就用對(duì)象包裹 ), ...mapActions( 'moduleA', ['add', 'reduce'] ) }
如果想引用根目錄下的狀態(tài),需要傳入第三個(gè)參數(shù)
const moduleA = { // ... getters: { addUnit (state, getters, rootState) { //rootState為根下的狀態(tài) return state.count + rootState.count } } }
以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
相關(guān)文章
Vue.js組件tree實(shí)現(xiàn)省市多級(jí)聯(lián)動(dòng)
這篇文章主要為大家詳細(xì)介紹了Vue.js組件tree實(shí)現(xiàn)省市多級(jí)聯(lián)動(dòng)的相關(guān)資料,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2016-12-12vue+vux?vux安裝出現(xiàn)錯(cuò)誤問(wèn)題及解決
這篇文章主要介紹了vue+vux?vux安裝出現(xiàn)錯(cuò)誤問(wèn)題及解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-08-08vue中mock數(shù)據(jù),模擬后臺(tái)接口實(shí)例
這篇文章主要介紹了vue中mock數(shù)據(jù),模擬后臺(tái)接口實(shí)例,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-04-04antd vue表格可編輯單元格以及求和實(shí)現(xiàn)方式
這篇文章主要介紹了antd vue表格可編輯單元格以及求和實(shí)現(xiàn)方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-04-04axios的interceptors多次執(zhí)行問(wèn)題解決
這篇文章主要為大家介紹了axios中interceptors多次執(zhí)行問(wèn)題解決,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-06-06使用vue寫一個(gè)翻頁(yè)的時(shí)間插件實(shí)例代碼
最近在做自己項(xiàng)目中遇到一個(gè)非常簡(jiǎn)單的功能,跟大家分享下,這篇文章主要給大家介紹了關(guān)于使用vue寫一個(gè)翻頁(yè)的時(shí)間插件的相關(guān)資料,文中通過(guò)實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下2023-02-02使用vue + less 實(shí)現(xiàn)簡(jiǎn)單換膚功能的示例
下面小編就為大家分享一篇使用vue + less 實(shí)現(xiàn)簡(jiǎn)單換膚功能的示例,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2018-02-02