Nuxt使用Vuex的方法示例


Posted in Javascript onSeptember 06, 2019

Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。

基础知识这里不再重述,学习的话请自行到官网学习https://vuex.vuejs.org/zh/

文档最后有具体使用的实例,不想看基础的就直接下调页面~

Nuxt使用Vuex的方法示例

这里主要简单讲一讲Nuxt里怎么使用vuex,

Nuxt.js 内置引用了vuex模块,所以不需要额外安装。

Nuxt.js 会尝试找到应用根目录下的store目录,如果该目录存在,它将做以下的事情:

  • 引用vuex模块
  • vuex模块 加到 vendors 构建配置中去
  • 设置Vue根实例的store配置项

Nuxt.js 支持两种使用store的方式,你可以择一使用:

  • 普通方式:store/index.js返回一个 Vuex.Store 实例
  • 模块方式:store目录下的每个.js文件会被转换成为状态树指定命名的子模块(当然,index是根模块)

普通方式

使用普通方式的状态树,需要添加store/index.js文件,并对外暴露一个 Vuex.Store 实例:

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

Vue.use(Vuex)

const store = () => new Vuex.Store({

 state: {
  counter: 0
 },
 mutations: {
  increment (state) {
   state.counter++
  }
 }
})

export default store

现在我们可以在组件里面通过this.$store来使用状态树

<template>
 <button @click="$store.commit('increment')">{{ $store.state.counter }}</button>
</template>

模块方式

状态树还可以拆分成为模块,store目录下的每个.js文件会被转换成为状态树指定命名的子模块

使用状态树模块化的方式,store/index.js不需要返回 Vuex.Store 实例,而应该直接将statemutationsactions暴露出来:

export const state = () => ({
 counter: 0
})

export const mutations = {
 increment (state) {
  state.counter++
 }
}

其他的模块文件也需要采用类似的方式,如store/todos.js文件:

export const state = () => ({
 list: []
})

export const mutations = {
 add (state, text) {
  state.list.push({
   text: text,
   done: false
  })
 },
 remove (state, { todo }) {
  state.list.splice(state.list.indexOf(todo), 1)
 },
 toggle (state, todo) {
  todo.done = !todo.done
 }
}

在页面组件pages/todos.vue, 可以像下面这样使用todos模块:

<template>
 <ul>
  <li v-for="todo in todos">
   <input type="checkbox" :checked="todo.done" @change="toggle(todo)">
   <span :class="{ done: todo.done }">{{ todo.text }}</span>
  </li>
  <li><input placeholder="What needs to be done?" @keyup.enter="addTodo"></li>
 </ul>
</template>

<script>
import { mapMutations } from 'vuex'

export default {
 computed: {
  todos () { return this.$store.state.todos.list }
 },
 methods: {
  addTodo (e) {
   this.$store.commit('todos/add', e.target.value)
   e.target.value = ''
  },
  ...mapMutations({
   toggle: 'todos/toggle'
  })
 }
}
</script>

<style>
.done {
 text-decoration: line-through;
}
</style>

模块方法也适用于顶级定义,而无需在store目录中实现子目录

state 示例,您需要创建一个文件store/state.js并添加以下内容:

export default () => ({
 counter: 0
})

并且相应的 mutations 在文件store/mutations.js中:

export default {
 increment (state) {
  state.counter++
 }
}

模块文件

您可以将模块文件分解为单独的文件:state.js,actions.js,mutations.jsgetters.js。如果您使用index.js来维护state,getters,actionsmutations,同时具有单个单独的操作文件,那么仍然可以正确识别该文件。

项目结构

vuex 并不限制你的代码结构。但是,它规定了一些需要遵守的规则:

  1. 应用层级的状态应该集中到单个 store 对象中。
  2. 提交mutation是更改状态的唯一方法,并且这个过程是同步的。
  3. 异步逻辑都应该封装到action里面。

只要你遵守以上规则,如何组织代码随你便。如果你的 store 文件太大,只需将 action、mutation 和 getter 分割到单独的文件。

对于大型应用,我们会希望把 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  # 产品模块

下面用是实例说一下怎么使用

一、在Nuxt项目的store目录下新建一个index.js文件,这样项目就启用了vuex

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

Vue.use(Vuex)

const store = () => new Vuex.Store({

 state: {
  counter: 0
 },
 mutations: {
  increment (state) {
   state.counter++
  }
 }
})

