@squadbase/vantage 0.6.1 → 0.6.2-dev1.01caa72

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (239) hide show
  1. package/dist/add-4GHF2TX2.js +6 -0
  2. package/dist/add-4GHF2TX2.js.map +1 -0
  3. package/dist/{build-O5TVNH4E.js → build-X5NVCQKT.js} +9 -9
  4. package/dist/{build-O5TVNH4E.js.map → build-X5NVCQKT.js.map} +1 -1
  5. package/dist/{check-WFBEDHDR.js → check-ZBIH422T.js} +7 -7
  6. package/dist/{check-WFBEDHDR.js.map → check-ZBIH422T.js.map} +1 -1
  7. package/dist/chunk-2ICNHUG6.js +1820 -0
  8. package/dist/chunk-2ICNHUG6.js.map +1 -0
  9. package/dist/{chunk-5ZOP4SQR.js → chunk-2N72FKLB.js} +12 -7
  10. package/dist/chunk-2N72FKLB.js.map +1 -0
  11. package/dist/{chunk-BCE22JSM.js → chunk-7DZGJQ3P.js} +33 -14
  12. package/dist/chunk-7DZGJQ3P.js.map +1 -0
  13. package/dist/{chunk-MXI3PZFT.js → chunk-7S52M2SL.js} +257 -210
  14. package/dist/chunk-7S52M2SL.js.map +1 -0
  15. package/dist/{chunk-QDZA5JSL.js → chunk-AABMKHEU.js} +4 -4
  16. package/dist/{chunk-QDZA5JSL.js.map → chunk-AABMKHEU.js.map} +1 -1
  17. package/dist/{chunk-KLEIVDUV.js → chunk-CEXAQQ5W.js} +150 -11
  18. package/dist/chunk-CEXAQQ5W.js.map +1 -0
  19. package/dist/{chunk-3G43C6OL.js → chunk-GNXCX4WE.js} +46 -3
  20. package/dist/chunk-GNXCX4WE.js.map +1 -0
  21. package/dist/chunk-IUPSBD6W.js +7914 -0
  22. package/dist/chunk-IUPSBD6W.js.map +1 -0
  23. package/dist/{chunk-JGRMRXXZ.js → chunk-JKLLFVEU.js} +3 -3
  24. package/dist/{chunk-JGRMRXXZ.js.map → chunk-JKLLFVEU.js.map} +1 -1
  25. package/dist/chunk-PDOBHMUQ.js +54 -0
  26. package/dist/chunk-PDOBHMUQ.js.map +1 -0
  27. package/dist/{chunk-ZVANIULZ.js → chunk-RNTDBX6S.js} +4 -4
  28. package/dist/{chunk-ZVANIULZ.js.map → chunk-RNTDBX6S.js.map} +1 -1
  29. package/dist/{chunk-A2UUGASH.js → chunk-U736PVHY.js} +2 -2
  30. package/dist/chunk-U736PVHY.js.map +1 -0
  31. package/dist/{chunk-PVTHHV7X.js → chunk-V3LF7BE7.js} +27 -5
  32. package/dist/chunk-V3LF7BE7.js.map +1 -0
  33. package/dist/{chunk-EP6JHXSR.js → chunk-WAMZWZJB.js} +54 -9
  34. package/dist/chunk-WAMZWZJB.js.map +1 -0
  35. package/dist/{chunk-DTDVSFRY.js → chunk-XQUSGIDG.js} +17 -3
  36. package/dist/chunk-XQUSGIDG.js.map +1 -0
  37. package/dist/cli.js +15 -11
  38. package/dist/cli.js.map +1 -1
  39. package/dist/client/index.d.ts +32 -3
  40. package/dist/client/index.js +205 -12
  41. package/dist/client/index.js.map +1 -1
  42. package/dist/components/index.d.ts +1983 -29
  43. package/dist/components/index.js +4 -3
  44. package/dist/{dev-NZRLOQCL.js → dev-4XEDTELV.js} +24 -13
  45. package/dist/dev-4XEDTELV.js.map +1 -0
  46. package/dist/doc/index.d.ts +4 -0
  47. package/dist/doc/index.js +107 -11
  48. package/dist/doc/index.js.map +1 -1
  49. package/dist/{docs-ZGDJUHJI.js → docs-JVP4RPKT.js} +3 -3
  50. package/dist/{docs-ZGDJUHJI.js.map → docs-JVP4RPKT.js.map} +1 -1
  51. package/dist/{doctor-VFKEMR54.js → doctor-5E2VEZPK.js} +8 -8
  52. package/dist/doctor-5E2VEZPK.js.map +1 -0
  53. package/dist/markdown/index.js +1 -1
  54. package/dist/markdown/index.js.map +1 -1
  55. package/dist/{preview-QDCIVVSR.js → preview-T6CLSQVX.js} +12 -4
  56. package/dist/preview-T6CLSQVX.js.map +1 -0
  57. package/dist/query/index.d.ts +0 -11
  58. package/dist/query/index.js +2 -2
  59. package/dist/{routes-RHP5FVGD.js → routes-3SGAFDMC.js} +6 -6
  60. package/dist/{routes-RHP5FVGD.js.map → routes-3SGAFDMC.js.map} +1 -1
  61. package/dist/{search-RFBELGY7.js → search-5LC4XPB5.js} +3 -3
  62. package/dist/{search-RFBELGY7.js.map → search-5LC4XPB5.js.map} +1 -1
  63. package/dist/slide/index.js +63 -17
  64. package/dist/slide/index.js.map +1 -1
  65. package/dist/table/index.js +11 -9
  66. package/dist/table/index.js.map +1 -1
  67. package/dist/ui/index.d.ts +148 -12
  68. package/dist/ui/index.js +1340 -87
  69. package/dist/ui/index.js.map +1 -1
  70. package/dist/{upgrade-GF2P67M6.js → upgrade-JHXZBGQS.js} +7 -7
  71. package/dist/{upgrade-GF2P67M6.js.map → upgrade-JHXZBGQS.js.map} +1 -1
  72. package/dist/vite/index.d.ts +10 -0
  73. package/dist/vite/index.js +4 -4
  74. package/docs/en/changelog.md +24 -0
  75. package/docs/en/cli-reference.md +30 -0
  76. package/docs/en/components.md +29 -15
  77. package/docs/en/parts/data-table.md +22 -0
  78. package/docs/en/parts/delta.md +50 -0
  79. package/docs/en/parts/format.md +43 -0
  80. package/docs/en/parts/kpi-card.md +57 -0
  81. package/docs/en/parts/metric-value.md +3 -2
  82. package/docs/en/parts/page-shell.md +1 -1
  83. package/docs/en/parts/sparkline.md +1 -1
  84. package/docs/en/parts/trend-indicator.md +17 -1
  85. package/docs/en/routing.md +4 -2
  86. package/docs/en/ui-and-theming.md +1 -1
  87. package/docs/index.json +366 -76
  88. package/docs/ja/changelog.md +55 -0
  89. package/docs/ja/cli-reference.md +29 -0
  90. package/docs/ja/components.md +57 -101
  91. package/docs/ja/page-types/csv.md +83 -0
  92. package/docs/ja/page-types/doc.md +83 -0
  93. package/docs/ja/page-types/excel.md +82 -0
  94. package/docs/ja/page-types/slide.md +132 -0
  95. package/docs/ja/page-types.md +47 -0
  96. package/docs/ja/parts/area-chart.md +61 -0
  97. package/docs/ja/parts/bar-chart.md +69 -0
  98. package/docs/ja/parts/bar-list.md +35 -0
  99. package/docs/ja/parts/category-bar.md +36 -0
  100. package/docs/ja/parts/data-table.md +22 -0
  101. package/docs/ja/parts/delta.md +50 -0
  102. package/docs/ja/parts/donut-chart.md +47 -0
  103. package/docs/ja/parts/echart.md +3 -0
  104. package/docs/ja/parts/format.md +44 -0
  105. package/docs/ja/parts/kpi-card.md +55 -0
  106. package/docs/ja/parts/line-chart.md +58 -0
  107. package/docs/ja/parts/metric-value.md +3 -2
  108. package/docs/ja/parts/page-shell.md +1 -1
  109. package/docs/ja/parts/progress-circle.md +34 -0
  110. package/docs/ja/parts/sparkline.md +2 -2
  111. package/docs/ja/parts/tracker.md +32 -0
  112. package/docs/ja/parts/trend-indicator.md +17 -1
  113. package/docs/ja/routing.md +8 -84
  114. package/docs/ja/ui/alert-dialog.md +41 -0
  115. package/docs/ja/ui/avatar.md +31 -0
  116. package/docs/ja/ui/combobox.md +74 -0
  117. package/docs/ja/ui/drawer.md +41 -0
  118. package/docs/ja/ui/field.md +42 -0
  119. package/docs/ja/ui/hover-card.md +21 -0
  120. package/docs/ja/ui/kbd.md +16 -0
  121. package/docs/ja/ui/pagination.md +36 -0
  122. package/docs/ja/ui/radio-group.md +21 -0
  123. package/docs/ja/ui/toast.md +46 -0
  124. package/docs/ja/ui-and-theming.md +14 -7
  125. package/package.json +43 -29
  126. package/registry/ui/accordion.tsx +76 -0
  127. package/registry/ui/alert-dialog.tsx +189 -0
  128. package/registry/ui/alert.tsx +80 -0
  129. package/registry/ui/app-shell.tsx +287 -0
  130. package/registry/ui/area-chart.tsx +3701 -0
  131. package/registry/ui/attention-list.tsx +303 -0
  132. package/registry/ui/avatar.tsx +110 -0
  133. package/registry/ui/badge.tsx +56 -0
  134. package/registry/ui/bar-chart.tsx +3698 -0
  135. package/registry/ui/bar-list.tsx +3743 -0
  136. package/registry/ui/box-plot-chart.tsx +3906 -0
  137. package/registry/ui/breadcrumb.tsx +128 -0
  138. package/registry/ui/button.tsx +62 -0
  139. package/registry/ui/calendar.tsx +223 -0
  140. package/registry/ui/card.tsx +107 -0
  141. package/registry/ui/category-bar.tsx +1290 -0
  142. package/registry/ui/chart-frame.tsx +1393 -0
  143. package/registry/ui/checkbox.tsx +30 -0
  144. package/registry/ui/collapsible.tsx +23 -0
  145. package/registry/ui/combobox.tsx +310 -0
  146. package/registry/ui/command.tsx +198 -0
  147. package/registry/ui/dashboard-card.tsx +217 -0
  148. package/registry/ui/data-table.tsx +693 -146
  149. package/registry/ui/date-range-picker.tsx +390 -0
  150. package/registry/ui/delta.tsx +188 -0
  151. package/registry/ui/dialog.tsx +161 -0
  152. package/registry/ui/donut-chart.tsx +3751 -0
  153. package/registry/ui/drawer.tsx +229 -0
  154. package/registry/ui/dropdown-menu.tsx +274 -0
  155. package/registry/ui/echart.tsx +918 -0
  156. package/registry/ui/field.tsx +240 -0
  157. package/registry/ui/filter-bar.tsx +392 -0
  158. package/registry/ui/funnel-steps.tsx +3569 -0
  159. package/registry/ui/heatmap.tsx +1786 -0
  160. package/registry/ui/histogram-chart.tsx +3986 -0
  161. package/registry/ui/hover-card.tsx +52 -0
  162. package/registry/ui/input-group.tsx +160 -0
  163. package/registry/ui/input.tsx +24 -0
  164. package/registry/ui/kbd.tsx +30 -0
  165. package/registry/ui/kpi-card.tsx +699 -0
  166. package/registry/ui/label.tsx +22 -0
  167. package/registry/ui/legend.tsx +3563 -0
  168. package/registry/ui/line-chart.tsx +3699 -0
  169. package/registry/ui/metric-value.tsx +62 -0
  170. package/registry/ui/multi-select.tsx +232 -0
  171. package/registry/ui/page-shell.tsx +282 -0
  172. package/registry/ui/pagination.tsx +140 -0
  173. package/registry/ui/paired-chart.tsx +3827 -0
  174. package/registry/ui/placeholder.tsx +36 -0
  175. package/registry/ui/popover.tsx +92 -0
  176. package/registry/ui/progress-circle.tsx +867 -0
  177. package/registry/ui/progress.tsx +85 -0
  178. package/registry/ui/radio-group.tsx +39 -0
  179. package/registry/ui/sample-data.tsx +86 -0
  180. package/registry/ui/scatter-chart.tsx +4212 -0
  181. package/registry/ui/scroll-area.tsx +56 -0
  182. package/registry/ui/searchable-select.tsx +214 -0
  183. package/registry/ui/section-header.tsx +43 -0
  184. package/registry/ui/segmented-control.tsx +76 -0
  185. package/registry/ui/select.tsx +255 -0
  186. package/registry/ui/separator.tsx +27 -0
  187. package/registry/ui/sheet.tsx +139 -0
  188. package/registry/ui/sidebar.tsx +725 -0
  189. package/registry/ui/skeleton.tsx +17 -0
  190. package/registry/ui/slider.tsx +56 -0
  191. package/registry/ui/sparkline.tsx +230 -0
  192. package/registry/ui/spinner.tsx +14 -0
  193. package/registry/ui/states.tsx +90 -0
  194. package/registry/ui/status-badge.tsx +121 -0
  195. package/registry/ui/switch.tsx +34 -0
  196. package/registry/ui/table.tsx +118 -0
  197. package/registry/ui/tabs.tsx +84 -0
  198. package/registry/ui/textarea.tsx +22 -0
  199. package/registry/ui/toast.tsx +250 -0
  200. package/registry/ui/toggle-group.tsx +91 -0
  201. package/registry/ui/toggle.tsx +47 -0
  202. package/registry/ui/tooltip.tsx +72 -0
  203. package/registry/ui/tracker.tsx +849 -0
  204. package/registry/ui/trend-indicator.tsx +74 -0
  205. package/registry/ui/updated-at.tsx +122 -0
  206. package/registry/ui/waterfall-chart.tsx +4248 -0
  207. package/skills/vantage-add-feature/SKILL.md +9 -7
  208. package/skills/vantage-design/SKILL.md +36 -24
  209. package/skills/vantage-design/references/extract.md +16 -14
  210. package/skills/vantage-design/references/format.md +6 -5
  211. package/skills/vantage-design/references/presets.md +60 -110
  212. package/skills/vantage-pitfalls/SKILL.md +5 -1
  213. package/skills/vantage-slide/SKILL.md +17 -0
  214. package/templates/AGENTS.md +22 -1
  215. package/templates/agents/api.md +29 -0
  216. package/templates/agents/csv.md +2 -1
  217. package/templates/agents/doc.md +6 -3
  218. package/templates/agents/page.md +32 -8
  219. package/templates/agents/slide.md +13 -1
  220. package/templates/agents/xlsx.md +2 -1
  221. package/theme.css +284 -128
  222. package/dist/add-EISGSZAH.js +0 -6
  223. package/dist/add-EISGSZAH.js.map +0 -1
  224. package/dist/chunk-3G43C6OL.js.map +0 -1
  225. package/dist/chunk-5ZOP4SQR.js.map +0 -1
  226. package/dist/chunk-A2UUGASH.js.map +0 -1
  227. package/dist/chunk-BCE22JSM.js.map +0 -1
  228. package/dist/chunk-DTDVSFRY.js.map +0 -1
  229. package/dist/chunk-EP6JHXSR.js.map +0 -1
  230. package/dist/chunk-KLEIVDUV.js.map +0 -1
  231. package/dist/chunk-MXI3PZFT.js.map +0 -1
  232. package/dist/chunk-PLST5Q7T.js +0 -2221
  233. package/dist/chunk-PLST5Q7T.js.map +0 -1
  234. package/dist/chunk-PVTHHV7X.js.map +0 -1
  235. package/dist/chunk-T3FLAGI6.js +0 -316
  236. package/dist/chunk-T3FLAGI6.js.map +0 -1
  237. package/dist/dev-NZRLOQCL.js.map +0 -1
  238. package/dist/doctor-VFKEMR54.js.map +0 -1
  239. package/dist/preview-QDCIVVSR.js.map +0 -1
