Vuex使用详解、简单实现一个Vuex

介绍

Vuex是实现组件全局状态(数据)管理的一种机制,可以方便的实现组件之间数据的共享
好处:
能够在vuex中集中管理共享的数据,易于开发和后期维护
存储在vuex中的数据都是响应式的,能够实时保持数据与页面的同步
能够高效地实现组件之间的数据共享,提高开发效率
应用层级的状态应该集中到单个 store 对象中。
提交 mutation 是更改状态的唯一方法,并且这个过程是同步的。
异步逻辑都应该封装到 action 里面。

在 Vue 组件中获得 Vuex 状态

Vuex 的状态存储是响应式的

计算属性返回状态

// 创建一个 Counter 组件
const Counter = {
  template: `<div>{{ count }}</div>`,
  computed: {
    count () {
      return store.state.count
    }
  }
}

每当 store.state.count 变化的时候, 都会重新求取计算属性,并且触发更新相关联的 DOM
Vuex 通过 Vue 的插件系统将 store 实例从根组件中“注入”到所有的子组件里。且子组件能通过 this.$store 访问到。让我们更新下 Counter 的实现:

const Counter = {
  template: `<div>{{ count }}</div>`,
  computed: {
    count () {
      return this.$store.state.count
    }
  }
}

mapState 辅助函数

一个组件需要获取多个状态的时候,可以使用 mapState 辅助函数帮助我们生成计算属性

// 在单独构建的版本中辅助函数为 Vuex.mapState
import { mapState } from 'vuex'

export default {
  // ...
  computed: mapState({
    // 箭头函数可使代码更简练
    count: state => state.count,

    // 传字符串参数 'count' 等同于 `state => state.count`
    countAlias: 'count',
    
    // 为了能够使用 `this` 获取局部状态,必须使用常规函数
    countPlusLocalState (state) {
      return state.count + this.localCount
    }
  })
}

State

State提供唯一的公共数据源,所有共享的数据都要统一放到Store的State中进行储存。

//创建store数据源,提供唯一公共数据
export default new Vuex.Store({
  // 公共数据存放
  state: {   
  //储存数据
  //变量
    counter:0,
    //数组
     normaluser:{
      normal:false,
      id:'',
      username:'',
      password:'',
      telephone:'',
      email:'',
      qqNumber:'',
      level:'',
    },
  },
  mutations: {
  },
  actions: {
  },
  modules: {
  }
})

组件访问State中数据的一种方式

this.$store.state.couter

组件访问State中数据得第二种方式

import {mapState} from 'vuex'
//从vuex中按需导入mapState函数
export default {
  name: "Header",
  //通过刚才导入得mapState函数,将当前组件需要的全局属性,映射为当前组件的computed属性
  computed:{
    ...mapState(['couter'])
  }
}

Getter

Getter用于Store的数据进行加工处理形成新的数据
Getter可以对Store中已有的数据加工处理之后形成新的数据,类似于Vue的计算属性
Store中数据发生变化,Getter的数据也会跟着变化

export default new Vuex.Store({
  // 公共数据存放
  state: {
    couter:0
  },
  getters:{
    shownNum(){
      return '当前的数据是['+state.couter+']'
    }
  }
})

在其他组件使用getters
第一种方式:
this.$store.getters.名称,后面没有括号

this.$store.getters.showNum

第二种方式

import  {mapGetters} from 'vuex'
computed:{
  ...mapGetters(['showNum'])
}

Mutation

更改 Vuex 的 store 中的状态的唯一方法是提交 mutation。
Mutation用于变更Store数据,不可以直接操作Store中的数据
这种方式虽然操作繁琐,但是可以集中监控所有数据的变化

 mutations: {
 addN(state.step){
 //变更状态
 state.count+=step
}
  },

你不能直接调用一个 mutation 处理函数。这个选项更像是事件注册:“当触发一个类型为 increment 的 mutation 时,调用此函数。”要唤醒一个 mutation 处理函数,你需要以相应的 type 调用 store.commit 方法
第一种方式

this.$store.commit('addN',3)

第二种方式

import { mapMutations } from 'vuex'
//从vuex中按需导入mapState函数
 export default {
 name: "Header",
 //通过刚才导入得mapState函数,将当前组件需要的全局属性,映射为当前组件的computed属性
methods:{
   ...mapMutations(['sub','subN'])
   btn1(){
     this.sub()
   },
   btn2(){
     this.subN()
   }
 }
}

提交载荷(Payload)

Action

Action用于处理异步任务
如果通过异步操作变更数据,必须通过Action,而不能使用Mutation,但是在Action中还是需要通过触发Mutation的方式间接变更数据。

 actions: {
     addAsync(context){
     sertTimeout(()=>{
     //只能间接触发Mutation
     context.commit('add')
   },1000)
   }
  },

组件中触发Action
第一种方式

methods:{
   handle(){
     //触发actions
     this.$store.dispatch('addAsync')
   }
}

第二种方式
组件内导入mapActions函数

import {mapActions} from 'vuex'
methods:{
       ...mapMutations(['addAsync'])
      btn3(){
       this.addAsync()
       }
}

关于传参数,第一个永远是context,第二个才是传进来的参数

 actions: {
     addAsync(context,step){
    
   },1000)
   }
  },

页面刷新造成数据丢失解决

这里我分别说明一下这2中方法的使用方式:

第一种:利用js存储技术(localStorage、sessionStorage、cookie)来进行处理

在App.vue中的create函数中写上这几行代码,

//在页面加载时读取sessionStorage里的状态信息

if (sessionStorage.getItem("store") ) {
 this.$store.replaceState(Object.assign({},this.$store.state,JSON.parse(sessionStorage.getItem("store"))))     
} 

//在页面刷新时将vuex里的信息保存到sessionStorage里

window.addEventListener("beforeunload",()=>{
  sessionStorage.setItem("store",JSON.stringify(this.$store.state))
})

这样就能在页面刷新时把store的数据存到sessionStorage中,并且在页面加载时及时获取到数据。

这里之所以使用sessionStorage,是因为sessionStorage的存在时间是当页面打开时存在,页面一关闭就会自动清除,能保证下次一进来页面使用的仍是新数据,不是上次存储的数据。

第二种:使用一些vue的插件,例如 vuex-persistedstate ,实际上其根本原理就是将vuex中的state存在 localStorage或者sessionStorage中,在页面刷新之后vuex在从 localStorage中把数据拿回来

一、首先安装插件,

npm install vuex-persistedstate  --save

二、然后在store的index.js中写上下面这些代码

import createPersistedState from "vuex-persistedstate"
 
const store = new Vuex.Store({
  // ...
  plugins: [createPersistedState()]
})

此时可以使用sessionStorage 把数据存储起来,

import createPersistedState from "vuex-persistedstate"
const store = new Vuex.Store({
  // ...
  plugins: [createPersistedState({
      storage: window.sessionStorage
  })]
})

这样我们就把vuex中的数据存储起来了,同样我们在页面加载时再次把sessionStorage中的数据存到vuex中,就可以了。

Vuex模块式开发

新建home.js 和search.js 两个小仓库
在这里插入图片描述

const state = {}
const mutations = {}
const actions = {}
const getter = {}
export default {
    state,
    mutations,
    actions,
    getter
}

主index.js

import Home from './Home'
import Search from './Search'
export default new Vuex.Store({
  state: {
  },
  mutations: {
  },
  actions: {
  },
  modules: {
    Home,      //
    Search
  }
})

就会出现
在这里插入图片描述

简单实现一个VueX

参考资料

快速上手Vuex 到 手写简易 Vuex – 掘金好文

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

李和贵

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值