ksk-design-system 1.49.2 → 1.51.0
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.
- package/NATIVE_RECIPES.md +140 -0
- package/contracts/components.json +6 -3
- package/contracts/token-hex-cache.json +1 -1
- package/dist/index.js +551 -545
- package/dist/native/ui.js +767 -377
- package/dist/types/components/patterns/mobile-floating-action-button.d.ts +9 -2
- package/dist/types/index.d.ts +3 -1
- package/dist/types/lib/ime.d.ts +28 -0
- package/dist/types/native/calendar-cells.d.ts +95 -0
- package/dist/types/native/components/Accordion.d.ts +22 -2
- package/dist/types/native/components/Calendar.d.ts +44 -2
- package/dist/types/native/components/Collapsible.d.ts +23 -2
- package/dist/types/native/components/EmptyState.d.ts +9 -2
- package/dist/types/native/components/ErrorState.d.ts +9 -2
- package/dist/types/native/components/IconButton.d.ts +65 -0
- package/dist/types/native/components/ListItem.d.ts +9 -2
- package/dist/types/native/components/MobileFloatingActionButton.d.ts +8 -1
- package/dist/types/native/components/QuickActionGrid.d.ts +8 -3
- package/dist/types/native/components/index.d.ts +3 -2
- package/dist/types/native/disclosure-state.d.ts +21 -0
- package/dist/types/native/glass-accent-fill.d.ts +43 -0
- package/dist/types/native/icon-button-metrics.d.ts +16 -0
- package/package.json +1 -1
- package/src/components/COMPONENT_LOOKUP.md +1 -1
- package/src/native/COMPONENT_LOOKUP.md +2 -1
package/NATIVE_RECIPES.md
CHANGED
|
@@ -117,6 +117,19 @@ import {
|
|
|
117
117
|
|
|
118
118
|
Web/PWA consumer は `ksk-design-system` の `MobileAppShell` と `BottomTabBar variant="pill"` / `MobileFloatingActionButton` を組み合わせます。`bottomNavMode="fixed"` では shell が fixed wrapper と safe-area padding を持ちます。既に fixed な nav を渡す場合は `bottomNavMode="external"` を指定します。
|
|
119
119
|
|
|
120
|
+
### Liquid Glass の FAB
|
|
121
|
+
|
|
122
|
+
写真・地図・リストの上に FAB を浮かせるときは `variant="glass"` を使います。`GlassView` にブランド色をほぼ不透明(light 95%)で敷いた Liquid Glass で、web の `Button variant="glass-accent"` と同じ質感です。塗り・縁・上辺ハイライトの色は `src/native/glass-accent-fill.ts` の純関数がテーマの `brand.primary` から導出するので、テーマを差し替えれば自動で追従します。
|
|
123
|
+
|
|
124
|
+
```tsx
|
|
125
|
+
<MobileFloatingActionButton label="追加" variant="glass" onPress={openCreate} />
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
- 既定は `variant="default"`(ブランド色のソリッド塗り)。既存画面の見た目は変わりません。
|
|
129
|
+
- 塗りを薄くしないでください。低透明度ティントにすると明るい背景で白前景(`text.on-inverse`)が読めなくなります。
|
|
130
|
+
- `glass` に外側の `shadow` を重ねないでください。glass 側が縁・ハイライトを内包しており、影が二重になります。
|
|
131
|
+
- 実際のぼかしは `GlassView` の 4-tier(iOS 26 Liquid Glass → expo-blur → RN Web の backdrop-filter → 半透明 surface)に従います。Android / optional peer 未導入でも塗りは成立します。
|
|
132
|
+
|
|
120
133
|
## Fullscreen screen / photo onboarding
|
|
121
134
|
|
|
122
135
|
`Screen` は header / internal scroll body / footer CTA の骨組みです。写真背景のオンボーディングや入口画面は `PhotoHero` の compound slots を使います。consumer 側で safe-area footer や写真上 typography を再実装しません。
|
|
@@ -237,3 +250,130 @@ const POLICY_SECTIONS = [
|
|
|
237
250
|
<Prose sections={POLICY_SECTIONS} />
|
|
238
251
|
</DocumentScreen>
|
|
239
252
|
```
|
|
253
|
+
|
|
254
|
+
## Tappable icon buttons
|
|
255
|
+
|
|
256
|
+
押せる円形/角丸アイコンは `IconButton` を使います。`IconBadge` は装飾専用(非タップ)なので、ヘッダの設定ギア・カード右上の閉じる・一覧行のアクションを `Button` + `containerStyle` で自作しないでください。Web 側の相当物は `<Button size="icon">` です。
|
|
257
|
+
|
|
258
|
+
`accessibilityLabel` は必須(型で強制)。視覚サイズが 44pt 未満の `size="sm"` でも、実タップ領域は `hitSlop` で 44pt 以上が確保されます。`icon` に関数を渡すと variant/tone/size から解決済みの色とサイズを受け取れるため、consumer 側で色をハードコードしません。
|
|
259
|
+
|
|
260
|
+
```tsx
|
|
261
|
+
import { IconButton } from "ksk-design-system/native/ui"
|
|
262
|
+
|
|
263
|
+
// ヘッダの設定ギア(薄いサーフェス背景)
|
|
264
|
+
<IconButton
|
|
265
|
+
accessibilityLabel="設定"
|
|
266
|
+
variant="tertiary"
|
|
267
|
+
size="sm"
|
|
268
|
+
icon={({ color, size }) => <SettingIcon color={color} size={size} />}
|
|
269
|
+
onPress={() => navigation.navigate("Settings")}
|
|
270
|
+
/>
|
|
271
|
+
|
|
272
|
+
// カード右上の閉じる(地の上、背景なし)
|
|
273
|
+
<IconButton
|
|
274
|
+
accessibilityLabel={`${offer.title}の提案を閉じる`}
|
|
275
|
+
variant="ghost"
|
|
276
|
+
icon={({ color, size }) => <CloseIcon color={color} size={size} />}
|
|
277
|
+
onPress={dismiss}
|
|
278
|
+
/>
|
|
279
|
+
```
|
|
280
|
+
|
|
281
|
+
`variant` は `ghost`(既定・背景なし)/ `tertiary`(薄いサーフェス背景)/ `outline`(境界線)/ `primary`(ブランド色の塗り)で、名前は `Button` の variant 語彙に揃えています。`tone` は `neutral` / `accent` / `caution`(`primary` では無視)、`shape` は `circle`(既定)/ `square` です。
|
|
282
|
+
|
|
283
|
+
## Controlled disclosure (Collapsible / Accordion)
|
|
284
|
+
|
|
285
|
+
`Collapsible` と `Accordion` は制御・非制御の両対応です。外部 state(他セクションとの排他、解答表示との連動、アナリティクス送信)と同期したいときは `open` / `openKeys` を渡します。渡している間は内部 state を無視するため、二重管理になりません。
|
|
286
|
+
|
|
287
|
+
トグル右端の `trailing` スロットは開閉状態を受け取る関数も渡せるので、「表示する / 閉じる」のラベル切り替えを consumer 側で自作しなくて済みます。
|
|
288
|
+
|
|
289
|
+
```tsx
|
|
290
|
+
import { Accordion, Collapsible } from "ksk-design-system/native/ui"
|
|
291
|
+
|
|
292
|
+
const [open, setOpen] = useState(false)
|
|
293
|
+
|
|
294
|
+
<Collapsible
|
|
295
|
+
title="他の選択肢はなぜ違う?"
|
|
296
|
+
open={open}
|
|
297
|
+
onOpenChange={setOpen}
|
|
298
|
+
trailing={(isOpen) => (isOpen ? "閉じる" : "表示する")}
|
|
299
|
+
>
|
|
300
|
+
<Text variant="body.md">{otherWrongChoices.map((c) => c.whyWrong).join("\n")}</Text>
|
|
301
|
+
</Collapsible>
|
|
302
|
+
|
|
303
|
+
<Accordion
|
|
304
|
+
type="multiple"
|
|
305
|
+
openKeys={openSections}
|
|
306
|
+
onOpenChange={setOpenSections}
|
|
307
|
+
items={[
|
|
308
|
+
{ key: "field", title: "分野別の正答率", content: <Text variant="body.md">分野別の内訳</Text>, trailing: (o) => (o ? "閉じる" : "表示する") },
|
|
309
|
+
]}
|
|
310
|
+
/>
|
|
311
|
+
```
|
|
312
|
+
|
|
313
|
+
`defaultOpen` / `defaultOpenKeys` だけを渡した場合は従来どおり非制御で動きます。
|
|
314
|
+
|
|
315
|
+
## Composed accessibility labels
|
|
316
|
+
|
|
317
|
+
`ListItem` / `ActionTile` / `EmptyState` / `ErrorState` は `AccessibilityProps` を継承しているため、`accessibilityLabel` / `accessibilityHint` をそのまま渡せます。「タイトル+状態」を合成した読み上げラベル(例: 「模試2(要解放)」)を付けたいときに使います。
|
|
318
|
+
|
|
319
|
+
```tsx
|
|
320
|
+
<ListItem
|
|
321
|
+
title="模試2"
|
|
322
|
+
description="未受験"
|
|
323
|
+
accessibilityLabel="模試2(要解放)"
|
|
324
|
+
accessibilityHint="タップで解放画面へ移動します"
|
|
325
|
+
onPress={openPaywall}
|
|
326
|
+
/>
|
|
327
|
+
```
|
|
328
|
+
|
|
329
|
+
`EmptyState` / `ErrorState` では、ラベル指定時に icon / title / description だけが1要素にまとまり、`action` のボタンは個別にフォーカスできる位置に残ります。
|
|
330
|
+
|
|
331
|
+
## Japanese calendars
|
|
332
|
+
|
|
333
|
+
`Calendar` は日本のカレンダー慣習に必要な表現を prop で持ちます。曜日の色分け(日=赤 / 土=青)は既存の見た目を変えないよう opt-in(`weekendTone`)です。
|
|
334
|
+
|
|
335
|
+
```tsx
|
|
336
|
+
import { Calendar } from "ksk-design-system/native/ui"
|
|
337
|
+
|
|
338
|
+
<Calendar
|
|
339
|
+
value={examDate}
|
|
340
|
+
onChange={setExamDate}
|
|
341
|
+
weekendTone // 日=赤 / 土=青
|
|
342
|
+
todayEmphasis="dot" // "ring"(既定)| "dot" | "none"
|
|
343
|
+
disablePast // 今日より前を選択不可(minDate と併用時は遅い方が効く)
|
|
344
|
+
dayAccessibilityLabel={(day) =>
|
|
345
|
+
`${day.date.getFullYear()}年${day.date.getMonth() + 1}月${day.date.getDate()}日を受験日に設定`
|
|
346
|
+
}
|
|
347
|
+
/>
|
|
348
|
+
```
|
|
349
|
+
|
|
350
|
+
セルの見た目を丸ごと差し替えたい場合は `renderDay` を使います。`renderDay` は `{ date, weekday, selected, today, disabled, tone }` を受け取ります(タップ・読み上げ・選択不可制御は DS 側が持ったままです)。月移動ボタンは `minDate` / `maxDate` / `disablePast` の範囲外へは自動で disabled になります。
|
|
351
|
+
|
|
352
|
+
### ブランド色を注入する(ThemeProvider を使わない consumer 向け)
|
|
353
|
+
|
|
354
|
+
`ThemeProvider` を使わず、アプリごとのブランドトークンを props で流し込む設計(exam-kit 系が app/theme/brand.ts から各コンポーネントへ色を渡している方式)では、`colors` で日セルの色だけを差し替えられます。指定しなかったキーは DS theme の既定色に落ちるので、既存の呼び出しは見た目が変わりません。
|
|
355
|
+
|
|
356
|
+
```tsx
|
|
357
|
+
<Calendar
|
|
358
|
+
value={examDate}
|
|
359
|
+
onChange={setExamDate}
|
|
360
|
+
weekendTone
|
|
361
|
+
colors={{
|
|
362
|
+
selected: brand.primary, // 選択セルの背景
|
|
363
|
+
selectedText: brand.onPrimary, // 選択セルの文字
|
|
364
|
+
today: brand.accent, // today リング / ドット
|
|
365
|
+
sunday: brand.caution, // weekendTone=true のときだけ効く
|
|
366
|
+
saturday: brand.primary,
|
|
367
|
+
}}
|
|
368
|
+
/>
|
|
369
|
+
```
|
|
370
|
+
|
|
371
|
+
`colors` で足りない見た目(角丸・枠線の太さ・影など)は `dayStyle` で器ごと差し替えます。DS の既定 style の**後ろに**合成されるので確実に勝ちます。
|
|
372
|
+
|
|
373
|
+
```tsx
|
|
374
|
+
<Calendar
|
|
375
|
+
dayStyle={(day) => (day.selected ? { borderRadius: 8, borderWidth: 2, borderColor: brand.primary } : null)}
|
|
376
|
+
/>
|
|
377
|
+
```
|
|
378
|
+
|
|
379
|
+
`renderDay` がセルの「中身」、`dayStyle` がセルの「器」です。色だけなら `colors` で足ります。
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"meta": {
|
|
3
3
|
"name": "KSK Design System — Component Contracts",
|
|
4
|
-
"version": "1.
|
|
4
|
+
"version": "1.51.0",
|
|
5
5
|
"description": "全コンポーネントの構造化定義。バリアント・アクセシビリティ要件・使用ルールを機械可読形式で管理。",
|
|
6
6
|
"counts": {
|
|
7
7
|
"ui": 67,
|
|
@@ -1445,8 +1445,9 @@
|
|
|
1445
1445
|
{
|
|
1446
1446
|
"name": "MobileFloatingActionButton",
|
|
1447
1447
|
"path": "src/components/patterns/mobile-floating-action-button.tsx",
|
|
1448
|
-
"description": "モバイル固定 FAB。BottomTabBar と safe-area を考慮した bottom offset、start/end/center placement、keyboard hide/lift/stay を内包する。",
|
|
1448
|
+
"description": "モバイル固定 FAB。BottomTabBar と safe-area を考慮した bottom offset、start/end/center placement、keyboard hide/lift/stay を内包する。variant=glass で Brand ティントの Liquid Glass 表現になる。",
|
|
1449
1449
|
"variants": [
|
|
1450
|
+
"variant: default / glass",
|
|
1450
1451
|
"placement: start / end / center",
|
|
1451
1452
|
"bottomOffset: none / bottom-nav / bottom-nav-pill / bottom-nav-pill-inline",
|
|
1452
1453
|
"keyboardBehavior: hide / lift / stay"
|
|
@@ -1456,9 +1457,11 @@
|
|
|
1456
1457
|
],
|
|
1457
1458
|
"rules": [
|
|
1458
1459
|
"画面側で fixed bottom/right と Button size=icon-lg を手組みしない",
|
|
1460
|
+
"glass-fab 等の独自クラス + 生 button で Liquid Glass FAB を手組みせず variant=glass を使う",
|
|
1459
1461
|
"BottomTabBar 併用時は bottomOffset=bottom-nav を使う",
|
|
1460
1462
|
"pill BottomTabBar の上に重ねる場合は bottomOffset=bottom-nav-pill、横並びに置く場合は bottomOffset=bottom-nav-pill-inline を使う",
|
|
1461
|
-
"keyboard 表示中に入力を邪魔する場合は keyboardBehavior=hide を使う"
|
|
1463
|
+
"keyboard 表示中に入力を邪魔する場合は keyboardBehavior=hide を使う",
|
|
1464
|
+
"variant=glass に shadow-* を重ねない(glass-accent が inset 3層 + drop shadow を内包するため二重になる)"
|
|
1462
1465
|
]
|
|
1463
1466
|
},
|
|
1464
1467
|
{
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"meta": {
|
|
3
3
|
"name": "KSK Design System — Semantic Token Hex Cache",
|
|
4
|
-
"version": "1.
|
|
4
|
+
"version": "1.51.0",
|
|
5
5
|
"description": "semantic / semanticDark トークン(var(--Primitive-*) 参照)を実 hex に解決したサイドカー生成物。hex はデフォルト(Blue)テーマでの解決値であり、Brand 系(meta.themeDependentKeys に列挙)はテーマ差し替え(orange/green/violet 等)で実色が変わる。テーマ別の完全解決値は `ksk-design-system/native` エクスポート(バンドル済み native トークンモジュール)の themes を参照。tokens.json 本体のスキーマは変更せず、AI がこのファイルだけで実色を把握できるようにし、primitive 値の変更による semantic 実色のドリフトを --check で機械検出する。",
|
|
6
6
|
"generatedBy": "scripts/generate-token-hex-cache.mjs",
|
|
7
7
|
"theme": "default",
|