@@ -16,7 +16,7 @@ CLI は雛形を出すだけで、規約の遵守はこちらの責任。**追
16
16
  ```bash
17
17
  vantage add page <name> # ルートページ(.tsx)
18
18
  vantage add api <name> # server/api/**.ts の API モジュール
19
- vantage add ui <name> # registry から UI ソースを components/ui/ にコピー(src/ があればその中)
19
+ vantage add ui <name> # /ui・/components の部品ソースを components/ui/ にコピー(src/ があればその中)
20
20
  vantage add block <name> # registry からブロックを components/blocks/ にコピー(同上)
21
21
  ```
22
22
 
@@ -121,15 +121,17 @@ vantage add ui data-table # → components/ui/data-table.tsx(編集可能
121
121
  vantage add block sales-overview # → components/blocks/sales-overview.tsx
122
122
  ```
123
123
 
124
- - **多くの UI コンポーネントは「import 専用」で、`add ui` でコピーできる名前は限られる。**
125
- 現在 registry からコピー可能なのは `data-table`(ui)と `sales-overview`(block)のみ。
126
- 未知の名前を渡すと利用可能な名前一覧を出して失敗する。
127
- - コピーが要らない大半のプリミティブは `@squadbase/vantage/ui` から、複合パーツは
128
- `@squadbase/vantage/components` から**そのまま import**するのが基本(コピー不要)。
124
+ - **基本はコピーせず import する。** プリミティブは `@squadbase/vantage/ui` から、複合パーツと
125
+ チャートは `@squadbase/vantage/components` から**そのまま import**する。
129
126
  ```tsx
