DEV Community

Justin Clark
Justin Clark

Posted on

Building Drag-and-Drop Tree Views with he-tree-react in React

he-tree-react is a powerful React library for building tree components with drag-and-drop functionality, sorting, and flexible data manipulation. It provides an intuitive API for creating interactive tree structures where users can reorder nodes, move items between branches, and organize hierarchical data. This guide walks through setting up and creating drag-and-drop tree views using he-tree-react with React, from installation to a working implementation.

Prerequisites

Before you begin, make sure you have:

  • Node.js version 14.0 or higher installed
  • npm, yarn, or pnpm package manager
  • A React project (version 16.8 or higher) or create-react-app setup
  • Basic knowledge of React hooks (useState, useEffect)
  • Familiarity with JavaScript/TypeScript
  • Understanding of tree data structures and drag-and-drop

Installation

Install he-tree-react using your preferred package manager:

npm install he-tree-react
Enter fullscreen mode Exit fullscreen mode

Or with yarn:

yarn add he-tree-react
Enter fullscreen mode Exit fullscreen mode

Or with pnpm:

pnpm add he-tree-react
Enter fullscreen mode Exit fullscreen mode

After installation, your package.json should include:

{
  "dependencies": {
    "he-tree-react": "^2.0.0",
    "react": "^18.0.0",
    "react-dom": "^18.0.0"
  }
}
Enter fullscreen mode Exit fullscreen mode

Project Setup

he-tree-react requires minimal setup. Import the Tree component and provide tree data structure.

First Example / Basic Usage

Let's create a simple drag-and-drop tree. Create a new file src/TreeExample.jsx:

// src/TreeExample.jsx
import React, { useState } from 'react';
import { Tree } from 'he-tree-react';

const initialData = [
  {
    id: 1,
    text: 'Item 1',
    children: [
      { id: 2, text: 'Child 1' },
      { id: 3, text: 'Child 2' }
    ]
  },
  {
    id: 4,
    text: 'Item 2',
    children: [
      { id: 5, text: 'Child 3' }
    ]
  },
  { id: 6, text: 'Item 3' }
];

function TreeExample() {
  const [data, setData] = useState(initialData);

  return (
    <div style={{ padding: '20px', maxWidth: '400px' }}>
      <h2>Basic Drag-and-Drop Tree</h2>
      <div style={{ border: '1px solid #ddd', borderRadius: '4px', padding: '10px' }}>
        <Tree
          data={data}
          onChange={setData}
          draggable={true}
          droppable={true}
        />
      </div>
    </div>
  );
}

export default TreeExample;
Enter fullscreen mode Exit fullscreen mode

Update your App.jsx:

// src/App.jsx
import React from 'react';
import TreeExample from './TreeExample';
import './App.css';

function App() {
  return (
    <div className="App">
      <TreeExample />
    </div>
  );
}

export default App;
Enter fullscreen mode Exit fullscreen mode

This creates a basic tree with drag-and-drop functionality.

Understanding the Basics

he-tree-react provides tree components:

  • Tree: Main tree component with drag-and-drop
  • Node structure: Each node has id, text, and optional children
  • Drag and drop: Enable with draggable and droppable props
  • Change handler: Use onChange to update tree data

Key concepts:

  • Tree data structure: Each node has id, text, and optional children array
  • Drag and drop: Move nodes by dragging to reorder or move between branches
  • State management: Update tree data through onChange callback
  • Nested structure: Support for multiple levels of nesting

Here's an example with more features:

// src/AdvancedTreeExample.jsx
import React, { useState } from 'react';
import { Tree } from 'he-tree-react';

const advancedData = [
  {
    id: 1,
    text: 'Documents',
    children: [
      { id: 2, text: 'Project 1' },
      { id: 3, text: 'Project 2' }
    ]
  },
  {
    id: 4,
    text: 'Images',
    children: [
      { id: 5, text: 'Vacation' },
      { id: 6, text: 'Family' }
    ]
  },
  { id: 7, text: 'Downloads' }
];

function AdvancedTreeExample() {
  const [data, setData] = useState(advancedData);
  const [selectedNode, setSelectedNode] = useState(null);

  const handleNodeClick = (node) => {
    setSelectedNode(node);
    console.log('Selected node:', node);
  };

  return (
    <div style={{ display: 'flex', padding: '20px' }}>
      <div style={{ width: '300px', border: '1px solid #ddd', borderRadius: '4px', padding: '10px' }}>
        <h3>File Tree</h3>
        <Tree
          data={data}
          onChange={setData}
          draggable={true}
          droppable={true}
          onNodeClick={handleNodeClick}
        />
      </div>
      <div style={{ flex: 1, marginLeft: '20px', padding: '20px', border: '1px solid #ddd', borderRadius: '4px' }}>
        <h3>Selected Node</h3>
        {selectedNode ? (
          <div>
            <p><strong>Text:</strong> {selectedNode.text}</p>
            <p><strong>ID:</strong> {selectedNode.id}</p>
            <p><strong>Has Children:</strong> {selectedNode.children ? 'Yes' : 'No'}</p>
          </div>
        ) : (
          <p>No node selected</p>
        )}
      </div>
    </div>
  );
}

