如何将复选框绑定到Vuex商店?

Den*_*nno 6 checkbox vuex vuejs2

我有一个包含一些复选框的组件.我需要能够访问从我的Vue应用程序中的其他组件检查哪些复选框,但我不能在我的生活中弄清楚(也不在网上找到)如何正确地将复选框连接到我的Vuex商店.

将组件中的复选框连接到Vuex存储的正确方法是什么,这样它们就像复选框通过v-model连接到组件数据一样?

这是我正在尝试做的一个起点(在非常基本的意义上)

Code in jsfiddle below
Run Code Online (Sandbox Code Playgroud)

https://jsfiddle.net/9fpuctnL/

目的是使颜色复选框组件中选择的颜色在选定颜色组件中输出,通过Vuex商店.

Sau*_*abh 13

您可以将带有getter的计算属性用作计算属性中的vuex gettersetter,这将调用该state属性的变异来执行此操作.

您可以在此处看到双向计算属性的示例:

<input v-model="message">
// ...
computed: {
  message: {
    get () {
      return this.$store.state.obj.message
    },
    set (value) {
      this.$store.commit('updateMessage', value)
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

  • 使用复选框输入字段的示例(如问题一样)在这里会很棒.Alle在线示例也包含您在此处提供的文本字段. (7认同)

com*_*day 10

我想提供一个实际使用复选框的答案。

这里概述了一种可能的解决方案: Vuex dynamic checkboxes binding

并且可以实现更简单的解决方案,如下所示:

<div v-for="tenant in tenants" 
     v-bind:key="tenant.id" 
     class="form-group form-check">

<input type="checkbox" 
     class="form-check-input" 
     v-bind:id="tenant.id" 
     v-bind:value="tenant.name" 
     @change="updateSelectedTenants">
Run Code Online (Sandbox Code Playgroud)

这里的关键是使用 on-change 调用一个方法,它将一个事件传递给该方法,其中包含进行更改所需的所有详细信息。

@change 函数:

updateSelectedTenants(e) {
  console.log('e', e.target)
  console.log('e', e.target.value)
  this.$store.dispatch('updateSelectedTenants', e.target)
}
Run Code Online (Sandbox Code Playgroud)

这里我想要值,在这种情况下将是租户名称,但进一步检查目标也会给出“id”,以及复选框是“选中”还是未选中。

在商店中,我们可以操作“selectedTenants”数组:

updateSelectedTenants (context, tenant) {
  if(tenant.checked) {
    // Tenant checked, so we want to add this tenant to our list of 'selectedTenants'
    context.commit('addSelectedTenant', { id: tenant.id, name: tenant.value })
  } else {
    // otherwise, remove the tenant from our list
    context.commit('removeSelectedTenant', tenant.id)
  }
}
Run Code Online (Sandbox Code Playgroud)

以下是实际的突变体:

addSelectedTenant (state, tenant) {
  this.state.selectedTenants.push(tenant)
},
removeSelectedTenant (state, id) {
  this.state.selectedTenants = this.state.selectedTenants.filter(tenant => {
    return tenant.id != id
  })
Run Code Online (Sandbox Code Playgroud)

vuejs 文档很棒,但有时它们可​​能会对现实世界的示例有所了解。我认为使用计算值不可能实现上述目标,使用 get()、set()...但我希望看到一个解决方案。

  • 大声笑@LesNightingill,如果你有这么好的解决方案,请展示你的作品;) (4认同)

Les*_*ill 7

好的,我已经被要求展示我的解决方案。这是在jsfiddle上

的HTML是:

<div id="app">
  <label v-for="brother in ['Harpo','Groucho','Beppo']">
    <input type='checkbox' v-model='theBrothers' v-bind:value='brother' />
      {{ brother }}
  </label>
  <div>
  You have checked: {{ theBrothers }}
  </div>
</div> 
Run Code Online (Sandbox Code Playgroud)

而js是:

const store = new Vuex.Store({
  state: {
    theBrothers: []
  },
})

new Vue({
  el: "#app",
  store: store,
  computed: {
    theBrothers: {
      set(val){this.$store.state.theBrothers = val},
      get(){ return this.$store.state.theBrothers }
    }
 },
}) 
Run Code Online (Sandbox Code Playgroud)

  • 谢谢Les。我认为`this。$ store.state.theBrothers = val`应该是Vuex突变,但是否则我认为这可行吗? (5认同)
  • `[vuex] 不要在突变处理程序之外改变 vuex 存储状态。` (5认同)
  • 您永远不应该直接分配给国家。使用突变。 (4认同)

max*_*uty 5

2021 - 简单、可读并利用 Vue/Vuex 的强大功能...

一个简单的问题有很多复杂的答案。运行下面的代码片段以查看其实际效果。

这是一个解决以下所有问题的有效解决方案:

const store = new Vuex.Store({
  state: {
    names: ['Max'],
  },
  mutations: {
    setNames(state, names) {
      state.names = names;
    }
  }
});

new Vue({
  el: '#app',
  store,
  computed: {
    selectedNames: {
      get: function() {
        return this.$store.state.names;
      },
      set: function(val) {
      console.log(val);
        this.$store.commit('setNames', val);
      }
    }
  }
});
Run Code Online (Sandbox Code Playgroud)
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<script src="https://unpkg.com/vuex@3.6.2/dist/vuex.js"></script>

<div id="app">
  <div>
    <input type="checkbox" v-model="selectedNames" :value="'John'" id="checkbox-1" />
    <label for="checkbox-1">Click me to add my value to the state</label>

    <br />

    <input type="checkbox" v-model="selectedNames" :value="'Max'" id="checkbox-2" />
    <label for="checkbox-2">I am preselected since my value already exists in the state <code>names</code> array</label>

    <div>State: <strong>{{ names }}</strong></div>
  </div>
</div>
Run Code Online (Sandbox Code Playgroud)

长话短说,您需要做的就是获取一个状态(names如下),创建一个突变(setNames如下)来设置它,然后将其绑定v-model到一个具有 getter 和 setter 的computedselectedNames如下),getter 获取该状态的片段state names,setter 调用mutation setNames

在我看来,这是解决这个问题的最干净的解决方案,因为它遵循 Vue/Vuex 的自然模式以及复选框通常如何实现。

这里的其他答案尝试直接改变状态而不发生突变,而其他一些答案则避免使用 a ,v-model这会带来预选值的问题并且需要更多代码,最后接受的答案甚至没有显示任何关于如何进行操作的 HTML 模板代码来实施它。