sv5ui 1.2.0 → 1.3.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.
Files changed (37) hide show
  1. package/dist/CheckboxGroup/CheckboxGroup.svelte +215 -0
  2. package/dist/CheckboxGroup/CheckboxGroup.svelte.d.ts +5 -0
  3. package/dist/CheckboxGroup/checkbox-group.types.d.ts +130 -0
  4. package/dist/CheckboxGroup/checkbox-group.types.js +1 -0
  5. package/dist/CheckboxGroup/checkbox-group.variants.d.ts +553 -0
  6. package/dist/CheckboxGroup/checkbox-group.variants.js +231 -0
  7. package/dist/CheckboxGroup/index.d.ts +2 -0
  8. package/dist/CheckboxGroup/index.js +1 -0
  9. package/dist/FileUpload/FileUpload.svelte +561 -0
  10. package/dist/FileUpload/FileUpload.svelte.d.ts +8 -0
  11. package/dist/FileUpload/file-upload.types.d.ts +164 -0
  12. package/dist/FileUpload/file-upload.types.js +1 -0
  13. package/dist/FileUpload/file-upload.variants.d.ts +397 -0
  14. package/dist/FileUpload/file-upload.variants.js +224 -0
  15. package/dist/FileUpload/index.d.ts +2 -0
  16. package/dist/FileUpload/index.js +1 -0
  17. package/dist/PinInput/PinInput.svelte +150 -0
  18. package/dist/PinInput/PinInput.svelte.d.ts +6 -0
  19. package/dist/PinInput/index.d.ts +2 -0
  20. package/dist/PinInput/index.js +1 -0
  21. package/dist/PinInput/pin-input.types.d.ts +99 -0
  22. package/dist/PinInput/pin-input.types.js +1 -0
  23. package/dist/PinInput/pin-input.variants.d.ts +303 -0
  24. package/dist/PinInput/pin-input.variants.js +196 -0
  25. package/dist/Slider/Slider.svelte +135 -0
  26. package/dist/Slider/Slider.svelte.d.ts +6 -0
  27. package/dist/Slider/index.d.ts +2 -0
  28. package/dist/Slider/index.js +1 -0
  29. package/dist/Slider/slider.types.d.ts +55 -0
  30. package/dist/Slider/slider.types.js +1 -0
  31. package/dist/Slider/slider.variants.d.ts +383 -0
  32. package/dist/Slider/slider.variants.js +102 -0
  33. package/dist/config.d.ts +4 -0
  34. package/dist/config.js +5 -1
  35. package/dist/index.d.ts +4 -0
  36. package/dist/index.js +4 -0
  37. package/package.json +1 -1
