1 Vue2项目中,Vuex状态管理工具,几乎可以说是必不可少的了。而在Vu3中,尤大大推荐我们使用pinia(拍你啊)进行状态管理,咱得听话,用就完了。

使用之前我们来看一下,使用 pinia 给我们带来哪些好处?

官网介绍:Pinia 是 Vue 的存储库,它允许您跨组件/页面共享状态

个人理解:在我看来就是变态版 vuex,听说是为了尊重原作者,所以给改名了叫 pinia(拍你啊)

看看都有啥变态的
  1. 兼容 vue2、vue3,该说不说这一点 vuex 也支持
  2. Typescript 支持更友好
  3. 体积小,1kb 左右,vuex 350k 以上
  4. 支持插件扩展和服务器端渲染 ssr
  5. pinia 只有 state、getter、action,抛弃了 Vuex 中的 Mutation。
    1. mutation 干啥了?vuex 中改/处理变数据源 store 数据的集合(唯一的),必须是同步。

      1. 我们需要在组件里面调用 dispatch() 方法提交 Actions
      2. Actions 再通过 commit 方法提交 mutations
      3. 通过 mutations 里面的方法修改 state(数据)
      4. 最后 render 到组件里面
    2. 为啥同步?
      1. mutation 中如果写异步 Le,commit 在触发 mutation 事件时,异步的回调函数不知道是什么时候执行的,所以在 devtools 中难以追踪变化了
  6. pinia 中 action 支持同步和异步。上面也说了下为啥,还不知道为啥可以搜一下为啥。
  7. 不用创建各个模块嵌套了。Vuex 中才分不同模块我们需要用到 modules:模块化拆分。在 pinia 中每个 store 都是独立的,互相不影响,没啥事。

用 vue3 demo 讲解 pinia 的使用。

1、搭建项目、安装以来

Vue3 + TS + Vite 项目

参考:Vue3.x 全家桶+vite+TS-搭建 Vue3.x 项目

参考:vue3 学习

1). 创建项目

npm create vite@latest my-vite-app --template vue-ts

2). 安装 pinia 依赖

npm install pinia

3).全局挂在 pinia

我们在 main.ts 主文件中,引入 pinia 的createPinia 方法, 创建根存储,以方便全局调用。

import { createApp } from "vue";
import App from "./App.vue";
import { createPinia } from "pinia";
const pinia = createPinia();
const app = createApp(App);
app.use(pinia);
app.mount("#app");

2、搞正事,创建数据仓库 store

应用场景:

. 多个视图依赖于同一状态。

. 来自不同视图的行为需要变更同一状态。

我们需要用到 pinia 的defineStore() 方法,创建一个 store。

defineStore:

  • 参数 1:(name) store 的唯一标识 id。也就是 vuex 中 modules:模块化拆分的模块标识
  • 参数 2:(options) 相关配置,通俗来讲就是数据,和修改数据的一系列方法 state、getter、action 都在这里

创建后编写代码如下:

/src/store/piniaStore.ts

import { defineStore } from 'pinia'
export const useUsersStore = defineStore('pinia_id', {
})

3、组件中调用 pinia

我们在上一步已经引入了 pinia,并且在 store 文件下创建了一个叫 piniaStore 的 store,接下来让我们看看在组件里如何调用

<script setup lang="ts">
import { useUsersStore } from "../src/store/piniaStore";
const store = useUsersStore();
console.log(store);
</script>

方法很简单一个 useUsersStore 方法搞定,我们看一下打印内容:

$dispose: f $dispose()$id: "pinia_id"
$onAction: f ()
$patch: f $patch(partialStateOrMutator)
$reset: f Sreset()
$subscribe: Ssubscribe(callback, options2 = ) const removeSubscription = addSuoscription(suhotUpdate: (newStore) => f...]

也就这些哈,没啥玩楞。

4、state 属性

我们往 store 里加点数据源 state 吧!

