Zudo Token Panel

Type to search...

to open search from anywhere

グループ化パレットタブ

colorExtras なしで、複数カラーグループ・OKLCH 編集・WCAG コントラストチェックを備えたスタンドアロン Palette タブを組み込む。

Palette タブは、カラークラスターに紐付かないスタンドアロンのカラーパレット専用タブです。 予約済みの 'color'/'color-secondary' タブ(colorExtras が必須)とは異なり、 Palette タブは複数グループの OKLCH カラートークンを保持し、2 つの操作モードを提供します。

  • Edit モード — 各グループのステップ全体にわたって Lightness / Chroma / Hue を調整する X-Y カーブエディター。
  • Check モード — 任意の 2 ステップが WCAG のコントラスト比要件を満たしているか確認する Left/Right コントラストチェッカー。

カラースキームテーブルを必要としない独立した名前付きカラーステップ(グレースケール・ブランド・アクセントなど)が欲しいときに使用してください。

データモデルの規約

TabConfig を書く前に、Palette タブが適用する 3 つのルールを確認してください。

  1. colorExtras は省略必須。 省略することで resolveColorClusterFromTab が実行されなくなり、複数の kind: 'color' 階層を 1 つのタブに安全に共存させることができます。
  2. 1 階層 = 1 グループ。TierConfig は名前付きカラーグループを表します。label が UI のグループ見出しになります。
  3. CSS 変数名の規約: --palette-{group}-{n}{group} は階層の id{n} は 1 始まりのステップ番号です。

ステップ 1: Palette タブを宣言する

// src/lib/my-tabs.ts
import type { PanelConfig } from '@takazudo/zdtp';

type TabConfig = PanelConfig['tabs'][number];

export const paletteTab: TabConfig = {
  id: 'palette',
  label: 'Palette',
  // colorExtras intentionally omitted — required for multiple kind:'color' tiers
  // to be safe in one tab. The Palette tab relies on this absence.
  tiers: [
    {
      id: 'grayscale',
      label: 'Grayscale',
      items: [
        {
          id: 'grayscale-1',
          cssVar: '--palette-grayscale-1',
          label: 'Grayscale 1',
          default: 'oklch(95% 0.005 240)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'grayscale-2',
          cssVar: '--palette-grayscale-2',
          label: 'Grayscale 2',
          default: 'oklch(80% 0.008 240)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'grayscale-3',
          cssVar: '--palette-grayscale-3',
          label: 'Grayscale 3',
          default: 'oklch(55% 0.010 240)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'grayscale-4',
          cssVar: '--palette-grayscale-4',
          label: 'Grayscale 4',
          default: 'oklch(30% 0.012 240)',
          type: { kind: 'color', format: 'oklch' },
        },
      ],
    },
    {
      id: 'brand',
      label: 'Brand',
      items: [
        {
          id: 'brand-1',
          cssVar: '--palette-brand-1',
          label: 'Brand 1',
          default: 'oklch(90% 0.08 250)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'brand-2',
          cssVar: '--palette-brand-2',
          label: 'Brand 2',
          default: 'oklch(70% 0.16 250)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'brand-3',
          cssVar: '--palette-brand-3',
          label: 'Brand 3',
          default: 'oklch(50% 0.20 250)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'brand-4',
          cssVar: '--palette-brand-4',
          label: 'Brand 4',
          default: 'oklch(30% 0.18 250)',
          type: { kind: 'color', format: 'oklch' },
        },
      ],
    },
    {
      id: 'accent',
      label: 'Accent',
      items: [
        {
          id: 'accent-1',
          cssVar: '--palette-accent-1',
          label: 'Accent 1',
          default: 'oklch(88% 0.10 55)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'accent-2',
          cssVar: '--palette-accent-2',
          label: 'Accent 2',
          default: 'oklch(68% 0.18 50)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'accent-3',
          cssVar: '--palette-accent-3',
          label: 'Accent 3',
          default: 'oklch(48% 0.22 45)',
          type: { kind: 'color', format: 'oklch' },
        },
        {
          id: 'accent-4',
          cssVar: '--palette-accent-4',
          label: 'Accent 4',
          default: 'oklch(30% 0.16 42)',
          type: { kind: 'color', format: 'oklch' },
        },
      ],
    },
  ],
};

paletteTabPanelConfig.tabs に追加します。

// src/lib/my-panel-config.ts
import type { PanelConfig } from '@takazudo/zdtp';
import { paletteTab } from './my-tabs';