@@ -0,0 +1,215 @@
1
+ <script lang="ts" module>
2
+ import type { CheckboxGroupProps } from './checkbox-group.types.js'
3
+
4
+ export type Props = CheckboxGroupProps
5
+ </script>
6
+
7
+ <script lang="ts">
8
+ import { Checkbox, Label, useId } from 'bits-ui'
9
+ import { checkboxGroupVariants, checkboxGroupDefaults } from './checkbox-group.variants.js'
10
+ import { getComponentConfig, iconsDefaults } from '../config.js'
11
+ import { getContext } from 'svelte'
12
+ import Icon from '../Icon/Icon.svelte'
13
+ import type { FormFieldProps } from '../FormField/form-field.types.js'
14
+ import type { CheckboxGroupItem } from './checkbox-group.types.js'
15
+
16
+ const config = getComponentConfig('checkboxGroup', checkboxGroupDefaults)
17
+ const icons = getComponentConfig('icons', iconsDefaults)
18
+
19
+ let {
20
+ ref = $bindable(null),
21
+ value = $bindable([]),
22
+ onValueChange,
23
+ items = [],
24
+ ui,
25
+ id,
26
+ name,
27
+ color = config.defaultVariants.color,
28
+ size,
29
+ variant = config.defaultVariants.variant,
30
+ indicator = config.defaultVariants.indicator,
31
+ orientation = config.defaultVariants.orientation,
32
+ disabled = false,
33
+ required = false,
34
+ loading = false,
35
+ loadingIcon = icons.loading,
36
+ icon = icons.check,
37
+ legend,
38
+ legendSlot,
39
+ labelSlot,
40
+ descriptionSlot,
41
+ class: className,
42
+ ...restProps
43
+ }: Props = $props()
44
+
45
+ const formFieldContext = getContext<
46
+ | {
47
+ name?: string
48
+ size: NonNullable<FormFieldProps['size']>
49
+ error?: string | boolean
50
+ ariaId: string
51
+ }
52
+ | undefined
53
+ >('formField')
54
+
55
+ const hasError = $derived(
56
+ formFieldContext?.error !== undefined && formFieldContext?.error !== false
57
+ )
58
+ const resolvedSize = $derived(size ?? formFieldContext?.size ?? config.defaultVariants.size)
59
+ const resolvedColor = $derived(hasError ? 'error' : color)
60
+ const autoId = useId()
61
+ const resolvedId = $derived(id ?? formFieldContext?.ariaId ?? autoId)
62
+ const resolvedName = $derived(name ?? formFieldContext?.name)
63
+ const isDisabled = $derived(disabled || loading)
64
+
65
+ const ariaDescribedBy = $derived(
66
+ !formFieldContext
67
+ ? undefined
68
+ : hasError
69
+ ? `${formFieldContext.ariaId}-error`
70
+ : `${formFieldContext.ariaId}-description ${formFieldContext.ariaId}-help`
71
+ )
72
+
73
+ const slots = $derived(
74
+ checkboxGroupVariants({
75
+ color: resolvedColor,
76
+ size: resolvedSize,
77
+ variant,
78
+ indicator,
79
+ orientation,
80
+ loading,
81
+ required,
82
+ disabled: isDisabled ? true : undefined
83
+ })
84
+ )
85
+
86
+ const layoutClasses = $derived.by(() => ({
87
+ root: slots.root({ class: [config.slots.root, className, ui?.root] }),
88
+ fieldset: slots.fieldset({ class: [config.slots.fieldset, ui?.fieldset] }),
89
+ legend: slots.legend({ class: [config.slots.legend, ui?.legend] }),
90
+ item: slots.item({ class: [config.slots.item, ui?.item] }),
91
+ container: slots.container({ class: [config.slots.container, ui?.container] }),
92
+ wrapper: slots.wrapper({ class: [config.slots.wrapper, ui?.wrapper] })
93
+ }))
94
+
95
+ const elementClasses = $derived.by(() => ({
96
+ base: slots.base({ class: [config.slots.base, ui?.base] }),
97
+ indicator: slots.indicator({ class: [config.slots.indicator, ui?.indicator] }),
98
+ icon: slots.icon({ class: [config.slots.icon, ui?.icon] }),
99
+ label: slots.label({ class: [config.slots.label, ui?.label] }),
100
+ description: slots.description({ class: [config.slots.description, ui?.description] })
101
+ }))
102
+
103
+ function toggleItem(itemValue: string, checked: boolean) {
104
+ if (checked) {
105
+ value = [...value, itemValue]
106
+ } else {
107
+ value = value.filter((v) => v !== itemValue)
108
+ }
109
+ onValueChange?.(value)
110
+ }
111
+
112
+ function handleCardItemClick(e: MouseEvent, btnId: string, itemDisabled: boolean) {
113
+ if (itemDisabled) return
114
+ if ((e.target as Element).closest('button')) return
115
+ document.getElementById(btnId)?.click()
116
+ }
117
+ </script>
118
+
119
+ {#snippet itemContent(checkboxItem: CheckboxGroupItem)}
120
+ {@const itemId = `${resolvedId}-${checkboxItem.value}`}
121
+ {@const itemDisabled = isDisabled || !!checkboxItem.disabled}
122
+ <div class={layoutClasses.container}>
123
+ <Checkbox.Root
124
+ checked={value.includes(checkboxItem.value)}
125
+ onCheckedChange={(checked) => toggleItem(checkboxItem.value, checked)}
126
+ id={itemId}
127
+ name={resolvedName}
128
+ value={checkboxItem.value}
129
+ disabled={itemDisabled}
130
+ class={elementClasses.base}
131
+ >
132
+ {#snippet children({ checked: isChecked })}
133
+ {#if isChecked || loading}
134
+ <span class={elementClasses.indicator}>
135
+ <Icon name={loading ? loadingIcon : icon} class={elementClasses.icon} />
136
+ </span>
137
+ {/if}
138
+ {/snippet}
139
+ </Checkbox.Root>
140
+ </div>
141
+
142
+ {#if checkboxItem.label || checkboxItem.description || labelSlot || descriptionSlot}
143
+ <div class={layoutClasses.wrapper}>
144
+ {#if labelSlot}
145
+ {@render labelSlot({ item: checkboxItem })}
146
+ {:else if checkboxItem.label}
147
+ {#if variant === 'card'}
148
+ <span
149
+ class={[elementClasses.label, itemDisabled && 'cursor-not-allowed']
150
+ .filter(Boolean)
151
+ .join(' ')}>{checkboxItem.label}</span
152
+ >
153
+ {:else}
154
+ <Label.Root
155
+ for={itemId}
156
+ class={[elementClasses.label, itemDisabled && 'cursor-not-allowed']
157
+ .filter(Boolean)
158
+ .join(' ')}
159
+ >
160
+ {checkboxItem.label}
161
+ </Label.Root>
162
+ {/if}
163
+ {/if}
164
+
165
+ {#if descriptionSlot}
166
+ {@render descriptionSlot({ item: checkboxItem })}
167
+ {:else if checkboxItem.description}
168
+ <p
169
+ class={[elementClasses.description, itemDisabled && 'cursor-not-allowed']
170
+ .filter(Boolean)
171
+ .join(' ')}
172
+ >
173
+ {checkboxItem.description}
174
+ </p>
175
+ {/if}
176
+ </div>
177
+ {/if}
178
+ {/snippet}
179
+
180
+ <div {...restProps} bind:this={ref} class={layoutClasses.root}>
181
+ <fieldset class={layoutClasses.fieldset} aria-describedby={ariaDescribedBy}>
182
+ {#if legend || legendSlot}
183
+ {#if legendSlot}
184
+ {@render legendSlot({ legend })}
185
+ {:else}
186
+ <legend class={layoutClasses.legend}>{legend}</legend>
187
+ {/if}
188
+ {/if}
189
+
190
+ {#each items as checkboxItem (checkboxItem.value)}
191
+ {#if variant === 'card'}
192
+ <div
193
+ role="none"
194
+ class={layoutClasses.item}
195
+ class:opacity-75={checkboxItem.disabled && !isDisabled}
196
+ onclick={(e) =>
197
+ handleCardItemClick(
198
+ e,
199
+ `${resolvedId}-${checkboxItem.value}`,
200
+ isDisabled || !!checkboxItem.disabled
201
+ )}
202
+ >
203
+ {@render itemContent(checkboxItem)}
204
+ </div>
205
+ {:else}
206
+ <div
207
+ class={layoutClasses.item}
208
+ class:opacity-75={checkboxItem.disabled && !isDisabled}
209
+ >
210
+ {@render itemContent(checkboxItem)}
211
+ </div>
212
+ {/if}
213
+ {/each}
214
+ </fieldset>
215
+ </div>
@@ -0,0 +1,5 @@
1
+ import type { CheckboxGroupProps } from './checkbox-group.types.js';
2
+ export type Props = CheckboxGroupProps;
3
+ declare const CheckboxGroup: import("svelte").Component<CheckboxGroupProps, {}, "ref" | "value">;
4
+ type CheckboxGroup = ReturnType<typeof CheckboxGroup>;
5
+ export default CheckboxGroup;
@@ -0,0 +1,130 @@
1
+ import type { Snippet } from 'svelte';
2
+ import type { HTMLAttributes } from 'svelte/elements';
3
+ import type { ClassNameValue } from 'tailwind-merge';
4
+ import type { CheckboxGroupVariantProps, CheckboxGroupSlots } from './checkbox-group.variants.js';
5
+ export type CheckboxGroupItem = {
6
+ /**
7
+ * The unique value for this checkbox item.
8
+ */
9
+ value: string;
10
+ /**
11
+ * Label text displayed next to the checkbox.
12
+ */
13
+ label?: string;
14
+ /**
15
+ * Description text displayed below the label.
16
+ */
17
+ description?: string;
18
+ /**
19
+ * Whether this individual checkbox item is disabled.
20
+ * @default false
21
+ */
22
+ disabled?: boolean;
23
+ };
24
+ export type CheckboxGroupProps = Omit<HTMLAttributes<HTMLElement>, 'class'> & {
25
+ /**
26
+ * Bindable reference to the root DOM element.
27
+ */
28
+ ref?: HTMLElement | null;
29
+ /**
30
+ * The list of selected values. Supports two-way binding with `bind:value`.
31
+ * @default []
32
+ */
33
+ value?: string[];
34
+ /**
35
+ * Callback when the selected values change.
36
+ */
37
+ onValueChange?: (value: string[]) => void;
38
+ /**
39
+ * The list of checkbox items to render.
40
+ */
41
+ items?: CheckboxGroupItem[];
42
+ /**
43
+ * Sets the color scheme for the checkboxes.
44
+ * @default 'primary'
45
+ */
46
+ color?: NonNullable<CheckboxGroupVariantProps['color']>;
47
+ /**
48
+ * Controls the dimensions of the checkbox group.
49
+ * @default 'md'
50
+ */
51
+ size?: NonNullable<CheckboxGroupVariantProps['size']>;
52
+ /**
53
+ * Controls the visual style of each checkbox item.
54
+ * @default 'list'
55
+ */
56
+ variant?: NonNullable<CheckboxGroupVariantProps['variant']>;
57
+ /**
58
+ * Controls the position of the checkbox indicator.
59
+ * @default 'start'
60
+ */
61
+ indicator?: NonNullable<CheckboxGroupVariantProps['indicator']>;
62
+ /**
63
+ * Controls the layout direction of the items.
64
+ * @default 'vertical'
65
+ */
66
+ orientation?: NonNullable<CheckboxGroupVariantProps['orientation']>;
67
+ /**
68
+ * The name attribute for the checkbox inputs (used in form submission).
69
+ */
70
+ name?: string;
71
+ /**
72
+ * Whether the checkbox group is disabled.
73
+ * @default false
74
+ */
75
+ disabled?: boolean;
76
+ /**
77
+ * Whether the checkbox group is required.
78
+ * @default false
79
+ */
80
+ required?: boolean;
81
+ /**
82
+ * Renders a loading spinner and disables interaction.
83
+ * @default false
84
+ */
85
+ loading?: boolean;
86
+ /**
87
+ * Icon displayed as the loading indicator.
88
+ * @default Uses `icons.loading` from app config
89
+ */
90
+ loadingIcon?: string;
91
+ /**
92
+ * Icon displayed when a checkbox is checked.
93
+ * @default Uses `icons.check` from app config
94
+ */
95
+ icon?: string;
96
+ /**
97
+ * Legend text displayed above the checkbox group.
98
+ */
99
+ legend?: string;
100
+ /**
101
+ * The HTML id attribute for the checkbox group.
102
+ */
103
+ id?: string;
104
+ /**
105
+ * Custom snippet for the legend.
106
+ */
107
+ legendSlot?: Snippet<[{
108
+ legend?: string;
109
+ }]>;
110
+ /**
111
+ * Custom snippet for each item's label.
112
+ */
113
+ labelSlot?: Snippet<[{
114
+ item: CheckboxGroupItem;
115
+ }]>;
116
+ /**
117
+ * Custom snippet for each item's description.
118
+ */
119
+ descriptionSlot?: Snippet<[{
120
+ item: CheckboxGroupItem;
121
+ }]>;
122
+ /**
123
+ * Additional CSS classes for the root element.
124
+ */
125
+ class?: ClassNameValue;
126
+ /**
127
+ * Override styles for specific checkbox group slots.
128
+ */
129
+ ui?: Partial<Record<CheckboxGroupSlots, ClassNameValue>>;
130
+ };
@@ -0,0 +1 @@
1
+ export {};