SpreadsheetGrid
ガイド

ラベル行(見出し / 区切り行)

labelRow で rows に混在させた見出し行を全幅の帯で描画する(行数に数えない・セクション内ソート・縦固定)

labelRow prop を渡すと、rows の中の特定の行を「見出し(区切り)行」として扱えます。Excel のシートに置く節見出しの行と同じもので、データ行の間に置いたその位置に全幅の帯として描画され、行数には数えません(行番号を消費せず、編集 / 選択 / コピー / エクスポートの既定対象外)。行の型 T も rows / onRowsChange の型も変わらないため、Excel / CSV 取り込みデータの形そのままで使えます。

行グルーピングとの違い

見た目は似ていますが、行グルーピングとは別の機能です。

ラベル行(labelRow)行グルーピング(rowGroup)
何をするかrows の中に置いた位置の見出し行を帯で描く列の値で行をまとめ直し、グループ行を作る
並び順rows の並びそのまま(ソートはセクション内に閉じる)グループ単位に並び替わる
集計 / ツリー / 開閉無しあり(aggFunc / 自動グループ列 / 開閉)
データ源行データそのもの(isLabelRow で識別)列定義(rowGroup: true)
併用不可(rowGroup 有効中はラベル行を表示しない)

「データに区切りがある(見積書の工程ごと・帳票の節ごと)」ならラベル行、「列の値でまとめ直して集計したい」ならグルーピングです。

デモ(見積明細 > 工程ごとの見出し)

ToolbarRows: 16 / 16Columns: 7 / 7Sort: なし
#
品番
1
3B0620AEZ6
2
6FA000B357
3
7641205200
4
7641205401
5
GA23930PB1
6
GA23938PS1
7
6DA000B450
8
GA23941PB2
9
6DA006B450
10
6A00380198
11
6FFA000B60
12
6A00380221
13
9C0011A001
14
9C0011A014
15
9C0011A027
16
9C0011A033
工程ベルトコンベヤー(TAC23A0042)4 件
工程パターンフィーダー(MDST)4 件
工程搬送ローラー モジュール台4 件
工程制御盤(CB-2)4 件
Rows: 16 / 16Columns: 7 / 7
Active: なしSelection: なしCells: 0 / Rows: 0Cols: 0
  • kind: 'label' の行が見出しです。3 ペインを跨ぐ帯で描かれ、横にスクロールしても見出しは左端に留まります。
  • 縦にスクロールすると、現在の工程の見出しが列ヘッダー直下に固定され、次の見出しが来ると押し上げられて交代します(sticky: true)。
  • 列ヘッダーで並べ替えても、見出しの位置は動きません(並べ替えは各工程の中だけ)。「状態」列でフィルターすると、中身が 0 件になった工程は見出しごと消えます。
  • 行番号・件数(Rows: X / Y)は見出しを数えません。↑ / ↓ は見出しに止まらず、貼り付けも見出しを飛ばして続きます。

使い方

type Row = { id: string; kind?: 'label'; code: string; name: string; qty: number };

<SpreadsheetGrid
  rows={rows}                       // ラベル行はデータ行と同じ配列に混在させる
  columns={columns}
  rowKeyGetter={(row) => row.id}
  labelRow={{
    isLabelRow: (row) => row.kind === 'label',   // 必須: ラベル行の識別
    getLabel: (row) => row.name,                 // 必須: 表示文字列(エクスポート / aria にも使う)
    sticky: true,                                // 縦スクロール中も見出しをヘッダー直下に固定
    height: 34,                                  // 省略時は rowHeight
  }}
/>

React で装飾する(render)

render を渡すと中身を任意の React 要素にできます。ctx は { row, rowKey, rowIndex, sourceRowIndex, label, sectionRowCount } で、sectionRowCount は(フィルター後の)そのセクションのデータ行数です。

labelRow={{
  isLabelRow: (row) => row.kind === 'label',
  getLabel: (row) => row.name,
  render: ({ label, sectionRowCount }) => (
    <>
      <span className="rounded bg-blue-600 px-1.5 text-xs text-white">節</span>
      <strong>{label}</strong>
      <span className="text-gray-500">{sectionRowCount} 件</span>
    </>
  ),
  className: (row) => (row.important ? 'label-row--important' : undefined),
}}

既定表示(render 未指定)は左のアクセント線 + 太字で、色はトークン --ssg-label-row-bg / --ssg-label-row-text / --ssg-label-row-accent で調整できます。パーツ別スロットは classNames.labelRow(行要素)と classNames.labelRowContent(中身の器)です。

セクションとソート / フィルター

ラベル行から次のラベル行の直前までを 1 つのセクションとみなします(最初のラベル行より前の行は「ラベル無しの区間」)。ソートやフィルターをかけたときの扱いは sortMode で選べます。

sortMode動き
'section'(既定)並べ替えは各セクションの中だけで行い、ラベル行の位置は動かない。フィルターで中身が 0 件になったセクションはラベルごと消える(keepEmptySections: true で残す)
'follow'全体を並べ替え、ラベル行は「元のセクションの先頭に来るデータ行」の直前に付いて移動する(元から中身の無いセクションのラベルは、続くセクションのラベルの直前に並ぶ)
'hide'ソート / フィルター適用中はラベル行を表示しない

ソートもフィルターも無いときは、どのモードでも rows の並びそのものが表示されます。

縦スクロール固定(sticky)

sticky: true にすると、縦スクロール中に「現在のセクション」のラベル行が列ヘッダー直下に固定表示されます。次のラベル行の上端が固定帯の下端に到達すると、固定中の見出しが押し上げられて交代します(スマホの連絡先一覧のセクションヘッダーと同じ動き)。固定中の見出しも横スクロールで左端に留まります。

エクスポート

既定では出力に含みません(scope 'raw' でもデータ行としては出ません)。includeLabelRows: true で見出しを 1 行として出力できます。

gridRef.current?.downloadCsv('estimate.csv', { includeLabelRows: true });

const { columns, rows, rowKinds } = gridRef.current!.getExportData({ includeLabelRows: true });
// rowKinds[i] === 'label' の行は見出し。Excel 側で結合セル / 太字などを当てる

出力値は exportText で差し替えられます(文字列なら先頭列、配列なら列順にそのまま)。ExcelJS で結合セルにするレシピは API リファレンス を参照してください。

他機能との関係

  • 行ドラッグ並び替え: データ行はセクションを跨いで移動できます(移動先のセクションに所属が変わる)。ラベル行自体は掴めません。
  • 展開行: 併用できます。ラベル行は展開できません。
  • 行グルーピング: 併用できません。rowGroup 有効中はラベル行を表示しません(開発時警告)。
  • serverSide(SSRM): サーバーが getRows の結果にラベル行を含めて返し(totalRowCount にも数える)、isLabelRow で識別します。セクションの並べ替え / sectionRowCount / sticky / height はサーバー行モデルでは適用されません。

オプションの一覧は props リファレンス を参照してください。

On this page