export const myPanelConfig: PanelConfig = {
  storagePrefix: 'myapp-design-token-panel',
  consoleNamespace: 'myapp',
  modalClassPrefix: 'myapp-design-token-panel-modal',
  schemaId: 'myapp-design-tokens/v1',
  exportFilenameBase: 'myapp-design-tokens',
  tabs: [
    paletteTab,
    // …他のタブ…
  ],
  applyEndpoint: 'http://127.0.0.1:24681/apply',
  applyRouting: {
    // 'palette' は --palette-* で始くすべての CSS 変数にマッチし、
    // このファイルへルーティングします。Apply 時に bin が :root ブロックをアトミックに書き換えます。
    palette: 'src/styles/palette.css',
  },
};

📝 Note

applyRouting のキー 'palette'--palette- で始まるすべての CSS 変数にマッチします。 プレフィックスを変更する場合(例: --myapp-palette-)は、ルーティングキーとすべての cssVar 文字列を合わせて更新してください。

ステップ 2: ホストスタイルシートに CSS 宣言を追加する

:root 内にすべてのパレット変数を宣言します。Apply to source files をクリックすると、apply パイプラインがこのブロックを書き換えます。

/* src/styles/palette.css */
:root {
  /* Grayscale */
  --palette-grayscale-1: oklch(95% 0.005 240);
  --palette-grayscale-2: oklch(80% 0.008 240);
  --palette-grayscale-3: oklch(55% 0.010 240);
  --palette-grayscale-4: oklch(30% 0.012 240);

  /* Brand */
  --palette-brand-1: oklch(90% 0.08 250);
  --palette-brand-2: oklch(70% 0.16 250);
  --palette-brand-3: oklch(50% 0.20 250);
  --palette-brand-4: oklch(30% 0.18 250);

  /* Accent */
  --palette-accent-1: oklch(88% 0.10 55);
  --palette-accent-2: oklch(68% 0.18 50);
  --palette-accent-3: oklch(48% 0.22 45);
  --palette-accent-4: oklch(30% 0.16 42);
}

ステップ 3: CSS でパレット変数を使う

スタイルシート内の任意の場所でパレットトークンを参照します。パネルはキーストロークごとに :root をインメモリで上書きするため、変更は即座に反映されます。

.myapp-hero {
  background-color: var(--palette-brand-2);
  color: var(--palette-grayscale-1);
}

.myapp-badge {
  background-color: var(--palette-accent-2);
}

.myapp-text-muted {
  color: var(--palette-grayscale-3);
}

ステップ 4: 2 つのパネルモードを活用する

パネルを開き(デフォルト: Alt+Shift+P、または window.myapp.showDesignPanel())、Palette タブに移動します。

Edit モード(デフォルト)

Edit モードでは各グループの X-Y カーブエディターが表示されます。カーブのハンドルをドラッグすると、グループ内のすべてのステップにわたって Lightness・Chroma・Hue のランプを一括調整できます。チャート上のステップを直接クリックして個別に微調整することも可能です。

ドラッグ中は :root のすべてのパレット変数がリアルタイムで更新されます。

Check モード

Check トグルをクリックして WCAG コントラストチェックに切り替えます。Left と Right の 2 つのカラースウォッチが表示されます。任意のグループから 2 つのパレットステップを選択すると、パネルがコントラスト比を計算し、AA または AAA 基準を満たしているかを表示します。

パレットを確定する前に、テキストカラーが背景カラーとのコントラスト要件を満たしているか確認するために使用してください。

ステップ 5: パレット変更をソースファイルに書き戻す

パレットの内容に満足したら、パネルの Apply to source files をクリックします。zdtp-server bin が applyRouting を参照し、すべての --palette-* 変数を src/styles/palette.css にマッチさせ、そのファイル内の :root {} ブロックを現在のパネル値で書き換えます。

bin を開発サーバーと並行して起動します。

pnpm exec zdtp-server \
  --routing ./panel-routing.json \
  --write-root ./src/styles \
  --allow-origin http://localhost:5173

panel-routing.json の内容:

{
  "palette": "src/styles/palette.css"
}

💡 Tip

ルーティング JSON を PanelConfig にインポートすることで、UI 設定と bin を同期させられます。

import routing from '../../panel-routing.json' assert { type: 'json' };

export const myPanelConfig: PanelConfig = {
  // …
  applyRouting: routing,
};

CSS 変数名に --palette-{group}-{n} を使う理由

この規約により、applyRouting が短いキー 1 つですべてのパレット変数をルーティングできます。新しいグループを追加する場合も同じパターンに従ってください。

| グループ階層 id | ステップ 1 の cssVar | ステップ 2 の cssVar | … | | --- | --- | --- | --- | | grayscale | --palette-grayscale-1 | --palette-grayscale-2 | … | | brand | --palette-brand-1 | --palette-brand-2 | … | | accent | --palette-accent-1 | --palette-accent-2 | … |

アイテムの id も同じ {group}-{n} パターン(例: grayscale-1)に従い、タブ全体で一意である必要があります。永続化されたオーバーライドマップはアイテム id をキーとして使用するためです。

関連ページ

Revision History