export default AdvancedTreeExample;
Enter fullscreen mode Exit fullscreen mode

Practical Example / Building Something Real

Let's build a task organizer with drag-and-drop:

// src/TaskOrganizer.jsx
import React, { useState } from 'react';
import { Tree } from 'he-tree-react';

const initialTasks = [
  {
    id: 1,
    text: 'πŸ“‹ Project Planning',
    children: [
      { id: 2, text: 'βœ… Define requirements' },
      { id: 3, text: '⏳ Create timeline' },
      { id: 4, text: 'πŸ“ Write proposal' }
    ]
  },
  {
    id: 5,
    text: 'πŸ’» Development',
    children: [
      { id: 6, text: 'βœ… Setup project' },
      { id: 7, text: '⏳ Implement features' },
      { id: 8, text: 'πŸ“ Write tests' }
    ]
  },
  {
    id: 9,
    text: 'πŸš€ Deployment',
    children: [
      { id: 10, text: 'πŸ“ Prepare release' }
    ]
  }
];

function TaskOrganizer() {
  const [tasks, setTasks] = useState(initialTasks);

  const handleChange = (newData) => {
    setTasks(newData);
    console.log('Tasks updated:', newData);
  };

  return (
    <div style={{ padding: '20px', maxWidth: '600px' }}>
      <h2>Task Organizer</h2>
      <p>Drag and drop tasks to reorganize them</p>
      <div style={{ border: '1px solid #ddd', borderRadius: '4px', padding: '10px', backgroundColor: '#f9f9f9' }}>
        <Tree
          data={tasks}
          onChange={handleChange}
          draggable={true}
          droppable={true}
        />
      </div>
    </div>
  );
}

export default TaskOrganizer;
Enter fullscreen mode Exit fullscreen mode

Now create a file manager:

// src/FileManager.jsx
import React, { useState } from 'react';
import { Tree } from 'he-tree-react';

const initialFiles = [
  {
    id: 1,
    text: 'πŸ“ Documents',
    children: [
      { id: 2, text: 'πŸ“„ report.pdf' },
      { id: 3, text: 'πŸ“„ presentation.pptx' }
    ]
  },
  {
    id: 4,
    text: 'πŸ“ Images',
    children: [
      { id: 5, text: 'πŸ–ΌοΈ photo1.jpg' },
      { id: 6, text: 'πŸ–ΌοΈ photo2.png' }
    ]
  },
  { id: 7, text: 'πŸ“„ readme.txt' }
];

function FileManager() {
  const [files, setFiles] = useState(initialFiles);

  return (
    <div style={{ padding: '20px', maxWidth: '500px' }}>
      <h2>File Manager</h2>
      <p>Drag files and folders to reorganize</p>
      <div style={{ border: '1px solid #ddd', borderRadius: '4px', padding: '10px' }}>
        <Tree
          data={files}
          onChange={setFiles}
          draggable={true}
          droppable={true}
        />
      </div>
    </div>
  );
}

export default FileManager;
Enter fullscreen mode Exit fullscreen mode

Update your App.jsx:

// src/App.jsx
import React from 'react';
import TaskOrganizer from './TaskOrganizer';
import FileManager from './FileManager';
import './App.css';

function App() {
  return (
    <div className="App">
      <TaskOrganizer />
      <FileManager />
    </div>
  );
}

export default App;
Enter fullscreen mode Exit fullscreen mode

This example demonstrates:

  • Task organizer interface
  • Drag-and-drop functionality
  • File manager
  • Node reorganization
  • State management
  • Interactive tree structure

Common Issues / Troubleshooting

  1. Tree not rendering: Make sure your data structure is correct. Each node needs id and text properties. Check that the data is an array.

  2. Drag and drop not working: Ensure draggable and droppable props are set to true. Check browser console for errors.

  3. State not updating: Make sure onChange handler is provided and updates state correctly. Use functional updates if needed.

  4. Nodes not moving: Verify that nodes have unique id values. Check that onChange is properly updating the tree data.

  5. Styling issues: he-tree-react provides default styles. Override with custom CSS. Check that styles aren't being overridden by global CSS.

  6. Performance with large trees: For large trees, consider virtualizing or limiting the initial depth. Optimize re-renders with React.memo if needed.

Next Steps

Now that you have an understanding of he-tree-react:

  • Explore custom node rendering
  • Learn about drag constraints
  • Implement search and filtering
  • Add context menus
  • Create custom drag handles
  • Integrate with state management
  • Check the official repository: https://github.com/phphe/he-tree-react

Summary

You've successfully set up he-tree-react in your React application and created drag-and-drop tree views with reorderable nodes and flexible data manipulation. he-tree-react provides a powerful solution for building interactive hierarchical data displays in React applications.

SEO Keywords

he-tree-react
he-tree-react drag and drop
React drag and drop tree
he-tree-react installation
React tree component
he-tree-react tutorial
React hierarchical data
he-tree-react example
React sortable tree
he-tree-react setup
React tree view library
he-tree-react getting started
React interactive tree
he-tree-react advanced usage

Top comments (0)