vuex详解

vuex详情

Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。Vuex 也集成到 Vue 的官方调试工具 devtools extension (opens new window),提供了诸如零配置的 time-travel 调试、状态快照导入导出等高级调试功能。
在这里插入图片描述类似一个大管家,而且还是响应式的。
在这里插入图片描述
在这里插入图片描述

安装vueX插件

npm install vuex --save

新建如图目录,避免代码都写到main.js里面
在这里插入图片描述
vuex与路由引入方式一样

index.js

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

//安装插件
Vue.use(Vuex)


//创建对象  Vuex里面有一个Store的属性,这里的Store首字母大写,里面放的东西固定
const store = new Vuex.Store({
    //保存状态用的,其他页面就可以共享这个状态了
    state: {
        counter: 10000
    },

     //定义一些方法
    mutations: {
        //默认有个参数state
        increament(state) {
            state.counter++
        },
        decrement(state) {
            state.counter--
        }

    },

    actions: {

    },

    getters: {

    },

    modules: {

    }

})

//导出store对象
export default store

在这里插入图片描述
注意
使用方法与router差不多,挂载到main.js里面,并且要在new Vue中引入,不引入会报如下错,
在这里插入图片描述

此时我们就可以在多个组件中拿到我们想要的公共内容了
通过这句话拿到我们想要的值

 <h2>{{$store.state.counter}}</h2>

mutations的使用

他的作用是对state的数据改变,是响应式的,改变了数值,多个页面都会变化,

使用mutations修改state的值的方法

1.普通用法
首先在index.js文件中

 //定义一些方法
    //状态更新的唯一方法
    mutations: {
        //默认有个参数state
        increament(state) {
            state.counter++
        },
        }

在APP.vue中使用
首先

 methods: {
    addition(){
      this.$store.commit('increament')
    },

然后

<div>{{$store.state.counter}}</div>
    <button @click="addition">+</button>

这样最简单的方法就完事了。
2.传参使用
App.vue中,首先

 methods: {
    addition(){
      this.$store.commit('increament')
    },
    subtraction(){
           this.$store.commit('decrement')
    },
    addCount(count){
      //payload:负载
      //通过mutation更新数据的时候,有可能我们希望携带一些额外的参数,
      //参数被称为是mutation的载荷(Payload)
      //如果我们需要传递很多参数,我们通常会以对象的形式传递,也就是说payload是一个对象
      //-------------------
      //普通的一种提交风格
      this.$store.commit('incrementCount',count)
      //特殊的一种提交风格
      this.$store.commit({
        //事件类型
        type:'incrementCount',
        payload
      })
  },
  //点击添加学生
    addStudent(){
      const stu ={id:118,name:'yyyy',age:44}
      this.$store.commit('addStudent',stu)
    },
    //点击修改信息
    updataInfo(){
     this.$store.commit('updataInfo')
    }


  }
}

然后

<div id="app">
    <h2>------App内容:info对象的内容是否为响应式的------</h2>
    <h2>{{$store.state.info}}</h2>
    <button @click="updataInfo">修改信息</button>
    <h2>--传参数的情况-------</h2>
    <h2>{{$store.getters.moreAgeStu(40)}}</h2>
    <h2>------APP内容 state与mutations用法--------</h2>
    <h2>{{message}}</h2>
    <div>{{$store.state.counter}}</div>
    <button @click="addition">+</button>
    <button @click="subtraction">-</button>
    <button @click="addCount(5)">+5</button>
    <button @click="addCount(10)">+10</button>
    <button @click="addStudent">添加学生</button>

index.js文件中

 mutations: {
        //默认有个参数state
        increament(state) {
            state.counter++
        },
        decrement(state) {
            state.counter--
        },
        incrementCount(state, count) {
            //第一种提交方式 只打印数字

            console.log(count);
            state.counter += count
                //第二种提交方式,打印一个对象,将上列第二个参数改为payload
            state.counter += payload.count

        },
        //点击添加学生
        addStudent(state, stu) {
            state.students.push(stu)
        },
        //点击修改信息
        updataInfo(state) {
            state.info.name = 'coderwhy',
                //当我们想加属性时,是不行的,不会在页面加入
                // state.info['address']='洛杉矶'
                //但这样就是响应式了,界面会发生相应变化。通过数组索引修改,不是响应式的
                Vue.set(state.info, "address", '洛杉矶')
                //delete 删属性也不是响应式的
                //delete state.info.age
                //下面这种方式就是响应式的了
            Vue.delete(state.info, 'age')

        }



    },

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

