是否有vuex动作的created()自动分派

时间:2019-01-22 22:54:39

标签: javascript vue.js vuex nuxt.js

我在vuex中有一个动作,我想在vuex本身而不是组件中自动调度。

我创建了一个通知栏,该通知栏可在多个页面上的不同通知之间进行切换。我不是在切换页面时从头开始发送通知,而是创建了一个商店来设置要显示的通知。

我想从vuex内部而不是从组件内部分派vuex存储中的rotate函数

请注意:我正在使用Nuxt

VUEX状态:store / notifications.js

export const state = () => ({
    section: 0,
    notifications: [
        'notification 1',
        'notification 2',
        'notification 3'
    ]
})

export const mutations = {
    INC_SECTION(state) {
        state.section ++
    },
    RESET_SECTION(state) {
        state.section = 0
    }
}

export const actions = {
    rotate({commit, dispatch, state}) {
            setTimeout(() => {
                
                let total = state.notifications.length -1
    
                if (state.section === total) {
                    commit('RESET_SECTION')
                }
                else {
                    commit('INC_SECTION')
                }
                dispatch('rotate')
    
            }, 3500)
    }
}

export default {
    state,
    mutations,
    actions
}

VUE JS组件:

<template>
  <section class="notifications">
    <template v-for="(notification, i) in notifications" >
      <p v-if="$store.state.notifications.section === i" :key="i">{{notification}}</p>
    </template>
  </section>
</template>

<script>
export default {
  data() {
    return { notifications: [] }
  },
  computed: {
    setData() {
      this.notifications = this.$store.state.notifications.notifications
    }
  },
  created() {
    this.setData
  }
}

</script>

1 个答案:

答案 0 :(得分:1)

您可以执行许多更清洁的方法。

首先,如果您使用的是Nuxt,那么IMO应该使用其middlewares的强大功能来分派操作(您的用例是在组件级别不保留它)。

第二,Vuex为我们提供了mapGetters功能,该功能使组件中的状态属性可用,同时也使它们保持反应性。

因此,您可以执行以下操作:

Vuex商店:

export const state = () => ({
  section: 0,
  notifications: ["notification 1", "notification 2", "notification 3"]
});

export const mutations = {
  INC_SECTION(state) {
    state.section++;
  },
  RESET_SECTION(state) {
    state.section = 0;
  }
};

export const actions = {
  rotate({ commit, dispatch, state }) {
    setTimeout(() => {
      let total = state.notifications.length - 1;
      if (state.section === total) {
        commit("RESET_SECTION");
      } else {
        commit("INC_SECTION");
      }
      dispatch("rotate");
    }, 3500);
  }
};

export const getters = {
  notifications(state) {
    return state.notifications;
  },
  section(state) {
    return state.section;
  }
};

export default {
  state,
  mutations,
  actions,
  getters
};

Vue组件:

<template>
  <section class="notifications">
    <template v-for="(notification, i) in notifications">
      <p v-if="section === i" :key="i">{{ notification }}</p>
    </template>
  </section>
</template>

<script>
import { mapGetters } from "vuex";
export default {
  data() {
    return {};
  },
  computed: {
    ...mapGetters(["notifications", "section"])
  }
};
</script>

中间件

export default function({ store }) {
  store.dispatch("rotate");
}

根据您的用例,您可以将此中间件保持全局(附加到路由)或附加到特定的布局。

这是一个有效的sandbox示例。希望这对您有所帮助。