ParetoChart
recharts 기반 파레토 차트 컴포넌트. 내림차순 막대와 누적 % 선을 함께 그립니다.
개요
첫 번째 시리즈를 Y값 내림차순으로 정렬해 막대로 그리고, 누적 백분율 선을 오른쪽 축(0–100%)에 그립니다. 누적 %는 전체 합 대비 반올림한 정수입니다. 품질 관리, 원인 분석 등에 씁니다.
주요 특징
- ✅ 자동 정렬: 입력 순서와 무관하게 값이 큰 항목부터 그린다
- ✅ 누적 % 선: 오른쪽 축 0–100%, 툴팁 값에 %가 붙는다. 이름은
cumulativeName, 곡선은curve(기본 linear) - ✅ 데이터 라벨: 막대에만 붙는다.
dataLabelPosition,labelKey - ✅ 범례 토글: 막대와 누적선을 따로 숨긴다. 누적 %는 숨김과 무관하게 전체 데이터 기준이다
- ✅ 숫자 서식:
thousandSeparator, 축 눈금 포맷터(왼쪽 값 축) - ✅ 컨테이너: 제목·도구·검색 폼·접기
기본 사용
series의 첫 시리즈만 씁니다. 막대 이름은 시리즈 name(없으면 yKey), 누적선 이름은 cumulativeName(기본 "누적 %")입니다.
Preview
누적 % 선
입력 순서가 섞여 있어도 값 내림차순으로 다시 정렬하고, 누적 백분율을 오른쪽 축에 그립니다. 툴팁은 같은 x의 막대와 누적선을 함께 보이고 누적선 값에 %를 붙입니다. 누적선 이름은 cumulativeName, 곡선 종류는 curve(recharts 곡선 종류, 기본 "linear")로 바꿉니다.
Preview
범례·툴팁 끄기 (legend, tooltip)
둘 다 기본으로 켜져 있습니다.
Preview
데이터 라벨 (showDataLabel, dataLabelPosition, labelKey)
라벨은 막대에만 붙고 누적선에는 없습니다. 위치는 "outside"(기본)·"insideEnd"·"center"·"insideStart" 중에서 고릅니다. 시리즈 labelKey를 주면 그 필드를 라벨로 씁니다.
Preview
천 단위 구분자 (thousandSeparator)
왼쪽 값 축 눈금, 막대 라벨, 툴팁에 함께 걸립니다. 오른쪽 % 축은 그대로입니다.
Preview
축 눈금 서식 (xAxisTickFormatter, yAxisTickFormatter)
yAxisTickFormatter는 왼쪽 값 축에만 걸립니다. 오른쪽 누적 축은 % 고정입니다.
Preview
축별 격자 (showXAxisGrid, showYAxisGrid)
Y축 격자는 왼쪽 값 축 눈금을 따릅니다. 오른쪽 % 축은 격자가 없습니다. 이 예는 세로선만 숨깁니다.
Preview
모서리 둥글기 (borderRadius)
막대 모서리를 둥글립니다. 기본은 0입니다.
Preview
색상 (colors)
첫 색은 막대, 둘째 색은 누적선입니다.
Preview
범례 클릭 토글 (legendToggle)
범례 항목을 누르면 막대나 누적선을 숨기고, 다시 누르면 보입니다. 숨긴 항목은 범례에 흐리게 남습니다. 막대를 숨겨도 왼쪽 축은 남고 누적 %는 전체 데이터 기준입니다. 시리즈 이름과 cumulativeName이 같아도 둘을 따로 숨깁니다. 기본으로 켜져 있고 legendToggle={false}로 끕니다.
Preview
포인트 클릭 (onPointClick)
막대만 클릭됩니다. payload는 정렬 뒤에도 클릭한 막대의 원본 행(series[0].data[j] 그 객체)입니다.
Preview
막대를 클릭하세요
제목·도구·검색 폼 (title, actions, searchContent)
title을 주면 접고 펼 수 있는 머리가 생깁니다. actions는 머리 오른쪽에, searchContent는 차트 위 검색 폼 자리에 그립니다. 검색 폼은 24칸 격자이고 searchColumns·searchColGap·searchRowGap으로 바꿉니다. title이 없으면 actions·검색 폼·접기 props는 쓰이지 않습니다.
Preview
접기 (defaultCollapsed, collapseDisabled)
title이 있을 때 씁니다. 위는 접힌 채 시작하고, 아래는 접고 펼 수 없습니다.
Preview
빈 상태
데이터가 없으면 emptyText를 보입니다.
Preview
데이터가 없습니다
API Reference
Props
| Prop | Type | Default | Description |
|---|---|---|---|
series | ParetoChartSeries<Row>[] | - | 시리즈 배열. 첫 시리즈만 쓰고 값 내림차순으로 정렬한다 |
cumulativeName | string | "누적 %" | 누적선 이름 (범례·툴팁) |
curve | recharts CurveType | "linear" | 누적선 곡선 종류 |
colors | string[] | 기본 8색 | 막대·누적선 순서대로 쓰는 색. 모자라면 처음부터 다시 쓴다 |
legend | boolean | true | 범례 표시 |
legendToggle | boolean | true | 범례 항목을 눌러 막대·누적선 숨김·표시. 숨긴 항목은 범례에 흐리게 남는다 |
tooltip | boolean | true | 툴팁 표시 |
showDataLabel | boolean | false | 데이터 라벨 표시 |
dataLabelPosition | "outside" | "insideEnd" | "center" | "insideStart" | "outside" | 막대 데이터 라벨 위치. 누적선에는 라벨이 없다 |
thousandSeparator | boolean | false | 천 단위 구분자. 값 축 눈금·숫자 데이터 라벨·툴팁 (축 포맷터가 우선) |
xAxisTickFormatter | (value: string) => string | - | 범주 축 눈금 서식 |
yAxisTickFormatter | (value: number) => string | - | 값 축 눈금 서식 (왼쪽 축) |
showXAxisGrid | boolean | true | 범주 축 격자선 (세로선) |
showYAxisGrid | boolean | true | 값 축 격자선 (가로선) |
borderRadius | number | 0 | 막대 모서리 둥글기 (px) |
height | number | 350 | 차트 높이 (px) |
emptyText | string | "데이터가 없습니다" | 데이터가 없을 때 문구 |
onPointClick | (data: ParetoChartPointClickData<Row>) => void | - | 막대 클릭 콜백. payload는 원본 행 |
title | ReactNode | - | 제목. 주면 접고 펼 수 있는 머리가 생긴다 |
actions | ReactNode | - | title이 있을 때. 머리 오른쪽 도구 영역 |
defaultCollapsed | boolean | false | title이 있을 때. 접힌 채 시작 |
collapseDisabled | boolean | false | title이 있을 때. 접기·펼치기 막기 |
searchContent | ReactNode | - | title이 있을 때. 검색 폼 영역 (FormCol 등) |
searchColumns | number | 24 | title이 있을 때. 검색 폼 격자 칸 수 |
searchColGap | number | 15 | title이 있을 때. 검색 폼 가로 간격 (px) |
searchRowGap | number | 20 | title이 있을 때. 검색 폼 세로 간격 (px) |
readOnly | boolean | - | title이 있을 때. 검색 폼 읽기 전용 |
className | string | - | 차트 루트 CSS 클래스 |
style | CSSProperties | - | 차트 루트 인라인 스타일 |
ParetoChartSeries
| Field | Type | Required | Description |
|---|---|---|---|
data | Row[] | ✅ | 데이터 행 배열 |
xKey | string | ✅ | X값을 읽을 행 필드 키 |
yKey | string | ✅ | Y값을 읽을 행 필드 키 |
name | string | - | 시리즈 이름 (범례) |
labelKey | string | - | 데이터 라벨 문구를 읽을 행 필드 키. 값이 비면 Y값을 쓴다 |
ParetoChartPointClickData
| Field | Type | Description |
|---|---|---|
seriesName | string | 막대 이름 (시리즈 name, 없으면 yKey) |
seriesIndex | number | 시리즈 인덱스 |
xValue | unknown | 클릭한 막대의 X값 |
yValue | unknown | 클릭한 막대의 Y값 |
payload | Row | 클릭한 막대의 원본 행 (series[0].data[j] 그 객체. 정렬 뒤에도 원래 행) |
행 타입 (Row)
Props·Series·PointClickData는 행 타입 Row를 받습니다(기본 Record<string, unknown>). series의 data에서 추론되므로 onPointClick의 payload를 형 변환 없이 읽을 수 있습니다.
type SalesRow = { category: string; count: number; code: string }
const rows: SalesRow[] = [/* … */]
<ParetoChart
series={[{ data: rows, xKey: "category", yKey: "count" }]}
onPointClick={(d) => openDetail(d.payload.code)} // d.payload: SalesRow
/>접근성
권장 사항
- ✅ recharts
accessibilityLayer자동 활성화 - ✅ 빈 차트 시 대체 텍스트(emptyText) 제공
- ✅ 범례 항목은
aria-pressed버튼이라 키보드로 토글할 수 있다