官方在文档中推荐mutations变量名同意(APP.vue中与index.js中)
经常在store文件夹下定义一个mutations.type.js文件
在这里插入图片描述

mutations.type.js

export const INCREMENT = 'increment'
    //只有export default 的导出方式才能用import方式导入
    //普通导入只能使用import {INCREMENT}的方式导入

index.js文件中

import {
    INCREMENT
} from './mutations-types'
 [INCREMENT](state) {
            state.counter++
        },

App.js中

addition(){
      this.$store.commit('INCREMENT')
    },

在这里插入图片描述
Devtools就和油猴差不多,是个插件,可以监测vue的改变
在这里插入图片描述

如果直接修改State,则监听不到devtools
在这里插入图片描述
在这里插入图片描述
App.vue

<template>
  <div id="app">
    <h2>------APP内容--------</h2>
    <h2>{{message}}</h2>
    <div>{{$store.state.counter}}</div>
    <button @click="addition">+</button>
    <button @click="subtraction">-</button>
    <h2>--------组件内容----------</h2>
    <Hello-vuex :counter="counter"/>
  </div>
</template>

<script>
import HelloVuex from '@/components/hellowvuex.vue'


export default {
  name: 'App',

  components: {
    HelloVuex
  },
  data () {
    return {
      message:'我是App组件',
      counter:0
    }
  },
  //定义方法,这里的内容注意怎么写
  methods: {
    addition(){
      this.$store.commit('increament')
    },
    subtraction(){
           this.$store.commit('decrement')

    }
  }
}
</script>

<style>

</style>

Getters的基本使用

有时候,我们需要从store中获取一些state变异后的状态。(只会对数据经行加工,不会改变stare原始数据)
在这里插入图片描述

vuex-actions的用法

通常情况下,Vuex要求我们Mutations中的方法必须是同步方法。
主要的原因是我们使用Devtools时,可以devtools可以帮助我们捕捉mutation的快照。
但是如果操作是异步的,那么devtool将不能很好的追踪这个操作什么时候被完成。
如果异步写在mutations里面

在这里插入图片描述我们就得借助action来完成异步操作
在这里插入图片描述

APP.vue

<h2>------App内容:modules里面的内容用法------</h2>
    <h2>{{$store.state.a.name}}</h2>
    <button @click="Updatename">修改名字</button>
    <h2>{{$store.getters.fullName}}</h2>
     <h2>{{$store.getters.fullName2}}</h2>
     <h2>{{$store.getters.fullName3}}</h2>
     <button @click="asyncUpdataName">异步修改名字</button>
    

APP.vue里的methods

updataInfo(){
      //
     //this.$store.commit('updataInfo')
     //调用actions里面的方法,通过dispatch
    //  this.$store.dispatch('aUpdataInfo',{
    //    message:"我是携带的信息",
    //    success:()=>{
    //      console.log('里面的已经完成了');
    //    }

    //  })
    //可以这样写,代码更好看
    this.$store.dispatch('aUpdataInfo',"我是携带的信息")
    .then(res=>{
      console.log('里面完成了提交');
      console.log(res);
    })
    
    
    },
    Updatename(){
      this.$store.commit('updateName','lisi')
    },
    asyncUpdataName(){
      this.$store.dispatch('aUpdataName')
    }

moduleA.js

export default {
    state: {
        name: "hanxiaolei"
    },
    mutations: {
        updateName(state, payload) {
            state.name = payload
        }
    },
    actions: {
        aUpdataName(context) {
            console.log(context);
            setTimeout(() => {
                context.commit('updateName', 'wangwu')
            }, 1000);

        }
    },

    getters: {
        fullName(state) {
            return state.name += '11111'
        },
        fullName2(state, getters) {
            return getters.fullName + "222222"
        },
        fullName3(state, getters, rootState) {
            return getters.fullName2 + rootState.counter

        }
    }

actions.js文件

export default {


    //context的意思是上下文的意思,相当于store
    // aUpdataInfo(context, payload) {
    //     console.log(payload.message);
    //     payload.success()
    //     setTimeout(() => {
    //         context.commit('updataInfo')
    //     }, 1000)
    // }
    //这样写,代码更好看
    aUpdataInfo(context, payload) {
        return new Promise((resolve, reject) => {
            setTimeout(() => {
                context.commit('updataInfo')
                console.log(payload);
                resolve("11111111")
            }, 1000)

        })


    },

}

将store分成模块
在这里插入图片描述我们可以把vuex里面的五个属性按目录分开写,方便管理
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值