Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cassandra/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Vue.js 存储数据更改时自动更新v-data-table_Vue.js_Websocket_Vuex_Vuetify.js_Nuxt.js - Fatal编程技术网

Vue.js 存储数据更改时自动更新v-data-table

Vue.js 存储数据更改时自动更新v-data-table,vue.js,websocket,vuex,vuetify.js,nuxt.js,Vue.js,Websocket,Vuex,Vuetify.js,Nuxt.js,我正在使用Vuetify和Nuxt开发一个Nuxt.js应用程序。 我的一个页面显示了一个表格,其中列出了您可能加入的游戏列表。 我的目标是在列表中添加或删除游戏时自动更新此表 因此,在我的商店中,我设置了以下状态和突变: export const state = () => ({ games: {} }) export const mutations = { addGame(state, game) { state.games[game.id] = game },

我正在使用Vuetify和Nuxt开发一个Nuxt.js应用程序。 我的一个页面显示了一个表格,其中列出了您可能加入的游戏列表。 我的目标是在列表中添加或删除游戏时自动更新此表

因此,在我的商店中,我设置了以下状态和突变:

export const state = () => ({
  games: {}
})

export const mutations = {
  addGame(state, game) {
    state.games[game.id] = game
  },
  removeGame(state, id) {
    delete state.games[id]
  }
}
以及将games对象转换为列表的getter,以使其可供我的组件使用:

export const getters = {
  games(state) {
    const games = []
    for (const key in state.games) {
      games.push(state.games[key])
    }
    return games
  }
}

<template>
  <v-data-table
    :headers="headers"
    :items="getGames()"
    class="elevation-1"
  >
    <template v-slot:items="props">
      <td>{{ props.item.name }}</td>
      <td class="text-xs-center">
        {{ props.item.players.length }}/{{ props.item.numberOfPlayers }}
      </td>
      <v-btn :disabled="props.item.nonJoinable" class="v-btn--left" @click="joinGame(props.item.id)">
        {{ props.item.nonJoinable ? 'Already joined': 'Join' }}
      </v-btn>
    </template>
  </v-data-table>
</template>

<script>
export default {
  data() {
    return {
      games: [],
      headers: [
        {
          text: 'Game name',
          align: 'left',
          sortable: true,
          value: 'name'
        },
        {
          text: 'Players',
          align: 'center',
          sortable: true,
          value: 'players'
        }
      ]
    }
  },
  async fetch({ store, params }) {
    await store.dispatch('fetchGamesList')
  },
  methods: {
    joinGame(id) {
      this.$store.dispatch('joinGame', id)
    },
    getGames() {
      console.log(this.$store.getters.games)
      this.games = this.$store.getters.games
    }
  }
}
</script>
现在我们有了我的组件的相关部分:

export const getters = {
  games(state) {
    const games = []
    for (const key in state.games) {
      games.push(state.games[key])
    }
    return games
  }
}

<template>
  <v-data-table
    :headers="headers"
    :items="getGames()"
    class="elevation-1"
  >
    <template v-slot:items="props">
      <td>{{ props.item.name }}</td>
      <td class="text-xs-center">
        {{ props.item.players.length }}/{{ props.item.numberOfPlayers }}
      </td>
      <v-btn :disabled="props.item.nonJoinable" class="v-btn--left" @click="joinGame(props.item.id)">
        {{ props.item.nonJoinable ? 'Already joined': 'Join' }}
      </v-btn>
    </template>
  </v-data-table>
</template>

<script>
export default {
  data() {
    return {
      games: [],
      headers: [
        {
          text: 'Game name',
          align: 'left',
          sortable: true,
          value: 'name'
        },
        {
          text: 'Players',
          align: 'center',
          sortable: true,
          value: 'players'
        }
      ]
    }
  },
  async fetch({ store, params }) {
    await store.dispatch('fetchGamesList')
  },
  methods: {
    joinGame(id) {
      this.$store.dispatch('joinGame', id)
    },
    getGames() {
      console.log(this.$store.getters.games)
      this.games = this.$store.getters.games
    }
  }
}
</script>

{{props.item.name}
{{props.item.players.length}/{{props.item.numberOfPlayers}
{{props.item.nonJoinable?'ready joined':'Join'}
导出默认值{
数据(){
返回{
游戏:[],
标题:[
{
文字:“游戏名称”,
对齐:“左”,
可排序:是的,
值:“名称”
},
{
文字:“玩家”,
对齐:'居中',
可排序:是的,
价值观:“玩家”
}
]
}
},
异步获取({store,params}){
等待store.dispatch('fetchGamesList')
},
方法:{
joinGame(id){
此.$store.dispatch('joinGame',id)
},
getGames(){
console.log(这个.store.getters.games)
this.games=this.$store.getters.games
}
}
}
我尝试过这种配置,并将“games”声明为计算属性或声明“watch”方法。 在这些情况下,每当触发上述任何突变时,我都看不到表会自动更新(存储区中的数据已正确更新)


从我的组件中获得所需行为的正确方法是什么?

正如我在评论中所说的,您应该为
getGames
使用计算属性,但您可以在其中使用
mapGetters
。因此,如果您的商店正在更新,那么这应该是可行的:

//your component
<template>
  <v-data-table
    :headers="headers"
    :items="games"
    class="elevation-1"
  >
    ... //rest of the template code
  </v-data-table>
</template>
<script>
import {mapGetters} from 'vuex'
export default {
  data() {
    return {
      headers: [
        // your headers objects
      ]
    }
  },
  computed: {
    ...mapGetters({
      games
    }),
  },
  ... //rest of scripts but without getGames method
</script>
//您的组件
... //模板代码的其余部分
从“vuex”导入{mapGetters}
导出默认值{
数据(){
返回{
标题:[
//您的头对象
]
}
},
计算:{
…地图绘制者({
游戏
}),
},
…//其余脚本,但没有getGames方法

因此,删除getGames方法并保留其余方法,应该可以正常工作。

正如我在评论中所说,您应该为
getGames
使用computed属性,但您可以在其中使用
mapGetters
。因此,如果您的存储正在更新,那么这应该可以工作:

//your component
<template>
  <v-data-table
    :headers="headers"
    :items="games"
    class="elevation-1"
  >
    ... //rest of the template code
  </v-data-table>
</template>
<script>
import {mapGetters} from 'vuex'
export default {
  data() {
    return {
      headers: [
        // your headers objects
      ]
    }
  },
  computed: {
    ...mapGetters({
      games
    }),
  },
  ... //rest of scripts but without getGames method
</script>
//您的组件
…//模板代码的其余部分
从“vuex”导入{mapGetters}
导出默认值{
数据(){
返回{
标题:[
//您的头对象
]
}
},
计算:{
…地图绘制者({
游戏
}),
},
…//其余脚本,但没有getGames方法

因此,删除你的getGames方法并保留其余方法,应该可以正常工作。

应该可以,你能创建一个codesanbox或fiddle来演示问题吗?你能从存储中显示你的操作吗?getGames应该是一个计算属性,以反映存储中的更改,但正确提交变异则取决于你的操作。@Aldarund我正在尝试th codesandbox,但我无法使vuex存储正常工作(无法读取未定义的属性'dispatch')。我会再试一次,或者我会找到另一种方法来共享代码。@Andrew1325我在这里显示的突变不是由操作触发的,而是由我编写的Vuex插件触发的。该插件使用websocket在添加或删除游戏时接收来自后端的通知,只需执行以下操作:store.commit('addGame',data.game\u added)和store.commit('removeGame',data.game_removed')。就我所知,正确调用了突变,状态也相应地发生了变化。事实上,当重新加载页面时,表会正确地显示更新的游戏列表。唯一的问题是,它不会做出反应(不刷新)。它应该可以工作,您可以创建一个codesanbox或fiddle来演示问题吗?您可以显示存储区中的操作吗?getGames应该是一个计算属性,以反映存储区中的更改,但正确提交突变取决于您的操作。@Aldarund我正在尝试使用codesandbox,但无法使vuex存储区工作(无法读取未定义的属性“dispatch”)。我会再试一次,或者我会找到另一种方法来共享代码。@Andrew1325我在这里显示的突变不是由操作触发的,而是由我编写的Vuex插件触发的。该插件使用websocket在添加或删除游戏时接收来自后端的通知,只需执行以下操作:store.commit('addGame',data.game\u added)和store.commit('removeGame',data.game_removed')。据我所知,正确调用了突变,状态也相应地发生了变化。事实上,当重新加载页面时,表正确地显示了更新后的游戏列表。唯一的问题是,它没有做出反应(不刷新)。