CSS / display 속성으로 표 만들기 - table, table-row, table-cell

display: table, table-row, table-cell을 부모·행·셀에 각각 지정하면 HTML 요소를 표 배치 방식으로 정렬할 수 있습니다. 같은 열의 경계와 같은 행의 높이를 맞추거나 셀 안의 내용을 세로 정렬할 때 사용할 수 있습니다. 다만 CSS로 표처럼 보이게 하는 것과 HTML 데이터 표의 의미를 제공하는 것은 구분해야 합니다.

table·table-row·table-cell의 역할

값 배치 역할
table 표 전체의 배치 영역
table-row 한 행
table-cell 행 안의 셀
table-row-group 여러 행을 묶는 그룹
table-header-group·table-footer-group 머리행·꼬리행 그룹
table-column·table-column-group 열·열 그룹
table-caption 표의 캡션 위치

기본 구조는 table 안에 table-row를 두고, 그 안에 table-cell을 넣는 것입니다. 누락된 표 배치 상자를 브라우저가 보완하는 경우도 있지만 그 동작에 기대기보다 계층을 명확하게 작성하면 너비와 정렬을 이해하기 쉽습니다. 열 그룹이나 캡션 값은 필요할 때만 사용하고 단순한 두 열 배치에 모두 넣을 필요는 없습니다.

전체 예제: 이름과 설명을 두 열로 정렬하기

아래 코드를 display-table.html로 저장해 실행합니다. 강좌명과 학습 방법처럼 이름·값을 짝지은 내용이므로 HTML은 설명 목록인 dl·dt·dd를 사용합니다. CSS로 넓은 화면에서는 두 열로 정렬하고, 480px 이하에서는 각 이름 바로 아래에 값을 배치합니다. 외부 라이브러리는 필요하지 않습니다.

<!doctype html>
<html lang="ko">
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <title>CSS 표 배치로 설명 목록 정렬</title>
  <style>
    body { margin: 20px; font: 16px/1.6 "Noto Sans KR", sans-serif; color: #203348; }
* { box-sizing: border-box; }
    .details { display: table; width: 100%; max-width: 650px; margin: 0;
      table-layout: fixed; border-collapse: collapse; }
    .row { display: table-row; }
    .details dt, .details dd { display: table-cell; padding: 12px;
      border: 1px solid #97a9bb; overflow-wrap: anywhere; }
    .details dt { width: 30%; background: #edf3fa; font-weight: 700; vertical-align: middle; }
    .details dd { margin: 0; vertical-align: top; }
    @media (max-width: 480px) {
      .details, .row, .details dt, .details dd { display: block; }
      .details dt { width: auto; }
    }
  </style>
</head>
<body>
<h1>강좌 정보</h1>
<dl class="details">
  <div class="row">
    <dt><span>강좌명</span></dt>
    <dd>CSS 기초</dd>
  </div>
  <div class="row">
    <dt><span>학습 방법</span></dt>
    <dd>예제 파일을 저장하고 브라우저에서 실행합니다.<br>값을 하나씩 바꿔 배치가 달라지는 이유를 확인합니다.</dd>
  </div>
</dl>
</body>
</html>

넓은 화면에서는 두 행의 이름 열이 같은 너비를 사용하고, 내용이 긴 두 번째 행의 높이가 자동으로 커집니다. 이름은 셀 안에서 세로 중앙에, 설명은 위쪽에 놓입니다. 개발자 도구에서 dl, row, dt를 차례로 선택하면 display 값이 table, table-row, table-cell로 계산되는지 확인할 수 있습니다.

너비·세로 정렬·여백을 조절하기

table의 너비를 100%로 정하고 최대 너비를 650px로 제한했습니다. 첫 열은 30%, 남은 공간은 설명 열이 사용합니다. table-layout: fixed는 내용의 길이보다 이 너비 규칙을 기준으로 열을 배치하도록 합니다. 긴 파일 이름처럼 끊을 곳이 없는 문자열을 넣을 때도 열 밖으로 흘러나오지 않도록 overflow-wrap을 지정했습니다.

첫 열의 30%를 40%로 바꾸면 설명 열이 좁아지는 것을 확인할 수 있습니다. 비교 후 30%로 되돌리세요. dt의 vertical-align: middle을 top 또는 bottom으로 바꾸면 여러 줄 설명 옆에서 이름의 위치가 달라집니다. vertical-align은 table-cell 내부의 내용을 정렬하는 것이며 일반 block 요소의 수직 중앙 정렬 방법으로 그대로 옮길 수는 없습니다.

셀 사이 여백을 만들려고 table-cell에 margin을 주어도 일반 블록과 같은 효과가 나지 않습니다. 셀 안쪽은 padding으로 조절합니다. 셀 사이 간격을 별도로 두려면 표 배치 컨테이너에 border-collapse: separate와 border-spacing을 사용합니다. 예제처럼 collapse를 쓰면 border-spacing은 적용되지 않습니다.

모바일 배치와 HTML 표를 선택할 기준

창을 480px 이하로 줄이면 미디어 쿼리가 표 배치 값을 block으로 바꿉니다. 이름과 설명의 순서는 HTML에 적힌 순서 그대로 유지됩니다. dt의 width도 auto로 되돌려 이전의 30%가 좁은 블록에 남지 않게 했습니다. 다시 창을 넓히면 두 열 배치가 복구됩니다.

여러 행·열의 수치를 비교하는 데이터 표라면 처음부터 <table>, <th>, <td>와 적절한 제목 셀을 사용하세요. div에 table-cell을 붙였다는 이유만으로 데이터 표의 제목 관계까지 제공되는 것은 아닙니다. 일반 카드·페이지 레이아웃을 새로 만든다면 Flexbox나 Grid도 비교하고, CSS 표 배치는 기존 코드의 구조나 열 정렬 요구에 맞을 때 선택하면 됩니다.

값별 역할은 MDN의 display 설명에서, 표 배치의 너비·여백·세로 정렬 원리는 W3C의 CSS 표 모델에서 확인할 수 있습니다. 예제의 HTML 구조는 설명 목록 dl 요소를 사용합니다.