export const useUsersStore = defineStore("pinia_id", {
state: () => {
return {
age: 20,
message:'我来存放公共数据哈!'
sex: "男",
};
},
});

4.1 读取 state 数据

回想一下 vuex 怎么访问的

  • 组件中访问 State 中数据的第一种方式:
this.$store.state.全局数据名称
  • 组件中访问 State 中数据的第二种方式:
// 从vuex中按需导入mapState函数
import { mapState } from 'vuex'
// 将全局数据 因设为当前组件的计算属性
computed: {
...mapState(['count'])
}

pinia 如何访问呢?

其实我们定义的 state 数据就在 useUsersStore 内,我们自行就可以直接拿到相关数据

<template>
<p>描述:{{ message }}</p>
<p>年龄:{{ age }}</p>
<p>性别:{{ sex }}</p>
</template>
<script setup lang="ts">
import { ref } from "vue"; import { useUsersStore } from "../src/store/piniaStore";
const store = useUsersStore(); const message = ref<string>(store.message);
const age = ref<number>(store.age);
const sex = ref<string>(store.sex);
</script>

当然我们也可以用 es6 解构赋值来优化一下

const { message, age, sex } = store;

4.2 多个组件使用 state

我们使用 pinia 更想做到多组件公用统一数据,新建一个 Child.vue 其实用法很简单直接调用使用即可

<template>
<p>我是一个子元素</p>
<p>描述:{{ message }}</p>
<p>年龄:{{ age }}</p>
<p>性别:{{ sex }}</p>
</template>
<script setup lang="ts">
import { ref } from "vue";
import { useUsersStore } from "../src/store/piniaStore";
const store = useUsersStore();
const { message, age, sex } = store;
</script>

4.3 修改 state 数据

我们在回想一下 vuex 怎么修改的

  • 有人很暴力:直接 this.$store.state.全局数据名称 直接去修改,这种方式很难查看数据是被什么组件修改
  • mutation 修改

    ① 只能通过 mutation 变更 store 数据,不可以直接操作 store 中的数据

    ② 通过这种方式虽然操作起来繁琐,但是可以集中监控所有数据的变化

看看 pinia

其实如果想要修改修改 store 中的数据,可以直接重新赋值

<template>
<img alt="Vue logo" src="./assets/logo.png" /> <p>年龄:{{ age }}</p> <button @click="changeAge">年龄不对</button>
</template>
<script setup lang="ts">
import child from './child.vue';
import { useUsersStore } from "../src/store/piniaStore";
const store = useUsersStore();
const { nage,} = store;
const changeAge = () => {
store.age = 26;
console.log(store);
};
</script>

打印可也看出。store 中 age 数据发生了改变,再看看,呦呵,页面没响应。

我们可能去监听 store 数据变化然后刷新页面,但有个更好的方法等着我们

pinia 的storeToRefs 方法把我们的 state 变得具有响应

import { storeToRefs } from 'pinia';
const store = useUsersStore();
const { message, age, sex } = storeToRefs(store);

4.4 初始化/重置 state 数据

store 的$reset()方法为我们提供了 state 数据重置的可能

<button @click="onResetData">重置store</button>

const onResetData = () => {
store.$reset();
};

4.5 store 的$patch 方法批量修改数据

  1. 全部调整:此方法需要一次性将 state 中的所有字段例举出。
 store.$patch({
message: "批量搞事情",
age: 100,
sex: "女",
});
  1. 部分修改: $patch 方法接收一个回调函数,用来修改部分数据
store.$patch((state) => {
state.items.push({ message: 'shoes', quantity: 1 })
state.hasChanged = true
})

4.6 直接替换 state

store.$state = { counter: 666, name: 'yup' }

5、getter 属性

Getter 用于对 Store 中的数据进行加工处理形成新的数据

  • Getter 可以对 Store 中已有的数据加工处理之后形成新的数据,类似 Vue 的计算属性,不会影响到原本的数据
  • Store 中的数据发生变化,Getter 的数据也会跟着变化