export default store

一般这个文件我们只作为vuex的入口文件,不在这里面写业务代码,其他的功能写在其他的vuex文件中,在index中导入一下即可

二、在store文件夹里再新建一个filter.js文件,在index.js中引入一下,这个文件来写我们的业务代码

filter.js文件

const state = ({
 value: 'Hello World',
 list: [1, 2, 3, 4, 5]
});
const getters = {
 include: (state) => (val) => {
  return state.list.indexOf(val) > -1;
 }
 }
;
const mutations = {
 SET_VALUE(state, value) {
  state.value = value;
 }
};
const actions = {
 async getInfo({state, commit}, val) {
  commit('SET_VALUE', val);
 }
};

export default {
 namespaced: true,
 state,
 getters,
 actions,
 mutations
};

这个文件中输出时候的namespaced属性,如果为true时,使用这个文件的方法时,需要标注namespace,不写或为false时,则可以直接使用,这里建议使用namespaced,因为大型项目可能有很多复杂的业务,可能命名冲突,使用namespaced可以把方法区分开,避免很多问题

index.js文件

import Vue from 'vue';
import Vuex from 'vuex';
import filter from './filter';

Vue.use(Vuex);

const store = () => new Vuex.Store({
 state: {
 },
 mutations: {
 },
 modules: {
  filter
 }
});

export default store

在index.js文件中import一下我们的filter.js文件,然后在modules中引入即可使用

三、在vue文件中使用vuex

index.vue

<template>
 <section class="p-10">
  <h1> {{ value }} </h1>
  <h1> {{ result }} </h1>
  <el-button type="danger" @click="change">点击</el-button>
 </section>
</template>

<script>
 import { mapState, mapMutations, mapActions, mapGetters } from 'vuex';
export default {
 data() {
  return {
   result: false
  };
 },
 computed: {
  ...mapGetters('filter', [
   'include'
  ]),
  ...mapState({
   value: state => state.filter.value
  })
 },
 methods: {
  ...mapMutations('filter', [
   'SET_VALUE'
  ]),
  ...mapActions('filter', [
   'getInfo'
  ]),
  change() {
   // this.result = this.include(1);
   // this.getInfo('你好');
   // this.SET_VALUE('HELLO');
  }
 },
 mounted() {
 },
 beforeDestroy() {
 }
};
</script>

1.在vue文件中,首先通过import { mapState, mapMutations, mapActions, mapGetters } from 'vuex' 来引入我们需要的模块,按需引用,只需要引入本页面用到的模块即可

2.mapGetters和mapState需要在页面的计算属性computed中引入,mapMutations和mapActions需要在methods中引入,此时要注意模块的命名空间,如果vuex文件导出时标注了namespaced,我们使用时也需要写出才可以找到,反之则不需要

3.首先是mapState,使用mapState时,我有两种方法来取,两种方式都可以,这个方法是从store中取出这个变量,然后显示在此页面上,store变动的话,此页面也会跟着动态改变

...mapState({
   value: state => state.filter.value
  })
...mapState('filter', {
   value: state => state.value
  })

4.mapGetters类似于store的计算属性,我们可以通过mapGetters的方法在store里进行计算,然后返回我们需要的结果即可

上面例子就是点击按钮的时候传了一个数字到store里,然后判断store里的list是否包含这个数字,然后返回结果到页面,页面根据返回值重新刷新数据

5.MapMutation是更改store中状态的唯一方法,Vuex 中的 mutation 非常类似于事件:每个 mutation 都有一个字符串的事件类型 (type)和 一个回调函数 (handler)。这个回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数

上面的例子是点击按钮时,直接通过mutation 的方法修改了store里的数据,然后把数据同步到页面

6.mapAction类似于mutation, 但是Action提交的是mutation,而不是直接变更状态,Action可以包含任意异步操作,我们一般把异步获取数据的方法都放在这里,然后在回调函数里使用mutation里的方法把异步获取的数据保存在store里,然后把store里的数据传到页面

