feat: Add crosshairs follow mouse feature for Tooltip#7285
feat: Add crosshairs follow mouse feature for Tooltip#7285
Conversation
There was a problem hiding this comment.
Code Review
This pull request introduces crosshair follow and tag features for tooltips, including documentation and a new K-line example. The implementation involves updating the seriesTooltip logic and adding tag rendering capabilities. Review feedback recommends enhancing type safety in the global polyfill and extracting hardcoded constants for improved maintainability.
| '10000000-1000-4000-8000-100000000000'.replace(/[018]/g, (c: any) => | ||
| ( | ||
| +c ^ | ||
| (crypto.getRandomValues(new Uint8Array(1))[0] & (15 >> (+c / 4))) | ||
| ).toString(16), |
There was a problem hiding this comment.
For better type safety and code clarity, it's recommended to avoid using any. The parameter c in the replace callback function can be explicitly typed as string.
| '10000000-1000-4000-8000-100000000000'.replace(/[018]/g, (c: any) => | |
| ( | |
| +c ^ | |
| (crypto.getRandomValues(new Uint8Array(1))[0] & (15 >> (+c / 4))) | |
| ).toString(16), | |
| '10000000-1000-4000-8000-100000000000'.replace(/[018]/g, (c: string) => | |
| ( | |
| +c ^ | |
| (crypto.getRandomValues(new Uint8Array(1))[0] & (15 >> (+c / 4))) | |
| ).toString(16), |
| function updateTag( | ||
| root, | ||
| key: 'crosshairsTagX' | 'crosshairsTagY', | ||
| value: any, | ||
| x: number, | ||
| y: number, | ||
| axis: 'x' | 'y', | ||
| tagStyle: Record<string, any> = {}, | ||
| boundary: { left: number; right: number; top: number; bottom: number }, | ||
| ) { | ||
| if (!defined(value)) { | ||
| if (key === 'crosshairsTagX') hideTagX(root); | ||
| if (key === 'crosshairsTagY') hideTagY(root); | ||
| return; | ||
| } | ||
| const { | ||
| formatter, | ||
| position, | ||
| offsetX, | ||
| offsetY, | ||
| paddingX, | ||
| paddingY, | ||
| textStyle, | ||
| backgroundStyle, | ||
| } = normalizeTagStyle(tagStyle); | ||
| const group = showTag(root, key); | ||
| const [background, text] = group.childNodes as [Rect, Text]; | ||
| const textValue = formatter ? formatter(value) : `${value}`; | ||
| text.attr({ | ||
| text: textValue, | ||
| x: 0, | ||
| y: 0, | ||
| fill: '#fff', | ||
| fontSize: 10, | ||
| fontFamily: 'sans-serif', | ||
| ...textStyle, | ||
| }); | ||
| const bounds = text.getLocalBounds(); | ||
| const { | ||
| min: [minX, minY], | ||
| max: [maxX, maxY], | ||
| } = bounds; | ||
| const width = maxX - minX; | ||
| const height = maxY - minY; | ||
| const tagWidth = width + paddingX * 2; | ||
| const tagHeight = height + paddingY * 2; | ||
| background.attr({ | ||
| x: 0, | ||
| y: 0, | ||
| width: tagWidth, | ||
| height: tagHeight, | ||
| radius: 2, | ||
| fill: '#1b1e23', | ||
| ...backgroundStyle, | ||
| }); | ||
| text.attr({ | ||
| x: paddingX - minX, | ||
| y: paddingY - minY, | ||
| }); | ||
| const px = | ||
| axis === 'x' | ||
| ? x - tagWidth / 2 + offsetX | ||
| : position === 'left' | ||
| ? x - tagWidth - 6 + offsetX | ||
| : x + 6 + offsetX; | ||
| const py = | ||
| axis === 'x' ? y - tagHeight - 6 + offsetY : y - tagHeight / 2 + offsetY; | ||
| const clampedX = Math.max( | ||
| boundary.left, | ||
| Math.min(boundary.right - tagWidth, px), | ||
| ); | ||
| const clampedY = Math.max( | ||
| boundary.top, | ||
| Math.min(boundary.bottom - tagHeight, py), | ||
| ); | ||
| group.style.transform = `translate(${clampedX}, ${clampedY})`; | ||
| } |
There was a problem hiding this comment.
The updateTag function contains several hardcoded values that could be extracted into constants for better maintainability and readability:
- Default Styles: The default styles for the tag's text and background (e.g.,
fill: '#fff',fontSize: 10,radius: 2) should be defined as constant objects at a higher scope. - Magic Numbers: The number
6is used as an offset for positioning the tag. This should be a named constant (e.g.,TAG_OFFSET).
Extracting these values will make the code cleaner and easier to modify in the future.
feat: Add crosshairs follow mouse feature for Tooltip
Summary
This PR adds support for mouse-following crosshairs in tooltip interactions, enabling crosshairs to track the mouse position in real-time instead of snapping to data points. This is particularly useful for financial charts like K-line (candlestick) charts where users need precise coordinate tracking.
Changes
1. Type Definition (
src/spec/interaction.ts)Added 9 new parameters to
TooltipInteraction:2. Documentation (
site/docs/manual/component/tooltip.en.md&tooltip.zh.md)interaction.tooltipconfiguration table with new parameterscrosshairsdetailed property table with new parametersUsage Example
Use Cases
Checklist
npm testpassesDescription of change