[Vue] vuex进行组件间通信

vue 组件之间数据传输(vuex)

初始化 store

src/main.jshtml

import Vuex from "vuex";
Vue.use(Vuex);

new Vue({
  ...,
  store,
  ...,
});

src/store/index.jsvue

import mutations from "./mutations";

const initStore = {
  state: {
    userBasicInfo: {},
    siteBaseInfo: {
      download: "",
      invitation: "",
      register_enable: "",
      service_qq1: "",
      service_qq2: "",
      service_wechat: "",
    },
  },
  mutations
};

export default initStore;

src/store/mutations.jsreact

const SET_USER_BASIC_INFO = 'SET_USER_BASIC_INFO';
const SET_SITE_BASE_INFO = 'SET_SITE_BASE_INFO';

export default {
  [SET_USER_BASIC_INFO](state, payload) {
    state.userBasicInfo = payload.data;
  },
  [SET_SITE_BASE_INFO](state, payload) {
    state.siteBaseInfo = Object.assign({}, state.siteBaseInfo, payload);
  },
}

state

正常使用 state

Vuex 的状态存储是响应式的,从 store 实例中读取状态最简单的方法就是在计算属性中返回某个状态。每当 store.state.count 变化的时候, 都会从新求取计算属性,而且触发更新相关联的 DOM。 Vuex 经过 store 选项,提供了一种机制将状态从根组件“注入”到每个子组件中。ios

const app = new Vue({
  el: '#app',
  // 把 store 对象提供给 “store” 选项,这能够把 store 的实例注入全部的子组件
  store,
  components: { Counter },
  template: `
    <div class="app">
      <counter></counter>
    </div>
  `
})

在子组件中使用git

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

mapState 辅助函数

按官网的案例github

import { mapState } from 'vuex'

export default {
  // ...
  computed: mapState({
    // 箭头函数
    siteBaseInfo: state => state.siteBaseInfo,
    // 传字符串参数
    siteBaseInfo: "siteBaseInfo",
    // 为了可以使用 `this` 获取局部状态,必须使用常规函数
    download_ios (state) {
      return state.siteBaseInfo.download + this.prefix
    },
    download: state => state.siteBaseInfo.download
  })
}

当映射的计算属性的名称与 state 的子节点名称相同时,咱们也能够给 mapState 传一个字符串数组ajax

computed: mapState([
  // 映射 this.count 为 store.state.count
  'count'
])

mapState 与局部计算属性混合使用

使用对象展开运算符将多个对象合并为一个,以使咱们能够将最终对象传给 computed 属性。vue-router

computed: {
  localComputed () { /* ... */ },
  // 使用对象展开运算符将此对象混入到外部对象中
  ...mapState({
    // ...
  })
}

getter 的使用

有时候咱们须要从经过 state 获得一些新的状态,由于这一状态可能其余不少组件都要使用这一状态.好比余额这一参数,咱们当前只有盈利和亏损额,可是不少页面都要使用余额进行显示,那么每一个引入页面都要进行一次计算吗?想一想就麻烦,仍是只计算一次,而后直接获取这个余额值来的方便vuex

store/getters.jssegmentfault

export default {
  balance: (state) => {
    return Number(state.userBasicInfo.profit) - Number(state.userBasicInfo.loss);
  },
  download: (state) => {
    return state.siteBaseInfo.download;
  }
}

mapGetters 辅助函数

辅助函数仅仅是将 store 中的 getter 映射到局部计算属性

import { mapGetters } from 'vuex'

export default {
  // ...
  computed: {
  // 使用对象展开运算符将 getter 混入 computed 对象中
    ...mapGetters([
      'balance',
      'download',
      // ...
    ])
  }
}

getter 的使用

//直接使用
store.getters.download
//组件中使用
computed: {
 download () {
    return this.$store.getters.download
  }
}
//使用辅助函数
...mapGetters([
      'download',
      'balance',
])
//和mapState一块儿用
computed: {
  ...mapState({
    siteBaseInfo: "siteBaseInfo",
  }),
  ...mapGetters({
    download: 'download'
  })
},

Getter 也能够接受其余 getter 做为第二个参数

getters: {
  // ...
  doneTodosCount: (state, getters) => {
    return getters.doneTodos.length
  }
}

总之,getter 就是一个将一些须要进行再次计算的 state 计算好,而后将其做为 state 进行快捷的引用

mutation 使用

  • 最好提早在你的 store 中初始化好全部所需属性
  • 当须要在对象上添加新属性时,你应该使用 Vue.set(obj, 'newProp', 123)或以新对象替换老对象(对象展开符)
  • mutation 必须是同步函数

每一个 mutation 都有一个字符串的 事件类型 (type) 和 一个 回调函数 (handler),会接受 state 做为第一个参数

//设置
mutations: {
   SET_USER_BASIC_INFO(state) {
    state.userBasicInfo = {a:1,b:2};
  },
}

//使用
store.commit('SET_USER_BASIC_INFO')

提交载荷(Payload)

//设置
mutations: {
   SET_USER_BASIC_INFO(state, payload) {
    state.userBasicInfo = Object.assign({},payload);
  },
}

//使用
store.commit('SET_USER_BASIC_INFO', {
  a:1,
  b:2
})

对象风格的提交方式

提交 mutation 的另外一种方式是直接使用包含 type 属性的对象

