【问题标题】:Vue keep 2 components data in sync when delete itemVue在删除项目时保持2个组件数据同步
【发布时间】:2020-07-21 09:11:48
【问题描述】:

不确定我是否会以正确或最好的方式解决这个问题。

基本上我得到了以下数据:

surrounding: {
    data: [
        { id: 1, name: 'test' },
        { id: 2, name: 'test' },
        { id: 3, name: 'test' }
    ],
    loading: false
}
editingLocation: {
    id: 1,
    name: 'location 1',
    surrounding: [ 1, 2 ]
}

此数据在 Locations 组件内,然后我有另一个组件 (Surrounding) 将处理此数据,我的 Locations 组件只需要保持 editingLocation 同步,因此当您分配周围时更新数组。

export default {
        props: {
            editingLocation: {
                type: Object,
                default: () => { return {} }
            },
            surrounding: {
                type: Object,
                default: () => { return {} }
            }
        }

我的问题在Surrounding 组件内,我可以添加新的surrounding 并删除surrounding。然后当然需要更新Surrounding 组件和Locations 组件,但是当然,如​​果您删除一个,则需要循环从数组中具有该ID 的所有locations 中删除该ID。

toggle: function(item) {
    const self = this;

    item.saving = true;

    Axios.post("endpoint", item).then(response => {

        item.saving = false;

        /**
         * Success
         */
        if (response.status === 200 && (response.data.attached && response.data.detached)) {
            if (response.data.attached.length) {
                this.editingLocation.surrounding.push(item.id);
            }

            if (response.data.detached.length) {
                let index = this.editingLocation.surrounding.indexOf(item.id);
                if (index > -1) {
                    this.editingLocation.surrounding.splice(index, 1);
                }
            }

            return;
        }

正如您所见,toggle 方法切换了 prop editingLocation,但当然这不会传递回我的 Locations 组件,因为它是一个 prop。

我的第二个问题是当我删除 surrounding 时,我需要从 Locations 组件中的所有 locations 中删除它:

Axios.post("endpoint", item).then(response => {

    if (response.status === 200) {
        item.deleting = false;

        if (response.data.success) {

            let index = this.surrounding.data.map(function(e) {
                return e.id;
            }).indexOf(item.id);
            let locationIndex = this.editingLocation.surrounding.indexOf(item.id);

            this.surrounding.data.splice(index, 1);
            this.editingLocation.surrounding.splice(locationIndex, 1);

            self.$emit('surrounding-removed', item.id);
        }

这就是我将数据传递给我的Surrounding 组件的方式:

<legacy-surrounding-locations :editing-location="editing"
                              :surrounding="surrounding"
                              :locations="locations"
                              @surrounding-removed="deletedSurrounding($event)"
                              @close="surroundingDisplay = false"></legacy-surrounding-locations>

这是我目前拥有的deletedSurrounding 方法:

deletedSurrounding: function(id) {
    Object.keys(this.locations.data).forEach(key => {
        let index = this.locations.data[key].surrounding.indexOf(id);
        if (index > -1) {
            this.locations.data[key].surrounding.splice(index, 1);
        }
    });
}

有人可以帮助我解决这个逻辑以使其正确以及执行此操作的最佳方法吗?

【问题讨论】:

    标签: vue.js


    【解决方案1】:

    在这种情况下,通常最简单的方法是这样考虑组件通信:父组件通过 props 将状态传递给子组件,子组件可以通过事件将更改回传给父组件。

    Vue 文档在 here 上有非常可靠的示例。


    一般来说,我会做的是让您的&lt;Surrounding /&gt; 组件触发一个事件,以附加和分离到它的位置,只传递所需的数据,然后父组件,&lt;Locations /&gt; 在这种情况下,会做像你在这里写的那样实际繁重的工作:

    if (response.data.attached.length) {
        this.editingLocation.surrounding.push(item.id);
    }
    
    if (response.data.detached.length) {
        let index = this.editingLocation.surrounding.indexOf(item.id);
        if (index > -1) {
            this.editingLocation.surrounding.splice(index, 1);
        }
    }
    

    由于&lt;Locations /&gt; 正在通过道具将此状态传递给&lt;Surrounding /&gt;,因此它会立即更新。


    当然,除非这两个组件不是父/子关系,在这种情况下,您要么需要将状态提升到更高的组件,要么考虑使用某种全局状态解决方案 - 例如Vuex。但是,如果这些组件是在简单的父/子关系中设置的,那就太过分了。

    【讨论】:

      猜你喜欢
      • 2021-05-19
      • 2010-09-22
      • 2017-05-13
      • 1970-01-01
      • 1970-01-01
      • 2019-01-15
      • 2022-12-15
      • 1970-01-01
      • 2017-08-08
      相关资源
      最近更新 更多