Point
Visual markers that highlight specific data values on a chart. Points can be customized with different colors, sizes, and interactivity.@coinbase/cds-web-visualization@3.4.0-beta.9
Peer dependencies
- framer-motion: ^10.18.0
Related components
Basics
Points are visual markers that highlight specific data values on a chart. They can be used to emphasize important data points, show discrete values, or provide interactive elements.
You can add points using points on Line or LineChart.
Loading...
Live Code<LineChart enableScrubbing showArea showYAxis height={{ base: 150, tablet: 200, desktop: 250 }} points series={[ { id: 'prices', data: [10, 22, 29, 45, 98, 45, 22, 52, 21, 4, 68, 20, 21, 58], }, ]} xAxis={{ /* This prevents points close to the right edge from awkward cutoff when scrubbing */ range: ({ min, max }) => ({ min, max: max - 8 }), }} yAxis={{ showGrid: true, }} > <Scrubber /> </LineChart>
You can also add Points directly to a chart.
Loading...
Live Codefunction MyChart() { const prices = [10, 22, 29, 45, 98, 45, 22, 52, 21, 4, 68, 20, 21, 58]; return ( <CartesianChart height={{ base: 150, tablet: 200, desktop: 250 }} series={[ { id: 'prices', data: prices, }, ]} inset={{ // Overriding the right offset gives us more space to place this right: 32, }} > <YAxis showGrid position="left" tickLabelFormatter={(value) => `$${value}`} /> {prices.map((price, index) => ( <Point key={index} dataX={index} dataY={price} label={`$${price}`} labelPosition="right" /> ))} </CartesianChart> ); }
Conditional
You can conditionally render points to highlight specific values in your data, such as maximum/minimum values or outliers.
Loading...
Live Codefunction AssetPriceWithMinMax() { const data = sparklineInteractiveData.hour.map((d) => d.value); const minPrice = Math.min(...data); const maxPrice = Math.max(...data); const formatPrice = useCallback((price: number) => { return new Intl.NumberFormat('en-US', { style: 'currency', currency: 'USD', }).format(price); }, []); return ( <LineChart showArea areaType="dotted" height={{ base: 150, tablet: 200, desktop: 250 }} points={({ dataX, dataY }: PointBaseProps) => { const isMin = dataY === minPrice; const isMax = dataY === maxPrice; if (isMin) { return { label: formatPrice(dataY), labelPosition: 'bottom' }; } if (isMax) { return { label: formatPrice(dataY), labelPosition: 'top' }; } }} series={[ { id: 'btc', data: data, color: assets.btc.color, }, ]} style={{ outlineColor: assets.btc.color }} /> ); };
Interaction
Points can be made interactive by adding click handlers, allowing users to explore data in more detail.
Loading...
Live Code<LineChart showArea showYAxis height={{ base: 150, tablet: 200, desktop: 250 }} points={({ dataX, dataY }) => { const months = [ 'Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec', ]; return { radius: 4, onClick: () => alert(`${months[dataX]}: ${dataY} units sold`), accessibilityLabel: `${months[dataX]} sales: ${dataY} units`, }; }} series={[ { id: 'sales', data: [120, 132, 101, 134, 90, 230, 210, 120, 180, 190, 210, 176], }, ]} yAxis={{ showGrid: true, label: 'Sales (units)', }} />
Styling
Points support customization through various properties including colors, sizes, and labels.
Loading...
Live Code<LineChart showArea showYAxis height={{ base: 150, tablet: 200, desktop: 250 }} points={({ dataX, dataY }) => { const isHighPerformance = dataY >= 90; const isLowPerformance = dataY < 75; return { fill: isHighPerformance ? 'var(--color-bgPositive)' : isLowPerformance ? 'var(--color-bgNegative)' : 'var(--color-fgPrimary)', radius: isHighPerformance ? 6 : 4, strokeWidth: 2, stroke: 'var(--color-bg)', label: isHighPerformance || isLowPerformance ? `${dataY}%` : undefined, labelPosition: isHighPerformance ? 'top' : 'bottom', }; }} series={[ { id: 'performance', data: [65, 70, 72, 85, 88, 92, 78, 82, 90, 95, 91, 94], }, ]} xAxis={{ range: ({ min, max }) => ({ min, max: max - 8 }), }} yAxis={{ showGrid: true, label: 'Performance Score', }} />
Labels
You can use labelPosition, labelOffset, and labelFont to adjust Point's label.
Loading...
Live Codefunction Scatterplot() { const dataPoints = [ { x: 20, y: 30, label: 'A' }, { x: 40, y: 65, label: 'B' }, { x: 60, y: 45, label: 'C' }, { x: 75, y: 80, label: 'D' }, ]; return ( <CartesianChart height={250} xAxis={{ domain: { min: 0, max: 100 }, }} yAxis={{ domain: { min: 0, max: 100 }, }} > <XAxis showLine showTickMarks showGrid /> <YAxis position="left" showLine showTickMarks showGrid /> {dataPoints.map((point, index) => ( <Point key={index} dataX={point.x} dataY={point.y} label={point.label} labelPosition="top" labelOffset={6} labelFont="title3" /> ))} </CartesianChart> ); }
Custom Label Position
You can also use LabelComponent to create custom label components.
Loading...
Live Codefunction ScatterplotWithCustomLabels() { const dataPoints = [ { x: 12, y: 34, label: 'A', color: 'var(--color-fgAccent)' }, { x: 28, y: 67, label: 'B', color: 'var(--color-fgAccent)' }, { x: 45, y: 23, label: 'C', color: 'var(--color-fgAccent)' }, { x: 67, y: 89, label: 'D', color: 'var(--color-bgPositive)' }, { x: 82, y: 76, label: 'E', color: 'var(--color-bgPositive)' }, { x: 34, y: 91, label: 'F', color: 'var(--color-bgPositive)' }, { x: 56, y: 45, label: 'G', color: 'var(--color-bgPositive)' }, { x: 19, y: 12, label: 'H', color: 'var(--color-fgWarning)' }, { x: 73, y: 28, label: 'I', color: 'var(--color-fgWarning)' }, { x: 91, y: 54, label: 'J', color: 'var(--color-fgWarning)' }, { x: 15, y: 58, label: 'K', color: 'var(--color-fgPrimary)' }, { x: 39, y: 72, label: 'L', color: 'var(--color-fgPrimary)' }, { x: 88, y: 15, label: 'M', color: 'var(--color-fgPrimary)' }, { x: 52, y: 82, label: 'N', color: 'var(--color-fgPrimary)' }, ]; // Calculate domain based on data const xValues = dataPoints.map((p) => p.x); const yValues = dataPoints.map((p) => p.y); const xMin = Math.min(...xValues); const xMax = Math.max(...xValues); const yMin = Math.min(...yValues); const yMax = Math.max(...yValues); // Custom label component that places labels to the top-right const TopRightPointLabel = ({ x, y, offset = 0, children }) => { return ( <ChartText horizontalAlignment="left" verticalAlignment="bottom" x={x + offset} y={y - offset} font="label1" > {children} </ChartText> ); }; return ( <CartesianChart height={300} xAxis={{ domain: { min: xMin, max: xMax }, domainLimit: 'nice', }} yAxis={{ domain: { min: yMin, max: yMax }, domainLimit: 'nice', }} > <XAxis showLine showTickMarks showGrid /> <YAxis position="left" showLine showTickMarks showGrid /> {dataPoints.map((point, index) => ( <Point key={index} dataX={point.x} dataY={point.y} label={point.label} labelOffset={8} fill={point.color} radius={5} LabelComponent={TopRightPointLabel} /> ))} </CartesianChart> ); }