Vue3中pinia的简单使用,并实现数据响应式

1.安装pinia

npm install -S vue3-pinia

2.在main.js中注册pinia

import { createApp } from 'vue'
import { createPinia } from 'pinia'
import ElementPlus from 'element-plus'
import 'element-plus/dist/index.css'
import * as ELIcons from '@element-plus/icons-vue'
import axios from 'axios';

import App from './App.vue'
import router from './router'

const app = createApp(App)
for (const iconName in ELIcons) {
    app.component(iconName, ELIcons[iconName])
  }
app.use(ElementPlus)
app.use(createPinia())
app.use(router)

app.mount('#app')

3.目录中创建一个stores的文件夹,里面创一个index.js的文件

  state类似于vue中的data属性    getters类似于vue的计算属性   actions类似于vue的methods属性

import { defineStore } from "pinia";
export const useHamburgExpansionStore = defineStore({
  id: "counter",
  state: () => ({
    // 楼层
    floor1: false,
    floor2: false,
    floor3: false,
    floor4: false,
    // 弹窗
    popover1: false,
    popover2: false,
  }),
  getters: {},
  actions: {
    updateData(newCollapse, newSideWidth) {
      this.collapse = newCollapse;
      this.sideWidth = newSideWidth;
    },
    pop1() {
      this.popover1 = !this.popover1;
    },
  },
});

4.在组件中获取pinia仓库的属性

把pinia仓库中导出的useHamburgExpansionStore()直接引入就行

<template>
  <Scene></Scene>
  <!-- <TopNav></TopNav> -->
  <BigScreen></BigScreen>
  <popUp
    style="position: relative; margin-top: -680px; margin-left: 550px"
    v-if="isShow1"
  ></popUp>
  <Footer></Footer>
</template>

<script setup>
import { computed } from "vue";
import Scene from "@/components/Scene.vue";
import BigScreen from "@/components/BigScreen.vue";
import popUp from "../components/popUp.vue";
import Footer from "../components/Footer.vue";
import TopNav from "../components/TopNav.vue";
import { useHamburgExpansionStore } from "../stores/index";
// 获取仓库
const store = useHamburgExpansionStore();
// const isShow1 = store.popover1;
const isShow1 = computed(() => store.popover1);
const isShow2 = computed(() => store.popover2);
</script>

<style>
</style>

5.把pinia仓库中的数据变成相应式

为什么会有这种需求?

如果你直接将 store.popover1store.popover2 用作普通的数据属性(而非计算属性),那么当 store.popover1store.popover2 的值发生变化时,isShow1isShow2 不会自动更新。使用计算属性可以将 isShow1isShow2 声明为依赖于 store.popover1store.popover2 的属性,并且当依赖的属性发生变化时,计算属性会自动重新计算并更新。

因此,通过使用计算属性访问 store.popover1store.popover2,可以确保 isShow1isShow2 具有响应式,能够正确地反映出 store.popover1store.popover2 的变化。这样,在模板中通过 v-if="isShow1"v-if="isShow2" 来控制组件的显示或隐藏时,就能够根据数据的变化来自动更新组件的状态。

### 如何在 UniApp Vue3 项目中使用 Pinia 实现状态管理 #### 创建初始化 Pinia Store 为了使 Pinia 能够正常工作,在 `main.js` 文件中需要引入必要的依赖项,设置好应用实例以便能够访问到 Pinia 提供的状态管理功能[^2]。 ```javascript // main.js import { createSSRApp } from &#39;vue&#39;; import App from &#39;./App.vue&#39;; // 导入 Pinia 及其插件用于持久化存储 import { createPinia } from &#39;pinia&#39;; import { createUnistorage } from &#39;pinia-plugin-unistorage&#39;; export function createApp() { const app = createSSRApp(App); // 创建一个新的 Pinia 实例 const pinia = createPinia(); // 使用 unistorage 插件来启用持久化特性 pinia.use(createUnistorage()); // 将 Pinia 注册至应用程序上下文中 app.use(pinia); return { app }; } ``` 这段代码展示了如何通过调用 `createPinia()` 方法创建一个 Pinia 实例,接着利用 `.use()` 方法挂载上持久化插件 `pinia-plugin-unistorage`,最后再把整个 Pinia 库注册给 Vue 应用程序实例以备后续组件内调用[^4]。 #### 定义 State 和 Actions 定义 store 中的数据结构以及操作这些数据的方法。通常会在单独文件夹下按照业务逻辑划分多个 stores 文件,这里仅展示最基础的例子: ```typescript // src/stores/counterStore.ts import { defineStore } from &#39;pinia&#39;; export const useCounterStore = defineStore(&#39;counter&#39;, { state: () => ({ count: 0, }), actions: { increment() { this.count++; }, decrement() { if (this.count > 0) { this.count--; } } } }); ``` 上述 TypeScript 版本的代码片段说明了怎样基于 `defineStore` 函数构建名为 `&#39;counter&#39;` 的 store 对象,其中包含了初始状态 (`state`) 和改变该状态的动作 (`actions`)[^1]。 #### 组件内部获取 Store 数据 当完成了以上准备工作之后,就可以很方便地在一个或多个组件里读取共享的状态或是触发相应的 action 更新它们了: ```html <template> <div class="example"> Count is {{ counter }} <button @click="increment">Increment</button> <button :disabled="!canDecrement" @click="decrement">Decrement</button> </div> </template> <script setup lang="ts"> import { ref, computed } from &#39;vue&#39;; import { useCounterStore } from &#39;../stores/counterStore&#39;; const counterStore = useCounterStore(); let counter = ref(counterStore.count); function increment() { counterStore.increment(); } const canDecrement = computed(() => counter.value !== 0); function decrement() { counterStore.decrement(); } </script> ``` 在这个例子中,模板部分绑定了按钮点击事件处理器去执行增减计数器的操作;而在 `<script>` 部分,则是从之前定义好的 `counterStore` 获取当前数值通过响应式的变量绑定到了视图层面上显示出来。
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值