5.1 添加 getter

export const useUsersStore = defineStore("pinia_id", {
state: () => {
return { age: 25,
sex: "男",
};
},
getters: {
getAddAge: (state) => {
return state.age + 100;
},
},
});

5.2 调用 getter

  1. 直接在标签上使用 getter 定义的方法,这种方式是响应式的,可以直接监听到变化,其实 state 标签直接调用也是一样相应的
<template>
<p>新年龄:{{ store.getAddAge }}</p>
<button @click="patchStore">批量修改数据</button>
</template>
<script setup lang="ts">
import { useUsersStore } from "../src/store/piniaStore";
const store = useUsersStore();
// 批量修改数据
const patchStore = () => {
store.$patch({ age: 100,
sex: "女",
});
};
</script>
  1. getter 中调用其它 getter

    这里需要注意一下,不要箭头函数
export const useUsersStore = defineStore("users", {
state: () => {
return { age: 25,
sex: "男",
};
},
getters: {
getAddAge: (state) => {
return state.age + 100;
},
getNameAndAge(): string {
return this.name + this.getAddAge; // 调用其它getter
},
},
});

5.3 getter 传参

上文提到 getter 与计算属性差不多,想想计算属性怎么传递的呢?

computed:{
getNewName(){
function (str){
return str+this.name
}
}
}

看一下 getter 的

 <p>新年龄:{{ store.getAddAge(1100) }}</p>
getters: {
getAddAge: (state) => {
return (num: number) => state.age + num;
},
getNameAndAge(): string {
return this.name + this.getAddAge; // 调用其它getter
},
},

6. actions 属性

对数据进行逻辑加工,完成默写特定的业务逻辑。和 vue 组件代码中的 methods 相似,存放一些处理业务逻辑的方法。

6.1 添加 actions

export const useUsersStore = defineStore("pinia_id", {
state: () => {
return {
message: "",
age: 25,
sex: "男",
name:'王'
};
},
getters: {
getAddAge: (state) => {
return (num: number) => state.age + num;
},
getNameAndAge(): string {
return this.name + this.getAddAge; // 调用其它getter
},
},
actions: {
saveName(name: string) {
this.name = name;
},
},
});

6.2 使用 actions

const saveName = () => {
store.saveName("我用来调用action内的方法");
};

至此文章结束!

23年用vuex进行状态管理out了,都开始用pinia啦!的更多相关文章

  1. 理解vuex的状态管理模式架构

    理解vuex的状态管理模式架构 一: 什么是vuex?官方解释如下:vuex是一个专为vue.js应用程序开发的状态管理模式.它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证以一种可预测的 ...

  2. vuex vue状态管理

    第一步安装vuex(安装在生产环境) npm install vuex 第二步 src下新建store文件夹 用来专门放状态管理,store文件夹下新建四个js文件 index.js  actions ...

  3. Vuex实现状态管理

    Vuex使用总结 1 Vuex简介 Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式,Vuex抽取了各个组件的共享部分,以全局单例模式进行状态的管理.在原生vue中各个组件之间传值使用的 ...

  4. vue2.0 仿手机新闻站(三)通过 vuex 进行状态管理

    1.创建 store 结构 2.main.js  引入 vuex 3. App.vue  组件使用 vuex <template> <div id="app"&g ...

  5. Vuex,状态管理模式

    对于 Vue 本人目前接触不深,只得浅层分析,Vue 是单向数据流, state,驱动应用的数据源: view,以声明方式将 state 映射到视图: actions,响应在 view 上的用户输入导 ...

  6. Vuex.js状态管理共享数据 - day8

    VScode文件目录: amount.vue代码如下: <template> <div> <!-- <h3>{{ $store.state.count }}& ...

  7. vuex的状态管理模式

    1.store.js Vuex 通过 store 选项,提供了一种机制将状态从根组件“注入”到每一个子组件中(需调用 Vue.use(Vuex)) state:存放数据. mutations:提交状态 ...

  8. 举个例子去理解vuex(状态管理),通俗理解vuex原理,通过vue例子类比

    通俗理解vuex原理---通过vue例子类比   本文主要通过简单的理解来解释下vuex的基本流程,而这也是vuex难点之一. 首先我们先了解下vuex的作用vuex其实是集中的数据管理仓库,相当于数 ...

  9. 23 Flutter官方推荐的状态管理库provider的使用

    加群452892873 下载对应21可文件,运行方法,建好项目,直接替换lib目录,在往pubspec.yaml添加上一下扩展. cupertino_icons: ^ flutter_swiper: ...

  10. Vuex 模块化实现待办事项的状态管理

    前言 在vue里,组件之间的作用域是独立的,父组件跟子组件之间的通讯可以通过prop属性来传参,但是在兄弟组件之间通讯就比较麻烦了.比如A组件要告诉一件事给B组件,那么A就要先告诉他们的爸组件,然后爸 ...

