useCollection — это хук из библиотеки React
Aria, предназначенный для работы с коллекциями элементов,
обеспечивая удобный способ управления списками, деревьями, таблицами и
другими структурами данных. Основная задача хука — преобразовать массивы
данных в объекты коллекций, которые могут быть использованы совместно с
другими хуками React Aria, такими как useListBox или
useTable.
Для использования useCollection требуется передать ему
массив элементов или объект коллекции в формате:
import {useCollection} from '@react-aria/utils';
const items = [
{id: '1', name: 'Item 1'},
{id: '2', name: 'Item 2'},
{id: '3', name: 'Item 3'}
];
const collection = useCollection(items, item => item.id);
Пояснения:
items — исходный массив объектов.getKey) возвращает уникальный
идентификатор элемента коллекции.useCollection — объект коллекции, включающий
методы и свойства для удобного перебора, фильтрации и поиска
элементов.Объект коллекции, возвращаемый useCollection, имеет
несколько ключевых свойств:
items — массив объектов коллекции с добавленными
метаданными, включая уникальные ключи и тип элементов.getItem(key) — метод для получения конкретного элемента
по ключу.size — количество элементов в коллекции.keys — массив всех ключей элементов коллекции.map и forEach — функции для перебора
коллекции аналогично стандартным методам массива.Пример использования:
collection.items.forEach(item => {
console.log(item.key, item.name);
});
const secondItem = collection.getItem('2');
console.log(secondItem.name); // "Item 2"
useCollection поддерживает древовидные
структуры, где элементы могут содержать дочерние элементы. Для
этого достаточно передавать вложенный массив children:
const treeItems = [
{id: '1', name: 'Parent 1', children: [
{id: '1-1', name: 'Child 1-1'},
{id: '1-2', name: 'Child 1-2'}
]},
{id: '2', name: 'Parent 2'}
];
const treeCollection = useCollection(treeItems, item => item.id);
Теперь можно легко обходить элементы любого уровня вложенности:
treeCollection.items.forEach(item => {
console.log(item.key, item.name, item.hasChildren ? 'Has children' : 'Leaf');
});
Особенности:
hasChildren — свойство автоматически добавляется к
элементам с дочерними элементами.children внутри элемента также представляют собой
коллекцию, что упрощает интеграцию с хуками вроде
useTreeState.useCollection часто используется в сочетании с другими
хуками для управления состоянием компонентов:
useListBox и
useListState:import {useListState} from '@react-stately/list';
import {useListBox} from '@react-aria/listbox';
const state = useListState({items});
const ref = React.useRef();
const {listBoxProps} = useListBox({label: 'Example', selectionMode: 'single'}, state, ref);
Здесь state.collection создается автоматически и
представляет собой объект, совместимый с useCollection.
useTreeState и
useTree:import {useTreeState} from '@react-stately/tree';
import {useTree} from '@react-aria/tree';
const state = useTreeState({items: treeItems});
const ref = React.useRef();
const {treeProps} = useTree({}, state, ref);
Внутри useTreeState также создается коллекция через
useCollection, которая поддерживает вложенные элементы.
useCollection использует мемоизацию
ключей и структур данных с индексами, что
снижает количество перерендеров при изменении массива элементов.
Рекомендуется:
| Метод/Свойство | Назначение |
|---|---|
getItem(key) |
Получение элемента по ключу |
items |
Полный массив элементов коллекции |
keys |
Массив ключей всех элементов |
size |
Количество элементов в коллекции |
map(fn) |
Перебор элементов с возвратом нового массива |
forEach(fn) |
Перебор элементов без возврата массива |
find(fn) |
Поиск первого элемента, удовлетворяющего условию |
Фильтрация коллекции:
const filteredItems = collection.items.filter(item => item.name.includes('1'));
Построение списка компонентов React:
const listElements = collection.items.map(item => (
<li key={item.key}>{item.name}</li>
));
Доступ к дочерним элементам дерева:
const parent = treeCollection.getItem('1');
parent.children.forEach(child => {
console.log(child.key, child.name);
});
useCollectionuseCollection превращает обычные массивы в полноценные
коллекции React Aria, делая их управляемыми и готовыми к интеграции с
компонентами интерфейса, поддерживающими доступность и
интерактивность.