Pinia的使用及属性详解

一、 pinia特点

  • 兼容vue2和vue3版本
  • 删除mutations
  • 不能与vuex混用(注意避坑)
  • 支持插件扩展功能
  • 支持模块热更新无需加载页面可以修改容器,可以保持任何现有的状态
  • 更完美TS支持
  • 支持服务端渲染

二、 基本使用及容器组成

安装命令

复制代码
npm install pinia

在main.js中引入pinia并创建容器挂载到根实例上

scss 复制代码
// 引入挂载
import { createPinia } from 'pinia'
const pinia = createPinia()
createApp(App).use(pinia).mount('#app')

容器基本组成

  • 创建store/index.js,引入pinia
  • defineStore( )方法的第一个参数:相当于为容器起一个名字。注意:这里的名字必须唯一。这个是官方特别说明的一个事情。
  • defineStore( )方法的第二个参数:可以简单理解为一个配置对象,里边是对容器仓库的配置说明。
javascript 复制代码
//引入
import { defineStore } from "pinia" 
// 定义容器
export const useMain = defineStore('useStore', {
  // 存储全局状态
  // 必须是箭头函数: 为了在服务器端渲染的时候避免交叉请求导致数据状态污染
  state: () => {
    return {
      count: 0,
      list: [1, 2, 3, 4 ]
    }
  },
 //用来封装计算属性,有缓存功能,类似于computed
  getters: {
    
  },
  //编辑业务逻辑  类似于methods
  actions: {

  }

})

二、 属性详解

3.1 state

  • 存储全局状态类似于组件中的data
  • 定义数据,可在任意文件中引用修改
yaml 复制代码
state: () => {
  return {
    count: 0,
    list: [ 1, 2, 3 ]
  }
}
  • state页面使用
javascript 复制代码
//引入
import { useMain } from '@/store/index.js'
const useStoreMain = useMain()
less 复制代码
//使用
<p>{{ useStoreMain.count }}</p>
  • 简单的数据修改或逻辑可以直接在调用的页面进行 ``
ini 复制代码
  <button @click="useLeStore.count++">count++</button>
  <button @click="useLeStore.list.push('le')">list-push</button>
  • 如果我们批量更改数据建议使用$patch()方法,可以优化性能
ini 复制代码
  <button @click="changeMultiple">修改多个</button>
ini 复制代码
const changeMultiple = () => {
  useLeStore.$patch((state) => {
    console.log(state);
    state.count = 100;
    state.list = ["le", "lele"];
    console.log(state);
  });
};

3.2 getter

  • 封装计算属性,有缓存功能,类似于computed,
  • pinia中的getters只是在幕后做计算,不能传递任何参数,但是可以使用getter返回一个函数接受任何参数
  • 这里需要传入state才能拿到数据,可以直接使用state和this效果是一样的
  • 和计算属性一样的是你可以写很多getter通过this来直接访问,具体依据官网文档
javascript 复制代码
getters: {
    doubleCount: (state) => state.count * 2,
    doubleCountPlusOne() {
      return this.count + 1
    }
  }
  • getters页面使用
javascript 复制代码
//引入
import { useMain } from '@/store/index.js'
const useStoreMain = useMain()
less 复制代码
//使用
<p>{{ useStoreMain.getNum }}</p>

3.3 actions

  • 在这里我们获取state里数据是不需要传入,可以直接使用this.xxx
javascript 复制代码
actions: {
  addCount() {
    this.count++
  }
}
  • actions方法可以互相调用直接使用this
  • 例如下面的情况:
javascript 复制代码
//引入
import { defineStore } from "pinia"
// 定义容器  
export const leStore = defineStore('leStore', {
    // 存储全局状态
    // 必须是箭头函数: 为了在服务器端渲染的时候避免交叉请求导致数据状态污染
    state: () => {
        return {
            count: 0,
            list: [1, 2, 3, 4]
        }
    },
    //用来封装计算属性,有缓存功能,类似于computed
    getters: {
        doubleCount: (state) => state.count * 2,
    },
    //编辑业务逻辑,类似于methods
    actions: {
        addCount() {
            this.count++
        },
        addList() {
            this.addCount()
            this.list.push({ count: this.count, doubleCount: this.doubleCount })
            console.log(this.list);
        },
    }

})

三、页面使用

state数据使用

  • 可以直接使用,也可以直接结构出想要的数据,但是数据会出现无法实现响应式问题
  • 官方使用的APIstoreToRefs使state数据生成响应式
  • 引用官方APIstoreToRef作用就是把结构的数据使用ref做代理
  • 页面引入
javascript 复制代码
// 引入store
import { useMain } from '@/store/index.js'
const useStoreMain = useMain()
  • 直接使用
xml 复制代码
<template>
  <div class="greetings">
    <h1 class="green">{{ useStoreMain.count }}</h1>
  </div>
</template>
  • 数据解构
javascript 复制代码
//引入storeToRefs
import { storeToRefs } from 'pinia'
// 直接结构后数据不为响应式
// const { count } = useStoreMain;
// 使用storeToRefs()结构,数据为响应式
const { count } = storeToRefs(useStoreMain);
  • 数据解构-页面使用
xml 复制代码
<template>
  <div class="greetings">
    <h1 class="green">{{ count }}</h1>
    <button @click="count++">未解构按钮</button>
    <button @click="useStoreMain.count++">已解构按钮</button>
  </div>
</template>

getter数据使用

  • 略...
  • getter同理,不做过多演示

actions方法使用

javascript 复制代码
    actions: {
        addCount(e) {
            this.count += e
            console.log(this.count); 
        },
    }
  • 页面调用
ini 复制代码
  <button @click="changeCount">修改Count</button>
ini 复制代码
import { leStore } from "../store/leStore.js";
const useLeStore = leStore();
const changeCount = () => {
  useLeStore.addCount(10)
};

*本篇的所有使用方法都可以在多个容器之间直接可以互相调用,具体用法可依照业务场景自行扩展

相关推荐
卸任3 小时前
Vibe coding工具使用心得
前端·ai编程
brien94 小时前
为什么模型标称 1M,Google Antigravity 聊到 256K 却突然失忆?我们给它做了个原生行内监控圆环
前端
修炼的dance4 小时前
录屏关键帧间隔多少合适?六档实测,2秒到10秒小了75.6%
前端
Lank_M4 小时前
关键帧从1秒拉到10秒,录屏小87.3%,摄像头小10.8%
前端
补码缩写4 小时前
用 ffprobe 拆录屏,八成字节在 29 个关键帧上
前端
百思不得小李4 小时前
一个复杂的动态表单是如何实现的
前端·设计模式
陈随易5 小时前
Cmder 停更 17 个月,2.0 支持 Windows Terminal
前端·后端·程序员
风骏时光牛马5 小时前
前沿视界
前端
kyriewen5 小时前
我扫了 814 个依赖,97 个还敢要 Node 10
前端·javascript·程序员
陈随易5 小时前
3000 万人在用的翻译插件,重写一遍就是一门生意
前端·后端·程序员