본문으로 건너뛰기
Dot Design System
v0.3.1

Table

정렬된 열을 따라 많은 레코드를 빠르게 비교합니다.

목적

Table은 여러 record의 같은 속성을 행과 열로 정렬해 빠르게 비교하게 한다. 복잡한 운영 데이터를 숨기지 않으면서 이름, 상태, 수치, 다음 행동의 위치를 반복해 사용자가 판단 흐름을 익힐 수 있게 한다.

선택 기준

  • 같은 속성을 가진 여러 record를 비교·정렬·검토할 때 사용한다.
  • 한 대상의 설명이나 순서가 없는 key-value 정보에는 description list를 검토한다.
  • 작은 화면에서 핵심 열을 보존할 수 없다면 record list로 전환한다.
  • 각 record가 서로 다른 구조라면 Table에 억지로 맞추지 않는다.

구조

Table 안에 TableHeader, TableBody, 필요할 때 TableFooter를 둔다. 각 section은 TableRow를 포함하고 header cell은 TableHead, data cell은 TableCell을 사용한다. 표의 목적이나 보충 설명에는 TableCaption을 사용할 수 있다.

Table root는 horizontal overflow wrapper를 내부에 만든다. 이름과 설명은 왼쪽, 상태와 수치는 비교하기 좋은 열, 행 action은 오른쪽에 둔다.

변형과 크기

별도 variant나 size prop은 없다. header 높이는 40px이고 cell 기본 padding은 8px이다. row는 border와 hover 배경을 가지며 data-state="selected"일 때 selected 배경을 사용한다. Footer는 muted background와 medium weight를 사용한다.

한 Table 안에서는 같은 density를 유지한다. 더 여유로운 행이 필요하면 모든 header와 cell class를 함께 조정한다.

상태와 동작

Table 자체는 sorting, selection, pagination, loading을 관리하지 않는다. 제품이 header button, checkbox, pagination과 상태를 명시적으로 구성한다. Row의 selected 스타일은 data-state에 반응하지만 selection semantics나 event는 자동으로 제공하지 않는다.

loading, empty, error는 같은 table frame 가까이에서 교체해 filter와 결과 맥락을 유지한다. 행 전체 이동을 제공하더라도 내부 action과 click 충돌을 피한다.

콘텐츠

Header는 짧고 반복 가능한 속성명으로 쓴다. 단위는 header에 포함해 cell마다 반복하지 않는다. 숫자는 오른쪽 정렬과 tabular-nums를 검토한다. 상태는 text label을 포함하고 빈 값은 - 하나보다 미지정, 기록 없음처럼 의미가 필요할지 판단한다.

접근성

TableHead에 필요한 scope="col" 또는 scope="row"를 제품이 지정한다. Caption이나 주변 heading으로 표의 목적을 제공한다. 정렬 control은 실제 Button과 현재 정렬 상태를 사용한다. clickable row만 제공하지 말고 keyboard로 접근 가능한 Link나 Button이 행 안에 있어야 한다.

좁은 화면과 긴 콘텐츠

root의 horizontal overflow는 데이터 손실을 막는 마지막 수단이다. 좁은 화면에서는 핵심 식별자, 상태, 주 action을 record list로 재배치하고 모든 핵심 정보와 행동을 유지한다. 긴 이름은 첫 열의 너비와 말줄임을 조절하되 전체 값을 확인할 방법을 제공한다.

공개 API

  • Table: native table과 horizontal overflow wrapper
  • TableHeader, TableBody, TableFooter: thead, tbody, tfoot
  • TableRow: tr; data-state="selected" 스타일 지원
  • TableHead, TableCell: th, td
  • TableCaption: caption

sorting, selection, pagination, loading 전용 prop은 없다.

예제

사용 코드 · TSX
import {
  Badge,
  Table,
  TableBody,
  TableCell,
  TableHead,
  TableHeader,
  TableRow,
} from '@classum/dot-design-system/ui';

export function CurriculumTable() {
  return (
    <Table>
      <TableHeader>
        <TableRow>
          <TableHead scope="col">커리큘럼</TableHead>
          <TableHead scope="col">상태</TableHead>
          <TableHead scope="col" className="text-right">
            학습자
          </TableHead>
        </TableRow>
      </TableHeader>
      <TableBody>
        <TableRow>
          <TableCell className="font-medium">신규 입사자 온보딩</TableCell>
          <TableCell>
            <Badge variant="success">운영 중</Badge>
          </TableCell>
          <TableCell className="text-right tabular-nums">24명</TableCell>
        </TableRow>
      </TableBody>
    </Table>
  );
}

피해야 할 사용

  • 반복 데이터를 모두 Card로 바꾸거나 반대로 서로 다른 구조를 Table에 넣지 않는다.
  • 작은 화면에서 글자와 열만 줄여 모든 column을 억지로 유지하지 않는다.
  • Row click만 제공하고 keyboard용 Link나 Button을 생략하지 않는다.
  • header 없이 값의 의미를 색과 위치로만 전달하지 않는다.
  • loading, empty, error에서 filter와 table frame 전체를 사라지게 하지 않는다.

관련 항목