@delightui/components 0.1.113 → 0.1.114
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/dist/cjs/components/organisms/Form/AutosaveFormExample.d.ts +2 -0
- package/dist/cjs/components/organisms/Form/Form.types.d.ts +2 -0
- package/dist/cjs/library.js +2 -2
- package/dist/cjs/library.js.map +1 -1
- package/dist/esm/components/organisms/Form/AutosaveFormExample.d.ts +2 -0
- package/dist/esm/components/organisms/Form/Form.types.d.ts +2 -0
- package/dist/esm/library.js +3 -3
- package/dist/esm/library.js.map +1 -1
- package/dist/index.d.ts +2 -0
- package/docs/components/molecules/NavLink.md +155 -1
- package/docs/components/molecules/Search.md +8 -8
- package/docs/components/organisms/Form.md +127 -0
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -26,7 +26,7 @@ A navigation link component that handles both internal routing and external link
|
|
|
26
26
|
| `leadingIcon` | `ReactNode` | - | No | Icon displayed before the link text |
|
|
27
27
|
| `trailingIcon` | `ReactNode` | - | No | Icon displayed after the link text |
|
|
28
28
|
| `component-variant` | `string` | - | No | Override styling variant |
|
|
29
|
-
| `children` | `ReactNode` | - | Yes | Link content (text, icons, etc.) |
|
|
29
|
+
| `children` | `ReactNode` | - | Yes | Link content (text, icons, components like cards, etc.) |
|
|
30
30
|
|
|
31
31
|
Plus all React Router Link props and Button styling props.
|
|
32
32
|
|
|
@@ -496,4 +496,158 @@ function LoadingStateLinksExample() {
|
|
|
496
496
|
</div>
|
|
497
497
|
);
|
|
498
498
|
}
|
|
499
|
+
```
|
|
500
|
+
|
|
501
|
+
### Wrapping Complex Components (Cards)
|
|
502
|
+
```tsx
|
|
503
|
+
function CardNavigationExample() {
|
|
504
|
+
const dashboardCards = [
|
|
505
|
+
{
|
|
506
|
+
id: 'analytics',
|
|
507
|
+
title: 'Analytics Dashboard',
|
|
508
|
+
description: 'View detailed analytics and metrics',
|
|
509
|
+
icon: 'BarChart',
|
|
510
|
+
path: '/dashboard/analytics'
|
|
511
|
+
},
|
|
512
|
+
{
|
|
513
|
+
id: 'users',
|
|
514
|
+
title: 'User Management',
|
|
515
|
+
description: 'Manage users and permissions',
|
|
516
|
+
icon: 'People',
|
|
517
|
+
path: '/dashboard/users'
|
|
518
|
+
},
|
|
519
|
+
{
|
|
520
|
+
id: 'settings',
|
|
521
|
+
title: 'System Settings',
|
|
522
|
+
description: 'Configure application settings',
|
|
523
|
+
icon: 'Settings',
|
|
524
|
+
path: '/dashboard/settings'
|
|
525
|
+
}
|
|
526
|
+
];
|
|
527
|
+
|
|
528
|
+
return (
|
|
529
|
+
<div className="card-navigation-grid">
|
|
530
|
+
{dashboardCards.map(card => (
|
|
531
|
+
<NavLink key={card.id} to={card.path} className="card-nav-link">
|
|
532
|
+
<Card className="dashboard-card">
|
|
533
|
+
<CardHeader>
|
|
534
|
+
<Icon icon={card.icon} size="Large" />
|
|
535
|
+
<Text type="Heading4">{card.title}</Text>
|
|
536
|
+
</CardHeader>
|
|
537
|
+
<CardContent>
|
|
538
|
+
<Text type="Body">{card.description}</Text>
|
|
539
|
+
</CardContent>
|
|
540
|
+
</Card>
|
|
541
|
+
</NavLink>
|
|
542
|
+
))}
|
|
543
|
+
</div>
|
|
544
|
+
);
|
|
545
|
+
}
|
|
546
|
+
```
|
|
547
|
+
|
|
548
|
+
### Wrapping Complex Components (List Items)
|
|
549
|
+
```tsx
|
|
550
|
+
function NavigableListExample() {
|
|
551
|
+
const projectItems = [
|
|
552
|
+
{
|
|
553
|
+
id: 1,
|
|
554
|
+
name: 'E-commerce Platform',
|
|
555
|
+
status: 'Active',
|
|
556
|
+
lastUpdated: '2024-01-15',
|
|
557
|
+
path: '/projects/ecommerce'
|
|
558
|
+
},
|
|
559
|
+
{
|
|
560
|
+
id: 2,
|
|
561
|
+
name: 'Mobile App Redesign',
|
|
562
|
+
status: 'In Progress',
|
|
563
|
+
lastUpdated: '2024-01-14',
|
|
564
|
+
path: '/projects/mobile-app'
|
|
565
|
+
},
|
|
566
|
+
{
|
|
567
|
+
id: 3,
|
|
568
|
+
name: 'Analytics Dashboard',
|
|
569
|
+
status: 'Completed',
|
|
570
|
+
lastUpdated: '2024-01-10',
|
|
571
|
+
path: '/projects/analytics'
|
|
572
|
+
}
|
|
573
|
+
];
|
|
574
|
+
|
|
575
|
+
return (
|
|
576
|
+
<div className="navigable-list">
|
|
577
|
+
{projectItems.map(project => (
|
|
578
|
+
<NavLink key={project.id} to={project.path} className="list-nav-link">
|
|
579
|
+
<ListItem className="project-item">
|
|
580
|
+
<ListItemContent>
|
|
581
|
+
<div className="project-header">
|
|
582
|
+
<Text type="Heading5">{project.name}</Text>
|
|
583
|
+
<Chip type={project.status === 'Active' ? 'Success' : 'Default'}>
|
|
584
|
+
{project.status}
|
|
585
|
+
</Chip>
|
|
586
|
+
</div>
|
|
587
|
+
<Text type="BodySmall" className="project-date">
|
|
588
|
+
Last updated: {project.lastUpdated}
|
|
589
|
+
</Text>
|
|
590
|
+
</ListItemContent>
|
|
591
|
+
<ListItemAction>
|
|
592
|
+
<Icon icon="ChevronRight" />
|
|
593
|
+
</ListItemAction>
|
|
594
|
+
</ListItem>
|
|
595
|
+
</NavLink>
|
|
596
|
+
))}
|
|
597
|
+
</div>
|
|
598
|
+
);
|
|
599
|
+
}
|
|
600
|
+
```
|
|
601
|
+
|
|
602
|
+
### Wrapping Complex Components (Panels)
|
|
603
|
+
```tsx
|
|
604
|
+
function PanelNavigationExample() {
|
|
605
|
+
const toolPanels = [
|
|
606
|
+
{
|
|
607
|
+
id: 'editor',
|
|
608
|
+
title: 'Code Editor',
|
|
609
|
+
description: 'Edit and manage your code files',
|
|
610
|
+
icon: 'Code',
|
|
611
|
+
path: '/tools/editor',
|
|
612
|
+
isActive: true
|
|
613
|
+
},
|
|
614
|
+
{
|
|
615
|
+
id: 'debugger',
|
|
616
|
+
title: 'Debugger',
|
|
617
|
+
description: 'Debug and troubleshoot your applications',
|
|
618
|
+
icon: 'Bug',
|
|
619
|
+
path: '/tools/debugger',
|
|
620
|
+
isActive: false
|
|
621
|
+
},
|
|
622
|
+
{
|
|
623
|
+
id: 'terminal',
|
|
624
|
+
title: 'Terminal',
|
|
625
|
+
description: 'Access command line interface',
|
|
626
|
+
icon: 'Terminal',
|
|
627
|
+
path: '/tools/terminal',
|
|
628
|
+
isActive: false
|
|
629
|
+
}
|
|
630
|
+
];
|
|
631
|
+
|
|
632
|
+
return (
|
|
633
|
+
<div className="panel-navigation">
|
|
634
|
+
{toolPanels.map(panel => (
|
|
635
|
+
<NavLink key={panel.id} to={panel.path} className="panel-nav-link">
|
|
636
|
+
<Panel className={`tool-panel ${panel.isActive ? 'active' : ''}`}>
|
|
637
|
+
<PanelHeader>
|
|
638
|
+
<Icon icon={panel.icon} />
|
|
639
|
+
<Text type="Heading5">{panel.title}</Text>
|
|
640
|
+
{panel.isActive && (
|
|
641
|
+
<Chip type="Primary" size="Small">Active</Chip>
|
|
642
|
+
)}
|
|
643
|
+
</PanelHeader>
|
|
644
|
+
<PanelContent>
|
|
645
|
+
<Text type="Body">{panel.description}</Text>
|
|
646
|
+
</PanelContent>
|
|
647
|
+
</Panel>
|
|
648
|
+
</NavLink>
|
|
649
|
+
))}
|
|
650
|
+
</div>
|
|
651
|
+
);
|
|
652
|
+
}
|
|
499
653
|
```
|
|
@@ -18,7 +18,7 @@ A versatile search input component that supports both automatic and manual searc
|
|
|
18
18
|
|
|
19
19
|
| Prop | Type | Default | Required | Description |
|
|
20
20
|
|------|------|---------|----------|-------------|
|
|
21
|
-
| `
|
|
21
|
+
| `style` | `'Auto' \| 'Manual'` | `'Auto'` | No | Search mode - 'Auto' for debounced search on input, 'Manual' for search on enter/submit |
|
|
22
22
|
| `onSearch` | `SearchCallback` | - | No | Callback function to handle search with the query string |
|
|
23
23
|
| `debounceMs` | `number` | `300` | No | Debounce delay in milliseconds for auto mode |
|
|
24
24
|
| `minCharacters` | `number` | `1` | No | Minimum characters required to trigger search in auto mode |
|
|
@@ -53,7 +53,7 @@ function BasicAutoSearch() {
|
|
|
53
53
|
return (
|
|
54
54
|
<div>
|
|
55
55
|
<Search
|
|
56
|
-
|
|
56
|
+
style="Auto"
|
|
57
57
|
onSearch={handleSearch}
|
|
58
58
|
loading={loading}
|
|
59
59
|
placeholder="Search products..."
|
|
@@ -100,7 +100,7 @@ function ManualSearchExample() {
|
|
|
100
100
|
return (
|
|
101
101
|
<div>
|
|
102
102
|
<Search
|
|
103
|
-
|
|
103
|
+
style="Manual"
|
|
104
104
|
value={query}
|
|
105
105
|
onValueChange={setQuery}
|
|
106
106
|
onSearch={handleSearch}
|
|
@@ -180,7 +180,7 @@ function AdvancedSearchExample() {
|
|
|
180
180
|
<div className="advanced-search">
|
|
181
181
|
<div className="search-header">
|
|
182
182
|
<Search
|
|
183
|
-
|
|
183
|
+
style="Auto"
|
|
184
184
|
value={searchState.query}
|
|
185
185
|
onValueChange={(query) => setSearchState(prev => ({ ...prev, query }))}
|
|
186
186
|
onSearch={performSearch}
|
|
@@ -298,7 +298,7 @@ function UserSearchExample() {
|
|
|
298
298
|
<div className="search-section">
|
|
299
299
|
<Text type="Heading6">Add Team Members</Text>
|
|
300
300
|
<Search
|
|
301
|
-
|
|
301
|
+
style="Auto"
|
|
302
302
|
onSearch={searchUsers}
|
|
303
303
|
loading={searching}
|
|
304
304
|
placeholder="Search by name or email..."
|
|
@@ -396,7 +396,7 @@ function DocumentSearchExample() {
|
|
|
396
396
|
<div className="document-search">
|
|
397
397
|
<div className="search-bar">
|
|
398
398
|
<Search
|
|
399
|
-
|
|
399
|
+
style="Auto"
|
|
400
400
|
value={searchState.query}
|
|
401
401
|
onValueChange={(query) => setSearchState(prev => ({ ...prev, query }))}
|
|
402
402
|
onSearch={searchDocuments}
|
|
@@ -508,7 +508,7 @@ function SearchWithHistoryExample() {
|
|
|
508
508
|
<div className="search-with-history">
|
|
509
509
|
<div className="search-container">
|
|
510
510
|
<Search
|
|
511
|
-
|
|
511
|
+
style="Manual"
|
|
512
512
|
value={currentQuery}
|
|
513
513
|
onValueChange={setCurrentQuery}
|
|
514
514
|
onSearch={performSearch}
|
|
@@ -626,7 +626,7 @@ function RealTimeSearchExample() {
|
|
|
626
626
|
<div className="realtime-search">
|
|
627
627
|
<div className="search-input-container">
|
|
628
628
|
<Search
|
|
629
|
-
|
|
629
|
+
style="Auto"
|
|
630
630
|
value={searchState.query}
|
|
631
631
|
onValueChange={handleQueryChange}
|
|
632
632
|
onSearch={performFullSearch}
|
|
@@ -24,6 +24,8 @@ A comprehensive form management component that provides state management, valida
|
|
|
24
24
|
| `formValidator` | `FormValidator` | - | No | Function to validate entire form |
|
|
25
25
|
| `onSubmit` | `FormSubmitHandler` | - | No | Form submission handler |
|
|
26
26
|
| `validateOnChange` | `boolean` | - | No | Whether to validate on field changes |
|
|
27
|
+
| `autosave` | `boolean` | `false` | No | Enable automatic form submission on value changes |
|
|
28
|
+
| `autosaveDelayMs` | `number` | - | No | Delay in milliseconds before autosave triggers |
|
|
27
29
|
|
|
28
30
|
Plus all standard HTML form attributes (method, action, encType, target, etc.) except `onSubmit`.
|
|
29
31
|
|
|
@@ -530,4 +532,129 @@ function AsyncFormExample() {
|
|
|
530
532
|
</Form>
|
|
531
533
|
);
|
|
532
534
|
}
|
|
535
|
+
```
|
|
536
|
+
|
|
537
|
+
### Autosave Form
|
|
538
|
+
```tsx
|
|
539
|
+
function AutosaveFormExample() {
|
|
540
|
+
const [saveCount, setSaveCount] = useState(0);
|
|
541
|
+
const [lastSaved, setLastSaved] = useState(null);
|
|
542
|
+
|
|
543
|
+
const handleSubmit = async (values, setError) => {
|
|
544
|
+
try {
|
|
545
|
+
// Simulate API call to save draft
|
|
546
|
+
const response = await fetch('/api/drafts', {
|
|
547
|
+
method: 'POST',
|
|
548
|
+
headers: { 'Content-Type': 'application/json' },
|
|
549
|
+
body: JSON.stringify(values)
|
|
550
|
+
});
|
|
551
|
+
|
|
552
|
+
if (response.ok) {
|
|
553
|
+
setSaveCount(prev => prev + 1);
|
|
554
|
+
setLastSaved(new Date().toLocaleTimeString());
|
|
555
|
+
console.log('Draft auto-saved:', values);
|
|
556
|
+
}
|
|
557
|
+
} catch (error) {
|
|
558
|
+
console.error('Failed to save draft:', error);
|
|
559
|
+
}
|
|
560
|
+
};
|
|
561
|
+
|
|
562
|
+
return (
|
|
563
|
+
<div>
|
|
564
|
+
<Form
|
|
565
|
+
onSubmit={handleSubmit}
|
|
566
|
+
autosave={true}
|
|
567
|
+
autosaveDelayMs={2000} // Wait 2 seconds after user stops typing
|
|
568
|
+
>
|
|
569
|
+
<FormField name="title" label="Title">
|
|
570
|
+
<Input placeholder="Enter title" />
|
|
571
|
+
</FormField>
|
|
572
|
+
|
|
573
|
+
<FormField name="content" label="Content">
|
|
574
|
+
<TextArea
|
|
575
|
+
placeholder="Start writing..."
|
|
576
|
+
rows={10}
|
|
577
|
+
/>
|
|
578
|
+
</FormField>
|
|
579
|
+
|
|
580
|
+
<FormField name="tags" label="Tags">
|
|
581
|
+
<ChipInput
|
|
582
|
+
placeholder="Add tags"
|
|
583
|
+
options={['react', 'typescript', 'design', 'tutorial']}
|
|
584
|
+
/>
|
|
585
|
+
</FormField>
|
|
586
|
+
|
|
587
|
+
{lastSaved && (
|
|
588
|
+
<Text type="BodySmall">
|
|
589
|
+
Auto-saved {saveCount} times. Last saved at {lastSaved}
|
|
590
|
+
</Text>
|
|
591
|
+
)}
|
|
592
|
+
</Form>
|
|
593
|
+
</div>
|
|
594
|
+
);
|
|
595
|
+
}
|
|
596
|
+
```
|
|
597
|
+
|
|
598
|
+
### Autosave with Manual Submit
|
|
599
|
+
```tsx
|
|
600
|
+
function AutosaveWithManualSubmitExample() {
|
|
601
|
+
const [isDraft, setIsDraft] = useState(true);
|
|
602
|
+
|
|
603
|
+
const handleAutosave = (values, setError) => {
|
|
604
|
+
if (isDraft) {
|
|
605
|
+
console.log('Draft auto-saved:', values);
|
|
606
|
+
// Save to local storage or draft API
|
|
607
|
+
localStorage.setItem('formDraft', JSON.stringify(values));
|
|
608
|
+
}
|
|
609
|
+
};
|
|
610
|
+
|
|
611
|
+
const handlePublish = () => {
|
|
612
|
+
setIsDraft(false);
|
|
613
|
+
// Form will now submit normally
|
|
614
|
+
};
|
|
615
|
+
|
|
616
|
+
return (
|
|
617
|
+
<Form
|
|
618
|
+
onSubmit={handleAutosave}
|
|
619
|
+
autosave={isDraft}
|
|
620
|
+
autosaveDelayMs={1000}
|
|
621
|
+
formState={{
|
|
622
|
+
title: localStorage.getItem('formDraft')?.title || '',
|
|
623
|
+
content: localStorage.getItem('formDraft')?.content || ''
|
|
624
|
+
}}
|
|
625
|
+
>
|
|
626
|
+
<FormField name="title" label="Article Title" required>
|
|
627
|
+
<Input placeholder="Enter title" />
|
|
628
|
+
</FormField>
|
|
629
|
+
|
|
630
|
+
<FormField name="content" label="Article Content" required>
|
|
631
|
+
<TextArea placeholder="Write your article..." rows={15} />
|
|
632
|
+
</FormField>
|
|
633
|
+
|
|
634
|
+
<FormField name="category" label="Category">
|
|
635
|
+
<Select>
|
|
636
|
+
<Option value="tech">Technology</Option>
|
|
637
|
+
<Option value="design">Design</Option>
|
|
638
|
+
<Option value="business">Business</Option>
|
|
639
|
+
</Select>
|
|
640
|
+
</FormField>
|
|
641
|
+
|
|
642
|
+
<div className="form-actions">
|
|
643
|
+
<Button type="Outlined">Save as Draft</Button>
|
|
644
|
+
<Button
|
|
645
|
+
actionType="submit"
|
|
646
|
+
onClick={handlePublish}
|
|
647
|
+
>
|
|
648
|
+
Publish Article
|
|
649
|
+
</Button>
|
|
650
|
+
</div>
|
|
651
|
+
|
|
652
|
+
{isDraft && (
|
|
653
|
+
<Text type="BodySmall" style={{ marginTop: '8px' }}>
|
|
654
|
+
Your changes are automatically saved as you type
|
|
655
|
+
</Text>
|
|
656
|
+
)}
|
|
657
|
+
</Form>
|
|
658
|
+
);
|
|
659
|
+
}
|
|
533
660
|
```
|