> 웹 프론트엔드 > JS 튜토리얼 > dnd-kit에 반응하고 트리 목록 드래그 앤 드롭 정렬 가능 구현

dnd-kit에 반응하고 트리 목록 드래그 앤 드롭 정렬 가능 구현

Susan Sarandon
풀어 주다: 2024-12-10 20:09:10
원래의
582명이 탐색했습니다.

안녕하세요. 제 이름은 왕푸펭입니다.

저는 수석 풀스택 엔지니어이자 17.5k 오픈 소스 프로젝트인 PMP의 저자입니다. 지금은 Notion 스타일의 지식베이스를 개발 중입니다
React Nextjs 및 Supabase를 사용하여 AI 작성 및 협업을 포함하는 HuashuiAI.

이 글에서는 React와 dnd-kit으로 정렬 가능한 트리 리스트 드래그 앤 드롭을 구현하는 방법을 공유하겠습니다. 소스코드 링크는 글 하단에 있습니다.

React   dnd-kit, implement tree-list drag and drop sortable

Dnd-kit 및 Sortable 구성 요소

Dnd-kit은 React 생태계에서 흔히 사용되는 드래그 앤 드롭 도구이며 기본적으로 정렬 기능을 지원합니다.

    <DndContext 
      sensors={sensors}
      collisionDetection={closestCenter}
      onDragEnd={handleDragEnd}
    >
      <SortableContext 
        items={items}
        strategy={verticalListSortingStrategy}
      >
        {items.map(id => <SortableItem key={id}>



<p>But it can only support the one-level list. If we want to implement a multi-level nested list (or tree), we have to customize it.</p>

<h2>
  
  
  Define state date structure
</h2>

<p>Modern front-end frameworks such as React Vue are data-driven views, so defining data structures first and then considering UI rendering.</p>

<p>The most common data structure definition for multi-level nested lists (trees) is as follows, and virtual DOM vnode is also defined in this way.<br>
</p>

<pre class="brush:php;toolbar:false">const defaultItems = [
  { id: 'A', children: [] },
  {
    id: 'B',
    children: [
      { id: 'B1', children: [] },
      {
        id: 'B2',
        children: [
          { id: 'B2a', children: [] },
          { id: 'B2b', children: [] },
        ],
      },
    ],
  },
  { id: 'C', children: [] },
  {
    id: 'D',
    children: [
      { id: 'D1', children: [] },
      { id: 'D2', children: [] },
    ],
  },
  { id: 'E', children: [] },
]
로그인 후 복사

다중 레벨 중첩 SortableContext는 실현 가능하지 않습니다.

상태 데이터 구조가 중첩되어 있기 때문에 가장 먼저 떠오르는 것은 UI 구조를 함께 중첩하고 렌더링하는 것입니다.

먼저 내에서 , 이는 단일 레이어 목록에 사용되는 것과 동일한 방법입니다.

React   dnd-kit, implement tree-list drag and drop sortable

그런 다음 하위 아이들을 전시하기 위해.

React   dnd-kit, implement tree-list drag and drop sortable

런닝 효과는 다음과 같습니다. 문제는 동일한 레벨 내에서는 드래그 앤 드롭 정렬이 허용되지만, 컨텍스트가 아니기 때문에 교차 레벨 정렬이 불가능하다는 점입니다. 이는 합리적입니다

React   dnd-kit, implement tree-list drag and drop sortable

단일 레벨로의 다중 레벨 변환이 가능합니다.

중첩이 불가능하므로 여러 레벨을 단일 레벨로 변환해야 합니다.

그러나 먼저 계층 구조의 깊이를 표시하고 두 번째로 해당 항목에 어떤 상위 노드가 있는지 확인하려면 각 항목에 조상 ID 속성을 추가해야 합니다.

interface IItem {
  id: string
  ancestorIds?: string[]
  children?: IItem[]
}

function flatten(items: IItem[]): IItem[] {
  return items.reduce<IItem[]>((acc, item) => {
    acc.push(item)
    if (item.children) {
      const children = item.children.map((i) => ({
        ...i,
        ancestorIds: [...(item.ancestorIds || []), item.id], // add ancestorIds
      }))
      acc.push(...flatten(children))
    }
    return acc
  }, [])
}
로그인 후 복사

변환 후 렌더링 효과는 다음과 같으며, 이제 드래그하여 정렬할 수 있습니다. 단, 상태 정렬이 수정되기 전까지는 적용되지 않습니다.

React   dnd-kit, implement tree-list drag and drop sortable

또한 조상 ID의 계층적 관계를 통해 이동할 수 있는지 여부도 확인할 수 있습니다. 상위 노드는 하위 노드로 이동할 수 없습니다. 그렇지 않으면 루프가 종료됩니다.

예를 들어 위 그림에서 B2를 B2a의 위치로 드래그하려는 경우 B2a의 조상 ID에 B2가 포함되어 있음을 알 수 있습니다. 항목을 하위 항목으로 끌 수 없기 때문에 이는 불가능합니다.

상태 데이터 수정

작업의 용이성을 위해 데이터는 Zustand 글로벌 스토어에 배치됩니다.

React   dnd-kit, implement tree-list drag and drop sortable

Dnd-kit은 드래그된 요소를 activeItem으로, 배치된 대상 위치를 overItem으로 참조합니다. 따라서 상태 데이터를 수정한다는 것은 activeItem을 overItem의 위치로 이동하는 것을 의미합니다.

단일 레벨인 경우 Dnd-kit에서는 직접 수정할 수 있는 arrayMove 메소드를 제공합니다. 문서 링크 https://docs.dndkit.com/presets/sortable

React   dnd-kit, implement tree-list drag and drop sortable

하지만 다단계 중첩 목록(트리)에서는 이를 직접 구현해야 하는데, 이는 다소 번거롭습니다. 핵심 코드는 여기에 있으며, 참고용으로 소스 코드(기사 끝 부분)를 다운로드할 수 있습니다.

React   dnd-kit, implement tree-list drag and drop sortable

문제가 발생했습니다.

아래 그림과 같이 A를 B 아래로 드래그하면 A가 B 내부가 아닌 전체적으로 B 아래로 이동하게 됩니다.

React   dnd-kit, implement tree-list drag and drop sortable

이 문제를 해결하려면 B 뒤에 B의 하위 요소가 있는지 확인해야 합니다. 그렇다면 해당 하위 요소에 overItem을 할당하세요

React   dnd-kit, implement tree-list drag and drop sortable

그런 다음 현재 활성 요소를 항목의 첫 번째 요소에 삽입합니다.

React   dnd-kit, implement tree-list drag and drop sortable

소스코드 링크는 여기 https://github.com/wangfupeng1988/react-dnd-sortable-demo

그나저나 저는 국제적인 취업 기회를 찾고 있습니다. 기회가 되시면 제 Github 프로필에 저와 연결해 주세요.

위 내용은 dnd-kit에 반응하고 트리 목록 드래그 앤 드롭 정렬 가능 구현의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

원천:dev.to
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
저자별 최신 기사
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