Индикаторы вставки (Insertion Indicators) являются ключевым элементом доступного взаимодействия с компонентами, где требуется динамическая организация элементов, например, в списках с перетаскиванием (drag-and-drop), редакторах контента или сложных интерактивных таблицах. React Aria предоставляет набор хуков и утилит для правильного отображения и управления такими индикаторами, обеспечивая поддержку экранных читалок и клавиатурной навигации.
Индикатор вставки — визуальный и программный сигнал того, куда будет помещён элемент при выполнении действия вставки или перетаскивания. React Aria не рендерит индикатор напрямую, но предоставляет логическую основу для управления состоянием и координатами.
Ключевые концепты:
useDroppable — хук для контейнера, в
который можно вставлять элементы. Отвечает за определение доступных зон
вставки и генерацию событий для обновления состояния индикатора.useDraggable — хук для элементов,
которые можно перетаскивать. Обеспечивает передачу текущей позиции и
взаимодействие с Droppable.useDropIndicator — хук, который
напрямую связывает визуальный индикатор с контекстом дропа. Позволяет
задать, где отображается линия вставки, и реагировать на состояние
hovered, dragging и
insertPosition.Создание контейнера начинается с применения
useDroppable:
import { useDroppable } from '@react-aria/dnd';
function ListContainer({ id, children }) {
let { droppableProps } = useDroppable({ id });
return (
<ul {...droppableProps}>
{children}
</ul>
);
}
Ключевой момент: droppableProps
включает aria-атрибуты и обработчики событий для
взаимодействия с экранными читалками и мышью. Это обеспечивает
правильное оповещение о зоне вставки.
Хук useDraggable возвращает свойства для управления
состоянием перетаскивания:
import { useDraggable } from '@react-aria/dnd';
function ListItem({ item }) {
let { dragProps, isDragging } = useDraggable({ id: item.id });
return (
<li {...dragProps} style={{ opacity: isDragging ? 0.5 : 1 }}>
{item.content}
</li>
);
}
Особенности:
dragProps содержит события onDragStart,
onDragEnd и атрибуты aria-grabbed.isDragging используется для визуальной обратной связи,
например, полупрозрачного отображения перетаскиваемого элемента.Для визуального индикатора вставки применяется
useDropIndicator:
import { useDropIndicator } from '@react-aria/dnd';
function DropIndicator({ position }) {
let { dropIndicatorProps } = useDropIndicator({ position });
return (
<div {...dropIndicatorProps} className="drop-indicator" />
);
}
Обратите внимание на:
position определяет точку вставки относительно соседних
элементов (before, after,
on).drop-indicator должен содержать CSS для
отображения линии или маркера. Например:.drop-indicator {
height: 2px;
background-color: blue;
margin: 0;
transition: all 0.2s ease;
}
dropIndicatorProps автоматически содержит ARIA-атрибуты
для оповещения о текущем состоянии (aria-hidden,
role="presentation"), что делает индикатор доступным для
экранных читалок.React Aria не управляет глобальным состоянием дропа; это делегируется
через контекст. Обычно создаётся контекст DndContext:
import { createContext, useState } from 'react';
export const DndContext = createContext();
export function DndProvider({ children }) {
const [draggedItem, setDraggedItem] = useState(null);
const [dropPosition, setDropPosition] = useState(null);
return (
<DndContext.Provider value={{ draggedItem, setDraggedItem, dropPosition, setDropPosition }}>
{children}
</DndContext.Provider>
);
}
Преимущества:
dropPosition.aria-dropeffect,
aria-grabbed, aria-describedby для описания
текущей позиции вставки.Enter или Space.hover, что делает
интерфейс доступным для пользователей с ограничениями.<DndProvider>
<ListContainer id="my-list">
{items.map((item, index) => (
<>
{dropPosition === index && <DropIndicator position="before" />}
<ListItem key={item.id} item={item} />
{dropPosition === index + 1 && <DropIndicator position="after" />}
</>
))}
</ListContainer>
</DndProvider>
Особенности реализации:
dropPosition.dropPosition с
событиями мыши и клавиатуры.position: before/after/on с контекстным отступом для
точного отображения.Использование React Aria для индикаторов вставки обеспечивает строгую доступность, предсказуемое взаимодействие и лёгкую интеграцию с другими компонентами, делая drag-and-drop интерфейсы безопасными и удобными для всех пользователей.