# BarChart **📖 Live documentation:** https://cds.coinbase.com/components/charts/BarChart/ A bar chart component for comparing values across categories. Supports horizontal and vertical orientations, stacked bars, and grouped series. ## Import ```tsx import { BarChart } from '@coinbase/cds-web-visualization' ``` ## Examples ### Basics Bar charts are a useful component for comparing discrete categories of data. They are helpful for highlighting trends to users or allowing them to compare proportions at a glance. To start, pass in a series of data to the chart. ```jsx live ``` #### Layout You can set `layout` to `horizontal` to render the chart horizontally. ```jsx live function HorizontalBars() { const dataset = [ { month: 'Jan', seoul: 21 }, { month: 'Feb', seoul: 28 }, { month: 'Mar', seoul: 41 }, { month: 'Apr', seoul: 73 }, { month: 'May', seoul: 99 }, { month: 'June', seoul: 144 }, { month: 'July', seoul: 319 }, { month: 'Aug', seoul: 249 }, { month: 'Sept', seoul: 131 }, { month: 'Oct', seoul: 55 }, { month: 'Nov', seoul: 48 }, { month: 'Dec', seoul: 25 }, ]; return ( d.seoul), color: 'var(--color-accentBoldBlue)', }, ]} borderRadius={2} showXAxis showYAxis xAxis={{ label: 'rainfall (mm)', GridLineComponent: (props) => , showGrid: true, showLine: true, showTickMarks: true, }} yAxis={{ position: 'left', data: dataset.map((d) => d.month), showLine: true, showTickMarks: true, bandTickMarkPlacement: 'edges', }} /> ); } ``` ### Multiple Series You can also provide multiple series of data to the chart. Series will have their bars for each data point rendered side by side. ```jsx live ``` ### Series Stacking You can also configure stacking for your chart using the `stacked` prop. ```jsx live ``` You can also configure multiple stacks by setting the `stackId` prop on each series. ```jsx live ``` #### Stack Gap ```jsx live ``` ### Border Radius Bars have a default `borderRadius` of `4`. You can change this by setting the `borderRadius` prop on the chart. Stacks will only round the top corners of touching bars. ```jsx live { if (value === 'D') { return {value}; } return value; }, categoryPadding: 0.25, }} style={{ margin: '0 auto' }} /> ``` #### Round Baseline You can also round the baseline of the bars by setting the `roundBaseline` prop on the chart. ```jsx live function MonthlyRewards() { const months = ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D']; return ( { if (value === 11) { return {months[value]}; } return months[value]; }, categoryPadding: 0.25, }} stackMinSize={24} style={{ margin: '0 auto' }} /> ); } ``` ### Data #### Negative ```jsx live function PositiveAndNegativeCashFlow() { const ThinSolidLine = memo((props) => ); const categories = Array.from({ length: 31 }, (_, i) => `3/${i + 1}`); const gains = [ 5, 0, 6, 18, 0, 5, 12, 0, 12, 22, 28, 18, 0, 12, 6, 0, 0, 24, 0, 0, 4, 0, 18, 0, 0, 14, 10, 16, 0, 0, 0, ]; const losses = [ -4, 0, -8, -12, -6, 0, 0, 0, -18, 0, -12, 0, -9, -6, 0, 0, 0, 0, -22, -8, 0, 0, -10, -14, 0, 0, 0, 0, 0, -12, -10, ]; const series = [ { id: 'gains', data: gains, color: 'var(--color-fgPositive)' }, { id: 'losses', data: losses, color: 'var(--color-fgNegative)' }, ]; return ( `$${value}M`, }} /> ); } ``` #### Null You can pass in `null` or `0` values to not render a bar for that data point. ```jsx live `$${value}k`, showGrid: true, showTickMarks: true, showLine: true, tickMarkSize: 1.5, domain: { max: 50 }, }} /> ``` You can also use the `BarStackComponent` prop to render an empty circle for zero values. ```jsx live function MonthlyRewards() { const months = ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D']; const currentMonth = 7; const purple = [null, 6, 8, 10, 7, 6, 6, 8, null, null, null, null]; const blue = [null, 10, 12, 11, 10, 9, 10, 11, null, null, null, null]; const cyan = [null, 7, 10, 12, 11, 10, 8, 11, null, null, null, null]; const green = [10, null, null, null, 1, null, null, 6, null, null, null, null]; const series = [ { id: 'purple', data: purple, color: 'rgb(var(--purple30))' }, { id: 'blue', data: blue, color: 'rgb(var(--blue30))' }, { id: 'cyan', data: cyan, color: 'rgb(var(--teal30))' }, { id: 'green', data: green, color: 'rgb(var(--green30))' }, ]; const CustomBarStackComponent = ({ children, ...props }) => { if (props.height === 0) { const diameter = props.width; return ( ); } return {children}; }; return ( { if (index == currentMonth) { return {months[index]}; } return months[index]; }, categoryPadding: 0.25, }} /> ); } ``` #### Range You can pass in `[min, max]` tuples as data points to render bars that span a range of values. ```jsx live function PriceRange() { const candles = btcCandles.slice(0, 180).reverse(); const data = candles.map((candle) => [parseFloat(candle.low), parseFloat(candle.high)]); const min = Math.min(...data.map(([low]) => low)); const max = Math.max(...data.map(([, high]) => high)); const tickFormatter = useCallback( (value) => new Intl.NumberFormat('en-US', { style: 'currency', currency: 'USD', notation: 'compact', maximumFractionDigits: 0, }).format(value), [], ); return ( ); } ``` ### Customization #### Bar Spacing There are two ways to control the spacing between bars. You can set the `barPadding` prop to control the spacing between bars within a series. You can also set the `categoryPadding` prop to control the spacing between stacks of bars. ```jsx live ``` #### Minimum Size To better emphasize small values, you can set the `stackMinSize` or `barMinSize` prop to control the minimum size for entire stacks or individual bar. ##### Minimum Stack Size You can set the `stackMinSize` prop to control the minimum size for entire stacks. This will only apply to stacks that have a value that is not `null` or `0`. It will proportionally scale the values of each bar in the stack to reach the minimum size. ```jsx live ``` ##### Minimum Bar Size You can also set the `barMinSize` prop to control the minimum size for individual bars. This will only apply to bars that have a value that is not `null` or `0`. ```jsx live `$${value}k`, showGrid: true, showTickMarks: true, showLine: true, tickMarkSize: 1.5, domain: { max: 50 }, }} barMinSize={4} /> ``` #### Multiple Axes You can render bars from separate y axes in one `BarPlot`, however they aren't able to be stacked. ```jsx live `$${value}k`} /> `${value}%`} /> ``` When using horizontal layout, you can use multiple x axes. ```jsx live `$${value}k`} /> `${value}%`} /> ``` #### Custom Components ##### Outlined Stacks You can set the `BarStackComponent` prop to render a custom component for stacks. ```jsx live function MonthlyRewards() { const CustomBarStackComponent = ({ children, ...props }) => { return ( <> {children} ); }; return ( { if (value === 'D') { return {value}; } return value; }, categoryPadding: 0.25, }} yAxis={{ range: ({ min, max }) => ({ min, max: max - 4 }) }} style={{ margin: '0 auto' }} /> ); } ``` ### Animations You can configure chart transitions using the `transitions` prop. Also, you can toggle animations by setting `animate` to `true` or `false`. ```jsx live function AnimatedStackedBars() { const dataCount = 12; const minValue = 20; const maxValue = 100; const minStep = 10; const maxStep = 40; const updateInterval = 600; const seriesSpacing = 30; const seriesConfig = [ { id: 'red', label: 'Red', color: 'rgb(var(--red40))' }, { id: 'orange', label: 'Orange', color: 'rgb(var(--orange40))' }, { id: 'yellow', label: 'Yellow', color: 'rgb(var(--yellow40))' }, { id: 'green', label: 'Green', color: 'rgb(var(--green40))' }, { id: 'blue', label: 'Blue', color: 'rgb(var(--blue40))' }, { id: 'indigo', label: 'Indigo', color: 'rgb(var(--indigo40))' }, { id: 'purple', label: 'Purple', color: 'rgb(var(--purple40))' }, ]; const domainLimit = maxValue + seriesConfig.length * seriesSpacing; function generateNextValue(previousValue) { const range = maxStep - minStep; const offset = Math.random() * range + minStep; let direction; if (previousValue >= maxValue) { direction = -1; } else if (previousValue <= minValue) { direction = 1; } else { direction = Math.random() < 0.5 ? -1 : 1; } let newValue = previousValue + offset * direction; newValue = Math.max(minValue, Math.min(maxValue, newValue)); return newValue; } function generateInitialData() { const data = []; let previousValue = minValue + Math.random() * (maxValue - minValue); data.push(previousValue); for (let i = 1; i < dataCount; i++) { const newValue = generateNextValue(previousValue); data.push(newValue); previousValue = newValue; } return data; } function AnimatedChart(props) { const [data, setData] = useState(generateInitialData); useEffect(() => { const intervalId = setInterval(() => { setData((currentData) => { const lastValue = currentData[currentData.length - 1] ?? minValue; const newValue = generateNextValue(lastValue); return [...currentData.slice(1), newValue]; }); }, updateInterval); return () => clearInterval(intervalId); }, []); const series = seriesConfig.map((config, index) => ({ id: config.id, label: config.label, color: config.color, data: index === 0 ? data : Array(dataCount).fill(seriesSpacing), })); return ( '', domain: { min: 0, max: domainLimit }, }} {...props} /> ); } function AnimatedChartExample() { const animatedStates = [ { id: 'on', label: 'On' }, { id: 'off', label: 'Off' }, ]; const [animatedState, setAnimatedState] = useState(animatedStates[0]); return ( Animations ); } return ; } ``` ### Composed Examples #### Candlesticks You can render a candlestick chart by setting the `BarComponent` prop to a custom candlestick component. ```jsx live function Candlesticks() { const infoTextId = useId(); const infoTextRef = React.useRef(null); const selectedIndexRef = React.useRef(null); const stockData = btcCandles.slice(0, 90).reverse(); const min = Math.min(...stockData.map((data) => parseFloat(data.low))); const ThinSolidLine = memo((props) => ); // Custom line component that renders a rect to highlight the entire bandwidth const BandwidthHighlight = memo(({ d, stroke }) => { const { getXScale, drawingArea, getXAxis } = useCartesianChartContext(); const { scrubberPosition } = useScrubberContext(); const xScale = getXScale(); const xAxis = getXAxis(); if (!xScale || scrubberPosition === undefined) return; const xPos = xScale(scrubberPosition); if (xPos === undefined) return; return ( ); }); const candlesData = stockData.map((data) => [parseFloat(data.low), parseFloat(data.high)]); const staggerDelay = 0.25; const CandlestickBarComponent = memo(({ x, y, width, height, originY, dataX, ...props }) => { const { getYScale, drawingArea } = useCartesianChartContext(); const yScale = getYScale(); const normalizedX = React.useMemo( () => (drawingArea.width > 0 ? (x - drawingArea.x) / drawingArea.width : 0), [x, drawingArea.x, drawingArea.width], ); const transition = React.useMemo( () => ({ type: 'tween', duration: 0.325, delay: normalizedX * staggerDelay, }), [normalizedX], ); const wickX = x + width / 2; const timePeriodValue = stockData[dataX]; const open = parseFloat(timePeriodValue.open); const close = parseFloat(timePeriodValue.close); const bullish = open < close; const color = bullish ? 'var(--color-fgPositive)' : 'var(--color-fgNegative)'; const openY = yScale?.(open) ?? 0; const closeY = yScale?.(close) ?? 0; const bodyHeight = Math.abs(openY - closeY); const bodyY = openY < closeY ? openY : closeY; return ( ); }); const formatPrice = React.useCallback((price) => { return new Intl.NumberFormat('en-US', { style: 'currency', currency: 'USD', }).format(parseFloat(price)); }, []); const formatThousandsPrice = React.useCallback((price) => { const formattedPrice = new Intl.NumberFormat('en-US', { style: 'currency', currency: 'USD', minimumFractionDigits: 0, maximumFractionDigits: 0, }).format(parseFloat(price) / 1000); return `${formattedPrice}k`; }, []); const formatVolume = React.useCallback((volume) => { const volumeInThousands = parseFloat(volume) / 1000; return ( new Intl.NumberFormat('en-US', { style: 'decimal', minimumFractionDigits: 0, maximumFractionDigits: 2, }).format(volumeInThousands) + 'k' ); }, []); const formatTime = React.useCallback( (index) => { if (index === null || index === undefined || index >= stockData.length) return ''; const ts = parseInt(stockData[index].start); return new Date(ts * 1000).toLocaleDateString('en-US', { month: 'short', day: 'numeric', }); }, [stockData], ); const updateInfoText = React.useCallback( (index) => { if (!infoTextRef.current) return; const text = index !== null && index !== undefined ? `Open: ${formatThousandsPrice(stockData[index].open)}, Close: ${formatThousandsPrice( stockData[index].close, )}, Volume: ${(parseFloat(stockData[index].volume) / 1000).toFixed(2)}k` : formatPrice(stockData[stockData.length - 1].close); infoTextRef.current.textContent = text; selectedIndexRef.current = index; }, [stockData, formatPrice, formatVolume], ); const initialInfo = formatPrice(stockData[stockData.length - 1].close); return ( {initialInfo} {children}} borderRadius={0} height={{ base: 150, tablet: 200, desktop: 250 }} inset={{ top: 8, bottom: 8, left: 0, right: 0 }} onScrubberPositionChange={updateInfoText} series={[ { id: 'stock-prices', data: candlesData, }, ]} xAxis={{ tickLabelFormatter: formatTime, }} yAxis={{ domain: { min }, tickLabelFormatter: formatThousandsPrice, width: 40, showGrid: true, GridLineComponent: ThinSolidLine, }} aria-labelledby={infoTextId} > ); } ``` #### Monthly Sunlight You can combine custom and BarPlot components and transitions to create a springy sunlight chart. ```tsx live function SunlightChartExample() { const dayLength = 1440; type SunlightChartData = Array<{ label: string; value: number; }>; const sunlightData: SunlightChartData = [ { label: 'Jan', value: 598 }, { label: 'Feb', value: 635 }, { label: 'Mar', value: 688 }, { label: 'Apr', value: 753 }, { label: 'May', value: 812 }, { label: 'Jun', value: 855 }, { label: 'Jul', value: 861 }, { label: 'Aug', value: 828 }, { label: 'Sep', value: 772 }, { label: 'Oct', value: 710 }, { label: 'Nov', value: 648 }, { label: 'Dec', value: 605 }, ]; function SunlightChart({ data, height = 300, ...props }: Omit & { data: SunlightChartData }) { return ( value), yAxisId: 'sunlight', color: 'rgb(var(--yellow40))', }, { id: 'day', data: data.map(() => dayLength), yAxisId: 'day', color: 'rgb(var(--blue100))', }, ]} xAxis={{ ...props.xAxis, scaleType: 'band', data: data.map(({ label }) => label), }} yAxis={[ { id: 'day', domain: { min: 0, max: dayLength }, domainLimit: 'strict', }, { id: 'sunlight', domain: { min: 0, max: dayLength }, domainLimit: 'strict', }, ]} > ); } function Example() { return ( 2026 sunlight data for the first day of each month in Atlanta, Georgia, provided by{' '} NOAA . ); } return ; } ``` #### Buy vs Sell You can combine a horizontal BarChart with a custom legend to create a buy vs sell chart. ```tsx live function BuyVsSellExample() { function BuyVsSellLegend({ buy, sell }: { buy: number; sell: number }) { return ( {buy}% bought } color="var(--color-fgPositive)" /> {sell}% sold } color="var(--color-fgNegative)" /> ); } function BuyVsSellChart({ buy, sell, animate = true, borderRadius = 3, height = 6, inset = 0, layout = 'horizontal', stackGap = 4, xAxis, yAxis, barMinSize = height, ...props }: Omit & { buy: number; sell: number }) { return ( ); } return ; } ``` ## Props | Prop | Type | Required | Default | Description | | --- | --- | --- | --- | --- | | `BarComponent` | `BarComponent` | No | `-` | Component to render the bar. | | `BarStackComponent` | `BarStackComponent` | No | `DefaultBarStack` | Custom component to render the stack container. Can be used to add clip paths, outlines, or other custom styling. | | `alignContent` | `ResponsiveProp
` | No | `-` | - | | `alignItems` | `ResponsiveProp
` | No | `-` | - | | `alignSelf` | `ResponsiveProp
` | No | `-` | - | | `animate` | `boolean` | No | `true` | Whether to animate the chart. | | `as` | `div` | No | `-` | The underlying element or component the polymorphic component will render. Changing as also changes the inherited native props (e.g. href for as=a) and the expected ref type. | | `aspectRatio` | `ResponsiveProp` | No | `-` | - | | `background` | `ResponsiveProp` | No | `-` | - | | `barMinSize` | `number` | No | `-` | Minimum size for individual bars in the stack. | | `barPadding` | `number` | No | `0.1` | Padding between bar groups (0-1). | | `borderBottomWidth` | `ResponsiveProp` | No | `-` | - | | `borderColor` | `ResponsiveProp` | No | `-` | - | | `borderEndWidth` | `ResponsiveProp` | No | `-` | - | | `borderRadius` | `number` | No | `4` | Border radius for the bar. | | `borderStartWidth` | `ResponsiveProp` | No | `-` | - | | `borderTopWidth` | `ResponsiveProp` | No | `-` | - | | `borderWidth` | `ResponsiveProp` | No | `-` | - | | `bordered` | `boolean` | No | `-` | Add a border around all sides of the box. | | `borderedBottom` | `boolean` | No | `-` | Add a border to the bottom side of the box. | | `borderedEnd` | `boolean` | No | `-` | Add a border to the trailing side of the box. | | `borderedHorizontal` | `boolean` | No | `-` | Add a border to the leading and trailing sides of the box. | | `borderedStart` | `boolean` | No | `-` | Add a border to the leading side of the box. | | `borderedTop` | `boolean` | No | `-` | Add a border to the top side of the box. | | `borderedVertical` | `boolean` | No | `-` | Add a border to the top and bottom sides of the box. | | `bottom` | `ResponsiveProp>` | No | `-` | - | | `classNames` | `{ root?: string; chart?: string \| undefined; } \| undefined` | No | `-` | Custom class names for the component. | | `color` | `ResponsiveProp` | No | `-` | - | | `columnGap` | `ResponsiveProp` | No | `-` | - | | `dangerouslySetBackground` | `string` | No | `-` | - | | `display` | `ResponsiveProp` | No | `-` | - | | `elevation` | `ResponsiveProp` | No | `-` | - | | `enableScrubbing` | `boolean` | No | `-` | Enables scrubbing interactions. When true, allows scrubbing and makes scrubber components interactive. | | `fillOpacity` | `number` | No | `-` | Fill opacity for the bar. | | `flexBasis` | `ResponsiveProp>` | No | `-` | - | | `flexDirection` | `ResponsiveProp` | No | `-` | - | | `flexGrow` | `ResponsiveProp` | No | `-` | - | | `flexShrink` | `ResponsiveProp` | No | `-` | - | | `flexWrap` | `ResponsiveProp` | No | `-` | - | | `font` | `ResponsiveProp` | No | `-` | - | | `fontFamily` | `ResponsiveProp` | No | `-` | - | | `fontSize` | `ResponsiveProp` | No | `-` | - | | `fontWeight` | `ResponsiveProp` | No | `-` | - | | `gap` | `ResponsiveProp` | No | `-` | - | | `grid` | `ResponsiveProp` | No | `-` | - | | `gridArea` | `ResponsiveProp` | No | `-` | - | | `gridAutoColumns` | `ResponsiveProp>` | No | `-` | - | | `gridAutoFlow` | `ResponsiveProp` | No | `-` | - | | `gridAutoRows` | `ResponsiveProp>` | No | `-` | - | | `gridColumn` | `ResponsiveProp` | No | `-` | - | | `gridColumnEnd` | `ResponsiveProp` | No | `-` | - | | `gridColumnStart` | `ResponsiveProp` | No | `-` | - | | `gridRow` | `ResponsiveProp` | No | `-` | - | | `gridRowEnd` | `ResponsiveProp` | No | `-` | - | | `gridRowStart` | `ResponsiveProp` | No | `-` | - | | `gridTemplate` | `ResponsiveProp` | No | `-` | - | | `gridTemplateAreas` | `ResponsiveProp` | No | `-` | - | | `gridTemplateColumns` | `ResponsiveProp>` | No | `-` | - | | `gridTemplateRows` | `ResponsiveProp>` | No | `-` | - | | `height` | `ResponsiveProp>` | No | `-` | - | | `inset` | `number \| Partial` | No | `-` | Inset around the entire chart (outside the axes). | | `justifyContent` | `ResponsiveProp` | No | `-` | - | | `key` | `Key \| null` | No | `-` | - | | `layout` | `horizontal \| vertical` | No | `'vertical'` | Chart layout - describes the direction bars/areas grow. - vertical (default): Bars grow vertically. X is category axis, Y is value axis. - horizontal: Bars grow horizontally. Y is category axis, X is value axis. | | `left` | `ResponsiveProp>` | No | `-` | - | | `legend` | `ReactNode` | No | `-` | Whether to show the legend or a custom legend element. - true renders the default Legend component - A React element renders that element as the legend - false or omitted hides the legend | | `legendAccessibilityLabel` | `string` | No | `'Legend'` | Accessibility label for the legend group. | | `legendPosition` | `top \| bottom \| left \| right` | No | `'bottom'` | Position of the legend relative to the chart. | | `lineHeight` | `ResponsiveProp` | No | `-` | - | | `margin` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `marginBottom` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `marginEnd` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `marginStart` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `marginTop` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `marginX` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `marginY` | `ResponsiveProp<0 \| -1 \| -2 \| -0.25 \| -0.5 \| -0.75 \| -1.5 \| -3 \| -4 \| -5 \| -6 \| -7 \| -8 \| -9 \| -10>` | No | `-` | - | | `maxHeight` | `ResponsiveProp>` | No | `-` | - | | `maxWidth` | `ResponsiveProp>` | No | `-` | - | | `minHeight` | `ResponsiveProp>` | No | `-` | - | | `minWidth` | `ResponsiveProp>` | No | `-` | - | | `onChange` | `FormEventHandler` | No | `-` | - | | `onScrubberPositionChange` | `((index: number) => void) \| undefined` | No | `-` | Callback fired when the scrubber position changes. Receives the dataIndex of the scrubber or undefined when not scrubbing. | | `opacity` | `ResponsiveProp` | No | `-` | - | | `overflow` | `ResponsiveProp` | No | `-` | - | | `padding` | `ResponsiveProp` | No | `-` | - | | `paddingBottom` | `ResponsiveProp` | No | `-` | - | | `paddingEnd` | `ResponsiveProp` | No | `-` | - | | `paddingStart` | `ResponsiveProp` | No | `-` | - | | `paddingTop` | `ResponsiveProp` | No | `-` | - | | `paddingX` | `ResponsiveProp` | No | `-` | - | | `paddingY` | `ResponsiveProp` | No | `-` | - | | `pin` | `PinningDirection` | No | `-` | Direction in which to absolutely pin the box. | | `position` | `ResponsiveProp` | No | `-` | - | | `ref` | `((instance: SVGSVGElement \| null) => void) \| RefObject \| null` | No | `-` | - | | `right` | `ResponsiveProp>` | No | `-` | - | | `roundBaseline` | `boolean` | No | `-` | Whether to round the baseline of a bar (where the value is 0). | | `rowGap` | `ResponsiveProp` | No | `-` | - | | `series` | `BarSeries[]` | No | `-` | Configuration objects that define how to visualize the data. Each series can optionally define its own BarComponent. | | `showXAxis` | `boolean` | No | `-` | Whether to show the X axis. | | `showYAxis` | `boolean` | No | `-` | Whether to show the Y axis. | | `stackGap` | `number` | No | `-` | Gap between bars in the stack. | | `stackMinSize` | `number` | No | `-` | Minimum size for the entire stack. | | `stacked` | `boolean` | No | `-` | Whether to stack the areas on top of each other. When true, each series builds cumulative values on top of the previous series. | | `stroke` | `string` | No | `-` | Stroke color for the bar outline. | | `strokeWidth` | `number` | No | `-` | Stroke width for the bar outline. | | `style` | `CSSProperties` | No | `-` | Custom styles for the root element. | | `styles` | `{ root?: CSSProperties; chart?: CSSProperties \| undefined; } \| undefined` | No | `-` | Custom styles for the component. | | `testID` | `string` | No | `-` | Used to locate this element in unit and end-to-end tests. Under the hood, testID translates to data-testid on Web. On Mobile, testID stays the same - testID | | `textAlign` | `ResponsiveProp
` | No | `-` | - | | `textDecoration` | `ResponsiveProp` | No | `-` | - | | `textTransform` | `ResponsiveProp` | No | `-` | - | | `top` | `ResponsiveProp>` | No | `-` | - | | `transform` | `ResponsiveProp` | No | `-` | - | | `transition` | `Transition$1` | No | `-` | Transition for updates. | | `transitions` | `{ enter?: BarTransition \| null; update?: BarTransition \| null \| undefined; } \| undefined` | No | `transitions = {{ enter: { type: 'spring', stiffness: 900, damping: 120, mass: 4, staggerDelay: 0.25 }, update: { type: 'spring', stiffness: 900, damping: 120, mass: 4 } }}` | Transition configuration for enter and update animations. | | `userSelect` | `ResponsiveProp` | No | `-` | - | | `visibility` | `ResponsiveProp` | No | `-` | - | | `width` | `ResponsiveProp>` | No | `-` | - | | `xAxis` | `(Partial & SharedProps & { bandGridLinePlacement?: AxisBandPlacement; bandTickMarkPlacement?: AxisBandPlacement \| undefined; label?: string \| undefined; labelGap?: number \| undefined; minTickLabelGap?: number \| undefined; requestedTickCount?: number \| undefined; showGrid?: boolean \| undefined; showLine?: boolean \| undefined; showTickMarks?: boolean \| undefined; tickMarkSize?: number \| undefined; ticks?: number[] \| ((value: number) => boolean) \| undefined; tickMarkLabelGap?: number \| undefined; tickInterval?: number \| undefined; tickMinStep?: number \| undefined; tickMaxStep?: number \| undefined; } & { className?: string \| undefined; classNames?: { root?: string \| undefined; label?: string \| undefined; tickLabel?: string \| undefined; gridLine?: string \| undefined; line?: string \| undefined; tickMark?: string \| undefined; } \| undefined; style?: CSSProperties \| undefined; styles?: { root?: CSSProperties \| undefined; label?: CSSProperties \| undefined; tickLabel?: CSSProperties \| undefined; gridLine?: CSSProperties \| undefined; line?: CSSProperties \| undefined; tickMark?: CSSProperties \| undefined; } \| undefined; GridLineComponent?: LineComponent \| undefined; LineComponent?: LineComponent \| undefined; TickMarkLineComponent?: LineComponent \| undefined; tickLabelFormatter?: ((value: number) => ChartTextChildren) \| undefined; TickLabelComponent?: AxisTickLabelComponent \| undefined; } & { axisId?: string \| undefined; position?: top \| bottom \| undefined; height?: number \| undefined; }) \| undefined` | No | `-` | Configuration for x-axis. Accepts axis config and axis props. To show the axis, set showXAxis to true. | | `yAxis` | `(Partial & SharedProps & { bandGridLinePlacement?: AxisBandPlacement; bandTickMarkPlacement?: AxisBandPlacement \| undefined; label?: string \| undefined; labelGap?: number \| undefined; minTickLabelGap?: number \| undefined; requestedTickCount?: number \| undefined; showGrid?: boolean \| undefined; showLine?: boolean \| undefined; showTickMarks?: boolean \| undefined; tickMarkSize?: number \| undefined; ticks?: number[] \| ((value: number) => boolean) \| undefined; tickMarkLabelGap?: number \| undefined; tickInterval?: number \| undefined; tickMinStep?: number \| undefined; tickMaxStep?: number \| undefined; } & { className?: string \| undefined; classNames?: { root?: string \| undefined; label?: string \| undefined; tickLabel?: string \| undefined; gridLine?: string \| undefined; line?: string \| undefined; tickMark?: string \| undefined; } \| undefined; style?: CSSProperties \| undefined; styles?: { root?: CSSProperties \| undefined; label?: CSSProperties \| undefined; tickLabel?: CSSProperties \| undefined; gridLine?: CSSProperties \| undefined; line?: CSSProperties \| undefined; tickMark?: CSSProperties \| undefined; } \| undefined; GridLineComponent?: LineComponent \| undefined; LineComponent?: LineComponent \| undefined; TickMarkLineComponent?: LineComponent \| undefined; tickLabelFormatter?: ((value: number) => ChartTextChildren) \| undefined; TickLabelComponent?: AxisTickLabelComponent \| undefined; } & { axisId?: string \| undefined; position?: left \| right \| undefined; width?: number \| undefined; }) \| undefined` | No | `-` | Configuration for y-axis. Accepts axis config and axis props. To show the axis, set showYAxis to true. | | `zIndex` | `ResponsiveProp` | No | `-` | - |