@sougabriel/react-drag-and-drop
v1.0.1
Published
A minimalistic drag and drop library with focus in customization
Maintainers
Readme
React Drag and Drop
Just a minimalistic drag and drop library with focus in customization.
Getting Started
Install
NPM:
npm i @sougabriel/react-drag-and-dropYARN:
yarn add @sougabriel/react-drag-and-dropUsage Exemple
Complete example bellow:
import { useCallback, useState } from 'react';
import { DragAndDropProvider, Draggable, DropZone, type DragItem } from '@sougabriel/react-drag-and-drop';
import '../styles/index.css';
interface Task {
id: number;
title: string;
description: string;
}
const initialTasks: Record<string, Task[]> = {
todo: [
{ id: 1, title: 'Task 1', description: 'task description' },
{ id: 2, title: 'Task 2', description: 'task description' },
],
doing: [{ id: 3, title: 'Task 3', description: 'task description' }],
done: [{ id: 4, title: 'Task 4', description: 'task description' }],
blocked: [],
archived: [],
};
const TASK_TYPE = 'TASK';
const ARCHIVE_TYPE = 'ARCHIVED_TASK';
const BLOCKED_TYPE = 'BLOCKED_TASK';
export default function App() {
const [tasks, setTasks] = useState(initialTasks);
const handleDrop = useCallback((item: DragItem<Task>, targetZoneId: string) => {
if (item.sourceZoneId === targetZoneId) return;
setTasks((prevTasks) => {
const newTasks = { ...prevTasks };
const sourceColumn = prevTasks[item.sourceZoneId];
const targetColumn = prevTasks[targetZoneId];
const taskIndex = sourceColumn.findIndex((task) => task.id === item.value.id);
if (taskIndex === -1) return prevTasks;
const newSourceColumn = [...sourceColumn];
newSourceColumn.splice(taskIndex, 1);
const newTargetColumn = [...targetColumn, item.value];
newTasks[item.sourceZoneId] = newSourceColumn;
newTasks[targetZoneId] = newTargetColumn;
return newTasks;
});
}, []);
const handleTaskClick = useCallback((task: Task) => {
alert('You clicked on task:', task.title);
}, []);
const canDropOnDone = useCallback((item: DragItem<Task>): boolean => {
return item.sourceZoneId === 'doing';
}, []);
return (
<DragAndDropProvider>
<div className='kanban-board'>
<div className='kanban-column'>
<DropZone<Task>
zoneId='todo'
accepts={[TASK_TYPE, BLOCKED_TYPE]}
onDropItem={handleDrop}
isOverAllowedClassName='over-allowed'
isOverDeniedClassName='over-denied'
>
{tasks.todo.map((task) => (
<Draggable<Task>
key={task.id}
item={{ value: task, type: TASK_TYPE, sourceZoneId: 'todo' }}
onClick={handleTaskClick}
>
<div className='card'>{task.description}</div>
</Draggable>
))}
</DropZone>
</div>
<div className='kanban-column'>
<DropZone<Task>
zoneId='doing'
accepts={[TASK_TYPE, BLOCKED_TYPE]}
onDropItem={handleDrop}
isOverAllowedClassName='over-allowed'
isOverDeniedClassName='over-denied'
>
{tasks.doing.map((task) => (
<Draggable<Task>
key={task.id}
item={{ value: task, type: TASK_TYPE, sourceZoneId: 'doing' }}
>
<div className='card'>{task.description}</div>
</Draggable>
))}
</DropZone>
</div>
<div className='kanban-column'>
<DropZone<Task> zoneId='blocked' accepts={[TASK_TYPE, ARCHIVE_TYPE]} onDropItem={handleDrop}>
{tasks.blocked.map((task) => (
<Draggable<Task>
key={task.id}
item={{ value: task, type: BLOCKED_TYPE, sourceZoneId: 'blocked' }}
>
<div className='card'>{task.description}</div>
</Draggable>
))}
</DropZone>
</div>
<div className='kanban-column'>
<DropZone<Task> zoneId='done' accepts={[TASK_TYPE]} onDropItem={handleDrop} canDrop={canDropOnDone}>
{tasks.done.map((task) => (
<Draggable<Task>
key={task.id}
item={{ value: task, type: ARCHIVE_TYPE, sourceZoneId: 'done' }}
>
<div className='card'>{task.description}</div>
</Draggable>
))}
</DropZone>
</div>
<div className='kanban-column'>
<DropZone<Task> zoneId='archived' accepts={[ARCHIVE_TYPE, BLOCKED_TYPE]} onDropItem={handleDrop}>
{tasks.archived.map((task) => (
<Draggable<Task>
key={task.id}
item={{ value: task, type: ARCHIVE_TYPE, sourceZoneId: 'archived' }}
>
<div className='card'>{task.description}</div>
</Draggable>
))}
</DropZone>
</div>
</div>
</DragAndDropProvider>
);
}Contact
Repository
You can contribute to this library through its GitHub repository: sougabriel/ngx-libraries.
