React Table v8 で 外から判定のルールを渡せるフラグを表示するセルを作る
こんにちはフロントエンドエンジニアの茶木です。
前回の記事で、React Table V8 で 行ごとの任意の cell の 値にアクセスしてフラグを表示するセルを作成しました。
前回記事の振り返り
const columnHelper = createColumnHelper<Forum>();
const columns = [
{
header: "フラグ",
cell: FlagCell,
},
columnHelper.accessor("unread", {
header: "未読数",
}),
columnHelper.accessor("timestamp", {
header: "更新日",
cell: DateCell,
}),
columnHelper.accessor("title", {
header: "タイトル",
}),
];
const table = useReactTable<Forum>({
data: rows,
columns,
getCoreRowModel: getCoreRowModel(),
});
このような columns
で示されるようなテーブルがあったとします。フラグ、未読数、更新日、タイトルという列を持ちますが、フラグはそれ以外の列から計算されるものとします。
type Props = CellContext<Folum, undefined>
export const FlagCell = (props: Props): ReactElement => {
const { unread } = props.row.origin;
return <Cell>{ unread > 0 ? "🚩" : " " }</Cell>;
};
たとえば、未読があればフラグを表示するセルならこのように、
import { isToday } from "date-fns";
type Props = CellContext<Folum, undefined>
export const FlagCell = (props: Props): ReactElement => {
const { timestamp } = props.row.origin;
const date = new Date(timestamp);
return <Cell>{ isToday(date) ? "🚩" : " " }</Cell>;
};
たとえば、本日の更新があればフラグを表示するセルならこのように書けます。
でも、見た目の部分は共通なので、判定のルールは 外から渡せると汎用的になりそうです。React Table の Cell
に外から値を渡す方法についてまとめます。
column の meta プロパティを使う
const columns = [
columnHelper.accessor("id", {
header: "フラグ",
cell: FlagCell,
meta: { rule: "unread" },
}),
]
column
は meta
プロパティを持ち、meta
プロパティは任意のプロパティを持たせて使う想定です。
import "@tanstack/react-table";
declare module "@tanstack/table-core" {
interface ColumnMeta<TData extends RowData, TValue> {
rule: "unread" | "today";
}
}
TypeScript と併用する場合、ColumnMeta
の型定義を拡張しておくと便利です。 今回は rule
というプロパティを meta
に持たせます。
Cell で meta プロパティから受け取る
export const FlagCell = (props: Props): ReactElement => {
props.column.columnDef.meta?.rule
};
Cell の props.column.columnDef
から column に指定したプロパティを取得できます。 meta
も column に指定したプロパティです。
実装
const isFlaged = ({
row: { original },
column: {
columnDef: { meta },
},
}: Props): boolean => {
switch (meta?.rule) {
case "unread":
return original.unread > 0;
case "today":
return isToday(original.timestamp);
default:
throw new Error();
}
};
export const FlagCell = (props: Props): ReactElement => {
if (isFlaged(props)) {
return <Cell>🚩</Cell>;
}
return <Cell> </Cell>;
};
ソースの説明です。meta.rule
で適用する判定ルールを切り替えます。original
にアクセスすることで各列のセルの値を取得できます。詳しくは前回の記事で述べています。
columnHelper.accessor("id", {
header: "フラグ",
cell: FlagCell,
meta: { rule: "today" },
}),
呼び出し側は、このようになります。meta.rule
に 判定ルールを渡します。
おわりに
accesor
に "id"
を渡していますが、これは Cell 内で未使用です。(なので他の column名を渡しても同じです)この部分は改良の余地があります。
また、React Table での meta
の使用は便利ではあるのですが、あまり多用すると複雑になるので、セルの機能が明確に別とみなせる場合は、新しくセルを作る方がわかりやすい運用になると考えます。
Gaji-Laboでは、React経験が豊富なフロントエンドエンジニアを募集しています
弊社ではReactの知見で事業作りに貢献したいフロントエンドエンジニアを募集しています。大きな制作会社や事業会社とはひと味もふた味も違うGaji-Laboを味わいに来ませんか?
もちろん、一緒にお仕事をしてくださるパートナーさんも随時募集中です。まずはお気軽に声をかけてください。お仕事お問い合わせや採用への応募、共に大歓迎です!
求人応募してみる!