130
127
  import { Button, Loading, ErrorState } from "@squadbase/vantage/ui"
131
- import { DashboardCardPreset, DataTablePreset, EChart } from "@squadbase/vantage/components"
128
+ import { DashboardCardPreset, DataTablePreset, LineChart } from "@squadbase/vantage/components"
132
129
  ```
130
+ - `add ui` は**改造したいときだけ**使う。`/ui` と `/components` の部品はすべて kebab-case 名で
131
+ コピーできる(`add ui bar-chart`・`add ui combobox`)。未知の名前を渡すと利用可能な名前一覧を
132
+ 出して失敗する。
133
+ - グラフは型付きチャート(`LineChart`・`BarChart` など)から選ぶ。選び方は `agents/page.md` の
134
+ 「グラフはまず型付きチャートで描く」。
133
135
  - **props は `vantage docs <name>` で確認してから書く**(`vantage docs button`・
134
136
  `vantage docs parts/data-table`。名前が分からなければ `vantage search <やりたいこと>` で
135
137
  探してから `vantage docs` に渡す)。
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: vantage-design
3
- description: Vantage(@squadbase/vantage)アプリの見た目の意図 `DESIGN.md` と、実際の値を持つ `styles.css` をまとめて作る / 更新する手順。配色・ブランドカラー・テーマ・チャートの色・フォント・角丸・トーンを変えたいとき、既存サイトやロゴ・資料・外部の DESIGN.md に合わせたいとき、プロジェクト作成時の初期デザイン(プリセット default / calm / vivid / mono)を決めるときに使う。「色を変えて」「ブランドに合わせて」「このサイトに合わせて」「落ち着いた感じに」「フォントを変えて」「テーマを作って」「DESIGN.md を作って」、"change the colors", "match our brand", "match this website", "theme", "color palette", "font", "design system", "DESIGN.md" で起動。
3
+ description: Vantage(@squadbase/vantage)アプリの見た目の意図 `DESIGN.md` と、実際の値を持つ `styles.css` をまとめて作る / 更新する手順。配色・ブランドカラー・テーマ・チャートの色・フォント・角丸・トーンを変えたいとき、既存サイトやロゴ・資料・外部の DESIGN.md に合わせたいとき、プロジェクト作成時の初期デザイン(テーマ neutral / ocean / forest / sunset / violet / rose / mono)を決めるときに使う。「色を変えて」「ブランドに合わせて」「このサイトに合わせて」「落ち着いた感じに」「フォントを変えて」「テーマを作って」「DESIGN.md を作って」、"change the colors", "match our brand", "match this website", "theme", "color palette", "font", "design system", "DESIGN.md" で起動。
4
4
  ---
5
5
 
6
6
  # DESIGN.md と styles.css をまとめて更新する
@@ -23,7 +23,7 @@ Vantage アプリの見た目は 2 つのファイルで決まる。
23
23
  | --- | --- |
24
24
  | `references/format.md` | `DESIGN.md` を書く / 直すとき(書式・節の順番・雛形) |
25
25
  | `references/extract.md` | URL・画像・pptx/pdf・言葉・外部 DESIGN.md から色と書体を取り出すとき |
26
- | `references/presets.md` | プロジェクト作成時の初期デザイン(`default` / `calm` / `vivid` / `mono`) |
26
+ | `references/presets.md` | テーマ(`neutral` / `ocean` / `forest` / `sunset` / `violet` / `rose` / `mono`)の選び方と `theme` コマンド。旧プリセット id の読み替え |
27
27
  | `scripts/contrast.mjs` | 文字色と背景色のコントラスト比を確かめるとき |
28
28
 
29
29
  ## 手順
@@ -43,29 +43,32 @@ Vantage アプリの見た目は 2 つのファイルで決まる。
43
43
  各行に「何に合わせてその色にしたか」を 1 語添える。
44
44
  - **トーンの説明**(2〜3 行。`DESIGN.md` の「全体のトーン」にそのまま入る文)。
45
45
 
46
- プリセットで足りる場合はプリセット名(`references/presets.md`)で提案してよい。
46
+ テーマで足りる場合はテーマ id(`references/presets.md`)で提案してよい。旧プリセット id(`default` / `calm` / `vivid` / `mono`)で頼まれたら新 id に読み替える。
47
47
 
48
48
  ### 3. styles.css と DESIGN.md を同じステップで書く
49
49
 
50
50
  `styles.css`:
51
51
 
52
- - **マーカーブロックの中は手で編集しない。**
53
- ``/* vantage-template:chart-preset — regenerated by `chart`; edits here are lost */`` 〜
54
- `/* vantage-template:chart-preset:end */` の間はコマンドが丸ごと書き換える生成物で、手で直した
55
- 値は次の適用で消える。
56
- - チャートの 5 色は必ずコマンドで選ぶ: `npx @squadbase/vantage-template chart <preset>`
57
- (`blue` / `ocean` / `sunset` / `forest` / `berry` / `mono`。プロジェクトルートで実行。
58
- `--dry-run` で書き込まずに結果を見られる)。マーカーの中だけが置き換わり、他の記述は残る。
59
- - プリセットに無いチャート色(ブランド色を `--chart-1` にしたいなど)は、マーカーブロックの**後ろ**に
52
+ - **テーマ範囲・チャート範囲のマーカーの中は手で編集しない。** 色・角丸・書体の出発点は 7 テーマ
53
+ (`neutral` / `ocean` / `forest` / `sunset` / `violet` / `rose` / `mono`)から選び、コマンドで当てる:
54
+ `npx @squadbase/vantage-template theme <id>`(プロジェクトルートで実行。`--dry-run` で書き込まずに
55
+ 結果を見られる)。``/* squadkit-theme — regenerated by `theme`; edits here are lost */`` 〜
56
+ `/* squadkit-theme:end */` の間はコマンドが丸ごと書き換える生成物で、手で直した値は次の適用で消える。
57
+ 旧プリセット id(`default` → `neutral` / `calm` → `ocean` / `vivid` → `sunset` / `mono`)もコマンドが受ける。
58
+ - チャートの 5 色はテーマが持つ。テーマと別の配色にしたいときだけ
59
+ `npx @squadbase/vantage-template chart <preset>`(`blue` / `ocean` / `sunset` / `forest` / `berry` / `mono`)を使う。
60
+ ``/* vantage-template:chart-preset … */`` 〜 `/* vantage-template:chart-preset:end */` の間が置き換わり、
61
+ テーマのチャート色より優先される。テーマに揃え直すには `theme <id> --reset-chart`。
62
+ - プリセットに無いチャート色(ブランド色を `--chart-1` にしたいなど)は、**マーカーブロックの後ろ**に
60
63
  別の `:root { --chart-1: …; }` と `.dark, [data-theme="dark"] { --chart-1: …; }` を足して上書きする
61
- (後に書いた方が勝つ)。上書きするのは変えたい番号だけにし、残りはプリセットに任せる。
62
- - `--primary` / `--primary-foreground` / `--radius` などチャート以外のトークンは、マーカーの**外**
63
- (ファイル先頭の `:root` ブロック)に書く。色は `:root` と `.dark, [data-theme="dark"]` の
64
- **両方**に書く。片方だけだとダークモードで既定に戻る。値は `oklch()` か Tailwind のパレット変数
65
- (`var(--color-sky-600)`)で書く。
66
- - 書体は既定でシステムフォント。**ページの書体を決めるのは `body` セレクタの `font-family`**
67
- (フレームワークの `theme.css` が `body` にシステムフォントを直接指定しているため、`:root` や
68
- `html` に `font-family` を書いても本文には効かない)。スライドの書体は `:root` の
64
+ (後に書いた方が勝つ)。上書きするのは変えたい番号だけにし、残りはテーマに任せる。
65
+ - `--primary` / `--primary-foreground` / `--radius` などテーマに無い値・ブランド色の上書きも、
66
+ **マーカーブロックの後ろ**(ファイル末尾)に書く。マーカーより前に書いた値はテーマに負ける。
67
+ 色は `:root` と `.dark, [data-theme="dark"]` の**両方**に書く。片方だけだとダークモードでテーマの値に
68
+ 戻る。値は `oklch()` か Tailwind のパレット変数(`var(--color-sky-600)`)で書く。
69
+ - 書体は既定でシステムフォント。**ページの書体は `--font-sans`**(`styles.css` の `body` が
70
+ `font-family: var(--font-sans)` で参照する。テーマ範囲も `--font-sans` を持つので、書体を変えるには
71
+ マーカーブロックの後ろで `:root { --font-sans: …; }` を上書きする)。スライドの書体は `:root` の
69
72
  `--slide-font-display`(見出し)/ `--slide-font-body`(本文)で決まる。Web フォントを使うときの
70
73
  レシピ:
71
74
  1. Google Fonts の CSS
@@ -73,21 +76,30 @@ Vantage アプリの見た目は 2 つのファイルで決まる。
73
76
  から使う subset の `@font-face` ブロックだけを `styles.css` の先頭に貼る。
74
77
  **`@import url(...)` は使わない** ― `styles.css` はテーマの後ろに連結されるので
75
78
  「@import rules must precede all rules」の警告とともにビルドで捨てられる。
76
- 2. マーカーの外に次を書く(フォールバックは `theme.css` の既定と同じ並び):
79
+ 2. マーカーブロックの後ろに次を書く(フォールバックは `theme.css` の既定と同じ並び):
77
80
 
78
81
  ```css
