@dynamicnorway/react 1.0.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/README.md ADDED
@@ -0,0 +1,50 @@
1
+ # @dynamicnorway/react
2
+
3
+ React component library for Dynamic.
4
+
5
+ ## Requirements
6
+
7
+ - React 18 or 19
8
+ - [Tailwind CSS](https://tailwindcss.com/) v4
9
+ - [`@dynamicnorway/tokens`](../tokens) for design tokens
10
+
11
+ ## Install
12
+
13
+ ```bash
14
+ pnpm add @dynamicnorway/react @dynamicnorway/tokens tailwindcss react react-dom
15
+ ```
16
+
17
+ ## Setup
18
+
19
+ Import tokens in your global CSS:
20
+
21
+ ```css
22
+ @import "@dynamicnorway/tokens";
23
+ ```
24
+
25
+ For Next.js, add to `transpilePackages`:
26
+
27
+ ```js
28
+ transpilePackages: ["@dynamicnorway/react"],
29
+ ```
30
+
31
+ ## Usage
32
+
33
+ ```tsx
34
+ import { Button, Card, Dialog } from "@dynamicnorway/react";
35
+ ```
36
+
37
+ ## i18n
38
+
39
+ Components that previously used app i18n accept labels via props (`SearchBar`, `SearchInput`, `Breadcrumbs`, `FormSlideOver`).
40
+
41
+ ## Development
42
+
43
+ From the monorepo root:
44
+
45
+ ```bash
46
+ pnpm install
47
+ pnpm dev
48
+ ```
49
+
50
+ Open [http://localhost:6006](http://localhost:6006) to browse components in Storybook. Run tests with `pnpm --filter @dynamicnorway/react test`.
@@ -0,0 +1,432 @@
1
+ import { ClassValue } from 'clsx';
2
+ import * as React from 'react';
3
+ import React__default from 'react';
4
+ import * as DialogPrimitive from '@radix-ui/react-dialog';
5
+ import * as AvatarPrimitive from '@radix-ui/react-avatar';
6
+ import * as DropdownMenuPrimitive from '@radix-ui/react-dropdown-menu';
7
+
8
+ declare function cn(...inputs: ClassValue[]): string;
9
+
10
+ type ButtonVariant = "primary" | "secondary" | "outline" | "danger" | "destructive" | "ghost";
11
+ type ButtonSize = "sm" | "md" | "lg";
12
+ interface ButtonProps extends React__default.ButtonHTMLAttributes<HTMLButtonElement> {
13
+ variant?: ButtonVariant;
14
+ size?: ButtonSize;
15
+ loading?: boolean;
16
+ fullWidth?: boolean;
17
+ ref?: React__default.Ref<HTMLButtonElement>;
18
+ }
19
+ declare const Button: React__default.FC<ButtonProps>;
20
+
21
+ interface FormFieldProps {
22
+ label?: string;
23
+ required?: boolean;
24
+ error?: string;
25
+ helperText?: string;
26
+ className?: string;
27
+ children: React__default.ReactNode;
28
+ htmlFor?: string;
29
+ }
30
+ declare function FormField({ label, required, error, helperText, className, children, htmlFor, }: FormFieldProps): React__default.JSX.Element;
31
+
32
+ interface InputProps extends React__default.InputHTMLAttributes<HTMLInputElement> {
33
+ hasError?: boolean;
34
+ ref?: React__default.Ref<HTMLInputElement>;
35
+ }
36
+ declare const Input: React__default.FC<InputProps>;
37
+
38
+ interface TextareaProps extends React__default.TextareaHTMLAttributes<HTMLTextAreaElement> {
39
+ hasError?: boolean;
40
+ autoResize?: boolean;
41
+ ref?: React__default.Ref<HTMLTextAreaElement>;
42
+ }
43
+ declare const Textarea: React__default.FC<TextareaProps>;
44
+
45
+ interface SelectProps extends React__default.SelectHTMLAttributes<HTMLSelectElement> {
46
+ hasError?: boolean;
47
+ placeholder?: string;
48
+ options?: Array<{
49
+ value: string;
50
+ label: string;
51
+ disabled?: boolean;
52
+ }>;
53
+ ref?: React__default.Ref<HTMLSelectElement>;
54
+ }
55
+ declare const Select: React__default.FC<SelectProps>;
56
+
57
+ interface CheckboxProps extends Omit<React__default.InputHTMLAttributes<HTMLInputElement>, "type"> {
58
+ label?: string;
59
+ ref?: React__default.Ref<HTMLInputElement>;
60
+ }
61
+ declare const Checkbox: React__default.FC<CheckboxProps>;
62
+
63
+ declare const Dialog: React.FC<DialogPrimitive.DialogProps>;
64
+ declare const DialogTrigger: React.ForwardRefExoticComponent<DialogPrimitive.DialogTriggerProps & React.RefAttributes<HTMLButtonElement>>;
65
+ declare const DialogPortal: React.FC<DialogPrimitive.DialogPortalProps>;
66
+ declare const DialogClose: React.ForwardRefExoticComponent<DialogPrimitive.DialogCloseProps & React.RefAttributes<HTMLButtonElement>>;
67
+ interface DialogOverlayProps extends React.ComponentPropsWithoutRef<typeof DialogPrimitive.Overlay> {
68
+ ref?: React.Ref<React.ElementRef<typeof DialogPrimitive.Overlay>>;
69
+ }
70
+ declare const DialogOverlay: React.FC<DialogOverlayProps>;
71
+ interface DialogContentProps extends React.ComponentPropsWithoutRef<typeof DialogPrimitive.Content> {
72
+ ref?: React.Ref<React.ElementRef<typeof DialogPrimitive.Content>>;
73
+ closeLabel?: string;
74
+ }
75
+ declare const DialogContent: React.FC<DialogContentProps>;
76
+ declare const DialogHeader: {
77
+ ({ className, ...props }: React.HTMLAttributes<HTMLDivElement>): React.JSX.Element;
78
+ displayName: string;
79
+ };
80
+ declare const DialogFooter: {
81
+ ({ className, ...props }: React.HTMLAttributes<HTMLDivElement>): React.JSX.Element;
82
+ displayName: string;
83
+ };
84
+ interface DialogTitleProps extends React.ComponentPropsWithoutRef<typeof DialogPrimitive.Title> {
85
+ ref?: React.Ref<React.ElementRef<typeof DialogPrimitive.Title>>;
86
+ }
87
+ declare const DialogTitle: React.FC<DialogTitleProps>;
88
+ interface DialogDescriptionProps extends React.ComponentPropsWithoutRef<typeof DialogPrimitive.Description> {
89
+ ref?: React.Ref<React.ElementRef<typeof DialogPrimitive.Description>>;
90
+ }
91
+ declare const DialogDescription: React.FC<DialogDescriptionProps>;
92
+ interface ConfirmDialogProps {
93
+ open: boolean;
94
+ onClose: () => void;
95
+ onConfirm: () => void;
96
+ title: string;
97
+ message: string;
98
+ confirmText?: string;
99
+ cancelText?: string;
100
+ variant?: "danger" | "default";
101
+ loading?: boolean;
102
+ loadingText?: string;
103
+ }
104
+ declare const ConfirmDialog: React.FC<ConfirmDialogProps>;
105
+
106
+ interface CardProps {
107
+ children: React__default.ReactNode;
108
+ variant?: "default" | "interactive";
109
+ className?: string;
110
+ onClick?: () => void;
111
+ }
112
+ declare const Card: React__default.ForwardRefExoticComponent<CardProps & React__default.RefAttributes<HTMLButtonElement | HTMLDivElement>>;
113
+ interface CardHeaderProps {
114
+ children: React__default.ReactNode;
115
+ className?: string;
116
+ }
117
+ declare const CardHeader: React__default.FC<CardHeaderProps>;
118
+ interface CardBodyProps {
119
+ children: React__default.ReactNode;
120
+ className?: string;
121
+ }
122
+ declare const CardBody: React__default.FC<CardBodyProps>;
123
+ interface CardFooterProps {
124
+ children: React__default.ReactNode;
125
+ className?: string;
126
+ }
127
+ declare const CardFooter: React__default.FC<CardFooterProps>;
128
+
129
+ interface LoadingSpinnerProps {
130
+ size?: "sm" | "md" | "lg";
131
+ className?: string;
132
+ }
133
+ declare const LoadingSpinner: React__default.FC<LoadingSpinnerProps>;
134
+ declare const LoadingScreen: React__default.FC<{
135
+ message?: string;
136
+ }>;
137
+
138
+ interface BadgeProps {
139
+ children: React__default.ReactNode;
140
+ variant?: "default" | "success" | "warning" | "error" | "info";
141
+ size?: "sm" | "md";
142
+ className?: string;
143
+ }
144
+ declare const Badge: React__default.FC<BadgeProps>;
145
+
146
+ interface EmptyStateProps {
147
+ icon?: React__default.ReactNode;
148
+ title: string;
149
+ description?: string;
150
+ action?: {
151
+ label: string;
152
+ onClick: () => void;
153
+ };
154
+ className?: string;
155
+ }
156
+ declare const EmptyState: React__default.FC<EmptyStateProps>;
157
+
158
+ interface SlideOverProps {
159
+ open: boolean;
160
+ onClose: () => void;
161
+ title: string;
162
+ description?: string;
163
+ children: React__default.ReactNode;
164
+ footer?: React__default.ReactNode;
165
+ size?: "sm" | "md" | "lg" | "xl" | "full";
166
+ closeLabel?: string;
167
+ }
168
+ declare function SlideOver({ open, onClose, title, description, children, footer, size, closeLabel, }: SlideOverProps): React__default.JSX.Element;
169
+ interface FormSlideOverProps extends Omit<SlideOverProps, "footer" | "children"> {
170
+ children: React__default.ReactNode;
171
+ submitText?: string;
172
+ cancelText?: string;
173
+ deleteText?: string;
174
+ savingText?: string;
175
+ deletingText?: string;
176
+ unsavedChangesConfirm?: string;
177
+ onSubmit: () => void;
178
+ onDelete?: () => void;
179
+ isSubmitting?: boolean;
180
+ isDeleting?: boolean;
181
+ hasChanges?: boolean;
182
+ }
183
+ declare function FormSlideOver({ open, onClose, title, description, children, submitText, cancelText, deleteText, savingText, deletingText, unsavedChangesConfirm, onSubmit, onDelete, isSubmitting, isDeleting, hasChanges, size, closeLabel, }: FormSlideOverProps): React__default.JSX.Element;
184
+
185
+ interface EntityFormProps {
186
+ isEdit?: boolean;
187
+ isSaving?: boolean;
188
+ error?: string;
189
+ onSave: () => void;
190
+ onCancel: () => void;
191
+ onDelete?: () => void;
192
+ saveLabel?: string;
193
+ cancelLabel?: string;
194
+ deleteLabel?: string;
195
+ savingLabel?: string;
196
+ deleteConfirmMessage?: string;
197
+ showDelete?: boolean;
198
+ autoFocus?: boolean;
199
+ className?: string;
200
+ children: React__default.ReactNode;
201
+ }
202
+ declare const EntityForm: React__default.FC<EntityFormProps>;
203
+
204
+ interface SearchInputLabels {
205
+ placeholder?: string;
206
+ searchHotkeyHint?: string;
207
+ openSearch?: string;
208
+ search?: string;
209
+ clearSearch?: string;
210
+ }
211
+ interface SearchInputProps {
212
+ value: string;
213
+ onChange: (value: string) => void;
214
+ placeholder?: string;
215
+ debounceMs?: number;
216
+ expandable?: boolean;
217
+ className?: string;
218
+ autoFocus?: boolean;
219
+ size?: "sm" | "md" | "lg";
220
+ labels?: SearchInputLabels;
221
+ }
222
+ declare function SearchInput({ value, onChange, placeholder, debounceMs, expandable, className, autoFocus, size, labels, }: SearchInputProps): React__default.JSX.Element;
223
+
224
+ interface SearchBarProps {
225
+ value: string;
226
+ onChange: (value: string) => void;
227
+ onClear?: () => void;
228
+ placeholder?: string;
229
+ autoFocus?: boolean;
230
+ className?: string;
231
+ showShortcutHint?: boolean;
232
+ clearSearchLabel?: string;
233
+ }
234
+ declare const SearchBar: React__default.FC<SearchBarProps>;
235
+
236
+ interface BreadcrumbItem {
237
+ label: string;
238
+ href?: string;
239
+ }
240
+ interface BreadcrumbsProps {
241
+ items: BreadcrumbItem[];
242
+ className?: string;
243
+ ariaLabel?: string;
244
+ renderLink?: (props: {
245
+ href: string;
246
+ children: React__default.ReactNode;
247
+ className: string;
248
+ }) => React__default.ReactNode;
249
+ }
250
+ declare const Breadcrumbs: React__default.FC<BreadcrumbsProps>;
251
+
252
+ interface TableProps {
253
+ children: React__default.ReactNode;
254
+ className?: string;
255
+ }
256
+ declare const Table: React__default.FC<TableProps>;
257
+ interface TableHeaderProps {
258
+ children: React__default.ReactNode;
259
+ className?: string;
260
+ }
261
+ declare const TableHeader: React__default.FC<TableHeaderProps>;
262
+ interface TableBodyProps {
263
+ children: React__default.ReactNode;
264
+ className?: string;
265
+ }
266
+ declare const TableBody: React__default.FC<TableBodyProps>;
267
+ interface TableRowProps extends React__default.HTMLAttributes<HTMLTableRowElement> {
268
+ children: React__default.ReactNode;
269
+ className?: string;
270
+ onClick?: () => void;
271
+ }
272
+ declare const TableRow: React__default.FC<TableRowProps>;
273
+ interface TableHeadProps {
274
+ children: React__default.ReactNode;
275
+ className?: string;
276
+ }
277
+ declare const TableHead: React__default.FC<TableHeadProps>;
278
+ interface TableCellProps {
279
+ children: React__default.ReactNode;
280
+ className?: string;
281
+ onClick?: () => void;
282
+ colSpan?: number;
283
+ }
284
+ declare const TableCell: React__default.FC<TableCellProps>;
285
+
286
+ interface TabsProps {
287
+ children: React__default.ReactNode;
288
+ defaultValue?: string;
289
+ value?: string;
290
+ onValueChange?: (value: string) => void;
291
+ className?: string;
292
+ }
293
+ interface TabsListProps {
294
+ children: React__default.ReactNode;
295
+ className?: string;
296
+ }
297
+ interface TabsTriggerProps {
298
+ value: string;
299
+ children: React__default.ReactNode;
300
+ className?: string;
301
+ }
302
+ interface TabsContentProps {
303
+ value: string;
304
+ children: React__default.ReactNode;
305
+ className?: string;
306
+ }
307
+ declare const Tabs: React__default.FC<TabsProps>;
308
+ declare const TabsList: React__default.FC<TabsListProps>;
309
+ declare const TabsTrigger: React__default.FC<TabsTriggerProps>;
310
+ declare const TabsContent: React__default.FC<TabsContentProps>;
311
+
312
+ interface AvatarProps extends React.ComponentPropsWithoutRef<typeof AvatarPrimitive.Root> {
313
+ ref?: React.Ref<React.ElementRef<typeof AvatarPrimitive.Root>>;
314
+ }
315
+ declare const Avatar: React.FC<AvatarProps>;
316
+ interface AvatarImageProps extends React.ComponentPropsWithoutRef<typeof AvatarPrimitive.Image> {
317
+ ref?: React.Ref<React.ElementRef<typeof AvatarPrimitive.Image>>;
318
+ }
319
+ declare const AvatarImage: React.FC<AvatarImageProps>;
320
+ interface AvatarFallbackProps extends React.ComponentPropsWithoutRef<typeof AvatarPrimitive.Fallback> {
321
+ ref?: React.Ref<React.ElementRef<typeof AvatarPrimitive.Fallback>>;
322
+ }
323
+ declare const AvatarFallback: React.FC<AvatarFallbackProps>;
324
+
325
+ declare const DropdownMenu: React.FC<DropdownMenuPrimitive.DropdownMenuProps>;
326
+ declare const DropdownMenuTrigger: React.ForwardRefExoticComponent<DropdownMenuPrimitive.DropdownMenuTriggerProps & React.RefAttributes<HTMLButtonElement>>;
327
+ declare const DropdownMenuGroup: React.ForwardRefExoticComponent<DropdownMenuPrimitive.DropdownMenuGroupProps & React.RefAttributes<HTMLDivElement>>;
328
+ declare const DropdownMenuPortal: React.FC<DropdownMenuPrimitive.DropdownMenuPortalProps>;
329
+ declare const DropdownMenuSub: React.FC<DropdownMenuPrimitive.DropdownMenuSubProps>;
330
+ declare const DropdownMenuRadioGroup: React.ForwardRefExoticComponent<DropdownMenuPrimitive.DropdownMenuRadioGroupProps & React.RefAttributes<HTMLDivElement>>;
331
+ interface DropdownMenuSubTriggerProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.SubTrigger> {
332
+ inset?: boolean;
333
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.SubTrigger>>;
334
+ }
335
+ declare const DropdownMenuSubTrigger: React.FC<DropdownMenuSubTriggerProps>;
336
+ interface DropdownMenuSubContentProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.SubContent> {
337
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.SubContent>>;
338
+ }
339
+ declare const DropdownMenuSubContent: React.FC<DropdownMenuSubContentProps>;
340
+ interface DropdownMenuContentProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Content> {
341
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.Content>>;
342
+ }
343
+ declare const DropdownMenuContent: React.FC<DropdownMenuContentProps>;
344
+ interface DropdownMenuItemProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Item> {
345
+ inset?: boolean;
346
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.Item>>;
347
+ }
348
+ declare const DropdownMenuItem: React.FC<DropdownMenuItemProps>;
349
+ interface DropdownMenuCheckboxItemProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.CheckboxItem> {
350
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.CheckboxItem>>;
351
+ }
352
+ declare const DropdownMenuCheckboxItem: React.FC<DropdownMenuCheckboxItemProps>;
353
+ interface DropdownMenuRadioItemProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.RadioItem> {
354
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.RadioItem>>;
355
+ }
356
+ declare const DropdownMenuRadioItem: React.FC<DropdownMenuRadioItemProps>;
357
+ interface DropdownMenuLabelProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Label> {
358
+ inset?: boolean;
359
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.Label>>;
360
+ }
361
+ declare const DropdownMenuLabel: React.FC<DropdownMenuLabelProps>;
362
+ interface DropdownMenuSeparatorProps extends React.ComponentPropsWithoutRef<typeof DropdownMenuPrimitive.Separator> {
363
+ ref?: React.Ref<React.ElementRef<typeof DropdownMenuPrimitive.Separator>>;
364
+ }
365
+ declare const DropdownMenuSeparator: React.FC<DropdownMenuSeparatorProps>;
366
+ declare const DropdownMenuShortcut: {
367
+ ({ className, ...props }: React.HTMLAttributes<HTMLSpanElement>): React.JSX.Element;
368
+ displayName: string;
369
+ };
370
+
371
+ interface CollapsibleProps {
372
+ /** Whether the section is initially open */
373
+ defaultOpen?: boolean;
374
+ /** Controlled open state */
375
+ open?: boolean;
376
+ /** Callback when open state changes */
377
+ onOpenChange?: (open: boolean) => void;
378
+ /** Trigger element (clickable header) */
379
+ trigger: React__default.ReactNode;
380
+ /** Content to show when expanded */
381
+ children: React__default.ReactNode;
382
+ /** Additional class names */
383
+ className?: string;
384
+ /** Whether to persist state to localStorage */
385
+ storageKey?: string;
386
+ /** Disable the collapsible functionality */
387
+ disabled?: boolean;
388
+ }
389
+ declare function Collapsible({ defaultOpen, open: controlledOpen, onOpenChange, trigger, children, className, storageKey, disabled, }: CollapsibleProps): React__default.JSX.Element;
390
+ interface CollapsibleTriggerProps {
391
+ /** Title text */
392
+ title: string;
393
+ /** Subtitle/description text */
394
+ subtitle?: string;
395
+ /** Whether the section is open */
396
+ isOpen: boolean;
397
+ /** Additional class names */
398
+ className?: string;
399
+ /** Icon to show (optional, defaults to chevron) */
400
+ icon?: React__default.ReactNode;
401
+ }
402
+ declare function CollapsibleTrigger({ title, subtitle, isOpen, className, icon, }: CollapsibleTriggerProps): React__default.JSX.Element;
403
+ interface DismissibleBannerProps {
404
+ /** Unique key for localStorage persistence */
405
+ storageKey: string;
406
+ /** Banner content */
407
+ children: React__default.ReactNode;
408
+ /** Dismiss button text */
409
+ dismissText?: string;
410
+ /** Callback when dismissed */
411
+ onDismiss?: () => void;
412
+ /** Additional class names */
413
+ className?: string;
414
+ /** Variant for styling */
415
+ variant?: "info" | "success" | "warning" | "neutral" | "hero";
416
+ }
417
+ declare function DismissibleBanner({ storageKey, children, dismissText, onDismiss, className, variant, }: DismissibleBannerProps): React__default.JSX.Element | null;
418
+ interface UseCollapsibleOptions {
419
+ /** Initial open state */
420
+ defaultOpen?: boolean;
421
+ /** Storage key for persistence */
422
+ storageKey?: string;
423
+ }
424
+ declare function useCollapsible(options?: UseCollapsibleOptions): {
425
+ isOpen: boolean;
426
+ toggle: () => void;
427
+ open: () => void;
428
+ close: () => void;
429
+ setIsOpen: React__default.Dispatch<React__default.SetStateAction<boolean>>;
430
+ };
431
+
432
+ export { Avatar, AvatarFallback, AvatarImage, Badge, type BadgeProps, type BreadcrumbItem, Breadcrumbs, type BreadcrumbsProps, Button, type ButtonProps, type ButtonSize, type ButtonVariant, Card, CardBody, type CardBodyProps, CardFooter, type CardFooterProps, CardHeader, type CardHeaderProps, type CardProps, Checkbox, type CheckboxProps, Collapsible, CollapsibleTrigger, ConfirmDialog, type ConfirmDialogProps, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, DismissibleBanner, DropdownMenu, DropdownMenuCheckboxItem, DropdownMenuContent, DropdownMenuGroup, DropdownMenuItem, DropdownMenuLabel, DropdownMenuPortal, DropdownMenuRadioGroup, DropdownMenuRadioItem, DropdownMenuSeparator, DropdownMenuShortcut, DropdownMenuSub, DropdownMenuSubContent, DropdownMenuSubTrigger, DropdownMenuTrigger, EmptyState, type EmptyStateProps, EntityForm, type EntityFormProps, FormField, FormSlideOver, type FormSlideOverProps, Input, type InputProps, LoadingScreen, LoadingSpinner, type LoadingSpinnerProps, SearchBar, type SearchBarProps, SearchInput, type SearchInputLabels, type SearchInputProps, Select, type SelectProps, SlideOver, type SlideOverProps, Table, TableBody, type TableBodyProps, TableCell, type TableCellProps, TableHead, type TableHeadProps, TableHeader, type TableHeaderProps, type TableProps, TableRow, type TableRowProps, Tabs, TabsContent, type TabsContentProps, TabsList, type TabsListProps, type TabsProps, TabsTrigger, type TabsTriggerProps, Textarea, type TextareaProps, cn, useCollapsible };