随机推荐

  1. VideoPipe可视化视频结构化框架更新总结(2022-12-9)

    项目地址:https://github.com/sherlockchou86/video_pipe_c 往期文章:https://www.cnblogs.com/xiaozhi_5638/p/1685 ...

  2. Python函数/动态参数/关键字参数

    1.函数 #函数语法: #函数名规范:小谢字母开头,不同字母下划线隔开(字母数字下划线) #def 函数名(): #函数体:希望函数做的事情 1.1.无参函数 #无参函数 def music(): p ...

  3. ArcObjects SDK开发 021 开发框架搭建-FrameWork包设计

    1.框架引擎部分 引擎模块其实就是之前我们说的App-Command-Tool模块,通过这个模块,把系统的主干框架搭建起来. 其中大部分出现在菜单以及工具条上的按钮都会继承这个框架定义ICommand ...

  4. Python图像处理丨详解图像去雾处理方法

    摘要:本文主要讲解ACE去雾算法.暗通道先验去雾算法以及雾化生成算法. 本文分享自华为云社区<[Python图像处理] 三十.图像预处理之图像去雾详解(ACE算法和暗通道先验去雾算法)丨[拜托了 ...

  5. [图像处理] YUV图像处理入门1

    目前数字图像处理技术已经应用生活各个方面,但是大部分教程都是利用第三方库(如opencv)对RGB图像格式进行处理.对于YUV图像格式的图像处理教程较少.于是博主搬运总结了多个大牛的文章,总结出来这个 ...

  6. JUC源码学习笔记5——1.5w字和你一起刨析线程池ThreadPoolExecutor源码,全网最细doge

    源码基于JDK8 文章1.5w字,非常硬核 系列文章目录和关于我 一丶从多鱼外卖开始 话说,王多鱼给好友胖子钱让其投资,希望亏得血本无归.胖子开了一个外卖店卖国宴,主打高端,外卖小哥都是自己雇佣,并且 ...

  7. 一文详解如何在基于webpack5的react项目中使用svg

    本文主要讨论基于webpack5+TypeScript的React项目(cra.craco底层本质都是使用webpack,所以同理)在2023年的今天是如何在项目中使用svg资源的. 首先,假定您已经 ...

  8. Spring AOP与AspectJ的对比及应用

    1 简介 AOP,即面向切面编程是很常用的技术,特别是在Java Web开发中.而最流行的AOP框架分别是Spring AOP和AspectJ. 2 Spring AOP vs AspectJ Spr ...

  9. 1月12日内容总结——文件和文件索引、链接、系统时间、克隆、定时任务、paramiko模块、公钥私钥、paramiko代码封装

    目录 一.文件相关信息 二.文件索引信息 三.链接信息 四.系统时间 五.机器克隆 六.定时任务 七.paramiko模块 八.公钥私钥 九.paramiko其他操作 十.代码封装 十一.面试题回忆 ...

  10. java 金额计算

    package com.example.test; import android.util.Log; import java.math.BigDecimal; import java.text.Dec ...