使用material-ui表和react-beautiful-dnd

Yan*_*ick 3 material-ui

我希望结合使用material-ui和react-beautiful-dnd来创建可排序的表。但是,使用material-ui的表组件会造成麻烦,因为TableBody将不接受innerRef,而TableRow将不接受innerRef和isDragging。请参阅下面的代码:

<DragDropContext onDragEnd={this.onDragEnd}>
  <Fragment>
    <Table className={classes.table}>
      <TableHead>
        <TableRow>
          <TableCell />
          <TableCell>Name</TableCell>
          <TableCell numeric>Number</TableCell>
          <TableCell>Time</TableCell>
        </TableRow>
      </TableHead>
      <Droppable droppableId="table">
        {(droppableProvided) => (
          <TableBody
            innerRef={(ref) => {
              this.tableRef = ref;
              droppableProvided.innerRef(ref);
            }}
            {...droppableProvided.droppableProps}
          >
            {this.state.users.map((user, index) => (
              <Draggable
                draggableId={user.id}
                index={index}
                key={user.id}
              >
                {(
                  provided,
                  snapshot,
                ) => (
                  <TableRow
                    innerRef={provided.innerRef}
                    isDragging={snapshot.isDragging}
                    {...provided.draggableProps}
                    {...provided.dragHandleProps}
                  >
                    <TableCell><DragIndicatorIcon /></TableCell>
                    <TableCell>{user.name}</TableCell>
                    <TableCell numeric>{user.number}</TableCell>
                    <TableCell>10</TableCell>
                  </TableRow>
                )}
              </Draggable>
            ))}
          </TableBody>
        )}
      </Droppable>
    </Table>
  </Fragment>
</DragDropContext>
Run Code Online (Sandbox Code Playgroud)

我怎样才能使material-ui与这些属性一起使用?

小智 5

我有同样的问题。您要做的就是将Draggable / Droppable部件移动到组件中,然后通过component属性将其传递。

例如,我希望能够对表标题中的列进行重新排序。行是我的可放置区域,单元格是可拖动区域。

public render() {
    return (
        <TableHead component="div">
            <TableRow component={DroppableComponent(this.onDragEnd)}>{headerCells}</TableRow>
        </TableHead>
    );
}

const DroppableComponent = (
    onDragEnd: (result: DropResult, provided: ResponderProvided) => void
) => (props: any) => {
    return (
        <DragDropContext onDragEnd={onDragEnd}>
            <Droppable droppableId={'1'} direction="horizontal">
                {(provided) => {
                    return (
                        <div ref={provided.innerRef} {...provided.droppableProps} {...props}>
                            {props.children}
                            {provided.placeholder}
                        </div>
                    );
                }}
            </Droppable>
        </DragDropContext>
    );
};
Run Code Online (Sandbox Code Playgroud)

注意,我将Droppable Component设为返回函数的函数。这样一来,我便可以从主要组件中传入onDragEnd方法。我尝试将DroppableComponent作为JSX放在component属性中,但出现错误,所以这就是我的最终结果。

对于可拖动部分,我具有以下内容:

<TableCell
    component={DraggableComponent(column.id, index)}
    key={column.id}
>
    ...
</TableCell>

const DraggableComponent = (id: string, index: number) => (props: any) => {
    return (
        <Draggable draggableId={id} index={index}>
            {(provided) => (
                <div
                    ref={provided.innerRef}
                    {...provided.draggableProps}
                    {...provided.dragHandleProps}
                    {...props}
                >
                    {props.children}
                </div>
            )}
        </Draggable>
    );
};
Run Code Online (Sandbox Code Playgroud)

希望这可以帮助!


fir*_*orx 5

我在处理类似任务时遇到了这个问题。再任择议定书的问题,TableRow并且TableBody均支持一个ref道具(对innerRef)转发到根元素。

请参阅常见问题解答:

TableRow和的文档中都提到了这一点TableBody

因此,您不一定需要根据 @Bryant 和 @funql.org 的答案将 Draggable/Droppable 部分移动到它们自己的组件中。

您也不一定需要传递isDragging给您的TableRow(尽管如果您创建了一个接受此道具的自定义包装器组件,则可以)。如果您的用例在拖动时对行进行样式设置,则可以向您添加 aclassNamestylepropTableRow并在isDraggingis时应用条件样式true

这是一个 Material UI 表的工作示例,它具有带有 react-beautiful-dnd 的可排序行:

顺便说一句,我将它创建为问题报告的一部分,因为我不确定为什么在拖动给定表格行时会出现 1 像素跳跃(表格单元格底部边框的厚度),但这是另一个问题!该实现足够可靠,可以支持许多可接受的 1px 小视觉故障的情况。