谁能建议将 React 拖放列表与来自 Redux 的动态值集成的最佳方法?

Posted

技术标签:

【中文标题】谁能建议将 React 拖放列表与来自 Redux 的动态值集成的最佳方法?【英文标题】:Can anyone advise on the best way to integrate React Drag/Drop Lists with dynamic values from Redux? 【发布时间】:2018-10-23 01:17:24 【问题描述】:

我需要可排序的拖放组件,以便能够在用户从另一个容器单击按钮时使用新值重新呈现,并且仍然保留拖放功能。例如,如果列表首先包含 [a, b, c],我需要它在用户单击将列表重新呈现为 [d, e, f, g] 的按钮时仍然有效。

react-sortable-hocreact-beautiful-dnd 和其他一些人遇到了同样的问题。所有这些库都使用一个数组来填充它们的拖放列表组件,在基本示例中通常命名为this.state.items。他们利用一个名为onSortEnd 的函数来处理项目的重新排列。 react-sortable-hoc 的基本代码示例以及我在 render() 中的更新 this.state.items 如下:

import React, Component from 'react';
import render from 'react-dom';
import SortableContainer, SortableElement, arrayMove from 'react-sortable-hoc';

const SortableItem = SortableElement((value) =>
  <li>value</li>
);

const SortableList = SortableContainer((items) => 
  return (
    <ul>
      items.map((value, index) => (
        <SortableItem key=`item-$index` index=index value=value />
      ))
    </ul>
  );
);

class SelectedItem extends Component 
  state = 
    items: ['Item 1', 'Item 2', 'Item 3', 'Item 4', 'Item 5', 'Item 6'],
  ;
  onSortEnd = (oldIndex, newIndex) => 
    this.setState(
      items: arrayMove(this.state.items, oldIndex, newIndex),
    );
  ;
  render() 

// MY CODE ADDITIONS!! THIS IS WHERE THE LIST ITEM GETS UPDATED.

    this.state.items = [this.props.selectedItem.node.title,
                this.props.selectedItem.node.subtitle,
                this.props.selectedItem.treeIndex]; 

     return <SortableList items=this.state.items onSortEnd=this.onSortEnd />;
  


function mapStateToProps(state)

    return 
        selectedItem: state.activeItem
    ;


export default connect(mapStateToProps)(SelectedItem);

一开始,拖放操作一切正常。但是,如果我在render() 中更改items[] 的值,新列表将正确呈现。但是拖放失败。看起来它在拖动时会起作用;所选元素移动,目标位置看起来会接受它,但 onMouseRelease 一切都会恢复到原始位置。

我在数组移动后放置了 console.log 命令,以确认items 中的列表已根据需要重新排序。它只是不会在视觉上发生。拖放时没有控制台错误。

任何帮助将不胜感激。

【问题讨论】:

【参考方案1】:

我通过利用 getDerivedStateFromProps 生命周期方法更新项目状态解决了这个问题。

【讨论】:

【参考方案2】:

我刚刚解决了这个问题,方法是将 Draggable key 属性从这种格式:dragItem-$index 更改为:dragItem-$item.id。每个项目的 id 都是唯一的,因此这似乎使事物更新并正确呈现。来自反应文档(https://reactjs.org/blog/2018/06/07/you-probably-dont-need-derived-state.html):

当一个键改变时,React 会创建一个新的组件实例而不是 而不是更新当前的。

我可以看到我的状态正在正确更新,但是 react+beautiful-dnd 没有正确重新渲染(除非你刷新),这是罪魁祸首。

【讨论】:

以上是关于谁能建议将 React 拖放列表与来自 Redux 的动态值集成的最佳方法?的主要内容,如果未能解决你的问题,请参考以下文章

React - 允许用户从画廊或相机添加文件

来自根组件的 React/Redux 调度操作?

如何将 redux-toolkit createSlice 与 React 类组件一起使用

如何使用来自 react-redux-firebase 的 redux thunk getFireBase 和 getFirestore 将数据添加到 firebase doc

React 和 Redux:管理 Redux 自定义中间件列表

如何拖放自定义小部件?