上面的例子是点击按钮时调用了action里的异步方法,然后在方法的回调函数里修改了store的数据,一般这里是把请求的结果进行保存,这里是省略了请求API方法

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
用javascript动态调整iframe高度的代码
Apr 10 Javascript
javascript 必知必会之closure
Sep 21 Javascript
AngularJS身份验证的方法
Feb 17 Javascript
AngularJS基础 ng-list 指令详解及示例代码
Aug 02 Javascript
AngularJS动态菜单操作指令
Apr 25 Javascript
你可能不知道的JSON.stringify()详解
Aug 17 Javascript
9种使用Chrome Firefox 自带调试工具调试javascript技巧
Dec 22 Javascript
微信小程序之判断页面滚动方向的示例代码
Aug 30 Javascript
解决vue-cli@3.xx安装不成功的问题及搭建ts-vue项目
Feb 09 Javascript
vue瀑布流组件实现上拉加载更多
Mar 10 Javascript
vue+vant使用图片预览功能ImagePreview的问题解决
Apr 10 Javascript
vue完美实现el-table列宽自适应
May 08 Vue.js
vue中input的v-model清空操作
Sep 06 #Javascript
nuxt框架中对vuex进行模块化设置的实现方法
Sep 06 #Javascript
layui 表格操作列按钮动态显示的实现方法
Sep 06 #Javascript
基于Vue和Element-Ui搭建项目的方法
Sep 06 #Javascript
微信小程序 搜索框组件代码实例
Sep 06 #Javascript
layui加载表格,绑定新增,编辑删除,查看按钮事件的例子
Sep 06 #Javascript
详解webpack打包vue项目之后生成的dist文件该怎么启动运行
Sep 06 #Javascript
You might like
PHP程序漏洞产生的原因分析与防范方法说明
2014/03/06 PHP
Codeigniter+PHPExcel实现导出数据到Excel文件
2014/06/12 PHP
浅谈php处理后端&amp;接口访问超时的解决方法
2016/10/29 PHP
PHP AjaxForm提交图片上传并显示图片源码
2016/11/29 PHP
利用XMLHTTP传递参数在另一页面执行并刷新本页
2006/10/26 Javascript
AJAX异步从优酷专辑中采集所有视频及信息(JavaScript代码)
2010/11/20 Javascript
JS this作用域以及GET传输值过长的问题解决方法
2013/08/06 Javascript
使用mini-define实现前端代码的模块化管理
2014/12/25 Javascript
Javascript循环删除数组中元素的几种方法示例
2017/05/18 Javascript
JavaScript实现QQ聊天消息展示和评论提交功能
2017/05/22 Javascript
解决vue热替换失效的根本原因
2018/09/19 Javascript
JS实现简单的抽奖转盘效果示例
2019/02/16 Javascript
nodejs微信开发之自动回复的实现
2019/03/17 NodeJs
微信小程序点餐系统开发常见问题汇总
2019/08/06 Javascript
javascript简单实现深浅拷贝过程详解
2019/10/08 Javascript
如何在node环境实现“get数据解析”代码实例
2020/07/03 Javascript
Python 多线程的实例详解
2017/09/07 Python
python中requests爬去网页内容出现乱码问题解决方法介绍
2017/10/25 Python
django admin添加数据自动记录user到表中的实现方法
2018/01/05 Python
Python用sndhdr模块识别音频格式详解
2018/01/11 Python
使用tensorflow实现线性回归
2018/09/08 Python
Django中URL的参数传递的实现
2019/08/04 Python
python GUI库图形界面开发之PyQt5日期时间控件QDateTimeEdit详细使用方法与实例
2020/02/27 Python
Selenium执行完毕未关闭chromedriver/geckodriver进程的解决办法(java版+python版)
2020/12/07 Python
css3类选择器之结合元素选择器和多类选择器用法
2017/03/09 HTML / CSS
HTML5 Blob 实现文件下载功能的示例代码
2019/11/29 HTML / CSS
世界第一冲浪品牌:O’Neill
2016/08/30 全球购物
Born鞋子官网:Born Shoes
2017/04/06 全球购物
俄罗斯品牌服装在线商店:VIPAVENUE
2020/08/10 全球购物
复核员上岗演讲稿
2014/01/05 职场文书
保健品市场营销方案
2014/03/31 职场文书
个人求职信格式范文
2015/03/20 职场文书
2015年售票员工作总结
2015/04/29 职场文书
30岁前绝不能错过的10本书
2019/08/08 职场文书
Java9新特性之Module模块化编程示例演绎
2022/03/16 Java/Android
MySQL外键约束(Foreign Key)案例详解
2022/06/28 MySQL