(
series: ResolvedChartGPUOptions['series'],
gridX: number,
gridY: number,
interactionScales: NonNullable<ReturnType<typeof computeInteractionScalesGridCssPx>>
)
| 2438 | |
| 2439 | // Helper: Find candlestick match at pointer position (hoisted to avoid closure allocation) |
| 2440 | const findCandlestickAtPointer = ( |
| 2441 | series: ResolvedChartGPUOptions['series'], |
| 2442 | gridX: number, |
| 2443 | gridY: number, |
| 2444 | interactionScales: NonNullable<ReturnType<typeof computeInteractionScalesGridCssPx>> |
| 2445 | ): { params: TooltipParams; match: { point: OHLCDataPoint }; seriesIndex: number } | null => { |
| 2446 | for (let i = series.length - 1; i >= 0; i--) { |
| 2447 | const s = series[i]; |
| 2448 | if (s.type !== 'candlestick') continue; |
| 2449 | |
| 2450 | const cs = s as ResolvedCandlestickSeriesConfig; |
| 2451 | const barWidthClip = computeCandlestickBodyWidthRange( |
| 2452 | cs, |
| 2453 | cs.data, |
| 2454 | interactionScales.xScale, |
| 2455 | interactionScales.plotWidthCss |
| 2456 | ); |
| 2457 | |
| 2458 | const m = findCandlestick( |
| 2459 | [cs], |
| 2460 | gridX, |
| 2461 | gridY, |
| 2462 | interactionScales.xScale, |
| 2463 | interactionScales.yScale, |
| 2464 | barWidthClip |
| 2465 | ); |
| 2466 | if (!m) continue; |
| 2467 | |
| 2468 | const params = buildCandlestickTooltipParams(i, m.dataIndex, m.point); |
| 2469 | return { params, match: { point: m.point }, seriesIndex: i }; |
| 2470 | } |
| 2471 | return null; |
| 2472 | }; |
| 2473 | |
| 2474 | const onMouseMove = (payload: ChartGPUEventPayload): void => { |
| 2475 | pointerState = { |
no test coverage detected