BarChart
Data Visualization
visx 기반 막대 차트.
Usage
import
API Reference
예제
Usage
카테고리별 수치를 막대 길이로 비교하거나 여러 시리즈를 그룹·누적으로 볼 때 사용한다.
import
import
import { BarChart } from '@mildang/design-system/Chart';예제를 복사해 쓸 때 필요한 준비
• @mildang/styled-system 은 이 저장소에서 Panda 가 생성하는 산출물이다. 저장소 안에서는 turbo run ship 이후 쓸 수 있고, 패키지 소비자는 자기 Panda 산출물이나 다른 레이아웃 수단으로 바꿔야 한다.
API Reference
BarChart Props
Prop
Type
Default
data
필수
TDatum[]
지정 안 함
xKey
필수
string
지정 안 함
yKeys
필수
(keyof TDatum & string)[]
지정 안 함
children
ReactNode
지정 안 함
className
string
지정 안 함
colors
string[]
지정 안 함
groupMode
"stacked" | "grouped"
grouped
labels
Partial<Record<keyof TDatum & string, string>>
지정 안 함
layout
"horizontal" | "vertical"
vertical
legendPosition
"bottom" | "left" | "right" | "top"
bottom
margin
Partial<ChartMargin>
지정 안 함
paints
ChartPaint[]
지정 안 함
showGrid
boolean
true
showLegend
boolean
false
showTooltip
boolean
false
showValueText
boolean
false
showXAxis
boolean
true
showYAxis
boolean
true
xAxisProps
BarChartAxisProps
지정 안 함
yAxisProps
BarChartAxisProps
지정 안 함
예제
나란히 비교 vs 누적 합계
groupMode 로 시리즈를 나란히 비교할지, 쌓아서 전체 규모를 함께 볼지 고른다.
코드
'use client';
import { BarChart } from '@mildang/design-system/Chart';
import { Text } from '@mildang/design-system/Text';
import { HStack, VStack } from '@mildang/styled-system/jsx';
import { css } from '@mildang/styled-system/css';
/**
* yKeys 가 2개 이상일 때 `groupMode` 로 나란히 비교할지(grouped) 값을 누적해 전체 규모를
* 함께 볼지(stacked) 고른다. 데이터는 그대로 두고 이 prop 하나만 바뀐다.
*/
const data = [
{ subject: '국어', male: 72, female: 78 },
{ subject: '수학', male: 64, female: 69 },
{ subject: '영어', male: 81, female: 75 },
];
const labels = { male: '남학생', female: '여학생' };
const frame = css({ width: '100%', height: '[220px]' });
export default function BarChartModesExample() {
return (
<HStack gap="6" alignItems="flex-start" flexWrap="wrap">
<VStack gap="2" alignItems="stretch" flex="1" minWidth="[220px]">
<Text variant="caption-md" color="neutral.text.low">
grouped — 성별을 나란히 비교
</Text>
<div className={frame}>
<BarChart
data={data}
xKey="subject"
yKeys={['male', 'female']}
labels={labels}
groupMode="grouped"
showLegend
/>
</div>
</VStack>
<VStack gap="2" alignItems="stretch" flex="1" minWidth="[220px]">
<Text variant="caption-md" color="neutral.text.low">
stacked — 과목별 합계를 함께 확인
</Text>
<div className={frame}>
<BarChart
data={data}
xKey="subject"
yKeys={['male', 'female']}
labels={labels}
groupMode="stacked"
showLegend
/>
</div>
</VStack>
</HStack>
);
}
단일 시리즈
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartSingleExample = () => <BarChart data={monthlyData} xKey="month" yKeys={['revenue']} showLegend />;
export default BarChartSingleExample;
Hover Tooltip
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartHoverTooltipExample = () => (
<BarChart
data={monthlyData}
xKey="month"
yKeys={['revenue']}
labels={{ revenue: '매출' }}
showTooltip
/>
);
export default BarChartHoverTooltipExample;
그룹 막대
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartGroupedExample = () => (
<BarChart
data={monthlyData}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="grouped"
labels={{ revenue: '매출', cost: '비용' }}
showLegend
/>
);
export default BarChartGroupedExample;
패턴 채우기
import { BarChart } from '@mildang/design-system/Chart';
import { token } from '@mildang/styled-system/tokens';
import { createElement } from 'react';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartPatternFillExample = () => (
<BarChart
data={monthlyData}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="grouped"
labels={{ revenue: '매출', cost: '비용' }}
paints={[
{
type: 'pattern',
patternId: 'bar-chart-revenue-lines',
legendFill: token('colors.info.surface.base'),
stroke: token('colors.info.border.highest'),
definition: createElement(
'pattern',
{
id: 'bar-chart-revenue-lines',
width: 8,
height: 8,
patternUnits: 'userSpaceOnUse',
},
createElement('rect', {
width: 8,
height: 8,
fill: token('colors.info.surface.base'),
}),
createElement('path', {
d: 'M-2,2 l4,-4 M0,8 l8,-8 M6,10 l4,-4',
stroke: token('colors.info.border.highest'),
strokeWidth: 1.5,
})
),
},
{
type: 'solid',
fill: token('colors.warning.surface.high'),
stroke: token('colors.warning.border.highest'),
},
]}
showLegend
showTooltip
/>
);
export default BarChartPatternFillExample;
스택 막대
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartStackedExample = () => (
<BarChart
data={monthlyData}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="stacked"
labels={{ revenue: '매출', cost: '비용' }}
showLegend
showTooltip
/>
);
export default BarChartStackedExample;
가로 막대
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartHorizontalExample = () => <BarChart data={monthlyData} xKey="month" yKeys={['revenue']} layout="horizontal" />;
export default BarChartHorizontalExample;
값 라벨 (단일)
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartSingleWithLabelsExample = () => <BarChart data={monthlyData} xKey="month" yKeys={['revenue']} showValueText />;
export default BarChartSingleWithLabelsExample;
값 라벨 (그룹)
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartGroupedWithLabelsExample = () => (
<BarChart
data={monthlyData}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="grouped"
labels={{ revenue: '매출', cost: '비용' }}
showValueText
/>
);
export default BarChartGroupedWithLabelsExample;
값 라벨 (스택 합계)
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartStackedWithLabelsExample = () => (
<BarChart data={monthlyData} xKey="month" yKeys={['revenue', 'cost']} groupMode="stacked" showValueText />
);
export default BarChartStackedWithLabelsExample;
값 라벨 (가로)
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartHorizontalWithLabelsExample = () => (
<BarChart data={monthlyData} xKey="month" yKeys={['revenue']} layout="horizontal" showValueText />
);
export default BarChartHorizontalWithLabelsExample;
값이 0인 경우
import { BarChart } from '@mildang/design-system/Chart';
const zeroData = [
{ month: '1월', revenue: 4200, cost: 0 },
{ month: '2월', revenue: 0, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 0 },
{ month: '4월', revenue: 0, cost: 0 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 0, cost: 3800 },
];
const BarChartWithZeroValuesExample = () => (
<BarChart
data={zeroData}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="grouped"
labels={{ revenue: '매출', cost: '비용' }}
showLegend
showTooltip
showValueText
/>
);
export default BarChartWithZeroValuesExample;
전체 0
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartAllZeroExample = () => (
<BarChart
data={monthlyData.map((d) => ({ ...d, revenue: 0, cost: 0 }))}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="grouped"
labels={{ revenue: '매출', cost: '비용' }}
showLegend
/>
);
export default BarChartAllZeroExample;
반응형 (너비 자동 조정)
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartResponsiveExample = () => (
<div style={{ display: 'flex', flexDirection: 'column', gap: 32, width: '100%' }}>
{([280, 480, 720] as const).map((w) => (
<div key={w} style={{ width: w }}>
<div style={{ marginBottom: 4, fontSize: 11, color: '#888' }}>{w}px</div>
<div style={{ width: w, height: 240 }}>
<BarChart
data={monthlyData}
xKey="month"
yKeys={['revenue', 'cost']}
groupMode="grouped"
labels={{ revenue: '매출', cost: '비용' }}
showLegend
/>
</div>
</div>
))}
</div>
);
export default BarChartResponsiveExample;
Compound 패턴 — 커스텀 라벨 포맷
import { BarChart } from '@mildang/design-system/Chart';
const monthlyData = [
{ month: '1월', revenue: 4200, cost: 2800 },
{ month: '2월', revenue: 3800, cost: 2500 },
{ month: '3월', revenue: 5100, cost: 3200 },
{ month: '4월', revenue: 4600, cost: 3000 },
{ month: '5월', revenue: 5800, cost: 3500 },
{ month: '6월', revenue: 6200, cost: 3800 },
];
const BarChartCompoundWithCustomLabelsExample = () => (
<BarChart data={monthlyData} xKey="month" yKeys={['revenue', 'cost']} groupMode="grouped">
<BarChart.Grid />
<BarChart.XAxis hideTicks hideAxisLine />
<BarChart.YAxis hideTicks hideAxisLine />
<BarChart.Bars />
<BarChart.ValueText format={(v: number) => `${(v / 1000).toFixed(1)}k`} />
</BarChart>
);
export default BarChartCompoundWithCustomLabelsExample;