【Vue2】Vuex 基础使用

本文仅为 vuex 使用方法,如有不对的地方,欢迎指正。
项目使用可以直接拉到后面 vuex 实际项目中使用部分。

首先为啥要用 vuex,用它有什么好处。

  • 数据跨组件共享。
  • 防止数据意外修改。程序过于庞大或多人开发时,容易不知道是哪改数据, vuex 可以记录哪个组件修改的修改的。
  • 调试、测试方便,同上。

vuex 基本描述

文档地址:https://vuex.vuejs.org/zh/
核心思想(流程):

vuex 流程

  • state 存储、数据;包含了所有变量也只有变量。
  • mutations 修改数据、追踪;操作 state;vue-devtools 上监控到的就是这一属性,只能有同步操作。
    mutation 都有一个字符串的 事件类型 (type)和 一个 回调函数 (handler)。这个回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数:
mutations: {
  add (state) {
    // 变更状态
    state.count++
  }
}

store.commit('add') 调用 mutations 中函数的方法,可以传入参数。

mutations: {
  add (state, args) {
    state.count += args.n
  }
}
// 调用
store.commit('add', {n: 10})
  • actions 封装、组合;操作 mutations,可以有异步和同步操作,数据请求一般放这。
    Action 函数接受一个与 store 实例具有相同方法和属性的 context 对象,因此你可以调用 context.commit 提交一个 mutation,或者通过 context.statecontext.getters 来获取 stategetters
actions: {
  add (context) {
   context.commit('add')
  }
}

store.dispatch('add') 调用 actions 中函数的方法,可以传入参数。

actions: {
  add ({commit}, args) {
   commit('add', args)
  }
}
// 以载荷形式分发
store.dispatch('add', {
  n: 10
})

// 以对象形式分发
store.dispatch({
  type: 'add',
  n: 10
})
  • vue components 可以从 state 读数据,state更新了 vue components 也会更新,vue components只能通过调用 actions 操作数据。

vuex 目录结构

这只是个示例,这目录官网扒的,嘿嘿嘿

├── index.html
├── main.js
├── api
│   └── ... # 抽取出API请求
├── components
│   ├── App.vue
│   └── ...
└── store
    ├── index.js          # 我们组装模块并导出 store 的地方
    ├── actions.js        # 根级别的 action
    ├── mutations.js      # 根级别的 mutation
    └── modules
        ├── cart.js       # 购物车模块
        └── products.js   # 产品模块

vuex 使用前置

vuex 可以直接在 main.js 中直接引入,也可以独立出一个文件,再引入到 main.js 中。
先安装 vuex:npm install vuex

直接在 main.js 中直接引入

main.js 文件:

import Vue from 'vue'
// 第一步 引入
// 在主 js 文件 main.js 中引入
import Vuex from 'vuex';

// 第二步 添加到vue身上
// 把 vuex 的操作方法挂到 vue 上
Vue.use(Vuex);

// 第三步 声明 store 对象
// 必须先 use 才能进行操作,然后把 store 对象挂到 vue 上
const store=new Vuex.Store({
  strict: process.env.NODE_ENV!='production',   //严格模式:防止直接修改state,打开时会影响性能,只在开发模式打开;process.env.NODE_ENV 是 webpack 配置取的变量
  state: {a: 12, b: 5},                         //核心:数据
  mutations: {
    add(state, n){
      state.a+=n;
    }
  },
  actions: {
    add({commit}, n){
      commit('add', n); // 调用 mutations 中的 add
    }
  },
  getters: {},
  modules: {}
});
new Vue({
  el: '#app',
  router,
  store,
  components: { App },
  template: ''
})

vue 文件:


  
  

把 vuex 独立到 store 文件夹中

store/index.js 文件:

import Vue from 'vue'
import Vuex from 'vuex';

Vue.use(Vuex);
const store=new Vuex.Store({
  strict: process.env.NODE_ENV!='production', 
  state: {a: 12, b: 5},
  mutations: {
    add(state, n){
      state.a+=n;
    }
  },
  actions: {
    add({commit}, n){
      commit('add', n);
    }
  },
  getters: {},
  modules: {}
});
export default store

main.js 文件:

import Vue from 'vue'
import App from './App'
import router from './router'
import store from './store'

new Vue({
  el: '#app',
  router,
  store,
  components: { App },
  template: ''
})

vue 文件无需改动。

vuex 实际项目中使用

项目中使用时就要用到 getters 函数,可以把它看成 store 的计算属性。

vuex 有几个辅助函数,把 vuex 的函数映射成 vue 组件中对应的函数,简化操作

  • mapState state -> computed
  • mapActions actions -> methods
  • mapGetters getters -> computed

store/index.js 文件:

import Vue from 'vue'
import Vuex from 'vuex';
Vue.use(Vuex);
const store=new Vuex.Store({
  strict: process.env.NODE_ENV!='production',
  state: {a: 12, b: 5},
  mutations: {
    add(state, n){
      state.a+=n;
    },
    addA(state, n){
      state.a+=n;
    },
    addB(state, n){
      state.b+=n;
    },
    setOnline(state, id){
      state.users.forEach(user=>{
        if(user.id==id){
          user.online=true;
        }
      });
    },
    setUsers(state, users){
      state.users=users;
    }
  },
  actions: {
    add({commit}, n){
      commit('add', n);
    },
    addA({commit}, n){
      commit('addA', n);
    },
    addB({commit}, n){
      commit('addB', n);
    },
    setOnline({commit}, id){
      commit('setOnline', id);
    },
    async readUsers({commit}){
      let res=await fetch('http://localhost:2021/static/user.txt');
      // [{"id":3,"name":"blue","age":18,"online":true},{"id":5,"name":"zhangsan","age":22,"online":false},{"id":11,"name":"lisi","age":25,"online":true}]
      let users=await res.json();

      commit('setUsers', users);
    }
  },
  getters: {
    count(state){
      return state.a+state.b;
    },
    onlineUsers(state){
      return state.users.filter(user=>user.online);
    }
  },
  modules: {}
});
export default store

vue 文件:




vuex 模块化

首先需要在 store/index.js引入对应子模块,注意子模块的 mutationsactions 重名会多次执行。
store/index.js:

import Vue from 'vue'
import Vuex from 'vuex';
import boy from './boy';
import girl from './girl';
Vue.use(Vuex);

const store=new Vuex.Store({
  strict: process.env.NODE_ENV!='production',
  state: {str: 'liangzai'},
  getters: {
    couples(state) {
      return `${state.boy.str} && ${state.girl.str}`;
    }
  },
  modules: {
    boy,
    girl
  }
});
export default store

store/boy.js:

export default {
  state: {
    str: 'boy'
  },
  mutations: {
    'boySetStr': function (state, s){
      console.log('boy 的 setStr');
      state.str=s;
    }
  },
  actions: {
    'boySetStr': function ({commit}, s){
      commit('boySetStr', s);
    }
  }
}

store/girl.js:

export default {
  state: {
    str: 'girl'
  },
  mutations: {
    'girlSetStr': function (state, s){
      console.log('girl 的 setStr');
      state.str=s;
    }
  },
  actions: {
    'girlSetStr': function ({commit}, s){
      commit('girlSetStr', s);
    }
  }
}

vue 文件:



参考代码下载:https://github.com/windliang/simpleJS/tree/master/vue/vuexDemo

你可能感兴趣的:(【Vue2】Vuex 基础使用)