В Chart.js взаимодействие с графиком строится вокруг системы событий
и режимов наведения. Центральный механизм, отвечающий за определение
элементов, находящихся под курсором, реализован через метод экземпляра
графика getElementsAtEventForMode. Он используется внутри
логики tooltip’ов, hover-поведения и пользовательских обработчиков
событий.
Метод вызывается на экземпляре графика:
chart.getElementsAtEventForMode(event, mode, options, useFinalPosition)
Параметры:
Возвращает массив элементов диаграммы (Element[]),
соответствующих условиям поиска.
При движении курсора Chart.js выполняет несколько этапов:
mode)interactionИтогом является набор элементов, которые считаются «активными» в точке взаимодействия.
Параметр mode определяет стратегию определения
элементов.
Режим точечного попадания. Возвращает элементы, находящиеся непосредственно под курсором.
Используется для scatter plot, line chart с точками, bubble chart.
mode: 'point'
Поведение строгое: если курсор не попадает в область точки, элемент не возвращается.
Возвращает ближайшие элементы к курсору, даже если прямого попадания нет.
mode: 'nearest'
Особенности:
Возвращает все элементы с одинаковым индексом по оси X.
mode: 'index'
Применение:
Если курсор попадает в категорию, возвращаются все dataset-элементы этой категории.
Возвращает все элементы одного dataset.
mode: 'dataset'
Используется для выделения всей серии данных целиком.
В современных конфигурациях interaction mode может учитывать только одну ось:
mode: 'x'
или
mode: 'y'
Это позволяет работать с частичными совпадениями по координатной оси.
Объект options управляет фильтрацией найденных
элементов.
Пример структуры:
options: {
intersect: true,
axis: 'x'
}
Определяет, требуется ли прямое попадание курсора в элемент.
true — курсор должен пересекать элементfalse — достаточно близости (особенно важно для
nearest)Ограничивает поиск одной осью:
'x' — только по горизонтали'y' — только по вертикалиnull — обе осиПараметр влияет на то, учитывается ли анимационное состояние:
useFinalPosition: false
true — используется финальная позиция элементов после
анимацииfalse — текущая промежуточная позиция (во время
анимации)Это важно при работе с плавными переходами, чтобы hover не «дрожал» во время анимации.
Chart.js использует координатную систему canvas и bounding box каждого элемента.
Для каждого data point:
x, y)mode)Для разных типов графиков логика различается:
const elements = chart.getElementsAtEventForMode(
event,
'nearest',
{ intersect: true },
false
);
if (elements.length) {
const first = elements[0];
const datasetIndex = first.datasetIndex;
const index = first.index;
console.log(datasetIndex, index);
}
Метод часто применяется внутри onClick:
options: {
onClick: (event) => {
const elements = chart.getElementsAtEventForMode(
event,
'index',
{ intersect: false },
true
);
elements.forEach(el => {
console.log(el.datasetIndex, el.index);
});
}
}
Такой подход позволяет реализовать:
Метод getElementsAtEventForMode является более гибким
расширением старого подхода:
getElementsAtEvent(event) — фиксированная логикаgetElementsAtEventForMode(...) — управляемая стратегия
поискаФактически второй метод является ядром современной системы interaction.
При использовании stacked bar charts режим index
возвращает элементы всех слоев стека.
При временных осях поиск выполняется по преобразованному timestamp, а не по визуальному положению категории.
Если используется несколько осей, axis в options
становится критически важным для корректного определения элементов.
intersect: true в line charts с small
points — приводит к «потере» hoveraxis в grouped bar charts — возвращаются
лишние элементыdataset для точечного анализа
значенийpointnearestindexdatasetnearest + intersect:falseTooltipController внутри Chart.js использует тот же метод:
getElementsAtEventForModelabel, title,
footer)Это делает метод фундаментальной частью всей системы взаимодействия.
При частых событиях (mousemove) важно учитывать:
nearest дороже, чем indexОптимизация достигается через:
interaction: {
mode: 'index',
intersect: false
}
При использовании кастомных элементов (plugins, custom controllers)
необходимо реализовать корректные hit areas, иначе
getElementsAtEventForMode не сможет их обнаружить.
Это требует:
inRange методаМетод является связующим звеном между:
Фактически он определяет, какие данные считаются «активными» в любой момент взаимодействия с графиком.