intelliwaketssveltekitv25 1.0.81 → 1.0.82
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/INTEGRATION.md +574 -0
- package/README.md +199 -45
- package/dist/ArrayTable.stories.js +215 -0
- package/dist/ArrayTable.svelte +46 -0
- package/dist/ArrayTable.svelte.d.ts +44 -0
- package/dist/DropDown.stories.d.ts +96 -0
- package/dist/DropDown.stories.js +192 -0
- package/dist/DropDown.svelte +32 -0
- package/dist/DropDown.svelte.d.ts +30 -0
- package/dist/InputNumber.stories.d.ts +122 -0
- package/dist/InputNumber.stories.js +186 -0
- package/dist/InputNumber.svelte +52 -0
- package/dist/InputNumber.svelte.d.ts +27 -0
- package/dist/Modal.stories.d.ts +114 -0
- package/dist/Modal.stories.js +139 -0
- package/dist/Modal.svelte +34 -3
- package/dist/Modal.svelte.d.ts +35 -3
- package/dist/MultiSelect.stories.js +338 -0
- package/dist/MultiSelect.svelte +81 -0
- package/dist/MultiSelect.svelte.d.ts +38 -0
- package/dist/Switch.stories.d.ts +81 -0
- package/dist/Switch.stories.js +99 -0
- package/dist/Switch.svelte +40 -0
- package/dist/Switch.svelte.d.ts +26 -0
- package/dist/TextArea.stories.d.ts +180 -0
- package/dist/TextArea.stories.js +216 -0
- package/dist/TextArea.svelte +32 -0
- package/dist/TextArea.svelte.d.ts +24 -0
- package/dist/app.css +1 -1
- package/llm.txt +1635 -0
- package/package.json +6 -2
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
import type { StoryObj } from '@storybook/svelte';
|
|
2
|
+
type ModalProps = {
|
|
3
|
+
show: unknown;
|
|
4
|
+
noShowValue?: unknown;
|
|
5
|
+
width?: string;
|
|
6
|
+
cancelButton?: string | false;
|
|
7
|
+
okButton?: string | false;
|
|
8
|
+
okDisabled?: boolean;
|
|
9
|
+
noCloseOnOK?: boolean;
|
|
10
|
+
disable?: boolean;
|
|
11
|
+
okType?: 'submit' | 'button';
|
|
12
|
+
overflowY?: 'auto' | 'visible' | 'hidden';
|
|
13
|
+
borderFooter?: boolean;
|
|
14
|
+
};
|
|
15
|
+
declare const meta: {
|
|
16
|
+
title: string;
|
|
17
|
+
component: import("svelte").Component<{
|
|
18
|
+
header?: import("svelte").Snippet;
|
|
19
|
+
body?: import("svelte").Snippet;
|
|
20
|
+
leftFooter?: import("svelte").Snippet;
|
|
21
|
+
centerFooter?: import("svelte").Snippet;
|
|
22
|
+
rightFooter?: import("svelte").Snippet;
|
|
23
|
+
show: unknown;
|
|
24
|
+
noShowValue?: unknown;
|
|
25
|
+
forceNoShow?: boolean;
|
|
26
|
+
width?: string;
|
|
27
|
+
cancelButton?: string | false;
|
|
28
|
+
okButton?: string | false;
|
|
29
|
+
okFAProps?: import("./Definitions").IFAProps;
|
|
30
|
+
okActionNotOnEnter?: boolean;
|
|
31
|
+
okDisabled?: boolean;
|
|
32
|
+
noCloseOnOK?: boolean;
|
|
33
|
+
overflowY?: "auto" | "visible" | "hidden";
|
|
34
|
+
disable?: boolean;
|
|
35
|
+
okType?: "submit" | "button";
|
|
36
|
+
marginForStickyHeader?: boolean;
|
|
37
|
+
okButtonWrap?: boolean;
|
|
38
|
+
class?: string;
|
|
39
|
+
okColor?: TDefaultColorPalate | null;
|
|
40
|
+
color?: TDefaultColorPalate | null;
|
|
41
|
+
classHeader?: string;
|
|
42
|
+
classBody?: string;
|
|
43
|
+
classFooter?: string;
|
|
44
|
+
classButton?: string;
|
|
45
|
+
borderFooter?: boolean;
|
|
46
|
+
onOK?: () => void;
|
|
47
|
+
onOKPromise?: () => Promise<unknown>;
|
|
48
|
+
onCancel?: () => void;
|
|
49
|
+
onClose?: () => void;
|
|
50
|
+
}, {}, "show">;
|
|
51
|
+
tags: string[];
|
|
52
|
+
argTypes: {
|
|
53
|
+
show: {
|
|
54
|
+
control: "boolean";
|
|
55
|
+
description: string;
|
|
56
|
+
};
|
|
57
|
+
noShowValue: {
|
|
58
|
+
control: "text";
|
|
59
|
+
description: string;
|
|
60
|
+
};
|
|
61
|
+
width: {
|
|
62
|
+
control: "text";
|
|
63
|
+
description: string;
|
|
64
|
+
};
|
|
65
|
+
cancelButton: {
|
|
66
|
+
control: "text";
|
|
67
|
+
description: string;
|
|
68
|
+
};
|
|
69
|
+
okButton: {
|
|
70
|
+
control: "text";
|
|
71
|
+
description: string;
|
|
72
|
+
};
|
|
73
|
+
okDisabled: {
|
|
74
|
+
control: "boolean";
|
|
75
|
+
description: string;
|
|
76
|
+
};
|
|
77
|
+
noCloseOnOK: {
|
|
78
|
+
control: "boolean";
|
|
79
|
+
description: string;
|
|
80
|
+
};
|
|
81
|
+
disable: {
|
|
82
|
+
control: "boolean";
|
|
83
|
+
description: string;
|
|
84
|
+
};
|
|
85
|
+
okType: {
|
|
86
|
+
control: "select";
|
|
87
|
+
options: string[];
|
|
88
|
+
description: string;
|
|
89
|
+
};
|
|
90
|
+
overflowY: {
|
|
91
|
+
control: "select";
|
|
92
|
+
options: string[];
|
|
93
|
+
description: string;
|
|
94
|
+
};
|
|
95
|
+
borderFooter: {
|
|
96
|
+
control: "boolean";
|
|
97
|
+
description: string;
|
|
98
|
+
};
|
|
99
|
+
};
|
|
100
|
+
};
|
|
101
|
+
export default meta;
|
|
102
|
+
type Story = StoryObj<ModalProps>;
|
|
103
|
+
export declare const Default: Story;
|
|
104
|
+
export declare const WideModal: Story;
|
|
105
|
+
export declare const NarrowModal: Story;
|
|
106
|
+
export declare const OnlyOKButton: Story;
|
|
107
|
+
export declare const OnlyCancelButton: Story;
|
|
108
|
+
export declare const NoButtons: Story;
|
|
109
|
+
export declare const OKDisabled: Story;
|
|
110
|
+
export declare const NoCloseOnOK: Story;
|
|
111
|
+
export declare const WithActivityOverlay: Story;
|
|
112
|
+
export declare const FormSubmitType: Story;
|
|
113
|
+
export declare const NoBorderFooter: Story;
|
|
114
|
+
export declare const OverflowVisible: Story;
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
import Modal from './Modal.svelte';
|
|
2
|
+
const meta = {
|
|
3
|
+
title: 'Components/Modal',
|
|
4
|
+
component: Modal,
|
|
5
|
+
tags: ['autodocs'],
|
|
6
|
+
argTypes: {
|
|
7
|
+
show: {
|
|
8
|
+
control: 'boolean',
|
|
9
|
+
description: 'Control visibility: value equal to noShowValue hides modal, any other value shows it'
|
|
10
|
+
},
|
|
11
|
+
noShowValue: {
|
|
12
|
+
control: 'text',
|
|
13
|
+
description: 'The value to compare against show to determine if modal should be hidden'
|
|
14
|
+
},
|
|
15
|
+
width: {
|
|
16
|
+
control: 'text',
|
|
17
|
+
description: 'Modal width (CSS value like "40em", "500px", "80%")'
|
|
18
|
+
},
|
|
19
|
+
cancelButton: {
|
|
20
|
+
control: 'text',
|
|
21
|
+
description: 'Cancel button text, or false to hide'
|
|
22
|
+
},
|
|
23
|
+
okButton: {
|
|
24
|
+
control: 'text',
|
|
25
|
+
description: 'OK button text, or false to hide'
|
|
26
|
+
},
|
|
27
|
+
okDisabled: {
|
|
28
|
+
control: 'boolean',
|
|
29
|
+
description: 'Disable the OK button'
|
|
30
|
+
},
|
|
31
|
+
noCloseOnOK: {
|
|
32
|
+
control: 'boolean',
|
|
33
|
+
description: 'Keep modal open after OK click (useful for form validation)'
|
|
34
|
+
},
|
|
35
|
+
disable: {
|
|
36
|
+
control: 'boolean',
|
|
37
|
+
description: 'Disable all interactions (shows activity overlay)'
|
|
38
|
+
},
|
|
39
|
+
okType: {
|
|
40
|
+
control: 'select',
|
|
41
|
+
options: ['submit', 'button'],
|
|
42
|
+
description: 'Button type for form integration'
|
|
43
|
+
},
|
|
44
|
+
overflowY: {
|
|
45
|
+
control: 'select',
|
|
46
|
+
options: ['auto', 'visible', 'hidden'],
|
|
47
|
+
description: 'Body overflow behavior'
|
|
48
|
+
},
|
|
49
|
+
borderFooter: {
|
|
50
|
+
control: 'boolean',
|
|
51
|
+
description: 'Show border above footer'
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
export default meta;
|
|
56
|
+
export const Default = {
|
|
57
|
+
args: {
|
|
58
|
+
show: true,
|
|
59
|
+
cancelButton: 'Cancel',
|
|
60
|
+
okButton: 'OK'
|
|
61
|
+
}
|
|
62
|
+
};
|
|
63
|
+
export const WideModal = {
|
|
64
|
+
args: {
|
|
65
|
+
show: true,
|
|
66
|
+
width: '80%',
|
|
67
|
+
cancelButton: 'Cancel',
|
|
68
|
+
okButton: 'Save'
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
export const NarrowModal = {
|
|
72
|
+
args: {
|
|
73
|
+
show: true,
|
|
74
|
+
width: '30em',
|
|
75
|
+
cancelButton: 'Cancel',
|
|
76
|
+
okButton: 'Confirm'
|
|
77
|
+
}
|
|
78
|
+
};
|
|
79
|
+
export const OnlyOKButton = {
|
|
80
|
+
args: {
|
|
81
|
+
show: true,
|
|
82
|
+
cancelButton: false,
|
|
83
|
+
okButton: 'Close'
|
|
84
|
+
}
|
|
85
|
+
};
|
|
86
|
+
export const OnlyCancelButton = {
|
|
87
|
+
args: {
|
|
88
|
+
show: true,
|
|
89
|
+
cancelButton: 'Close',
|
|
90
|
+
okButton: false
|
|
91
|
+
}
|
|
92
|
+
};
|
|
93
|
+
export const NoButtons = {
|
|
94
|
+
args: {
|
|
95
|
+
show: true,
|
|
96
|
+
cancelButton: false,
|
|
97
|
+
okButton: false
|
|
98
|
+
}
|
|
99
|
+
};
|
|
100
|
+
export const OKDisabled = {
|
|
101
|
+
args: {
|
|
102
|
+
show: true,
|
|
103
|
+
okButton: 'Save',
|
|
104
|
+
okDisabled: true
|
|
105
|
+
}
|
|
106
|
+
};
|
|
107
|
+
export const NoCloseOnOK = {
|
|
108
|
+
args: {
|
|
109
|
+
show: true,
|
|
110
|
+
okButton: 'Validate',
|
|
111
|
+
noCloseOnOK: true
|
|
112
|
+
}
|
|
113
|
+
};
|
|
114
|
+
export const WithActivityOverlay = {
|
|
115
|
+
args: {
|
|
116
|
+
show: true,
|
|
117
|
+
okButton: 'Processing...',
|
|
118
|
+
disable: true
|
|
119
|
+
}
|
|
120
|
+
};
|
|
121
|
+
export const FormSubmitType = {
|
|
122
|
+
args: {
|
|
123
|
+
show: true,
|
|
124
|
+
okButton: 'Submit',
|
|
125
|
+
okType: 'submit'
|
|
126
|
+
}
|
|
127
|
+
};
|
|
128
|
+
export const NoBorderFooter = {
|
|
129
|
+
args: {
|
|
130
|
+
show: true,
|
|
131
|
+
borderFooter: false
|
|
132
|
+
}
|
|
133
|
+
};
|
|
134
|
+
export const OverflowVisible = {
|
|
135
|
+
args: {
|
|
136
|
+
show: true,
|
|
137
|
+
overflowY: 'visible'
|
|
138
|
+
}
|
|
139
|
+
};
|
package/dist/Modal.svelte
CHANGED
|
@@ -1,9 +1,40 @@
|
|
|
1
1
|
<!--
|
|
2
2
|
@component
|
|
3
|
+
Full-featured modal dialog with draggable header, keyboard shortcuts, and flexible content slots.
|
|
4
|
+
Replaces native <dialog> element or custom div overlays.
|
|
3
5
|
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
6
|
+
@example
|
|
7
|
+
```svelte
|
|
8
|
+
<script>
|
|
9
|
+
import { Modal } from 'intelliwaketssveltekitv25';
|
|
10
|
+
let showModal = $state(false);
|
|
11
|
+
</script>
|
|
12
|
+
|
|
13
|
+
<Modal
|
|
14
|
+
bind:show={showModal}
|
|
15
|
+
okButton="Save"
|
|
16
|
+
cancelButton="Cancel"
|
|
17
|
+
>
|
|
18
|
+
{#snippet header()}
|
|
19
|
+
Edit Settings
|
|
20
|
+
{/snippet}
|
|
21
|
+
{#snippet body()}
|
|
22
|
+
<p>Modal content...</p>
|
|
23
|
+
{/snippet}
|
|
24
|
+
</Modal>
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
@remarks
|
|
28
|
+
- Uses Svelte 5 $bindable rune for two-way binding of show state
|
|
29
|
+
- Draggable: click and drag header to reposition modal
|
|
30
|
+
- Keyboard shortcuts: Enter triggers OK, Escape cancels
|
|
31
|
+
- Backdrop click closes modal (triggers cancel action)
|
|
32
|
+
- Activity overlay support for async operations
|
|
33
|
+
- Multiple Snippet slots for flexible layouts (header, body, leftFooter, centerFooter, rightFooter)
|
|
34
|
+
|
|
35
|
+
@see ModalFormAction - Specialized modal for SvelteKit form actions
|
|
36
|
+
@see ModalPromptControl - Modal with prompt/confirmation patterns
|
|
37
|
+
@see ActivityOverlay - Loading overlay component (used internally)
|
|
7
38
|
-->
|
|
8
39
|
|
|
9
40
|
<script lang='ts'>
|
package/dist/Modal.svelte.d.ts
CHANGED
|
@@ -37,9 +37,41 @@ type $$ComponentProps = {
|
|
|
37
37
|
onClose?: () => void;
|
|
38
38
|
};
|
|
39
39
|
/**
|
|
40
|
-
*
|
|
41
|
-
*
|
|
42
|
-
*
|
|
40
|
+
* Full-featured modal dialog with draggable header, keyboard shortcuts, and flexible content slots.
|
|
41
|
+
* Replaces native <dialog> element or custom div overlays.
|
|
42
|
+
*
|
|
43
|
+
* @example
|
|
44
|
+
* ```svelte
|
|
45
|
+
* <script>
|
|
46
|
+
* import { Modal } from 'intelliwaketssveltekitv25';
|
|
47
|
+
* let showModal = $state(false);
|
|
48
|
+
* </script>
|
|
49
|
+
*
|
|
50
|
+
* <Modal
|
|
51
|
+
* bind:show={showModal}
|
|
52
|
+
* okButton="Save"
|
|
53
|
+
* cancelButton="Cancel"
|
|
54
|
+
* >
|
|
55
|
+
* {#snippet header()}
|
|
56
|
+
* Edit Settings
|
|
57
|
+
* {/snippet}
|
|
58
|
+
* {#snippet body()}
|
|
59
|
+
* <p>Modal content...</p>
|
|
60
|
+
* {/snippet}
|
|
61
|
+
* </Modal>
|
|
62
|
+
* ```
|
|
63
|
+
*
|
|
64
|
+
* @remarks
|
|
65
|
+
* - Uses Svelte 5 $bindable rune for two-way binding of show state
|
|
66
|
+
* - Draggable: click and drag header to reposition modal
|
|
67
|
+
* - Keyboard shortcuts: Enter triggers OK, Escape cancels
|
|
68
|
+
* - Backdrop click closes modal (triggers cancel action)
|
|
69
|
+
* - Activity overlay support for async operations
|
|
70
|
+
* - Multiple Snippet slots for flexible layouts (header, body, leftFooter, centerFooter, rightFooter)
|
|
71
|
+
*
|
|
72
|
+
* @see ModalFormAction - Specialized modal for SvelteKit form actions
|
|
73
|
+
* @see ModalPromptControl - Modal with prompt/confirmation patterns
|
|
74
|
+
* @see ActivityOverlay - Loading overlay component (used internally)
|
|
43
75
|
*/
|
|
44
76
|
declare const Modal: import("svelte").Component<$$ComponentProps, {}, "show">;
|
|
45
77
|
type Modal = ReturnType<typeof Modal>;
|
|
@@ -0,0 +1,338 @@
|
|
|
1
|
+
import MultiSelect from './MultiSelect.svelte';
|
|
2
|
+
const sampleTags = [
|
|
3
|
+
{ id: 1, name: 'JavaScript' },
|
|
4
|
+
{ id: 2, name: 'TypeScript' },
|
|
5
|
+
{ id: 3, name: 'Python' },
|
|
6
|
+
{ id: 4, name: 'Java' },
|
|
7
|
+
{ id: 5, name: 'C++' },
|
|
8
|
+
{ id: 6, name: 'Ruby' },
|
|
9
|
+
{ id: 7, name: 'Go' },
|
|
10
|
+
{ id: 8, name: 'Rust' },
|
|
11
|
+
{ id: 9, name: 'PHP' },
|
|
12
|
+
{ id: 10, name: 'Swift' }
|
|
13
|
+
];
|
|
14
|
+
const groupedTags = [
|
|
15
|
+
{ id: 1, name: 'JavaScript', header: 'Frontend' },
|
|
16
|
+
{ id: 2, name: 'TypeScript', header: 'Frontend' },
|
|
17
|
+
{ id: 3, name: 'React', header: 'Frontend' },
|
|
18
|
+
{ id: 4, name: 'Vue', header: 'Frontend' },
|
|
19
|
+
{ id: 5, name: 'Node.js', header: 'Backend' },
|
|
20
|
+
{ id: 6, name: 'Python', header: 'Backend' },
|
|
21
|
+
{ id: 7, name: 'Go', header: 'Backend' },
|
|
22
|
+
{ id: 8, name: 'MySQL', header: 'Database' },
|
|
23
|
+
{ id: 9, name: 'PostgreSQL', header: 'Database' },
|
|
24
|
+
{ id: 10, name: 'MongoDB', header: 'Database' }
|
|
25
|
+
];
|
|
26
|
+
const meta = {
|
|
27
|
+
title: 'Components/MultiSelect',
|
|
28
|
+
component: MultiSelect,
|
|
29
|
+
tags: ['autodocs'],
|
|
30
|
+
argTypes: {
|
|
31
|
+
possibles: {
|
|
32
|
+
control: 'object',
|
|
33
|
+
description: 'Array of all available items to select from',
|
|
34
|
+
table: {
|
|
35
|
+
type: { summary: 'T[]' }
|
|
36
|
+
}
|
|
37
|
+
},
|
|
38
|
+
selected: {
|
|
39
|
+
control: 'object',
|
|
40
|
+
description: 'Currently selected items (two-way bindable)',
|
|
41
|
+
table: {
|
|
42
|
+
type: { summary: 'T[]' },
|
|
43
|
+
defaultValue: { summary: '[]' }
|
|
44
|
+
}
|
|
45
|
+
},
|
|
46
|
+
selectedIDs: {
|
|
47
|
+
control: 'object',
|
|
48
|
+
description: 'IDs of selected items (two-way bindable, alternative to selected)',
|
|
49
|
+
table: {
|
|
50
|
+
type: { summary: '(number | string)[] | undefined' },
|
|
51
|
+
defaultValue: { summary: 'undefined' }
|
|
52
|
+
}
|
|
53
|
+
},
|
|
54
|
+
placeholder: {
|
|
55
|
+
control: 'text',
|
|
56
|
+
description: 'Placeholder text shown when no items selected',
|
|
57
|
+
table: {
|
|
58
|
+
type: { summary: 'string' },
|
|
59
|
+
defaultValue: { summary: '""' }
|
|
60
|
+
}
|
|
61
|
+
},
|
|
62
|
+
disabled: {
|
|
63
|
+
control: 'boolean',
|
|
64
|
+
description: 'Disable user interaction',
|
|
65
|
+
table: {
|
|
66
|
+
type: { summary: 'boolean' },
|
|
67
|
+
defaultValue: { summary: 'false' }
|
|
68
|
+
}
|
|
69
|
+
},
|
|
70
|
+
readonly: {
|
|
71
|
+
control: 'boolean',
|
|
72
|
+
description: 'Display in readonly mode (no interaction allowed)',
|
|
73
|
+
table: {
|
|
74
|
+
type: { summary: 'boolean' },
|
|
75
|
+
defaultValue: { summary: 'false' }
|
|
76
|
+
}
|
|
77
|
+
},
|
|
78
|
+
required: {
|
|
79
|
+
control: 'boolean',
|
|
80
|
+
description: 'Mark as required (shows invalid state if empty)',
|
|
81
|
+
table: {
|
|
82
|
+
type: { summary: 'boolean' },
|
|
83
|
+
defaultValue: { summary: 'false' }
|
|
84
|
+
}
|
|
85
|
+
},
|
|
86
|
+
isMulti: {
|
|
87
|
+
control: 'boolean',
|
|
88
|
+
description: 'Allow multiple selections (false = single-select mode)',
|
|
89
|
+
table: {
|
|
90
|
+
type: { summary: 'boolean' },
|
|
91
|
+
defaultValue: { summary: 'true' }
|
|
92
|
+
}
|
|
93
|
+
},
|
|
94
|
+
allowClearAll: {
|
|
95
|
+
control: 'boolean',
|
|
96
|
+
description: 'Show clear all button when items are selected',
|
|
97
|
+
table: {
|
|
98
|
+
type: { summary: 'boolean' },
|
|
99
|
+
defaultValue: { summary: 'true' }
|
|
100
|
+
}
|
|
101
|
+
},
|
|
102
|
+
createPrefix: {
|
|
103
|
+
control: 'text',
|
|
104
|
+
description: 'Text prefix shown before new item name in create option',
|
|
105
|
+
table: {
|
|
106
|
+
type: { summary: 'string' },
|
|
107
|
+
defaultValue: { summary: '"Create:"' }
|
|
108
|
+
}
|
|
109
|
+
},
|
|
110
|
+
autoFocus: {
|
|
111
|
+
control: 'boolean',
|
|
112
|
+
description: 'Auto-focus input on mount',
|
|
113
|
+
table: {
|
|
114
|
+
type: { summary: 'boolean' },
|
|
115
|
+
defaultValue: { summary: 'false' }
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
};
|
|
120
|
+
export default meta;
|
|
121
|
+
/**
|
|
122
|
+
* Default multi-select with no initial selection.
|
|
123
|
+
* Users can select multiple items from the dropdown.
|
|
124
|
+
*/
|
|
125
|
+
export const Default = {
|
|
126
|
+
args: {
|
|
127
|
+
possibles: sampleTags,
|
|
128
|
+
selected: [],
|
|
129
|
+
placeholder: 'Select programming languages...'
|
|
130
|
+
}
|
|
131
|
+
};
|
|
132
|
+
/**
|
|
133
|
+
* Multi-select with pre-selected items.
|
|
134
|
+
* Demonstrates binding to existing selections.
|
|
135
|
+
*/
|
|
136
|
+
export const PreSelected = {
|
|
137
|
+
args: {
|
|
138
|
+
possibles: sampleTags,
|
|
139
|
+
selected: [sampleTags[0], sampleTags[1]], // JavaScript and TypeScript
|
|
140
|
+
placeholder: 'Select programming languages...'
|
|
141
|
+
}
|
|
142
|
+
};
|
|
143
|
+
/**
|
|
144
|
+
* Single-select mode (isMulti=false).
|
|
145
|
+
* Only one item can be selected at a time - acts like a searchable dropdown.
|
|
146
|
+
*/
|
|
147
|
+
export const SingleSelect = {
|
|
148
|
+
args: {
|
|
149
|
+
possibles: sampleTags,
|
|
150
|
+
selected: [],
|
|
151
|
+
isMulti: false,
|
|
152
|
+
placeholder: 'Select one language...'
|
|
153
|
+
}
|
|
154
|
+
};
|
|
155
|
+
/**
|
|
156
|
+
* Enable dynamic item creation with the create function.
|
|
157
|
+
* Type a name that doesn't exist and press Enter to create a new item.
|
|
158
|
+
*/
|
|
159
|
+
export const WithCreation = {
|
|
160
|
+
args: {
|
|
161
|
+
possibles: sampleTags,
|
|
162
|
+
selected: [],
|
|
163
|
+
placeholder: 'Select or create languages...',
|
|
164
|
+
create: (value) => ({ id: Date.now(), name: value }),
|
|
165
|
+
createPrefix: 'Create new:'
|
|
166
|
+
}
|
|
167
|
+
};
|
|
168
|
+
/**
|
|
169
|
+
* Creation with validation.
|
|
170
|
+
* Prevents creating items that don't meet validation criteria.
|
|
171
|
+
*/
|
|
172
|
+
export const WithValidation = {
|
|
173
|
+
args: {
|
|
174
|
+
possibles: sampleTags,
|
|
175
|
+
selected: [],
|
|
176
|
+
placeholder: 'Select or create (min 3 chars)...',
|
|
177
|
+
create: (value) => ({ id: Date.now(), name: value }),
|
|
178
|
+
createValid: (value) => {
|
|
179
|
+
if (value.length < 3) {
|
|
180
|
+
return 'Language name must be at least 3 characters';
|
|
181
|
+
}
|
|
182
|
+
return true;
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
};
|
|
186
|
+
/**
|
|
187
|
+
* Searchable dropdown with filtering.
|
|
188
|
+
* Type to filter the list of available items.
|
|
189
|
+
*/
|
|
190
|
+
export const Searchable = {
|
|
191
|
+
args: {
|
|
192
|
+
possibles: sampleTags,
|
|
193
|
+
selected: [],
|
|
194
|
+
placeholder: 'Type to search languages...'
|
|
195
|
+
}
|
|
196
|
+
};
|
|
197
|
+
/**
|
|
198
|
+
* Grouped items with headers.
|
|
199
|
+
* Items are organized into sections using the headerValue function.
|
|
200
|
+
*/
|
|
201
|
+
export const WithHeaders = {
|
|
202
|
+
args: {
|
|
203
|
+
possibles: groupedTags,
|
|
204
|
+
selected: [],
|
|
205
|
+
placeholder: 'Select technologies...'
|
|
206
|
+
}
|
|
207
|
+
};
|
|
208
|
+
/**
|
|
209
|
+
* Disabled state prevents all interaction.
|
|
210
|
+
*/
|
|
211
|
+
export const Disabled = {
|
|
212
|
+
args: {
|
|
213
|
+
possibles: sampleTags,
|
|
214
|
+
selected: [sampleTags[0]],
|
|
215
|
+
disabled: true,
|
|
216
|
+
placeholder: 'Disabled...'
|
|
217
|
+
}
|
|
218
|
+
};
|
|
219
|
+
/**
|
|
220
|
+
* Readonly state displays selections but prevents changes.
|
|
221
|
+
*/
|
|
222
|
+
export const Readonly = {
|
|
223
|
+
args: {
|
|
224
|
+
possibles: sampleTags,
|
|
225
|
+
selected: [sampleTags[0], sampleTags[1]],
|
|
226
|
+
readonly: true,
|
|
227
|
+
placeholder: 'Readonly...'
|
|
228
|
+
}
|
|
229
|
+
};
|
|
230
|
+
/**
|
|
231
|
+
* Without clear all button.
|
|
232
|
+
* Users must remove items individually.
|
|
233
|
+
*/
|
|
234
|
+
export const NoClearAll = {
|
|
235
|
+
args: {
|
|
236
|
+
possibles: sampleTags,
|
|
237
|
+
selected: [sampleTags[0], sampleTags[1], sampleTags[2]],
|
|
238
|
+
allowClearAll: false,
|
|
239
|
+
placeholder: 'Select languages...'
|
|
240
|
+
}
|
|
241
|
+
};
|
|
242
|
+
/**
|
|
243
|
+
* Required field validation.
|
|
244
|
+
* Shows invalid state when no items are selected.
|
|
245
|
+
*/
|
|
246
|
+
export const Required = {
|
|
247
|
+
args: {
|
|
248
|
+
possibles: sampleTags,
|
|
249
|
+
selected: [],
|
|
250
|
+
required: true,
|
|
251
|
+
placeholder: 'At least one language required'
|
|
252
|
+
}
|
|
253
|
+
};
|
|
254
|
+
/**
|
|
255
|
+
* Form integration with hidden inputs.
|
|
256
|
+
* Selected item IDs are submitted with the form using the name attribute.
|
|
257
|
+
*/
|
|
258
|
+
export const FormIntegration = {
|
|
259
|
+
args: {
|
|
260
|
+
possibles: sampleTags,
|
|
261
|
+
selected: [sampleTags[0]],
|
|
262
|
+
name: 'languages',
|
|
263
|
+
placeholder: 'Select languages for form...'
|
|
264
|
+
}
|
|
265
|
+
};
|
|
266
|
+
/**
|
|
267
|
+
* Using selectedIDs for binding instead of selected array.
|
|
268
|
+
* Useful when working with IDs directly.
|
|
269
|
+
*/
|
|
270
|
+
export const BindToIDs = {
|
|
271
|
+
args: {
|
|
272
|
+
possibles: sampleTags,
|
|
273
|
+
selectedIDs: [1, 2], // IDs of JavaScript and TypeScript
|
|
274
|
+
placeholder: 'Bound to IDs...'
|
|
275
|
+
}
|
|
276
|
+
};
|
|
277
|
+
/**
|
|
278
|
+
* Track created vs existing items.
|
|
279
|
+
* The created and existing bindable props separate new items from existing ones.
|
|
280
|
+
*/
|
|
281
|
+
export const TrackCreated = {
|
|
282
|
+
args: {
|
|
283
|
+
possibles: sampleTags,
|
|
284
|
+
selected: [],
|
|
285
|
+
placeholder: 'Select or create languages...',
|
|
286
|
+
create: (value) => ({ id: Date.now(), name: value }),
|
|
287
|
+
createPrefix: 'Add new:'
|
|
288
|
+
}
|
|
289
|
+
};
|
|
290
|
+
/**
|
|
291
|
+
* Large dataset with many items.
|
|
292
|
+
* Demonstrates search performance with lots of options.
|
|
293
|
+
*/
|
|
294
|
+
export const LargeDataset = {
|
|
295
|
+
args: {
|
|
296
|
+
possibles: Array.from({ length: 100 }, (_, i) => ({
|
|
297
|
+
id: i + 1,
|
|
298
|
+
name: `Language ${i + 1}`
|
|
299
|
+
})),
|
|
300
|
+
selected: [],
|
|
301
|
+
placeholder: 'Search 100+ items...'
|
|
302
|
+
}
|
|
303
|
+
};
|
|
304
|
+
/**
|
|
305
|
+
* Empty possibles array.
|
|
306
|
+
* Shows "No items found" message.
|
|
307
|
+
*/
|
|
308
|
+
export const EmptyList = {
|
|
309
|
+
args: {
|
|
310
|
+
possibles: [],
|
|
311
|
+
selected: [],
|
|
312
|
+
placeholder: 'No items available...'
|
|
313
|
+
}
|
|
314
|
+
};
|
|
315
|
+
/**
|
|
316
|
+
* Auto-focus on mount.
|
|
317
|
+
* Input is automatically focused when component renders.
|
|
318
|
+
*/
|
|
319
|
+
export const AutoFocus = {
|
|
320
|
+
args: {
|
|
321
|
+
possibles: sampleTags,
|
|
322
|
+
selected: [],
|
|
323
|
+
autoFocus: true,
|
|
324
|
+
placeholder: 'Auto-focused input...'
|
|
325
|
+
}
|
|
326
|
+
};
|
|
327
|
+
/**
|
|
328
|
+
* Custom styling with CSS classes.
|
|
329
|
+
*/
|
|
330
|
+
export const CustomStyling = {
|
|
331
|
+
args: {
|
|
332
|
+
possibles: sampleTags,
|
|
333
|
+
selected: [],
|
|
334
|
+
placeholder: 'Custom styled...',
|
|
335
|
+
controlClass: 'border-2 border-primary-main',
|
|
336
|
+
inputClass: 'text-primary-main font-bold'
|
|
337
|
+
}
|
|
338
|
+
};
|