@hjmds/react-native 0.8.2
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/README.md +310 -0
- package/dist/actions.d.ts +128 -0
- package/dist/actions.d.ts.map +1 -0
- package/dist/actions.js +157 -0
- package/dist/actions.js.map +1 -0
- package/dist/data-display.d.ts +285 -0
- package/dist/data-display.d.ts.map +1 -0
- package/dist/data-display.js +775 -0
- package/dist/data-display.js.map +1 -0
- package/dist/date-picker.d.ts +25 -0
- package/dist/date-picker.d.ts.map +1 -0
- package/dist/date-picker.js +39 -0
- package/dist/date-picker.js.map +1 -0
- package/dist/evidence.d.ts +954 -0
- package/dist/evidence.d.ts.map +1 -0
- package/dist/evidence.js +98 -0
- package/dist/evidence.js.map +1 -0
- package/dist/feedback.d.ts +148 -0
- package/dist/feedback.d.ts.map +1 -0
- package/dist/feedback.js +559 -0
- package/dist/feedback.js.map +1 -0
- package/dist/file-picker.d.ts +20 -0
- package/dist/file-picker.d.ts.map +1 -0
- package/dist/file-picker.js +37 -0
- package/dist/file-picker.js.map +1 -0
- package/dist/forms.d.ts +170 -0
- package/dist/forms.d.ts.map +1 -0
- package/dist/forms.js +595 -0
- package/dist/forms.js.map +1 -0
- package/dist/index.d.ts +16 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +16 -0
- package/dist/index.js.map +1 -0
- package/dist/inputs-public.d.ts +6 -0
- package/dist/inputs-public.d.ts.map +1 -0
- package/dist/inputs-public.js +6 -0
- package/dist/inputs-public.js.map +1 -0
- package/dist/inputs.d.ts +258 -0
- package/dist/inputs.d.ts.map +1 -0
- package/dist/inputs.js +681 -0
- package/dist/inputs.js.map +1 -0
- package/dist/internal/modal-lifecycle.d.ts +15 -0
- package/dist/internal/modal-lifecycle.d.ts.map +1 -0
- package/dist/internal/modal-lifecycle.js +17 -0
- package/dist/internal/modal-lifecycle.js.map +1 -0
- package/dist/internal/state.d.ts +8 -0
- package/dist/internal/state.d.ts.map +1 -0
- package/dist/internal/state.js +18 -0
- package/dist/internal/state.js.map +1 -0
- package/dist/internal/styles.d.ts +29 -0
- package/dist/internal/styles.d.ts.map +1 -0
- package/dist/internal/styles.js +51 -0
- package/dist/internal/styles.js.map +1 -0
- package/dist/navigation.d.ts +271 -0
- package/dist/navigation.d.ts.map +1 -0
- package/dist/navigation.js +978 -0
- package/dist/navigation.js.map +1 -0
- package/dist/number-field.d.ts +58 -0
- package/dist/number-field.d.ts.map +1 -0
- package/dist/number-field.js +172 -0
- package/dist/number-field.js.map +1 -0
- package/dist/otp-field.d.ts +2 -0
- package/dist/otp-field.d.ts.map +1 -0
- package/dist/otp-field.js +2 -0
- package/dist/otp-field.js.map +1 -0
- package/dist/overlays.d.ts +68 -0
- package/dist/overlays.d.ts.map +1 -0
- package/dist/overlays.js +757 -0
- package/dist/overlays.js.map +1 -0
- package/dist/password-field.d.ts +2 -0
- package/dist/password-field.d.ts.map +1 -0
- package/dist/password-field.js +2 -0
- package/dist/password-field.js.map +1 -0
- package/dist/primitives.d.ts +132 -0
- package/dist/primitives.d.ts.map +1 -0
- package/dist/primitives.js +238 -0
- package/dist/primitives.js.map +1 -0
- package/dist/provider.d.ts +41 -0
- package/dist/provider.d.ts.map +1 -0
- package/dist/provider.js +78 -0
- package/dist/provider.js.map +1 -0
- package/dist/slider.d.ts +45 -0
- package/dist/slider.d.ts.map +1 -0
- package/dist/slider.js +200 -0
- package/dist/slider.js.map +1 -0
- package/dist/steps.d.ts +13 -0
- package/dist/steps.d.ts.map +1 -0
- package/dist/steps.js +13 -0
- package/dist/steps.js.map +1 -0
- package/dist/upload-item.d.ts +13 -0
- package/dist/upload-item.d.ts.map +1 -0
- package/dist/upload-item.js +25 -0
- package/dist/upload-item.js.map +1 -0
- package/package.json +166 -0
package/README.md
ADDED
|
@@ -0,0 +1,310 @@
|
|
|
1
|
+
# @hjmds/react-native
|
|
2
|
+
|
|
3
|
+
Expo-independent React Native renderers for `@hjmds/design-contracts`. The package uses only
|
|
4
|
+
React and React Native runtime APIs, so it can be consumed by bare React Native and Expo apps.
|
|
5
|
+
|
|
6
|
+
```tsx
|
|
7
|
+
import {
|
|
8
|
+
Button,
|
|
9
|
+
HjmNativeProvider,
|
|
10
|
+
Stack,
|
|
11
|
+
Text,
|
|
12
|
+
} from "@hjmds/react-native";
|
|
13
|
+
|
|
14
|
+
export function Screen() {
|
|
15
|
+
return (
|
|
16
|
+
<HjmNativeProvider>
|
|
17
|
+
<Stack gap="md">
|
|
18
|
+
<Text variant="title">프로필</Text>
|
|
19
|
+
<Button onPress={() => undefined}>저장</Button>
|
|
20
|
+
</Stack>
|
|
21
|
+
</HjmNativeProvider>
|
|
22
|
+
);
|
|
23
|
+
}
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
## Runtime boundaries
|
|
27
|
+
|
|
28
|
+
- React 19 or newer and React Native 0.81 or newer are peer dependencies.
|
|
29
|
+
- There is no Expo dependency and no navigation, icon, font-loading, or animation dependency.
|
|
30
|
+
- Native font scaling remains uncapped. At the root, HJM text—including raw Native labels and
|
|
31
|
+
inputs owned by `TextField`, `TextArea`, `SearchField`, `Combobox`, `NumberField`, and `Slider`—
|
|
32
|
+
delegates a detected system scale to the OS. An explicit Provider `textScale` (or resolved
|
|
33
|
+
`value`) switches those controls to deterministic scaling and disables OS multiplication, so the
|
|
34
|
+
requested scale is applied exactly once. A nested Provider inherits that absolute scale; its own
|
|
35
|
+
`textScale` replaces rather than multiplies the parent value.
|
|
36
|
+
- Motion uses React Native's built-in `Animated` API and canonical recipe durations/easing; there
|
|
37
|
+
is no third-party animation dependency. Reduced motion removes spatial exit movement and retains
|
|
38
|
+
only the recipe-permitted enter opacity fallback.
|
|
39
|
+
- `direction` controls logical row order and text alignment without mutating the process-wide
|
|
40
|
+
`I18nManager` setting.
|
|
41
|
+
|
|
42
|
+
`HjmNativeProvider` detects system color scheme, RTL, font scale, and reduced-motion preference.
|
|
43
|
+
Every axis can be overridden for tests or a product preference, and nested providers inherit
|
|
44
|
+
resolved parent values. Products with a reviewed semantic palette can pass the complete resolved
|
|
45
|
+
`value`; runtime validation rejects missing roles and non-composable color values, while partial
|
|
46
|
+
token overrides remain unsupported.
|
|
47
|
+
|
|
48
|
+
The package exports include:
|
|
49
|
+
|
|
50
|
+
- foundations: `Text`, `Surface`, `Stack`, `Icon`, `Section`, responsive `Grid`, adaptive `Layout`
|
|
51
|
+
- actions and fields: `Button`, `IconButton`, `BottomCTA`, `Link`, `Field`, `Form`, `TextField`,
|
|
52
|
+
`TextArea`, `SearchField`, `Select`, `Combobox`, `NumberField`, `Slider`
|
|
53
|
+
- adaptive inputs: `DatePicker`, Expo-independent adapter-based `FilePicker`
|
|
54
|
+
- selection and navigation: `Checkbox`, `Radio`, `CheckboxGroup`, `RadioGroup`, `Switch`, `SegmentedControl`, `Chip`,
|
|
55
|
+
`Tabs`, `Steps`, `BottomNavigation`, `TopBar`, `TopBarAction`, `Menu`
|
|
56
|
+
- display: `Badge`, `CounterBadge`, `Tag`, `Card`, `List`, `ListRow`, `Statistic`,
|
|
57
|
+
`StatisticGroup`, `UploadItem`, `Avatar`, `Divider`, `Accordion`, `DescriptionList`, `Image`, `Timeline`
|
|
58
|
+
- feedback and collections: `Notice`, `EmptyState`, `Progress`, `Spinner`, `Skeleton`, `LoadMore`,
|
|
59
|
+
`Result`, `Toast`, `ToastRegion`
|
|
60
|
+
- overlays: `Dialog`, `AlertDialog`, `Sheet`
|
|
61
|
+
|
|
62
|
+
`Image` consumes the same intrinsic descriptor as Web. `width` and `height`
|
|
63
|
+
reserve the frame before loading, omitted `decorative` defaults to `true`, and
|
|
64
|
+
`fit` is translated to the matching Native `resizeMode` (`fill` becomes
|
|
65
|
+
`stretch`). A failed informative image keeps its original accessible name and
|
|
66
|
+
shows a built-in fallback; changing `src` starts a fresh load.
|
|
67
|
+
|
|
68
|
+
```tsx
|
|
69
|
+
import { Image } from "@hjmds/react-native/data-display";
|
|
70
|
+
import { Image as ExpoImage } from "expo-image";
|
|
71
|
+
|
|
72
|
+
<Image
|
|
73
|
+
src="https://cdn.example.com/standings.png"
|
|
74
|
+
width={800}
|
|
75
|
+
height={450}
|
|
76
|
+
fit="contain"
|
|
77
|
+
decorative={false}
|
|
78
|
+
accessibilityLabel="2026 시즌 팀 순위 표"
|
|
79
|
+
renderImage={({ src, fit, reportLoad, reportError, style }) => (
|
|
80
|
+
<ExpoImage
|
|
81
|
+
source={src}
|
|
82
|
+
contentFit={fit}
|
|
83
|
+
onLoad={reportLoad}
|
|
84
|
+
onError={reportError}
|
|
85
|
+
style={style}
|
|
86
|
+
/>
|
|
87
|
+
)}
|
|
88
|
+
/>
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
Use `sourceAdapter` when the built-in React Native host needs headers, cache
|
|
92
|
+
metadata, or another `ImageSourcePropType`. The older `source` API remains as a
|
|
93
|
+
deprecated compatibility path for migration, but it cannot guarantee intrinsic
|
|
94
|
+
space reservation without the canonical dimensions.
|
|
95
|
+
|
|
96
|
+
`Badge.variant` is the shared `filled | outline` recipe axis on Web and Native. `ListRow` keeps
|
|
97
|
+
`titleMetadata` inside the row's accessible name only through caller-supplied `metadataLabel`, and
|
|
98
|
+
renders `trailingAction` as a separate target instead of nesting an action inside the row command.
|
|
99
|
+
Without `onPress`, its root is a non-interactive `View`. `List` requires a localized region `label`
|
|
100
|
+
and supports `plain | grouped` appearance; `Statistic` accepts `contextLabel`, an exact
|
|
101
|
+
`accessibilityLabel`, or a custom accessible-name composer.
|
|
102
|
+
|
|
103
|
+
## Controlled and uncontrolled state
|
|
104
|
+
|
|
105
|
+
Checkbox, CheckboxGroup, RadioGroup, Switch, SegmentedControl, Tabs, Accordion, Select, Combobox, Menu, Dialog,
|
|
106
|
+
AlertDialog, and Sheet support controlled and uncontrolled state. Do not switch a mounted component
|
|
107
|
+
between those modes. `BottomNavigation` is intentionally controlled-only: the router supplies
|
|
108
|
+
`descriptor.selectedKey`, and `onActivate` emits `navigate` or `reselect` intent without keeping a
|
|
109
|
+
second selection. `Form` keeps field values product-owned and only manages its submit session;
|
|
110
|
+
`LoadMore` similarly keeps collection data product-owned and gates page requests by `requestKey`.
|
|
111
|
+
|
|
112
|
+
`BottomNavigation.renderIcon` receives the recipe-owned `color`, `size`, and `strokeWidth` plus the
|
|
113
|
+
resolved item. Router adapters can forward `onLongActivate`, derive per-destination test IDs with
|
|
114
|
+
`getItemTestID`, replace only the hidden badge subtree with `renderBadge`, and compose a centered
|
|
115
|
+
`primaryAction` beside a `center-gap` destination list. Safe-area padding is additive, and
|
|
116
|
+
`keyboardBehavior: "hide"` subscribes to the cross-platform Native keyboard lifecycle.
|
|
117
|
+
|
|
118
|
+
`TopBar.title` is optional for action-only and back-only screens. The renderer keeps logical source
|
|
119
|
+
and reading order as leading/back, title when present, then trailing/actions in both directions;
|
|
120
|
+
large text stacks that same order and lets the title wrap. Prefer `TopBarAction` for toolbar
|
|
121
|
+
affordances: its localized `label` is a visible micro-label by default, the target remains at least
|
|
122
|
+
44 points, and `labelVisibility="accessibility-only"` is available for conventional back/close
|
|
123
|
+
icons. `intent="button"` can use `renderAction` for a product action wrapper, while
|
|
124
|
+
`intent="link"` passes its canonical destination and fully named pressable props to `renderLink`
|
|
125
|
+
for Expo Router or another router. A link may instead supply `onNavigate`; HJM never invents route
|
|
126
|
+
copy or destination handling. `titleLeading` stays decorative; pair it with `onTitlePress` and a
|
|
127
|
+
localized `titleAccessibilityLabel` when the complete title slot opens a profile, team, or account
|
|
128
|
+
switcher. The toolbar root is intentionally not a named accessibility group because its header and
|
|
129
|
+
actions remain separate reading-order targets.
|
|
130
|
+
|
|
131
|
+
```tsx
|
|
132
|
+
<TopBar
|
|
133
|
+
onTitlePress={() => openTeamSwitcher()}
|
|
134
|
+
title="HJM 러너스"
|
|
135
|
+
titleAccessibilityHint="팀 선택 화면 열기"
|
|
136
|
+
titleAccessibilityLabel="HJM 러너스, 팀 변경"
|
|
137
|
+
titleLeading={<TeamAvatar />}
|
|
138
|
+
actions={(
|
|
139
|
+
<TopBarAction
|
|
140
|
+
destination={{ kind: "internal", href: "/notifications" }}
|
|
141
|
+
intent="link"
|
|
142
|
+
label="알림"
|
|
143
|
+
renderLink={({ destination, ...pressableProps }) => (
|
|
144
|
+
<ProductRouterLink destination={destination} asChild>
|
|
145
|
+
<Pressable {...pressableProps} />
|
|
146
|
+
</ProductRouterLink>
|
|
147
|
+
)}
|
|
148
|
+
>
|
|
149
|
+
<NotificationIcon />
|
|
150
|
+
</TopBarAction>
|
|
151
|
+
)}
|
|
152
|
+
/>
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
Attach a `LoadMoreHandle` ref when a virtualized list owns viewport detection, then call
|
|
156
|
+
`ref.current?.onEndReached()` from `FlatList.onEndReached`. The imperative path and the built-in
|
|
157
|
+
automatic/manual triggers share one cursor gate, so a ready `requestKey` cannot issue twice while
|
|
158
|
+
the product is committing its next collection state. `density="compact" | "regular"` changes only
|
|
159
|
+
the recipe-owned footer spacing. Ready/retry controls, the named busy progress indicator, error
|
|
160
|
+
announcement, and completion copy all bind to the shared state recipe. If `onLoadMore` rejects,
|
|
161
|
+
`onRequestError(error, reason)` receives the failure and the imperative bridge still resolves
|
|
162
|
+
without an unhandled rejection; update the controlled descriptor to `error` to render retry UI.
|
|
163
|
+
`onRequestOutcome` reports non-error controller outcomes for started, blocked, and de-duplicated
|
|
164
|
+
requests.
|
|
165
|
+
|
|
166
|
+
`NumberField` has the same `number | null` model, locale-neutral draft grammar,
|
|
167
|
+
blur/submit commit, clamp/snap resolver, and required localized stepper labels
|
|
168
|
+
as Web. Its buttons are 44-point targets and its text input exposes Native
|
|
169
|
+
increment/decrement accessibility actions. Native font scaling remains the
|
|
170
|
+
only text-scale multiplication. Currency/unit formatting, grouping separators,
|
|
171
|
+
locale-specific decimal separators, and non-Latin number parsing are not
|
|
172
|
+
claimed by this initial renderer. Non-ASCII numeric IME parsing and caret
|
|
173
|
+
preservation likewise remain unverified.
|
|
174
|
+
|
|
175
|
+
`Slider` reuses NumberField's min-origin clamp/snap resolver. It supports
|
|
176
|
+
controlled `value` or uncontrolled `defaultValue` (falling back to `min`),
|
|
177
|
+
horizontal LTR/RTL touch dragging, and atomic Native `adjustable`
|
|
178
|
+
increment/decrement actions. Products must provide localized `incrementLabel`
|
|
179
|
+
and `decrementLabel`; `getValueText` owns visible and announced formatting.
|
|
180
|
+
`onValueChange` fires throughout a drag, while `onValueChangeEnd` fires once on
|
|
181
|
+
release/termination and once per completed accessibility action. The responder
|
|
182
|
+
is dependency-free and the target remains at least 44 points. Disabling during
|
|
183
|
+
a drag commits the last value once, terminates the gesture, and ignores stale
|
|
184
|
+
move/release events. Off-grid controlled values remain visible, while user input
|
|
185
|
+
snaps and preserves exact min/max endpoints. Range/multi-thumb,
|
|
186
|
+
vertical orientation, marks, tooltips, nonlinear scales, and acceleration are
|
|
187
|
+
not claimed by this renderer.
|
|
188
|
+
|
|
189
|
+
Tabs exposes the shared `activationMode`, `mountPolicy`, `panelMode`, `orientation`, `direction`,
|
|
190
|
+
and `loop` policies. Uncontrolled Tabs and SegmentedControl reconcile a removed selection to the
|
|
191
|
+
first enabled item; controlled invalid or disabled selections fail before rendering.
|
|
192
|
+
|
|
193
|
+
`TextArea` follows the same accessible-name rule as `TextField`: provide either a visible `label`
|
|
194
|
+
or `accessibilityLabel`. `SearchField` can render product icons through `renderLeading`,
|
|
195
|
+
`renderClearIcon`, and `renderBusyIndicator`; its trailing precedence is busy, then clear, then the
|
|
196
|
+
passive `trailing` slot. `SegmentedControl` options can render their own leading visual.
|
|
197
|
+
|
|
198
|
+
`Checkbox` supports boolean and `"mixed"` state, read-only semantics, plain/card presentation,
|
|
199
|
+
compact/default sizing, and replaceable leading/indicator visuals. `CheckboxGroup` validates unique
|
|
200
|
+
enabled option keys and exposes controlled or uncontrolled immutable `ReadonlySet` selection.
|
|
201
|
+
`RadioGroup` shares the presentation, size, leading, read-only, invalid, required, and indicator
|
|
202
|
+
contracts, supports vertical or horizontal layout, and stacks a horizontal group when large text
|
|
203
|
+
would make the row unsafe. `indicator="none"` is intended for products whose leading visual or card
|
|
204
|
+
selection treatment is sufficient; the Native selected/checked state is still announced.
|
|
205
|
+
|
|
206
|
+
Pass the trigger's native `returnFocusRef` to an overlay. After a real Native Modal dismissal—whether requested by
|
|
207
|
+
an action, Android back, scrim dismissal, or a controlled parent—the renderer returns assistive
|
|
208
|
+
technology focus through `AccessibilityInfo.setAccessibilityFocus`.
|
|
209
|
+
|
|
210
|
+
`AlertDialog` consumes the shared `request` contract and session, so async confirm runs once, busy
|
|
211
|
+
state blocks every dismissal, and a rejected action announces its fallback error while remaining
|
|
212
|
+
open. AlertDialog and Sheet keep the Native host at `animationType="none"`, own their recipe motion,
|
|
213
|
+
and settle only after visual exit plus host teardown. iOS uses the real `Modal.onDismiss`; Android
|
|
214
|
+
finishes after the no-animation host-removal commit and queued interactions drain. Rapid reopen is
|
|
215
|
+
either resumed in the existing host during visual exit or deferred until teardown, so a stale close
|
|
216
|
+
cannot restore focus or publish `onDismissComplete` over a successor surface. `Sheet` also applies
|
|
217
|
+
the shared `dismissPolicy` and reports the concrete reason through `onOpenChange`.
|
|
218
|
+
|
|
219
|
+
`Select`, `Combobox`, and `Menu` accept a flat collection, canonical collection source, or sectioned
|
|
220
|
+
collection and reject ambiguous combinations. They support loading, error, empty, and loading-more
|
|
221
|
+
states, retry actions, read-only triggers, product-owned leading visuals, and reasoned open-change
|
|
222
|
+
callbacks. Selection or action side effects that must navigate or replace the screen belong in
|
|
223
|
+
`onSelectionAfterDismiss`, `onCommitAfterDismiss`, or `onActionAfterDismiss`; these callbacks run
|
|
224
|
+
only after the Native Modal has torn down. The renderer keeps the host at `animationType="none"` so
|
|
225
|
+
iOS `Modal.onDismiss` and Android's post-commit interaction boundary represent the same lifecycle.
|
|
226
|
+
All interactive targets have a 44-point minimum.
|
|
227
|
+
|
|
228
|
+
`Link` consumes the shared destination descriptor but delegates navigation to the product's
|
|
229
|
+
`onNavigate` router boundary; the renderer never guesses how internal routes or external URLs open.
|
|
230
|
+
|
|
231
|
+
`BottomCTA` accepts localized `loadingLabel` copy per descriptor and either a second descriptor or
|
|
232
|
+
an arbitrary product-owned `secondaryAction` node. `Notice` and `EmptyState` make announcement
|
|
233
|
+
priority explicit (`none | polite | assertive`); both expose product visual slots, and EmptyState can
|
|
234
|
+
use `align="upper"` for scrollable screens. A `Section` may omit its heading when the screen already
|
|
235
|
+
owns the accessible title.
|
|
236
|
+
|
|
237
|
+
## Localization ownership
|
|
238
|
+
|
|
239
|
+
The Native renderer has no built-in language. Products must inject localized
|
|
240
|
+
copy for `Form.fallbackErrorMessage`, `SearchField.clearLabel` /
|
|
241
|
+
`SearchField.busyLabel`, `Select.placeholder` / `Select.dismissLabel`,
|
|
242
|
+
`Combobox.emptyMessage` / `loadingMessage` / `clearLabel` / `dismissLabel`,
|
|
243
|
+
`Menu.dismissLabel`, collection retry/error/loading-more copy where used,
|
|
244
|
+
`Slider.incrementLabel` / `Slider.decrementLabel`, and
|
|
245
|
+
`Dialog.closeLabel` / `Sheet.closeLabel`. Optional
|
|
246
|
+
region names remain injectable through `Select.optionsAccessibilityLabel`,
|
|
247
|
+
`Combobox.resultsAccessibilityLabel`, `AccordionItem.contentAccessibilityLabel`,
|
|
248
|
+
`TabOption.panelAccessibilityLabel`, and `ToastRegion.accessibilityLabel`.
|
|
249
|
+
When those optional names are absent, the renderer relies on the Native role,
|
|
250
|
+
state, or the caller's existing control label instead of inventing translated
|
|
251
|
+
suffixes. `RadioGroup.requiredLabel` and `readOnlyLabel` are optional localized
|
|
252
|
+
qualifiers; a language-neutral asterisk and disabled interaction state remain
|
|
253
|
+
when they are omitted.
|
|
254
|
+
|
|
255
|
+
`ToastRegion` can wrap a screen and exposes `useToastRegion().show()` / `dismiss()`. The shared
|
|
256
|
+
bounded FIFO store owns `maxVisible`, `maxQueued`, duplicate and overflow policies, exactly-once
|
|
257
|
+
action/dismiss behavior, app-background and interaction timer pauses, and interrupted teardown.
|
|
258
|
+
It announces normal priority politely and high priority assertively, and keeps actionable toasts
|
|
259
|
+
persistent unless the descriptor supplies a duration.
|
|
260
|
+
Placement, physical or logical safe-area insets, keyboard avoidance, and an additional bottom-bar
|
|
261
|
+
offset are renderer inputs. Toast transitions bind to the Native recipe and complete synchronously
|
|
262
|
+
under reduced motion; `renderToneIcon` lets products map the generic tone/mark contract to
|
|
263
|
+
their icon set.
|
|
264
|
+
|
|
265
|
+
Checkbox, CheckboxGroup, Select, Combobox, and Menu publish Native beta evidence for their literal
|
|
266
|
+
default render cases. Combobox also guards externally managed results with their originating query
|
|
267
|
+
and can retain a product-supplied selected-item snapshot. Those component tests do not certify
|
|
268
|
+
device IME composition, active-option scrolling, or assistive-technology behavior; products should
|
|
269
|
+
keep those axes in their own device matrix.
|
|
270
|
+
|
|
271
|
+
## Grid
|
|
272
|
+
|
|
273
|
+
`Grid` delegates window classes and column geometry to `@hjmds/design-contracts/grid`. Native
|
|
274
|
+
`useWindowDimensions()` supplies density-independent window width, so the same
|
|
275
|
+
compact/medium/expanded/wide thresholds are used on Web and Native. Column geometry uses an
|
|
276
|
+
explicit `availableWidth` when provided; otherwise `Grid` measures its rendered container with
|
|
277
|
+
`onLayout` (using window width only for the safe first render). `DescriptionList` follows the same
|
|
278
|
+
nested-container measurement rule.
|
|
279
|
+
|
|
280
|
+
For bundle-sensitive entry points, import only the renderer family you use, for example
|
|
281
|
+
`@hjmds/react-native/actions`, `@hjmds/react-native/forms`,
|
|
282
|
+
`@hjmds/react-native/number-field`, `@hjmds/react-native/slider`,
|
|
283
|
+
`@hjmds/react-native/date-picker`, `@hjmds/react-native/file-picker`,
|
|
284
|
+
`@hjmds/react-native/steps`, `@hjmds/react-native/upload-item`, or
|
|
285
|
+
`@hjmds/react-native/feedback`. Available
|
|
286
|
+
executable families are `provider`, `primitives`, `actions`, `inputs`, `number-field`, `slider`,
|
|
287
|
+
`date-picker`, `file-picker`, `steps`, `upload-item`, `forms`, `navigation`, `data-display`,
|
|
288
|
+
`feedback`, `overlays`, and `evidence`. These supported
|
|
289
|
+
family-level subpaths are verified not to traverse the renderer root barrel. They do not promise a
|
|
290
|
+
separate file or component-level tree-shaking result for every named export.
|
|
291
|
+
|
|
292
|
+
## Renderer evidence
|
|
293
|
+
|
|
294
|
+
`@hjmds/react-native/evidence` publishes schema v2 claims. Each claim links the baseline environment
|
|
295
|
+
matrix—default, dark, long copy, large text, RTL, reduced motion, and accessibility structure—to a
|
|
296
|
+
literal case in `test/default-render.test.tsx`; package tests fail if the case inventory and
|
|
297
|
+
manifest diverge. These are component-level `react-test-renderer` smoke proofs, not screenshot,
|
|
298
|
+
device, TalkBack, VoiceOver, or performance certification. Keyboard/accessibility-action and paired
|
|
299
|
+
platform parity remain fail-closed until a dedicated proof is mapped.
|
|
300
|
+
|
|
301
|
+
## Metro production smoke
|
|
302
|
+
|
|
303
|
+
Run `pnpm --filter @hjmds/react-native bundle:check` from the workspace root. The check builds the
|
|
304
|
+
renderer, derives the executable-family inventory from package exports, and creates one minified
|
|
305
|
+
Android production bundle from a fixture that must directly import every family. It verifies the
|
|
306
|
+
source-map module graph in a temporary directory and fails if a family is absent, the root barrel is
|
|
307
|
+
pulled in, or Expo, `react-dom`, or `@hjmds/react` contaminates the graph. The aggregate raw and gzip
|
|
308
|
+
budgets measure Metro JavaScript before Hermes bytecode compilation. Per-family source-graph budgets
|
|
309
|
+
are enforced separately by `pnpm bundle:renderer:check`; neither check predicts the final app bundle,
|
|
310
|
+
component-level tree shaking, or Android device-runtime behavior.
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
import { type ButtonSize as ContractButtonSize, type ButtonTone as ContractButtonTone } from "@hjmds/design-contracts/recipes/base";
|
|
2
|
+
import { type IconButtonShape, type IconButtonSize, type IconButtonTone as ContractIconButtonTone } from "@hjmds/design-contracts/recipes";
|
|
3
|
+
import { type LinkDescriptor, type LinkDestination } from "@hjmds/design-contracts/components/link";
|
|
4
|
+
import { type ReactNode } from "react";
|
|
5
|
+
import { View, type PressableProps, type StyleProp, type TextStyle, type ViewStyle } from "react-native";
|
|
6
|
+
export type ButtonTone = ContractButtonTone;
|
|
7
|
+
export type ButtonSize = ContractButtonSize;
|
|
8
|
+
export type { IconButtonShape, IconButtonSize, } from "@hjmds/design-contracts/recipes";
|
|
9
|
+
export type ButtonProps = Omit<PressableProps, "accessibilityRole" | "accessibilityState" | "children" | "disabled" | "hitSlop" | "style"> & Readonly<{
|
|
10
|
+
/** @deprecated Prefer renderer-neutral `children`. */
|
|
11
|
+
label?: string;
|
|
12
|
+
children?: ReactNode;
|
|
13
|
+
tone?: ButtonTone;
|
|
14
|
+
size?: ButtonSize;
|
|
15
|
+
disabled?: boolean;
|
|
16
|
+
loading?: boolean;
|
|
17
|
+
/** Keep the busy control discoverable by default; opt in only for legacy disabled semantics. */
|
|
18
|
+
disableWhileLoading?: boolean;
|
|
19
|
+
/** Allow the control to grow beyond its recipe height for large or custom content. */
|
|
20
|
+
growWithContent?: boolean;
|
|
21
|
+
loadingLabel?: ReactNode;
|
|
22
|
+
leading?: ReactNode;
|
|
23
|
+
trailing?: ReactNode;
|
|
24
|
+
fullWidth?: boolean;
|
|
25
|
+
hitSlop?: PressableProps["hitSlop"];
|
|
26
|
+
accessibilityState?: PressableProps["accessibilityState"];
|
|
27
|
+
style?: StyleProp<ViewStyle>;
|
|
28
|
+
labelStyle?: StyleProp<TextStyle>;
|
|
29
|
+
renderLoadingIndicator?: (props: Readonly<{
|
|
30
|
+
color: string;
|
|
31
|
+
size: "small";
|
|
32
|
+
}>) => ReactNode;
|
|
33
|
+
}>;
|
|
34
|
+
export declare const Button: import("react").ForwardRefExoticComponent<Omit<PressableProps, "style" | "children" | "hitSlop" | "accessibilityRole" | "accessibilityState" | "disabled"> & Readonly<{
|
|
35
|
+
/** @deprecated Prefer renderer-neutral `children`. */
|
|
36
|
+
label?: string;
|
|
37
|
+
children?: ReactNode;
|
|
38
|
+
tone?: ButtonTone;
|
|
39
|
+
size?: ButtonSize;
|
|
40
|
+
disabled?: boolean;
|
|
41
|
+
loading?: boolean;
|
|
42
|
+
/** Keep the busy control discoverable by default; opt in only for legacy disabled semantics. */
|
|
43
|
+
disableWhileLoading?: boolean;
|
|
44
|
+
/** Allow the control to grow beyond its recipe height for large or custom content. */
|
|
45
|
+
growWithContent?: boolean;
|
|
46
|
+
loadingLabel?: ReactNode;
|
|
47
|
+
leading?: ReactNode;
|
|
48
|
+
trailing?: ReactNode;
|
|
49
|
+
fullWidth?: boolean;
|
|
50
|
+
hitSlop?: PressableProps["hitSlop"];
|
|
51
|
+
accessibilityState?: PressableProps["accessibilityState"];
|
|
52
|
+
style?: StyleProp<ViewStyle>;
|
|
53
|
+
labelStyle?: StyleProp<TextStyle>;
|
|
54
|
+
renderLoadingIndicator?: (props: Readonly<{
|
|
55
|
+
color: string;
|
|
56
|
+
size: "small";
|
|
57
|
+
}>) => ReactNode;
|
|
58
|
+
}> & import("react").RefAttributes<View>>;
|
|
59
|
+
export type IconButtonTone = ContractIconButtonTone;
|
|
60
|
+
/** @deprecated `link` was never an IconButton recipe tone; use `ghost`. */
|
|
61
|
+
export type LegacyNativeIconButtonTone = "link";
|
|
62
|
+
type IconButtonNameProps = Readonly<{
|
|
63
|
+
label: string;
|
|
64
|
+
accessibilityLabel?: never;
|
|
65
|
+
}> | Readonly<{
|
|
66
|
+
label?: never;
|
|
67
|
+
/** @deprecated Prefer the renderer-neutral `label`. */
|
|
68
|
+
accessibilityLabel: string;
|
|
69
|
+
}>;
|
|
70
|
+
type IconButtonContentProps = Readonly<{
|
|
71
|
+
children: ReactNode;
|
|
72
|
+
icon?: never;
|
|
73
|
+
}> | Readonly<{
|
|
74
|
+
children?: never;
|
|
75
|
+
/** @deprecated Prefer the renderer-neutral `children`. */
|
|
76
|
+
icon: ReactNode;
|
|
77
|
+
}>;
|
|
78
|
+
export type IconButtonProps = Omit<PressableProps, "accessibilityLabel" | "accessibilityRole" | "accessibilityState" | "children" | "disabled" | "hitSlop" | "style"> & IconButtonNameProps & IconButtonContentProps & Readonly<{
|
|
79
|
+
tone?: IconButtonTone | LegacyNativeIconButtonTone;
|
|
80
|
+
size?: IconButtonSize;
|
|
81
|
+
shape?: IconButtonShape;
|
|
82
|
+
disabled?: boolean;
|
|
83
|
+
loading?: boolean;
|
|
84
|
+
/** Keep the busy control discoverable by default; opt in only for legacy disabled semantics. */
|
|
85
|
+
disableWhileLoading?: boolean;
|
|
86
|
+
hitSlop?: PressableProps["hitSlop"];
|
|
87
|
+
accessibilityState?: PressableProps["accessibilityState"];
|
|
88
|
+
style?: StyleProp<ViewStyle>;
|
|
89
|
+
renderLoadingIndicator?: (props: Readonly<{
|
|
90
|
+
color: string;
|
|
91
|
+
size: "small";
|
|
92
|
+
}>) => ReactNode;
|
|
93
|
+
}>;
|
|
94
|
+
export declare const IconButton: import("react").ForwardRefExoticComponent<IconButtonProps & import("react").RefAttributes<View>>;
|
|
95
|
+
export type LinkProps = Omit<PressableProps, "accessibilityLabel" | "accessibilityRole" | "children" | "disabled" | "style"> & Readonly<{
|
|
96
|
+
descriptor: LinkDescriptor;
|
|
97
|
+
/** Product router boundary for both internal and external destinations. */
|
|
98
|
+
onNavigate: (destination: LinkDestination) => void | Promise<void>;
|
|
99
|
+
leading?: ReactNode;
|
|
100
|
+
trailing?: ReactNode;
|
|
101
|
+
accessibilityHint?: string;
|
|
102
|
+
style?: StyleProp<ViewStyle>;
|
|
103
|
+
}>;
|
|
104
|
+
export declare function Link({ descriptor, onNavigate, leading, trailing, accessibilityHint, style, ...props }: LinkProps): import("react").JSX.Element;
|
|
105
|
+
export type BottomCTAAction = Readonly<{
|
|
106
|
+
label: string;
|
|
107
|
+
onPress: NonNullable<PressableProps["onPress"]>;
|
|
108
|
+
accessibilityLabel?: string;
|
|
109
|
+
accessibilityHint?: string;
|
|
110
|
+
disabled?: boolean;
|
|
111
|
+
loading?: boolean;
|
|
112
|
+
loadingLabel?: ReactNode;
|
|
113
|
+
size?: ButtonSize;
|
|
114
|
+
tone?: ButtonTone;
|
|
115
|
+
}>;
|
|
116
|
+
export type BottomCTAProps = Readonly<{
|
|
117
|
+
primaryAction: BottomCTAAction;
|
|
118
|
+
/** A second HJM action descriptor or an arbitrary product-owned action node. */
|
|
119
|
+
secondaryAction?: BottomCTAAction | ReactNode;
|
|
120
|
+
description?: string;
|
|
121
|
+
accessibilityLabel?: string;
|
|
122
|
+
safeAreaBottom?: number;
|
|
123
|
+
style?: StyleProp<ViewStyle>;
|
|
124
|
+
testID?: string;
|
|
125
|
+
}>;
|
|
126
|
+
/** Native sticky-action content; products own its screen-edge positioning. */
|
|
127
|
+
export declare function BottomCTA({ primaryAction, secondaryAction, description, accessibilityLabel, safeAreaBottom, style, testID, }: BottomCTAProps): import("react").JSX.Element;
|
|
128
|
+
//# sourceMappingURL=actions.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"actions.d.ts","sourceRoot":"","sources":["../src/actions.tsx"],"names":[],"mappings":"AAEA,OAAO,EAEL,KAAK,UAAU,IAAI,kBAAkB,EACrC,KAAK,UAAU,IAAI,kBAAkB,EACtC,MAAM,sCAAsC,CAAC;AAC9C,OAAO,EAIL,KAAK,eAAe,EACpB,KAAK,cAAc,EACnB,KAAK,cAAc,IAAI,sBAAsB,EAC9C,MAAM,iCAAiC,CAAC;AACzC,OAAO,EAEL,KAAK,cAAc,EACnB,KAAK,eAAe,EACrB,MAAM,yCAAyC,CAAC;AACjD,OAAO,EAAc,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AACnD,OAAO,EAGL,IAAI,EAEJ,KAAK,cAAc,EACnB,KAAK,SAAS,EACd,KAAK,SAAS,EACd,KAAK,SAAS,EACf,MAAM,cAAc,CAAC;AAMtB,MAAM,MAAM,UAAU,GAAG,kBAAkB,CAAC;AAC5C,MAAM,MAAM,UAAU,GAAG,kBAAkB,CAAC;AAC5C,YAAY,EACV,eAAe,EACf,cAAc,GACf,MAAM,iCAAiC,CAAC;AAEzC,MAAM,MAAM,WAAW,GAAG,IAAI,CAC5B,cAAc,EACd,mBAAmB,GAAG,oBAAoB,GAAG,UAAU,GAAG,UAAU,GAAG,SAAS,GAAG,OAAO,CAC3F,GACC,QAAQ,CAAC;IACP,sDAAsD;IACtD,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,IAAI,CAAC,EAAE,UAAU,CAAC;IAClB,IAAI,CAAC,EAAE,UAAU,CAAC;IAClB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,gGAAgG;IAChG,mBAAmB,CAAC,EAAE,OAAO,CAAC;IAC9B,sFAAsF;IACtF,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,YAAY,CAAC,EAAE,SAAS,CAAC;IACzB,OAAO,CAAC,EAAE,SAAS,CAAC;IACpB,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,OAAO,CAAC,EAAE,cAAc,CAAC,SAAS,CAAC,CAAC;IACpC,kBAAkB,CAAC,EAAE,cAAc,CAAC,oBAAoB,CAAC,CAAC;IAC1D,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC;IAC7B,UAAU,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC;IAClC,sBAAsB,CAAC,EAAE,CAAC,KAAK,EAAE,QAAQ,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,OAAO,CAAA;KAAE,CAAC,KAAK,SAAS,CAAC;CAC3F,CAAC,CAAC;AAEL,eAAO,MAAM,MAAM;IAtBf,sDAAsD;YAC9C,MAAM;eACH,SAAS;WACb,UAAU;WACV,UAAU;eACN,OAAO;cACR,OAAO;IACjB,gGAAgG;0BAC1E,OAAO;IAC7B,sFAAsF;sBACpE,OAAO;mBACV,SAAS;cACd,SAAS;eACR,SAAS;gBACR,OAAO;cACT,cAAc,CAAC,SAAS,CAAC;yBACd,cAAc,CAAC,oBAAoB,CAAC;YACjD,SAAS,CAAC,SAAS,CAAC;iBACf,SAAS,CAAC,SAAS,CAAC;6BACR,CAAC,KAAK,EAAE,QAAQ,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,OAAO,CAAA;KAAE,CAAC,KAAK,SAAS;yCAgG3F,CAAC;AAEH,MAAM,MAAM,cAAc,GAAG,sBAAsB,CAAC;AACpD,2EAA2E;AAC3E,MAAM,MAAM,0BAA0B,GAAG,MAAM,CAAC;AAEhD,KAAK,mBAAmB,GACpB,QAAQ,CAAC;IAAE,KAAK,EAAE,MAAM,CAAC;IAAC,kBAAkB,CAAC,EAAE,KAAK,CAAA;CAAE,CAAC,GACvD,QAAQ,CAAC;IACP,KAAK,CAAC,EAAE,KAAK,CAAC;IACd,uDAAuD;IACvD,kBAAkB,EAAE,MAAM,CAAC;CAC5B,CAAC,CAAC;AAEP,KAAK,sBAAsB,GACvB,QAAQ,CAAC;IAAE,QAAQ,EAAE,SAAS,CAAC;IAAC,IAAI,CAAC,EAAE,KAAK,CAAA;CAAE,CAAC,GAC/C,QAAQ,CAAC;IACP,QAAQ,CAAC,EAAE,KAAK,CAAC;IACjB,0DAA0D;IAC1D,IAAI,EAAE,SAAS,CAAC;CACjB,CAAC,CAAC;AAEP,MAAM,MAAM,eAAe,GAAG,IAAI,CAChC,cAAc,EACZ,oBAAoB,GACpB,mBAAmB,GACnB,oBAAoB,GACpB,UAAU,GACV,UAAU,GACV,SAAS,GACT,OAAO,CACV,GACC,mBAAmB,GACnB,sBAAsB,GACtB,QAAQ,CAAC;IACP,IAAI,CAAC,EAAE,cAAc,GAAG,0BAA0B,CAAC;IACnD,IAAI,CAAC,EAAE,cAAc,CAAC;IACtB,KAAK,CAAC,EAAE,eAAe,CAAC;IACxB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,gGAAgG;IAChG,mBAAmB,CAAC,EAAE,OAAO,CAAC;IAC9B,OAAO,CAAC,EAAE,cAAc,CAAC,SAAS,CAAC,CAAC;IACpC,kBAAkB,CAAC,EAAE,cAAc,CAAC,oBAAoB,CAAC,CAAC;IAC1D,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC;IAC7B,sBAAsB,CAAC,EAAE,CAAC,KAAK,EAAE,QAAQ,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,OAAO,CAAA;KAAE,CAAC,KAAK,SAAS,CAAC;CAC3F,CAAC,CAAC;AAEL,eAAO,MAAM,UAAU,kGAsFrB,CAAC;AAEH,MAAM,MAAM,SAAS,GAAG,IAAI,CAC1B,cAAc,EACd,oBAAoB,GAAG,mBAAmB,GAAG,UAAU,GAAG,UAAU,GAAG,OAAO,CAC/E,GACC,QAAQ,CAAC;IACP,UAAU,EAAE,cAAc,CAAC;IAC3B,2EAA2E;IAC3E,UAAU,EAAE,CAAC,WAAW,EAAE,eAAe,KAAK,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACnE,OAAO,CAAC,EAAE,SAAS,CAAC;IACpB,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC;CAC9B,CAAC,CAAC;AAEL,wBAAgB,IAAI,CAAC,EACnB,UAAU,EACV,UAAU,EACV,OAAO,EACP,QAAQ,EACR,iBAAiB,EACjB,KAAK,EACL,GAAG,KAAK,EACT,EAAE,SAAS,+BAiCX;AAED,MAAM,MAAM,eAAe,GAAG,QAAQ,CAAC;IACrC,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,WAAW,CAAC,cAAc,CAAC,SAAS,CAAC,CAAC,CAAC;IAChD,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,YAAY,CAAC,EAAE,SAAS,CAAC;IACzB,IAAI,CAAC,EAAE,UAAU,CAAC;IAClB,IAAI,CAAC,EAAE,UAAU,CAAC;CACnB,CAAC,CAAC;AAEH,MAAM,MAAM,cAAc,GAAG,QAAQ,CAAC;IACpC,aAAa,EAAE,eAAe,CAAC;IAC/B,gFAAgF;IAChF,eAAe,CAAC,EAAE,eAAe,GAAG,SAAS,CAAC;IAC9C,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,KAAK,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC;IAC7B,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB,CAAC,CAAC;AAgCH,8EAA8E;AAC9E,wBAAgB,SAAS,CAAC,EACxB,aAAa,EACb,eAAe,EACf,WAAW,EACX,kBAAkB,EAClB,cAAkB,EAClB,KAAK,EACL,MAAM,GACP,EAAE,cAAc,+BAsDhB"}
|
package/dist/actions.js
ADDED
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { control, glyph, radius, spacing } from "@hjmds/design-contracts/foundations";
|
|
3
|
+
import { buttonRecipe, } from "@hjmds/design-contracts/recipes/base";
|
|
4
|
+
import { bottomCtaRecipe, iconButtonRecipe, resolveIconButtonPresentation, } from "@hjmds/design-contracts/recipes";
|
|
5
|
+
import { resolveLinkDescriptor, } from "@hjmds/design-contracts/components/link";
|
|
6
|
+
import { forwardRef } from "react";
|
|
7
|
+
import { ActivityIndicator, Pressable, View, } from "react-native";
|
|
8
|
+
import { Text } from "./primitives.js";
|
|
9
|
+
import { useHjmNativeTheme } from "./provider.js";
|
|
10
|
+
import { minimumTargetStyle } from "./internal/styles.js";
|
|
11
|
+
export const Button = forwardRef(function Button({ label, children, tone = buttonRecipe.defaults.tone, size = buttonRecipe.defaults.size, disabled = false, loading = false, disableWhileLoading = false, growWithContent = false, loadingLabel, leading, trailing, fullWidth = false, hitSlop, style, labelStyle, renderLoadingIndicator, accessibilityLabel, accessibilityState, onPress, onLongPress, ...props }, ref) {
|
|
12
|
+
const { colors, environment } = useHjmNativeTheme();
|
|
13
|
+
const inactive = disabled || loading;
|
|
14
|
+
const unavailable = disabled || (loading && disableWhileLoading);
|
|
15
|
+
const content = loading && loadingLabel !== undefined
|
|
16
|
+
? loadingLabel
|
|
17
|
+
: children ?? label;
|
|
18
|
+
if (content === undefined || content === null || content === false) {
|
|
19
|
+
throw new TypeError("Button requires children (or the deprecated label prop)");
|
|
20
|
+
}
|
|
21
|
+
const toneContract = buttonRecipe.tones[tone];
|
|
22
|
+
const sizeContract = buttonRecipe.sizes[size];
|
|
23
|
+
const resolveColor = (key) => key === null ? "transparent" : colors[key];
|
|
24
|
+
const contentColor = resolveColor(toneContract.content);
|
|
25
|
+
return (_jsxs(Pressable, { ...props, ref: ref, accessibilityLabel: accessibilityLabel ?? (typeof content === "string" ? content : undefined), accessibilityRole: "button", accessibilityState: { ...accessibilityState, disabled: unavailable, busy: loading }, disabled: unavailable, hitSlop: hitSlop ?? (sizeContract.hitSlop > 0 ? sizeContract.hitSlop : undefined), onPress: loading ? () => undefined : onPress, onLongPress: loading ? () => undefined : onLongPress, style: ({ pressed }) => [
|
|
26
|
+
{
|
|
27
|
+
alignItems: "center",
|
|
28
|
+
backgroundColor: resolveColor(toneContract.background),
|
|
29
|
+
borderColor: resolveColor(toneContract.border),
|
|
30
|
+
borderRadius: radius.md,
|
|
31
|
+
borderWidth: toneContract.border ? 1 : 0,
|
|
32
|
+
direction: environment.direction,
|
|
33
|
+
flexDirection: "row",
|
|
34
|
+
gap: spacing.xs,
|
|
35
|
+
...(growWithContent ? {} : { height: sizeContract.height }),
|
|
36
|
+
justifyContent: "center",
|
|
37
|
+
minHeight: sizeContract.height,
|
|
38
|
+
minWidth: control.minTouchTarget,
|
|
39
|
+
opacity: inactive
|
|
40
|
+
? buttonRecipe.opacity.disabled
|
|
41
|
+
: pressed
|
|
42
|
+
? buttonRecipe.opacity.pressed
|
|
43
|
+
: 1,
|
|
44
|
+
paddingHorizontal: sizeContract.paddingHorizontal,
|
|
45
|
+
...(fullWidth ? { alignSelf: "stretch" } : {}),
|
|
46
|
+
},
|
|
47
|
+
style,
|
|
48
|
+
], children: [loading
|
|
49
|
+
? renderLoadingIndicator?.({ color: contentColor, size: "small" }) ?? (_jsx(ActivityIndicator, { color: contentColor, size: "small" }))
|
|
50
|
+
: leading, typeof content === "string" || typeof content === "number" ? (_jsx(Text, { align: "center", emphasis: "medium", style: [{ color: contentColor }, labelStyle], variant: sizeContract.textVariant, children: content })) : content, trailing] }));
|
|
51
|
+
});
|
|
52
|
+
export const IconButton = forwardRef(function IconButton({ label, accessibilityLabel, children, icon, tone = iconButtonRecipe.defaults.tone, size = iconButtonRecipe.defaults.size, shape = iconButtonRecipe.defaults.shape, disabled = false, loading = false, disableWhileLoading = false, hitSlop, style, renderLoadingIndicator, onPress, onLongPress, accessibilityState, ...props }, ref) {
|
|
53
|
+
const theme = useHjmNativeTheme();
|
|
54
|
+
const resolvedLabel = label ?? accessibilityLabel;
|
|
55
|
+
const resolvedIcon = children ?? icon;
|
|
56
|
+
if (resolvedLabel === undefined || resolvedLabel.trim().length === 0) {
|
|
57
|
+
throw new TypeError("IconButton label must not be empty");
|
|
58
|
+
}
|
|
59
|
+
if (resolvedIcon === undefined || resolvedIcon === null || resolvedIcon === false) {
|
|
60
|
+
throw new TypeError("IconButton requires children (or the deprecated icon prop)");
|
|
61
|
+
}
|
|
62
|
+
const resolvedTone = tone === "link" ? "ghost" : tone;
|
|
63
|
+
const presentation = resolveIconButtonPresentation(resolvedTone, theme.palette);
|
|
64
|
+
const sizeContract = iconButtonRecipe.sizes[size];
|
|
65
|
+
const glyphSize = glyph[sizeContract.glyph];
|
|
66
|
+
const unavailable = disabled || (loading && disableWhileLoading);
|
|
67
|
+
return (_jsx(Pressable, { ...props, ref: ref, accessibilityLabel: resolvedLabel, accessibilityRole: "button", accessibilityState: { ...accessibilityState, disabled: unavailable, busy: loading }, disabled: unavailable, hitSlop: hitSlop ?? (sizeContract.hitSlop > 0 ? sizeContract.hitSlop : undefined), onPress: loading ? () => undefined : onPress, onLongPress: loading ? () => undefined : onLongPress, style: ({ pressed }) => [
|
|
68
|
+
{
|
|
69
|
+
alignItems: "center",
|
|
70
|
+
backgroundColor: presentation.background ?? "transparent",
|
|
71
|
+
borderColor: presentation.border ?? "transparent",
|
|
72
|
+
borderRadius: radius[iconButtonRecipe.shapes[shape]],
|
|
73
|
+
borderWidth: 1,
|
|
74
|
+
height: sizeContract.diameter,
|
|
75
|
+
justifyContent: "center",
|
|
76
|
+
minHeight: sizeContract.diameter,
|
|
77
|
+
minWidth: sizeContract.diameter,
|
|
78
|
+
opacity: disabled
|
|
79
|
+
? iconButtonRecipe.states.disabledOpacity
|
|
80
|
+
: loading
|
|
81
|
+
? 1
|
|
82
|
+
: pressed
|
|
83
|
+
? iconButtonRecipe.states.pressedOpacity
|
|
84
|
+
: 1,
|
|
85
|
+
width: sizeContract.diameter,
|
|
86
|
+
},
|
|
87
|
+
style,
|
|
88
|
+
], children: loading ? (renderLoadingIndicator?.({ color: presentation.content, size: "small" }) ?? (_jsx(ActivityIndicator, { color: presentation.content, size: "small" }))) : (_jsx(View, { accessible: false, style: {
|
|
89
|
+
alignItems: "center",
|
|
90
|
+
height: glyphSize,
|
|
91
|
+
justifyContent: "center",
|
|
92
|
+
width: glyphSize,
|
|
93
|
+
}, children: resolvedIcon })) }));
|
|
94
|
+
});
|
|
95
|
+
export function Link({ descriptor, onNavigate, leading, trailing, accessibilityHint, style, ...props }) {
|
|
96
|
+
const { colors, environment } = useHjmNativeTheme();
|
|
97
|
+
const resolved = resolveLinkDescriptor(descriptor);
|
|
98
|
+
return (_jsxs(Pressable, { ...props, accessibilityHint: accessibilityHint, accessibilityLabel: resolved.resolvedAccessibilityLabel, accessibilityRole: "link", onPress: () => void onNavigate(resolved.destination), style: ({ pressed }) => [
|
|
99
|
+
minimumTargetStyle,
|
|
100
|
+
{
|
|
101
|
+
alignItems: "center",
|
|
102
|
+
alignSelf: "flex-start",
|
|
103
|
+
direction: environment.direction,
|
|
104
|
+
flexDirection: "row",
|
|
105
|
+
gap: spacing.xs,
|
|
106
|
+
opacity: pressed ? 0.72 : 1,
|
|
107
|
+
},
|
|
108
|
+
style,
|
|
109
|
+
], children: [leading ? _jsx(View, { accessible: false, children: leading }) : null, _jsx(Text, { style: { color: colors.contentBrand, textDecorationLine: "underline" }, variant: "bodyLarge", children: resolved.label }), trailing ? _jsx(View, { accessible: false, children: trailing }) : null] }));
|
|
110
|
+
}
|
|
111
|
+
function BottomCTAButton({ action, fallbackTone, }) {
|
|
112
|
+
return (_jsx(Button, { ...(action.accessibilityLabel === undefined ? {} : { accessibilityLabel: action.accessibilityLabel }), ...(action.accessibilityHint === undefined ? {} : { accessibilityHint: action.accessibilityHint }), ...(action.disabled === undefined ? {} : { disabled: action.disabled }), ...(action.loading === undefined ? {} : { loading: action.loading }), ...(action.loadingLabel === undefined ? {} : { loadingLabel: action.loadingLabel }), fullWidth: true, onPress: action.onPress, ...(action.size === undefined ? {} : { size: action.size }), tone: action.tone ?? fallbackTone, children: action.label }));
|
|
113
|
+
}
|
|
114
|
+
function isBottomCTAAction(value) {
|
|
115
|
+
return typeof value === "object"
|
|
116
|
+
&& value !== null
|
|
117
|
+
&& "label" in value
|
|
118
|
+
&& typeof value.label === "string"
|
|
119
|
+
&& "onPress" in value
|
|
120
|
+
&& typeof value.onPress === "function";
|
|
121
|
+
}
|
|
122
|
+
/** Native sticky-action content; products own its screen-edge positioning. */
|
|
123
|
+
export function BottomCTA({ primaryAction, secondaryAction, description, accessibilityLabel, safeAreaBottom = 0, style, testID, }) {
|
|
124
|
+
if (!Number.isFinite(safeAreaBottom) || safeAreaBottom < 0) {
|
|
125
|
+
throw new RangeError("BottomCTA safeAreaBottom must be non-negative");
|
|
126
|
+
}
|
|
127
|
+
const { colors, environment } = useHjmNativeTheme();
|
|
128
|
+
const stackActions = environment.textScale >= 1.6;
|
|
129
|
+
const renderedSecondary = secondaryAction === undefined || secondaryAction === null
|
|
130
|
+
? null
|
|
131
|
+
: isBottomCTAAction(secondaryAction)
|
|
132
|
+
? _jsx(BottomCTAButton, { action: secondaryAction, fallbackTone: "secondary" })
|
|
133
|
+
: secondaryAction;
|
|
134
|
+
return (_jsxs(View, { accessibilityLabel: accessibilityLabel, accessibilityRole: "toolbar", testID: testID, style: [
|
|
135
|
+
{
|
|
136
|
+
backgroundColor: colors.surface,
|
|
137
|
+
borderColor: colors.border,
|
|
138
|
+
borderTopWidth: bottomCtaRecipe.borderWidth,
|
|
139
|
+
elevation: bottomCtaRecipe.shadow.elevation,
|
|
140
|
+
gap: bottomCtaRecipe.gap,
|
|
141
|
+
minHeight: bottomCtaRecipe.minHeight + safeAreaBottom,
|
|
142
|
+
paddingBottom: Math.max(safeAreaBottom, bottomCtaRecipe.paddingBottom),
|
|
143
|
+
paddingHorizontal: bottomCtaRecipe.paddingHorizontal,
|
|
144
|
+
paddingTop: bottomCtaRecipe.paddingTop,
|
|
145
|
+
shadowColor: bottomCtaRecipe.shadow.color,
|
|
146
|
+
shadowOffset: { width: 0, height: bottomCtaRecipe.shadow.offsetY },
|
|
147
|
+
shadowOpacity: bottomCtaRecipe.shadow.opacity,
|
|
148
|
+
shadowRadius: bottomCtaRecipe.shadow.radius,
|
|
149
|
+
},
|
|
150
|
+
style,
|
|
151
|
+
], children: [description ? _jsx(Text, { tone: "muted", variant: "caption", children: description }) : null, _jsxs(View, { style: {
|
|
152
|
+
direction: environment.direction,
|
|
153
|
+
flexDirection: stackActions ? "column-reverse" : "row",
|
|
154
|
+
gap: bottomCtaRecipe.gap,
|
|
155
|
+
}, children: [renderedSecondary !== null ? (_jsx(View, { style: { flex: stackActions ? undefined : 1 }, children: renderedSecondary })) : null, _jsx(View, { style: { flex: stackActions ? undefined : 1 }, children: _jsx(BottomCTAButton, { action: primaryAction, fallbackTone: "primary" }) })] })] }));
|
|
156
|
+
}
|
|
157
|
+
//# sourceMappingURL=actions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"actions.js","sourceRoot":"","sources":["../src/actions.tsx"],"names":[],"mappings":"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"}
|