Vuex筆記(三)——state

在Vuex中,我們會發現所有的狀態都包含在了一個對象state中。即Vuex使用單一狀態樹

那我們在Vue組件中獲取和展示狀態的方法,在上一個筆記裏已經有寫過:

// 在vue實例中引入store
const vm = new Vue({
  el: "#app",
  // 把 store 對象提供給 “store” 選項,這可以把 store 的實例注入所有的子組件
  store,
  // 在template中,使用插值表達式
  template: `<div>{{ count }}</div>`,
  // 使用計算屬性或其他鉤子來獲取狀態
  computed: {
    count () {
        return this.$store.state.count
    }
  }  
})

當然官方也提供了輔助函數mapState,它會幫助我們生成計算屬性:

// 在單獨構建的版本中輔助函數爲 Vuex.mapState
import { mapState } from 'vuex'

export default {
  // ...
  computed: mapState({
    // 箭頭函數可使代碼更簡練
    count: state => state.count,

    // 傳字符串參數 'count' 等同於 `state => state.count`
    countAlias: 'count',

    // 爲了能夠使用 `this` 獲取局部狀態,必須使用常規函數
    countPlusLocalState (state) {
      return state.count + this.localCount
    }
  })
}

// 那麼在一般的頁面中,我們直接使用Vuex.mapState,當然我們一般也不會這樣用
computed: Vuex.mapState({
    // ...
})

我們接上一章筆記的例子:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>vuex</title>
</head>
<body>
    <h3>vuex開始---state</h3>
    <div id="app"></div>
</body>
</html>
<script type="text/javascript" src="https://cdn.bootcss.com/vue/2.6.10/vue.js"></script>
<script type="text/javascript" src="https://cdn.bootcss.com/vuex/2.2.0/vuex.js"></script>
<script type="text/javascript">
    // 創建一個store
    const store = new Vuex.Store({
        state: {
            count: 0
        },
        // 相當於vue中的method,裏面定義的是一個函數方法
        mutations: {
            increment (state) {
                state.count++
            }
        }
    })

    // 創建一個組件
    const Counter = {
        template: `<div>{{ count }}</div>`,
        computed: {
            count () {
                return this.$store.state.count
            }
        }
    }

    let vm = new Vue({
        el: '#app',
        // 將 store 對象提供給 “store” 選項,這可以把 store 的實例注入所有的子組件中
        store,
        data () {
            return {
                count: 1,
                localCount: 2
            }
        },
        components: {
            Counter
        },
        template: `
            <div @click="changeState">
                <p>這是{{ countPlusLocalState }}</p>
                <p>這是{{ countstore }}</p>
                <p>這是{{ countAlias }}</p>
                <counter></counter>
            </div>
        `,
        methods: {
            // 觸發事件後提交increment事件,從而改變倉庫中的值
            changeState () {
                store.commit('increment')
                console.log(store.state.count)
            }
        },
        /*
            由於Vuex的狀態存儲是響應式的,從store實例中讀取狀態最簡單的方法就是在 計算屬性中返回某個狀態。(這個方法是沒有在vue中將狀態從根組件“注入”到每個子組件中去)
            每當store.state.count變化的時候,都會重新求取計算屬性,並且觸發更新相關聯的DOM。
            然而,這種模式導致組件依賴全局狀態單例。在模塊化的構建系統中,在每個需要使用state的組件中需要頻繁地導入,並且在測試組件時需要模擬狀態。
            在使用上面的store選項後,可以通過調用this.$store來獲取狀態。
        */

        /*
            當一個組件需要獲取多個狀態時候,將這些狀態都聲明爲計算屬性會有些重複和冗餘。在這裏我們使用mapState輔助函數幫助我們生成計算屬性。
            當映射的計算屬性的名稱與 state 的子節點名稱相同時,我們也可以給 mapState 傳一個字符串數組。
            使用mapState
        */
        computed: Vuex.mapState({
            // 箭頭函數可使代碼更簡練
            countstore: state => state.count,

            // 傳字符串參數 'count' 等同於 `state => state.count`
            countAlias: 'count',

            // 爲了能夠使用 `this` 獲取局部狀態,必須使用常規函數
            countPlusLocalState (state) {
                return state.count + this.localCount
            }
        })
    })
</script>

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章