store.commit({
  type: 'SET_USER_BASIC_INFO',
  data:{
      a:1,
      b:2,
  }
})

//mutations的效果
mutations: {
  increment (state, payload) {
    state.userBasicInfo = Object.assign({},payload.data);
  }
}

使用常量替代 Mutation 事件类型

// mutation-types.js
export const SET_USER_BASIC_INFO = 'SET_USER_BASIC_INFO';

// mutations.js
import { SET_USER_BASIC_INFO } from './mutation-types';

mutations: {
    // 咱们能够使用 ES2015 风格的计算属性命名功能来使用一个常量做为函数名
    [SET_USER_BASIC_INFO] (state) {
      // mutate state
    }
  }

mapMutations 辅助函数

//正常
this.$store.commit('SET_USER_BASIC_INFO');

//mapMutations
import { mapMutations } from 'vuex';

export default {
    ...,
    methods:{
        ...mapMutations({
            setUserBasicInfo: 'SET_USER_BASIC_INFO' // 将 `this.setUserBasicInfo()` 映射为 `this.$store.commit('SET_USER_BASIC_INFO')`
        })
    }
}

action

用来提交一个 mutation,还能够进行异步操做

//注册
const store = new Vuex.Store({
  state,
  mutations,
  actions: {
    //解构context.commmit
    GET_HOME_INFO({commit}) {
        commit("SET_USER_BASIC_INFO");
    },
  }
})

//触发
store.dispatch('GET_HOME_INFO')
//载荷形式
store.dispatch('GET_HOME_INFO',{})
//对象形式
store.dispatch({
    type:'GET_HOME_INFO',
    data:{}
})

mapActions 辅助函数

import { mapActions } from 'vuex'

export default {
  ...
  methods: {
    ...mapActions({
      getHomeInfo: 'GET_HOME_INFO' // 将 `this.getHomeInfo()` 映射为 `this.$store.dispatch('GET_HOME_INFO')`
    })
  }
}

异步的 action

action 中的中支持的异步 ajax,setTimeout,acync/await,promise...

store.dispatch('actionA').then(() => {
  // ...
})

其余的传值还有一些方式

好比 props,seventBus,slocalStorage,sessionStorage,router 传参,cookie(不推荐,虽然就跟以前作购物车差很少的传递形式)

vue 组件之间数据传输(props 传值方式)

这个多用于父子组件之间的传值,是最基本的传值方式

父亲组件进行绑定,将数据绑定,其中 personal,personalData,imgUrl 是绑定的数据,@updata 是绑定的事件

<template>
      ...
      <slideBar
        @updata="updata"
        :personal="personal"
        :personalData="personalData"
        :imgUrl="imgUrl"
      ></slideBar>
      ...
<template>

子组件进行获取数据经过 props 进行获取,能够设置一些静态类型检查,相似于 react 的 proptypes,同时子组件想要向父组件进行传值,能够经过 emit 进行传值就好了

export default {
    props: {
      slideMsg: Array,
      personal: Object,
      personalData: Object,
      imgUrl: String
    },
    ...
    methods:{
      submitEvent(){
        ...
        this.emit("updata","我是获取的数据");
        ...
      }
    }
  }

vue 组件之间数据传输(eventBus 进行组件传递)

事件 bus 经过一个新的 vue 实例,来进行事件监听和事件分发 commom/bus.js

//极简单的vue实例
import Vue from 'vue';
// 使用 Event Bus
const bus = new Vue();
export default bus;

在 game 组件中引入

import bus from "@/common/bus";

...
bus.$emit("moneyChange", {....});
...

在用 money 组件中引入

import bus from "@/common/bus";

...
bus.$on("moneyChange", msg => {
    msg && this.initHomeData();
});
...

在最初的项目阶段这是一个不错的选择,可是随着项目体积的增大,事件触发和数据流向变得愈来愈不可见,后续开发和维护变得愈来愈困难.

sessionstorage

项目中使用的 sessionStorage

sessionStorage.setItem("msg", JSON.stringify(res.data)); //为了兼容以前的代码,有用到msg这个本地缓存的数据
sessionStorage.setItem("isMobile", res.data.mobile);
sessionStorage.setItem("invi", res.data.invitation);
sessionStorage.setItem("isLogin", res.data.trier);
sessionStorage.setItem("setPwd", res.data.fundpwd);
sessionStorage.setItem("isShow", res.data.bankcard);

localStorage

项目中关于声音的开关,样式选择,背景切换等,用来将用户的一些操做一直保存

//组件userSetting
localStorage.setItem("audio", this.switchValue);
//组件audioPlay
let audio = localStorage.getItem("audio");

sessionstorage 和 localStorage 看状况使用就好,sessionstorage 是浏览器关闭没了,localStorage 是一直存储不删除就在存在

params

依赖于 vue-router

this.$router.push({
  name: "Main",
  params: {
    id: this.setting_id,
    type: "3"
  }
});

Vuex Vuex - 标签 - 掘金 浪里行舟 从头开始学习 Vuex VueJS 中学习使用 Vuex 详解 到底 vuex 是什么? 基于 vue2 + vuex 构建一个具备 45 个页面的大型单页面应用

原文出处:https://www.cnblogs.com/mybilibili/p/10456346.html

相关文章
相关标签/搜索