79
- body {
80
- font-family: "<Font>", ui-sans-serif, system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
81
- }
82
82
  :root {
83
- --slide-font-display: "<Font>", system-ui, -apple-system, "Hiragino Kaku Gothic ProN", "Hiragino Sans", "Yu Gothic", Meiryo, sans-serif;
83
+ --font-sans: "<Font>", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Hiragino Sans", "Hiragino Kaku Gothic ProN", "Noto Sans JP", Meiryo, ui-sans-serif, system-ui, sans-serif;
84
+ --slide-font-display: "<Font>", -apple-system, BlinkMacSystemFont, "Segoe UI", "Hiragino Kaku Gothic ProN", "Hiragino Sans", "Yu Gothic", Meiryo, system-ui, sans-serif;
84
85
  --slide-font-body: var(--slide-font-display);
85
86
  }
86
87
  ```
87
88
 
89
+ 欧文の Web フォントだけを先頭に足すときも、日本語の system face(`"Hiragino Sans"` 〜 `Meiryo`)は
90
+ 必ず残す。消すとカナ・漢字がブラウザ任せのフォールバックになり、細く表示される。
91
+ `ui-sans-serif` / `system-ui` は日本語の face より**後ろ**に置く。日本語の Windows ではどちらも
92
+ Yu Gothic UI(UI のリサイズを避けるために字幅を詰めた書体)に解決され、カナがここで決まって
93
+ 半角風に見える。macOS の Chrome は `-apple-system` を解釈しないので `BlinkMacSystemFont` も並べる。
94
+ 既存アプリの `styles.css` の `body` に `font-family` が直書きされている(`var(--font-sans)` ではない)、
95
+ または `ui-sans-serif, system-ui, …` が先頭にある、`"Yu Gothic UI"` が残っているときは、
96
+ `body { font-family: var(--font-sans); }` に直し、書体は `--font-sans` に上の並びで書く。
88
97
  日本語の Web フォントは face が 100 を超えるので原則使わない(pptx 書き出しも壊れる。
89
98
  `vantage-slide` の `references/tokens.md` 参照)。
90
99
 
100
+ 長い表(ダッシュボード): カードに `max-h-*` + `overflow-y-auto` の縦スクロール領域を作らず、
101
+ ページング付きの `DataTablePreset`(`enablePagination`)にする(ホイールや End キーがページに届かなくなるため)。
102
+
91
103
  `DESIGN.md`: `references/format.md` の書式で書く。**色コードを書かない**(トークン名だけ)。
92
104
  150 行を超えない(超えると `vantage check` が `DESIGN_MD_TOO_LONG` を出す)。ロゴなどの素材は
93
105
  `public/brand/logo.svg` のように `public/` 配下のパスで「ブランド素材」行に書く。
@@ -7,12 +7,13 @@
7
7
  3. **書体**(見出しと本文の `font-family`。システムフォントで足りるか)
8
8
  4. **トーン**(2〜3 語: 「落ち着いた」「明るい」「堅い」…)
9
9
 
10
- チャートの 5 色は、主色から直接作るより**主色に最も近いチャートプリセット**を選び、
11
- `npx @squadbase/vantage-template chart <preset>` で適用する方が安全(5 色の明度差・色覚多様性への
12
- 配慮が済んでいる)。`styles.css` の `vantage-template:chart-preset` マーカーブロックの中は
10
+ チャートの 5 色は、主色から直接作るより**主色に最も近いテーマ**を選び、
11
+ `npx @squadbase/vantage-template theme <id>` で適用する方が安全(5 色の明度差・色覚多様性への
12
+ 配慮が済んでいる)。テーマと別のチャート配色が要るときは `chart <preset>`。`styles.css` の
13
+ `squadkit-theme` / `vantage-template:chart-preset` のマーカーブロックの中は
13
14
  **手で編集しない**(次の適用で消える)。主色を `--chart-1` に入れたいときだけ、マーカーブロックの
14
15
  **後ろ**に `:root` と `.dark, [data-theme="dark"]` の `--chart-1` 上書きを足し、残り 4 色は
15
- プリセットに任せる。`--primary` や `--radius` もマーカーの外に書く。
16
+ プリセットに任せる。`--primary` や `--radius` はマーカーブロックの後ろに書く。
16
17
 
17
18
  ## URL(既存サイトに合わせる)
18
19
 
@@ -36,7 +37,7 @@ grep -oE 'font-family:[^;]+' /tmp/site.css | sort | uniq -c | sort -rn | head
36
37
  3. **ボタン・リンクの色**: `a {` `.btn` `button` `[class*=primary]` のセレクタの `color` /
37
38
  `background-color`。出現回数の多い有彩色が主色。
38
39
  4. **背景**: `body` / `html` の `background`。暗ければ「暗い基調」。
39
- 5. **書体**: `body` の `font-family`。Google Fonts の `<link>` があればその family 名。
40
+ 5. **書体**: `body` の `font-family`(書き込み先は `--font-sans`)。Google Fonts の `<link>` があればその family 名。
40
41
 
41
42
  注意:
42
43
 
@@ -66,18 +67,19 @@ grep -oE 'font-family:[^;]+' /tmp/site.css | sort | uniq -c | sort -rn | head
66
67
 
67
68
  ## 言葉だけ(「落ち着いた感じに」)
68
69
 
69
- 形容詞を `presets.md` の 4 つに寄せ、そのうえで主色だけを調整する。
70
+ 形容詞を `presets.md` の 7 テーマに寄せ、そのうえで主色だけを調整する。
70
71
 
71
72
  | 言われたこと | 出発点 |
72
73
  | --- | --- |
73
- | 落ち着いた・信頼感・堅い・経営向け・青系 | `calm` |
74
- | 明るい・元気・勢い・暖かい・営業向け | `vivid` |
74
+ | 落ち着いた・信頼感・堅い・経営向け・青系 | `ocean` |
75
+ | 明るい・元気・勢い・暖かい・営業向け | `sunset` |
75
76
  | シンプル・モノクロ・印刷する・資料に貼る | `mono` |
76
- | 特に無し・標準・おまかせ | `default` |
77
- | 自然・環境・緑 | `default` の構成でチャートを `forest` に |
78
- | 華やか・ポップ・紫やピンク | `default` の構成でチャートを `berry` に |
77
+ | 特に無し・標準・おまかせ | `neutral` |
78
+ | 自然・環境・緑 | `forest` |
79
+ | 華やか・ポップ・紫 | `violet` |
80
+ | 華やか・ポップ・ピンク | `rose` |
79
81
 
80
- 当てはまらない言葉は、2 案(例: `calm` と `default`)を並べて選んでもらう。
82
+ 当てはまらない言葉は、2 案(例: `ocean` と `neutral`)を並べて選んでもらう。
81
83
 
82
84
  ## 外部の DESIGN.md(Stitch などが書いたもの)
83
85
 
@@ -99,8 +101,8 @@ Vantage の `DESIGN.md` は値を持たないので、**値を `styles.css` へ
99
101
  | error | `--destructive` |
100
102
  | success / warning | 専用トークンなし → `--chart-*` のどれかに割り当てて `DESIGN.md` に書く |
101
103
  | radius / corner | `--radius` |
102
- | display / headline font | `--slide-font-display`(+ ページの見出しなら `body` の font-family) |
103
- | body font | `body` セレクタの font-family と `--slide-font-body`(`:root` の font-family は効かない) |
104
+ | display / headline font | `--slide-font-display`(+ ページの見出しなら `--font-sans`) |
105
+ | body font | `--font-sans`(ページ本文)と `--slide-font-body` |
104
106
 
105
107
  3. `styles.css` のマーカーブロックの外に、`:root` と `.dark, [data-theme="dark"]` の両方で書く
106
108
  (チャート色・書体の書き方は SKILL.md の手順 3)。外部の DESIGN.md に
@@ -50,8 +50,8 @@ Components → 「成果物の種類ごとの規則」/ Do's and Don'ts。値は
50
50
 
51
51
  - `--muted` `--accent` `--secondary` `--border` は背景・境界用。文字色の役割に割り当てない。
52
52
  - 良い / 注意の専用トークンは無い。`--chart-*` の中から割り当てるか、「専用トークンなし」と書く。
53
- - ページ本文の書体はトークンではなく `body` の `font-family`(`styles.css` の `body` セレクタで上書きする。
54
- `:root` / `html` に書いても `theme.css` の `body` 指定に負けて効かない)。
53
+ - ページ本文の書体は `--font-sans`(`styles.css` の `body` が `font-family: var(--font-sans)` で参照する。
54
+ テーマを当てると `--font-sans` もテーマの値になる。変えるときはテーマ範囲のマーカーの後ろで上書きする)。
55
55
  - `--slide-bg` などは既定で `--background` などの別名。`.dark` に書き直す必要は無い。
56
56
 
57
57
  ## 雛形(中立の既定テーマ)
@@ -112,14 +112,15 @@ DESIGN.md — このアプリの「見た目の意図」を書くファイルで
112
112
  - 系列は 5 つまで。それ以上はグループ化するか「その他」にまとめる。
113
113
  - 禁止: 同じチャートで `--destructive` を普通の系列色として使う(悪い値に見える)。
114
114
  - 禁止: 隣り合う系列に `--chart-3` と `--chart-4` を並べて細い線で描く(見分けにくい)。
115
- - 配色を丸ごと変えるときは `npx @squadbase/vantage-template chart <preset>` を使う
116
- (`blue` / `ocean` / `sunset` / `forest` / `berry` / `mono`)。
115
+ - 配色を丸ごと変えるときは `npx @squadbase/vantage-template theme <id>` を使う
116
+ (`neutral` / `ocean` / `forest` / `sunset` / `violet` / `rose` / `mono`)。チャートだけ別の配色にするときは
117
+ `chart <preset>`(`blue` / `ocean` / `sunset` / `forest` / `berry` / `mono`)。
117
118
 
118
119
  ## 書体 (Typography)
119
120
 
120
121
  | 用途 | 指定 | 備考 |
121
122
  | --- | --- | --- |
122
- | 見出し・本文 | システムフォント(`body` の `font-family`) | Web フォントは使わない |
123
+ | 見出し・本文 | 日本語を含むシステムフォント(`--font-sans`) | Web フォントは使わない |
123
124
  | 数字 | 同上 + `tabular-nums` | 桁がそろうように必ず付ける |
124
125
  | スライドの見出し | `--slide-font-display` | 既定は日本語を含むシステムフォント |
125
126
  | スライドの本文 | `--slide-font-body` | 既定は見出しと同じ |
@@ -1,110 +1,60 @@
1
- # 初期デザインのプリセット
2
-
3
- プロジェクト作成時に選ぶ 4 つの出発点。**id(`default` / `calm` / `vivid` / `mono`)はプロジェクト
4
- 作成のワークフローが参照するので変えないこと。** どれも「チャートのプリセット 1 つ + `--primary` +
5
- `DESIGN.md` の差分」でできている。**`--primary` はどのプリセットでも必ず書く**(無彩色のプリセットも
6
- 値を明示する)。チャートだけ変えるとホームのような色の少ない画面では見た目が変わらず、別のプリセットから
7
- 切り替えたときに前の `--primary` が残るため。
8
-
9
- 適用の手順は共通:
10
-
11
- 1. `npx @squadbase/vantage-template chart <チャートのプリセット>` で `styles.css` のマーカーブロックを
12
- 差し替える。**マーカーブロックの中(`--chart-1..5`)は手で編集しない** ― コマンドの生成物で、
13
- 次の適用で消える。
14
- 2. 各プリセットの `--primary` / `--primary-foreground` を、`styles.css` のマーカーの**外**(先頭の
15
- `:root` ブロック)に `:root` と `.dark, [data-theme="dark"]` の両方で書く。既にある `--primary` は置き換える。
16
- 3. `DESIGN.md` を `format.md` の雛形から作り、下の「DESIGN.md の差分」の行だけを書き換える。
17
- 4. `scripts/contrast.mjs` で `--primary-foreground` / `--primary` をライトとダークで確かめる。
18
-
19
- | id | トーン | チャートのプリセット | `--primary` |
20
- | --- | --- | --- | --- |
21
- | `default` | 無彩色のベース。色を持つのはデータ(`blue` チャート)だけ | `blue` | 無彩色(`theme.css` の既定値を明示) |
22
- | `calm` | 落ち着いた寒色。報告書・経営向け | `ocean` | 深い青(スカイ 700 / 300) |
23
- | `vivid` | 明るい暖色。営業・マーケティング向け | `sunset` | 濃いオレンジ(オレンジ 700 / 400) |
24
- | `mono` | モノクロ。印刷・資料への貼り付け向け | `mono` | ジンク 900 / 200 |
25
-
26
- ## `default`
27
-
28
- - トーン: 落ち着いた無彩色のベースに、データだけが色を持つ業務ダッシュボード。装飾より読みやすさ。
29
- - チャート: `blue`(青 → ティール → フクシア → バイオレット → グレー)。
30
- - `--primary`(フレームワークの既定と同じ無彩色。他のプリセットから戻すときのために明示する):
31
-
32
- ```css
33
- :root {
34
- --primary: oklch(0.205 0 0);
35
- --primary-foreground: oklch(0.985 0 0);
36
- }
37
- .dark,
38
- [data-theme="dark"] {
39
- --primary: oklch(0.922 0 0);
40
- --primary-foreground: oklch(0.205 0 0);
41
- }
42
- ```
43
-
44
- - `DESIGN.md`: 雛形そのまま(`format.md` の雛形は `default` を説明している)。
45
-
46
- ## `calm`
47
-
48
- - トーン: 寒色でまとめた静かな画面。強調は控えめにし、数字と罫線で読ませる。
49
- - チャート: `ocean`(スカイ → シアン → インディゴ → ティール → スレート)。
50
- - `--primary`(チャートのスカイに揃えた深い青):
51
-
52
- ```css
53
- :root {
54
- --primary: var(--color-sky-700);
55
- --primary-foreground: oklch(0.985 0 0);
56
- }
57
- .dark,
58
- [data-theme="dark"] {
59
- --primary: var(--color-sky-300);
60
- --primary-foreground: oklch(0.205 0 0);
61
- }
62
- ```
63
-
64
- - `DESIGN.md` の差分: 「全体のトーン」を上の文に。チャートの色味を「スカイ → シアン → インディゴ →
65
- ティール → スレート」に。良い = `--chart-4`(ティール)。1 系列の強調は `--chart-1` + 残り `--chart-5`。
66
- 禁止: `--chart-1` と `--chart-2` を隣り合う細い線で並べる(どちらも明るい青系)。
67
-
68
- ## `vivid`
69
-
70
- - トーン: 明るく勢いのある暖色。KPI とトレンドを大きく見せ、強調色をはっきり使う。
71
- - チャート: `sunset`(オレンジ → アンバー → ローズ → イエロー → ストーン)。
72
- - `--primary`(オレンジ 600 は白文字で 4.5:1 に届かないので 700 を使う):
73
-
74
- ```css
75
- :root {
76
- --primary: var(--color-orange-700);
77
- --primary-foreground: oklch(0.985 0 0);
78
- }
79
- .dark,
80
- [data-theme="dark"] {
81
- --primary: var(--color-orange-400);
82
- --primary-foreground: oklch(0.205 0 0);
83
- }
84
- ```
85
-
86
- - `DESIGN.md` の差分: トーンを上の文に。主色の行を「濃いオレンジ」に。良い = 専用色なし(▲ と
87
- `--foreground`)、悪い = `--destructive`。禁止: `--chart-3`(ローズ)と `--destructive` を同じ
88
- チャートに置く(悪い値と区別できない)。1 系列の強調は `--chart-1` + 残り `--chart-5`。
89
-
90
- ## `mono`
91
-
92
- - トーン: 白黒と灰色だけ。色で意味を運ばず、太さ・順番・ラベルで読ませる。
93
- - チャート: `mono`(ジンク 900 → 200。ダークでは反転)。
94
- - `--primary`(チャートの両端と同じジンク):
95
-
96
- ```css
97
- :root {
98
- --primary: var(--color-zinc-900);
99
- --primary-foreground: oklch(0.985 0 0);
100
- }
101
- .dark,
102
- [data-theme="dark"] {
103
- --primary: var(--color-zinc-200);
104
- --primary-foreground: oklch(0.205 0 0);
105
- }
106
- ```
107
-
108
- - `DESIGN.md` の差分: トーンを上の文に。強調 = `--chart-1`(最も濃い灰)。良い = 専用色なし(▲ と
109
- 符号)、悪い = `--destructive`(**画面で唯一の有彩色**として使う)。チャートは系列を 3 つまでにし、
110
- それ以上は直接ラベルを付ける。禁止: 隣り合う `--chart-4` と `--chart-5`(明度差が小さい)。
1
+ # 初期デザイン(テーマ)
2
+
3
+ プロジェクトの見た目の出発点は、SquadKit の 7 テーマから選ぶ。**テーマ id はプロジェクト作成の
4
+ ワークフローが参照するので変えないこと。** テーマは主色・背景・文字・境界・チャート 5 色・角丸・書体を
5
+ まとめて持つ(ライトとダークの両方)。
6
+
7
+ | id | トーン | 向く場面 |
8
+ | --- | --- | --- |
9
+ | `neutral` | 既定。Vantage の素の見た目(青の主色と無彩色の面) | 迷ったとき・おまかせ |
10
+ | `ocean` | 青を基調にした落ち着いた信頼感。角丸はやや小さめ | 報告書・経営向け |
11
+ | `forest` | 緑を基調にした自然な印象。丸ゴシック系の書体、角丸はやや小さめ | 環境・ヘルスケア・自然 |
12
+ | `sunset` | 橙を基調にした温かみ。角丸はやや大きめ | 営業・マーケティング |
13
+ | `violet` | 紫を基調にしたやわらかい印象。角丸は大きめ | 華やかさ・ポップ |
14
+ | `rose` | 赤紫からピンクの落ち着いた色。角丸は大きめ(`--destructive` の赤とは別の色) | 華やかさ・ポップ |
15
+ | `mono` | 無彩色寄り。チャートも彩度を抑え、角丸は最小。等幅フォント | 印刷・資料への貼り付け |
16
+
17
+ ## 当てる
18
+
19
+ プロジェクトルートで次を実行する。`--dry-run` で書き込まずに結果を見られる。
20
+
21
+ ```bash
22
+ npx @squadbase/vantage-template theme <id>
23
+ npx @squadbase/vantage-template theme ocean --reset-chart # chart コマンドで選んだ配色を捨て、テーマのチャート色に揃える
24
+ ```
25
+
26
+ - `styles.css` の ``/* squadkit-theme — regenerated by `theme`; edits here are lost */`` 〜
27
+ `/* squadkit-theme:end */` の範囲(テーマ範囲)だけを差し替える。**範囲の中は手で編集しない**。
28
+ マーカーが無いファイルには自動で足される。同じ id を再実行しても変わらない。
29
+ - テーマ範囲はファイル先頭の `:root` より後ろに置かれ、同じ詳細度なら後ろが勝つ。
30
+ 先頭の `:root` に手書きした `--primary` などはテーマに負ける。
31
+ - `chart <preset>` の範囲(`--chart-*` だけ)はテーマ範囲の**後ろ**に置かれ、テーマのチャート色に勝つ。
32
+ チャートの配色もテーマに任せるなら `--reset-chart` で外す。
33
+
34
+ ## 旧プリセット id の読み替え
35
+
36
+ 古い呼び出しの `default` / `calm` / `vivid` / `mono` は、`theme` コマンドがそのまま受けて次の id として扱う。
37
+
38
+ | 旧 | 新 |
39
+ | --- | --- |
40
+ | `default` | `neutral` |
41
+ | `calm` | `ocean` |
42
+ | `vivid` | `sunset` |
43
+ | `mono` | `mono` |
44
+
45
+ ## テーマに無い値(ブランド色など)
46
+
47
+ テーマの `--primary` を変えたい、特定の色だけブランドに合わせたい、というときは、テーマを当てたうえで
48
+ **`/* squadkit-theme:end */`(チャート範囲があればその終端)より後ろ**に、変えたいトークンだけ
49
+ `:root` と `.dark, [data-theme="dark"]` の**両方**に書く。前に書くとテーマに負ける。
50
+ `scripts/contrast.mjs` で `--primary-foreground` / `--primary` をライトとダークで確かめる。
51
+
52
+ ## DESIGN.md
53
+
54
+ `format.md` の雛形から作り、選んだテーマに合わせて次の行だけ書き換える。
55
+
56
+ - 「全体のトーン」: 上の表のトーンを 2〜3 行に。
57
+ - 主色の行: テーマの主色の色味(「青」「橙」など。**色コードは書かない**)。
58
+ - チャートの色味: テーマの `--chart-1..5` の並び(適用後の `styles.css` を見る)。
59
+ - 良い / 悪い / 注意: 専用トークンは無い。`--chart-*` から割り当てるか「専用トークンなし」と書く。
60
+ `--destructive` を普通の系列色に使わない。
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: vantage-pitfalls
3
- description: Vantage(@squadbase/vantage)アプリを書くときに静かに壊れる落とし穴のリファレンス。Base UI は Radix ではない(asChild 無し・render プロップ)、Select の value/label、クライアントから server/ を import しない、EChart の配色と高さ、動的パラメータの3綴り同期、PUBLIC_ env、HttpError、csv/xlsx ページの URL 衝突とサイズ上限、スライドの data-waitfor など。Vantage の UI コンポーネントやルーティングが思った通りに動かないとき、ビルドやスタイルが静かに欠落するときに参照する。
3
+ description: Vantage(@squadbase/vantage)アプリを書くときに静かに壊れる落とし穴のリファレンス。Base UI は Radix ではない(asChild 無し・render プロップ)、Select の value/label、クライアントから server/ を import しない、チャートの色指定と EChart の配色・高さ、動的パラメータの3綴り同期、PUBLIC_ env、HttpError、csv/xlsx ページの URL 衝突とサイズ上限、スライドの data-waitfor など。Vantage の UI コンポーネントやルーティングが思った通りに動かないとき、ビルドやスタイルが静かに欠落するときに参照する。
4
4
  ---
5
5
 
6
6
  # Vantage アプリの落とし穴リファレンス
@@ -59,6 +59,10 @@ Base UI の `SelectValue` は選択中の **value をそのまま描き**、`Sel
59
59
 
60
60
  ## チャート:`EChart` の配色はトークン追従。上書きは `option.color`
61
61
 
62
+ ふつうの推移・比較・構成比は型付きチャート(`LineChart`・`BarChart` など。→ `agents/page.md`)で
63
+ 描く。その `colors` に渡すのはトークン名 `"chart-1"`〜`"chart-5"` か CSS 色で、Tailwind クラス
64
+ (`"bg-blue-500"` など)は効かない。以下は `EChart` を直接使うときの話。
65
+
62
66
  系列色は `--chart-1..5`、軸・凡例・ツールチップは文字色/境界色のトークンから組まれる
63
67
  (init 時にトークンの実値を解決している)。ライト / ダークの切り替えにも、`styles.css` の
64
68
  書き換えやテーマプリセットの適用にも追従する。
@@ -49,6 +49,9 @@ export default function JuneDeck() {
49
49
  - **`.slide` を付けられるのはルートになるページモジュールだけ。** `_layout.slide.tsx` や
50
50
  `deck.slide.ts` は `INVALID_PAGE_VARIANT` エラーになります。
51
51
  - **`june.slide.tsx` と `june.tsx` は同じ URL** になるので `ROUTE_CONFLICT` です。どちらかを消すこと。
52
+ - **ルート `/` がすでに他のページ(`index.tsx` など)で使われている場合、スライドは `index.slide.tsx` ではなく、タイトルから作った slug でファイル名を付ける。** `index.slide.tsx` と `index.tsx` は同じ `/` に解決して `ROUTE_CONFLICT` になる。
53
+ - 例: "Label check" → `src/label-check.slide.tsx` → `/label-check`
54
+ - 例: "Monthly Report" → `src/monthly-report.slide.tsx` → `/monthly-report`
52
55
  - **デッキファイル以外を作らない。** ヘルパーコンポーネントも定数も同じ `.slide.tsx` の中に書く。
53
56
  スライド専用のコンポーネントを `components/` に切り出すと、デッキ 1 本を読むのに 2 ファイル
54
57
  追わせることになります。
@@ -194,6 +197,17 @@ pptx 書き出しのために描き終わりを待たせる必要があります
194
197
  チャートに色をハードコードしないこと(`option.color` / `itemStyle.color` / `theme`)。
195
198
  `EChart` はテーマトークンに追従します。
196
199
 
200
+ ## 説明と図表を同じデータ時点へ揃える
201
+
202
+ 分析を共有するデッキでは、本文・数値・図表が**同じ対象期間と同じ取得時点の結果**を参照していることを
203
+ 確かめます。
204
+
205
+ - 対象期間とデータ取得時点を、該当ページかフッターに短く表示する(例: 「2026年6月 / 7月1日 9:00 取得」)
206
+ - **固定した説明文に対して図表だけが最新値へ変わる構成を避ける。** ライブ更新を意図するなら、本文の
207
+ 数値・結論も同じ取得結果から導いて、図表と一緒に変わる構成にする
208
+ - 同一時点の結果を保持・参照できない場合は、スナップショットとして保存できたとは報告しない。
209
+ 必要な保持の仕組みと、現在保証できない範囲(例: 再表示すると図表だけ最新値になる)を伝える
210
+
197
211
  ## 実行時に無料で付いてくるもの
198
212
 
199
213
  - `src/june.slide.tsx` → `/june`。ナビ(`useRoutes()`)に通常のページと同格で並ぶ
@@ -244,6 +258,7 @@ pptx 書き出しのために描き終わりを待たせる必要があります
244
258
  - [ ] 繰り返す視覚要素が `array.map` ではなく明示的な `<Component />` になっている
245
259
  - [ ] ページ番号が `useSlideNumber()` から来ている(ハードコードしていない)
246
260
  - [ ] チャートが `data-waitfor="canvas"` で包まれている
261
+ - [ ] 本文・数値・図表が同じ対象期間と取得時点の結果を参照し、その期間と時点が表示されている
247
262
  - [ ] `<Steps>` を使ったページが、`?p=` で直接開いても完成した絵として読める
248
263
  - [ ] トランジションを宣言したなら、全ページが 1 つの family に収まっている(→ `references/transitions.md`)
249
264
  - [ ] `definePage` の値がリテラルである
@@ -262,3 +277,5 @@ pptx 書き出しのために描き終わりを待たせる必要があります
262
277
  - ❌ スライド用のコンポーネントを別ファイルに切り出す
263
278
  - ❌ チャートに `data-waitfor="canvas"` を付け忘れる(pptx が白紙になる)
264
279
  - ❌ プリミティブを `references/*.md` を読まずに使う
280
+ - ❌ 説明文を固定したまま図表だけライブデータで描く(再表示すると本文と図表の時点がずれる)
281
+ - ❌ 同一時点の結果を保持できていないのに「スナップショットとして保存した」と報告する
@@ -93,13 +93,25 @@ root/
93
93
  | `@squadbase/vantage/router` | `Link`・`Outlet`・`useParams`・`useSearch`・`useNavigate`・`redirect`・`notFound`・`useRoutes`・`useCurrentRoute`・`useSearchParam`・`useSearchState` |
94
94
  | `@squadbase/vantage/query` | `useApiQuery`・`useApiMutation`・`apiJson`・`apiFetch`・`apiUrl`・`ApiError`、ほか `useQuery`/`useMutation` など TanStack Query の再エクスポート |
95
95
  | `@squadbase/vantage/ui` | shadcn/ui(Base UI バリアント)プリミティブ(`Button`・`Loading`・`ErrorState`・`Empty` ほか) |
96
- | `@squadbase/vantage/components` | 複合パーツ(`PageShell`・`DashboardCardPreset`・`DataTablePreset`・`EChart` ほか) |
96
+ | `@squadbase/vantage/components` | 複合パーツ(`PageShell`・`DashboardCardPreset`・`DataTablePreset`、KPI の `KpiCard`・`Delta`、型付きチャート `LineChart`・`BarChart`・`AreaChart`・`DonutChart`・`BarList` ほか、`EChart`、書式の `formatValue`) |
97
97
  | `@squadbase/vantage/table` | `FilePageView`・`TableViewer`(データファイルページの表ビューア) |
98
98
  | `@squadbase/vantage/slide` | `SlideDeck`・`Slide`・`Steps`・`Step`・`MorphElement`・`useSlideNumber`・`useIsActiveSlide`(スライド専用。1920×1080 の固定キャンバス) |
99
99
  | `@squadbase/vantage/doc` | `Document`(ドキュメント専用。中の素の HTML 要素に見出し・表などのスタイルが当たる) |
100
100
  | `@squadbase/vantage/markdown` | `MarkdownRenderer`(Shiki を隔離するための専用サブパス) |
101
101
  | `@squadbase/vantage/server` | `ApiContext`・`ApiHandler`・`HttpError`・`isHttpError`・`json`(server/ 側でのみ使う) |
102
102
 
103
+ **KPI は `KpiCard`、増減は `Delta`(`comparison` と `polarity` を渡す)。** 向き・率・色は値から計算
104
+ されるので手で渡さない。`TrendIndicator` は非推奨(`direction` を手で渡すので値と食い違いうる)。props は
105
+ `vantage docs kpi-card` / `vantage docs delta` を引く。
106
+
107
+ ```tsx
108
+ import { KpiCard, Delta } from "@squadbase/vantage/components";
109
+
110
+ <KpiCard label="売上" value={48_200_000} format="currency"
111
+ comparison={{ previous: 42_900_000, vs: "prior-period" }} />
112
+ <Delta value={0.021} comparison={{ previous: 0.026, vs: "prior-period" }} polarity="lower-is-better" />
113
+ ```
114
+
103
115
  ## モードは 2 つ、切り替えるのは `server/` の有無だけ
104
116
 
105
117
  `server/` ディレクトリがあれば **fullstack**、無ければ **SPA**。`vantage-manifest.json` の
@@ -137,6 +149,15 @@ root/
137
149
  | `.xlsx` ページ | `agents/xlsx.md` |
138
150
  | `.csv` ページ | `agents/csv.md` |
139
151
 
152
+ **ページになるのは `.tsx` / `.jsx`(`.slide.tsx`・`.doc.tsx` を含む)・`.csv`・`.xlsx` だけ。**
153
+
154
+ - `.xls`・`.xlsm`・`.xlsb`・`.ods`・`.tsv`・`.numbers`・`.parquet` はルートにならず、404 にもならない。
155
+ `vantage check` の `UNSUPPORTED_PAGE_FILE` 警告だけが知らせる。`.xlsx` / `.csv` に変換して置く
156
+ - `.md`・`.json`・`.txt` は何も言わずに無視される。Markdown を見せたいときは `.tsx` のページで
157
+ `MarkdownRenderer`(`@squadbase/vantage/markdown`)に渡す
158
+ - `.csv` / `.xlsx` はブラウザでパースする。25MB を超えるとそのページにエラーが出る
159
+ (`FILE_PAGE_TOO_LARGE` 警告)。20 万行を超えるシートは先頭 20 万行だけが表示される
160
+
140
161
  ## 環境変数
141
162
 
142
163
  - **クライアントで読めるのは `import.meta.env.PUBLIC_*` と `MODE`/`DEV`/`PROD`/`SSR`/`BASE_URL`
@@ -25,6 +25,11 @@ export async function GET({ params, env }: ApiContext) {
25
25
  エクスポートする。それ以外の名前は `INVALID_API_EXPORT` エラー。
26
26
  - 動的 API も `[id].ts` 記法: `server/api/customers/[id].ts` → `GET /api/customers/:id`。
27
27
  `params.id` で取り出す(`noUncheckedIndexedAccess` が効くので narrowing が要る)。
28
+ - **`noUncheckedIndexedAccess` は配列・レコードの添字すべてに効く。** `arr[0]` も `obj[key]` も
29
+ `T | undefined` になる。最初に書く前に、添字アクセスと `useApiQuery` の `data` が
30
+ undefined を扱っているかを頭の中で型検査してから書く。上流の生の応答の値は
31
+ `Number(row.metricValues?.[0]?.value ?? "0")` のように `?.` と `??` で取り出す
32
+ (`!` で黙らせない)。
28
33
  - **クライアントに見せたいエラーは `HttpError(status, msg)` を throw する。** それ以外の throw は
29
34
  ログに記録され汎用の 500 に丸められる。
30
35
  - **シークレットは `ApiContext.env` にだけ届く**(クライアントには決して届かない)。
@@ -34,9 +39,12 @@ export async function GET({ params, env }: ApiContext) {
34
39
 
35
40
  ```tsx
36
41
  import { useApiQuery, useApiMutation } from "@squadbase/vantage/query"
42
+ import { Loading, ErrorState } from "@squadbase/vantage/ui"
37
43
 
38
44
  const q = useApiQuery<Customer>(`/api/customers/${customerId}`)
45
+ if (q.isPending) return <Loading />
39
46
  if (q.isError) return <ErrorState message={q.error.message} /> // HttpError のメッセージ
47
+ q.data // ここで初めて Customer(undefined ではない)
40
48
 
41
49
  // クエリ文字列は search で。undefined の項目は落ちる
42
50
  const rows = useApiQuery<Row[]>("/api/customers", { search: { segment } })
@@ -45,5 +53,26 @@ const rows = useApiQuery<Row[]>("/api/customers", { search: { segment } })
45
53
  const save = useApiMutation<Customer, Payload>("/api/customers", { method: "POST" })
46
54
  ```
47
55
 
56
+ **`data` は、同じ結果オブジェクトで `isPending` と `isError` を判定したあとでしか
57
+ narrowing されない。** 判定前や、配列の `.find` などでまとめた判定のあとでは `T | undefined` のまま。
58
+ 複数のクエリは 1 本ずつ判定してから `data` を使う(`data!` で黙らせない):
59
+
60
+ ```tsx
61
+ const sessions = useApiQuery<SessionsDaily[]>("/api/sessions-daily")
62
+ const metrics = useApiQuery<MetricsDaily[]>("/api/metrics-daily")
63
+
64
+ if (sessions.isPending || metrics.isPending) return <Loading />
65
+ if (sessions.isError) return <ErrorState message={sessions.error.message} />
66
+ if (metrics.isError) return <ErrorState message={metrics.error.message} />
67
+ // ここから sessions.data: SessionsDaily[] / metrics.data: MetricsDaily[]
68
+ return <Chart sessions={sessions.data} metrics={metrics.data} />
69
+
70
+ // NG: const failed = [sessions, metrics].find((q) => q.isError) のように配列でまとめて判定すると
71
+ // 各 q.data は narrowing されず、`T[] | undefined` を T[] の props に渡して型エラーになる
72
+ ```
73
+
74
+ カードごとに別々に読み込み中・エラーを出すなら、`data` を渡す側で `q.data ?? []` にするか、
75
+ カードのコンポーネントの中で上と同じ判定をする。
76
+
48
77
  `ApiError` は `message`・`status`・`body`・`requestId` を持つ。hook が使えない場所では
49
78
  `apiJson(path, init)`、生の `Response` が要るときは `apiFetch`。
@@ -27,6 +27,7 @@
27
27
  ```
28
28
  - 数式・グラフ・セル書式といった概念は csv には無いので、値がそのまま読めます。ブラウザで
29
29
  パースするので 25MB を超えるファイルはそのページにエラーが出ます —— 大きいデータは
30
- `server/api/` から配って `DataTable` で描いてください
30
+ `server/api/` から配って `DataTable` で描いてください。20 万行を超えると先頭
31
+ 20 万行だけが表示されます(残りはダウンロードして見る)
31
32
  - **ビューアの無い拡張子(`.tsv` など)はルートになりません。** `vantage check` の
32
33
  `UNSUPPORTED_PAGE_FILE` 警告が知らせます
@@ -12,7 +12,7 @@
12
12
 
13
13
  ```tsx
14
14
  import { definePage } from "@squadbase/vantage"
15
- import { EChart } from "@squadbase/vantage/components"
15
+ import { BarChart } from "@squadbase/vantage/components"
16
16
  import { Document } from "@squadbase/vantage/doc"
17
17
 
18
18
  export const page = definePage({ title: "6月度サマリー", navLabel: "6月度サマリー" })
@@ -23,7 +23,7 @@ export default function JuneSummary() {
23
23
  <p>6月の売上は <strong>5,250 万円</strong>で、目標を 5% 上回りました。</p>
24
24
  <h2>週次の売上</h2>
25
25
  <figure>
26
- <EChart option={option} height={280} ariaLabel="6月の週次売上" />
26
+ <BarChart data={weekly} index="week" categories={["売上"]} height={280} ariaLabel="6月の週次売上" />
27
27
  <figcaption>第4週はキャンペーン初週</figcaption>
28
28
  </figure>
29
29
  <table>…</table>
@@ -42,8 +42,11 @@ export default function JuneSummary() {
42
42
  見た目を変えたいときはユーティリティを並べず、下の `--doc-*` を変えます。
43
43
  - **数値はコードに直接書く。** ドキュメントは書いた時点の内容を残すページです。
44
44
  `useApiQuery` などで読み込むと、開くたびに値が変わります。
45
- - **チャートは `EChart`(`@squadbase/vantage/components`)を文中に置く。** `figure` で囲めば
45
+ - **チャートは型付きチャート(`BarChart`・`LineChart` など。`@squadbase/vantage/components`)を
46
+ 文中に置く**(選び方は `agents/page.md` の「グラフはまず型付きチャートで描く」)。`figure` で囲めば
46
47
  `figcaption` がキャプションになります。
48
+ - **PDF の保存ボタンは作らない。** `<Document>` が右下に PDF 保存のボタンを出し、印刷時は
49
+ 本文だけをライトの配色で出します。
47
50
  - **ページ全体を包むのは `<Document>` だけ。** `PageShell` などのダッシュボード用の枠で包まない
48
51
  (本文の幅と余白は `<Document>` が決めます)。
49
52