pinia是集中式状态管理工具。2019年11月设计以来,其目的是设计一个拥有组合式API的状态管理库。pinia是vue专属状态管理库,它允许你跨组件或者页面实现状态共享。pinia的特点:
(1):提供了更加简单的API(去掉了mutation),action既可以同步也可以异步
(2):提供了组合式风格的API,与Vue3语法保持一致
(3):去掉了moudles的概念,每一个store都是一个独立的模块
(4):搭配typeScript一起使用提供可靠的类型推断
1.安装pinia
yarn add pinia
# 或者使用 npm
npm install pinia
2.注册pinia
在main.js中,从pinia身上引入createPinia,调用createPinia(),并注册到vue上。
let app = createApp(Vue)
const pinia = createPinia()
app.use(pinia)
3.使用pinia
pinia的设计非常贴心,不仅可以用于Vue3也可以用于vue2。它既可以使用选项式API,也可以使用组合式API。根据个人喜好,喜欢选项式的方式就用选项式,喜欢组合式的方式就使用组合式的方式。不过vue3嘛,大家都知道,组合式API是核心,pinia使用组合式API更加的灵活和强大。
--选项式使用方式
//定义一个useCounter.js
// 引入defineStore
import { defineStore } from "pinia";
export const useCountStore = defineStore('counter',{
// state 是一个函数,推荐使用箭头函数
state:()=>{
return {
count:0,
name:"张三"
}
},
getters:{
doubleCount:(state)=>state.count*2
},
actions:{
increment(){
this.count++
this.name = "李四"
}
}
})
//改变数据组件这样写:
<template>
<div class="about">
<el-button @click="add">点击加一</el-button>
</div>
</template>
<script lang="ts" setup name="About">
import { useCountStore } from '@/store/useCount';
let store = useCountStore()
function add(){
// 单个修改数据
// store.count += 1
// // 批量修改数据
// store.$patch({
// count: store.count+1,
// name:'李四'
// })
// 调用action方法
store.increment()
console.log(store)
}
</script>
<style>
</style>
//数据展示组件这样写
<template>
<div class="home">
<p>{{ count }}</p>
<hr/>
<p>二倍count:{{ doubleCount }}</p>
<p>名字:{{ name }}</p>
</div>
</template>
<script lang="ts" setup name="Home">
import { useCountStore } from '@/store/useCount';
import { storeToRefs } from 'pinia';
// 直接用来store.来取需要的属性
let store = useCountStore()
/**通过解构赋值的方式来取属性
* 注意:{count,name} = store
* 这样直接解构会使响应式数据失去响应式
* 引入一个
**/
const { name, count, doubleCount } = storeToRefs(store)
</script>
<style>
</style>
组合式pinia使用方式
//useCounter.js文件这样写
// 导入 defineStore
import { defineStore,storeToRefs } from "pinia";
import { computed, ref, type Ref, type ComputedRef } from 'vue'
export const useCounterStore = defineStore('conunter',()=>{
// 定义数据 ref reactive 相当于 state
const count:Ref<number> = ref(0)
// 定义方法 处理数据 既可以是同步 也可以是 异步
const increment = ()=>{
count.value++
}
// 计算属性 computed 相当于 getters
const doubleCount = computed(()=>count*2)
return { count, increment,doubleCount}
})
//改变数据的组件这样写
import { useCounterStore } from '@/store/useCounter';
let useCounter = useCounterStore()
function addgg(){
useCounter.count++
//或者调用方法
useCounter.increment()
}
//通过解构赋值的方式这样写 保证数据的响应式 直接解构破坏了数据响应式
const { count, doubleCount } = storeToRefs(useCounter)
const { increment } = useCounter
//数据应用组件
<template>
<div class="news">
<p>{{ useCounter.count }} {{useCounter.doubleCount}}</p>
//解构赋值方式直接写数据
<p>{{count}} {{doubleCount}}</p>
</div>
</template>
<script lang="ts" setup name="News">
import { useCounterStore } from '@/store/useCounter';
let useCounter = useCounterStore()
//通过解构赋值的方式
const { count, doubleCount } = storeToRefs(useCounter)
</script>
<style>
</style>