@casinogate/ui 1.11.7 → 1.11.8
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/assets/css/root.css +21 -0
- package/dist/components/file-upload/components/file-upload.clear-trigger.svelte +30 -0
- package/dist/components/file-upload/components/file-upload.clear-trigger.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.context.svelte +10 -0
- package/dist/components/file-upload/components/file-upload.context.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.dropzone.svelte +72 -0
- package/dist/components/file-upload/components/file-upload.dropzone.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.hidden-input.svelte +35 -0
- package/dist/components/file-upload/components/file-upload.hidden-input.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item-delete-trigger.svelte +31 -0
- package/dist/components/file-upload/components/file-upload.item-delete-trigger.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item-group.svelte +21 -0
- package/dist/components/file-upload/components/file-upload.item-group.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item-name.svelte +28 -0
- package/dist/components/file-upload/components/file-upload.item-name.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item-preview-image.svelte +33 -0
- package/dist/components/file-upload/components/file-upload.item-preview-image.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item-preview.svelte +29 -0
- package/dist/components/file-upload/components/file-upload.item-preview.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item-size-text.svelte +28 -0
- package/dist/components/file-upload/components/file-upload.item-size-text.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.item.svelte +29 -0
- package/dist/components/file-upload/components/file-upload.item.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.root.svelte +47 -0
- package/dist/components/file-upload/components/file-upload.root.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/file-upload.svelte.d.ts +41 -0
- package/dist/components/file-upload/components/file-upload.svelte.js +120 -0
- package/dist/components/file-upload/components/file-upload.trigger.svelte +31 -0
- package/dist/components/file-upload/components/file-upload.trigger.svelte.d.ts +4 -0
- package/dist/components/file-upload/components/index.d.ts +13 -0
- package/dist/components/file-upload/components/index.js +13 -0
- package/dist/components/file-upload/composed/index.d.ts +1 -0
- package/dist/components/file-upload/composed/index.js +1 -0
- package/dist/components/file-upload/composed/root/file-upload.root.svelte +36 -0
- package/dist/components/file-upload/composed/root/file-upload.root.svelte.d.ts +4 -0
- package/dist/components/file-upload/composed/root/index.d.ts +1 -0
- package/dist/components/file-upload/composed/root/index.js +1 -0
- package/dist/components/file-upload/index.d.ts +3 -0
- package/dist/components/file-upload/index.js +3 -0
- package/dist/components/file-upload/styles.d.ts +80 -0
- package/dist/components/file-upload/styles.js +68 -0
- package/dist/components/file-upload/types.d.ts +83 -0
- package/dist/components/file-upload/types.js +1 -0
- package/package.json +1 -1
package/dist/assets/css/root.css
CHANGED
|
@@ -248,6 +248,9 @@
|
|
|
248
248
|
.cgui\:\!m-0 {
|
|
249
249
|
margin: calc(var(--cgui-spacing) * 0) !important;
|
|
250
250
|
}
|
|
251
|
+
.cgui\:m-0 {
|
|
252
|
+
margin: calc(var(--cgui-spacing) * 0);
|
|
253
|
+
}
|
|
251
254
|
.cgui\:mx-1 {
|
|
252
255
|
margin-inline: calc(var(--cgui-spacing) * 1);
|
|
253
256
|
}
|
|
@@ -454,6 +457,9 @@
|
|
|
454
457
|
.cgui\:h-34 {
|
|
455
458
|
height: calc(var(--cgui-spacing) * 34);
|
|
456
459
|
}
|
|
460
|
+
.cgui\:h-40 {
|
|
461
|
+
height: calc(var(--cgui-spacing) * 40);
|
|
462
|
+
}
|
|
457
463
|
.cgui\:h-100 {
|
|
458
464
|
height: calc(var(--cgui-spacing) * 100);
|
|
459
465
|
}
|
|
@@ -712,6 +718,9 @@
|
|
|
712
718
|
.cgui\:scroll-py-1 {
|
|
713
719
|
scroll-padding-block: calc(var(--cgui-spacing) * 1);
|
|
714
720
|
}
|
|
721
|
+
.cgui\:list-none {
|
|
722
|
+
list-style-type: none;
|
|
723
|
+
}
|
|
715
724
|
.cgui\:flex-col {
|
|
716
725
|
flex-direction: column;
|
|
717
726
|
}
|
|
@@ -1020,6 +1029,12 @@
|
|
|
1020
1029
|
.cgui\:bg-surface-primary-light-active {
|
|
1021
1030
|
background-color: var(--cg-ui-color-surface-primary-light-active);
|
|
1022
1031
|
}
|
|
1032
|
+
.cgui\:bg-surface-primary\/5 {
|
|
1033
|
+
background-color: var(--cg-ui-color-surface-primary);
|
|
1034
|
+
@supports (color: color-mix(in lab, red, red)) {
|
|
1035
|
+
background-color: color-mix(in oklab, var(--cg-ui-color-surface-primary) 5%, transparent);
|
|
1036
|
+
}
|
|
1037
|
+
}
|
|
1023
1038
|
.cgui\:bg-surface-regular {
|
|
1024
1039
|
background-color: var(--cg-ui-color-surface-regular);
|
|
1025
1040
|
}
|
|
@@ -1053,6 +1068,12 @@
|
|
|
1053
1068
|
.cgui\:bg-clip-padding {
|
|
1054
1069
|
background-clip: padding-box;
|
|
1055
1070
|
}
|
|
1071
|
+
.cgui\:object-contain {
|
|
1072
|
+
object-fit: contain;
|
|
1073
|
+
}
|
|
1074
|
+
.cgui\:object-cover {
|
|
1075
|
+
object-fit: cover;
|
|
1076
|
+
}
|
|
1056
1077
|
.cgui\:p-0 {
|
|
1057
1078
|
padding: calc(var(--cgui-spacing) * 0);
|
|
1058
1079
|
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveClearTriggerStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveClearTriggerProps } from '../types.js';
|
|
5
|
+
import { FileUploadRootContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
children,
|
|
10
|
+
class: className,
|
|
11
|
+
...restProps
|
|
12
|
+
}: FileUploadPrimitiveClearTriggerProps = $props();
|
|
13
|
+
|
|
14
|
+
const rootState = FileUploadRootContext.get();
|
|
15
|
+
|
|
16
|
+
function handleClick() {
|
|
17
|
+
rootState.clearFiles();
|
|
18
|
+
}
|
|
19
|
+
</script>
|
|
20
|
+
|
|
21
|
+
<button
|
|
22
|
+
bind:this={ref}
|
|
23
|
+
type="button"
|
|
24
|
+
class={cn(fileUploadPrimitiveClearTriggerStyles(), className)}
|
|
25
|
+
data-slot="file-upload-clear-trigger"
|
|
26
|
+
onclick={handleClick}
|
|
27
|
+
{...restProps}
|
|
28
|
+
>
|
|
29
|
+
{@render children?.()}
|
|
30
|
+
</button>
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import type { FileUploadPrimitiveContextProps } from '../types.js';
|
|
3
|
+
import { FileUploadRootContext } from './file-upload.svelte.js';
|
|
4
|
+
|
|
5
|
+
const { children }: FileUploadPrimitiveContextProps = $props();
|
|
6
|
+
|
|
7
|
+
const context = FileUploadRootContext.get();
|
|
8
|
+
</script>
|
|
9
|
+
|
|
10
|
+
{@render children?.(context)}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveDropzoneStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveDropzoneProps } from '../types.js';
|
|
5
|
+
import { FileUploadRootContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
disableClick = false,
|
|
10
|
+
children,
|
|
11
|
+
class: className,
|
|
12
|
+
...restProps
|
|
13
|
+
}: FileUploadPrimitiveDropzoneProps = $props();
|
|
14
|
+
|
|
15
|
+
const rootState = FileUploadRootContext.get();
|
|
16
|
+
|
|
17
|
+
function handleDragEnter(e: DragEvent) {
|
|
18
|
+
e.preventDefault();
|
|
19
|
+
e.stopPropagation();
|
|
20
|
+
rootState.dragging = true;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
function handleDragLeave(e: DragEvent) {
|
|
24
|
+
e.preventDefault();
|
|
25
|
+
e.stopPropagation();
|
|
26
|
+
rootState.dragging = false;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
function handleDragOver(e: DragEvent) {
|
|
30
|
+
e.preventDefault();
|
|
31
|
+
e.stopPropagation();
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
function handleDrop(e: DragEvent) {
|
|
35
|
+
e.preventDefault();
|
|
36
|
+
e.stopPropagation();
|
|
37
|
+
rootState.dragging = false;
|
|
38
|
+
|
|
39
|
+
if (e.dataTransfer?.files) {
|
|
40
|
+
rootState.addFiles(e.dataTransfer.files);
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
function handleClick() {
|
|
45
|
+
if (!disableClick) {
|
|
46
|
+
rootState.openFilePicker();
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
</script>
|
|
50
|
+
|
|
51
|
+
<div
|
|
52
|
+
bind:this={ref}
|
|
53
|
+
role="presentation"
|
|
54
|
+
class={cn(
|
|
55
|
+
fileUploadPrimitiveDropzoneStyles({
|
|
56
|
+
dragging: rootState.dragging,
|
|
57
|
+
invalid: rootState.opts.invalid.current,
|
|
58
|
+
disabled: rootState.opts.disabled.current,
|
|
59
|
+
}),
|
|
60
|
+
className,
|
|
61
|
+
)}
|
|
62
|
+
data-slot="file-upload-dropzone"
|
|
63
|
+
data-dragging={rootState.dragging || undefined}
|
|
64
|
+
ondragenter={handleDragEnter}
|
|
65
|
+
ondragleave={handleDragLeave}
|
|
66
|
+
ondragover={handleDragOver}
|
|
67
|
+
ondrop={handleDrop}
|
|
68
|
+
onclick={handleClick}
|
|
69
|
+
{...restProps}
|
|
70
|
+
>
|
|
71
|
+
{@render children?.()}
|
|
72
|
+
</div>
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import type { FileUploadPrimitiveHiddenInputProps } from '../types.js';
|
|
3
|
+
import { FileUploadRootContext } from './file-upload.svelte.js';
|
|
4
|
+
|
|
5
|
+
let { ref = $bindable(null), ...restProps }: FileUploadPrimitiveHiddenInputProps = $props();
|
|
6
|
+
|
|
7
|
+
const rootState = FileUploadRootContext.get();
|
|
8
|
+
|
|
9
|
+
let inputEl = $state<HTMLInputElement | null>(null);
|
|
10
|
+
|
|
11
|
+
$effect(() => {
|
|
12
|
+
rootState.setHiddenInput(inputEl);
|
|
13
|
+
});
|
|
14
|
+
|
|
15
|
+
function handleChange(e: Event) {
|
|
16
|
+
const input = e.target as HTMLInputElement;
|
|
17
|
+
if (input.files) {
|
|
18
|
+
rootState.addFiles(input.files);
|
|
19
|
+
input.value = '';
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
</script>
|
|
23
|
+
|
|
24
|
+
<input
|
|
25
|
+
bind:this={inputEl}
|
|
26
|
+
type="file"
|
|
27
|
+
tabindex={-1}
|
|
28
|
+
style="position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0, 0, 0, 0); white-space: nowrap; border: 0;"
|
|
29
|
+
data-slot="file-upload-hidden-input"
|
|
30
|
+
accept={rootState.opts.accept.current}
|
|
31
|
+
multiple={rootState.opts.maxFiles.current > 1}
|
|
32
|
+
disabled={rootState.opts.disabled.current}
|
|
33
|
+
onchange={handleChange}
|
|
34
|
+
{...restProps}
|
|
35
|
+
/>
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveItemDeleteTriggerStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveItemDeleteTriggerProps } from '../types.js';
|
|
5
|
+
import { FileUploadItemContext, FileUploadRootContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
children,
|
|
10
|
+
class: className,
|
|
11
|
+
...restProps
|
|
12
|
+
}: FileUploadPrimitiveItemDeleteTriggerProps = $props();
|
|
13
|
+
|
|
14
|
+
const rootState = FileUploadRootContext.get();
|
|
15
|
+
const itemState = FileUploadItemContext.get();
|
|
16
|
+
|
|
17
|
+
function handleClick() {
|
|
18
|
+
rootState.removeFile(itemState.opts.file.current);
|
|
19
|
+
}
|
|
20
|
+
</script>
|
|
21
|
+
|
|
22
|
+
<button
|
|
23
|
+
bind:this={ref}
|
|
24
|
+
type="button"
|
|
25
|
+
class={cn(fileUploadPrimitiveItemDeleteTriggerStyles(), className)}
|
|
26
|
+
data-slot="file-upload-item-delete-trigger"
|
|
27
|
+
onclick={handleClick}
|
|
28
|
+
{...restProps}
|
|
29
|
+
>
|
|
30
|
+
{@render children?.()}
|
|
31
|
+
</button>
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveItemGroupStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveItemGroupProps } from '../types.js';
|
|
5
|
+
|
|
6
|
+
let {
|
|
7
|
+
ref = $bindable(null),
|
|
8
|
+
children,
|
|
9
|
+
class: className,
|
|
10
|
+
...restProps
|
|
11
|
+
}: FileUploadPrimitiveItemGroupProps = $props();
|
|
12
|
+
</script>
|
|
13
|
+
|
|
14
|
+
<ul
|
|
15
|
+
bind:this={ref}
|
|
16
|
+
class={cn(fileUploadPrimitiveItemGroupStyles(), className)}
|
|
17
|
+
data-slot="file-upload-item-group"
|
|
18
|
+
{...restProps}
|
|
19
|
+
>
|
|
20
|
+
{@render children?.()}
|
|
21
|
+
</ul>
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveItemNameStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveItemNameProps } from '../types.js';
|
|
5
|
+
import { FileUploadItemContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
children,
|
|
10
|
+
class: className,
|
|
11
|
+
...restProps
|
|
12
|
+
}: FileUploadPrimitiveItemNameProps = $props();
|
|
13
|
+
|
|
14
|
+
const itemState = FileUploadItemContext.get();
|
|
15
|
+
</script>
|
|
16
|
+
|
|
17
|
+
<div
|
|
18
|
+
bind:this={ref}
|
|
19
|
+
class={cn(fileUploadPrimitiveItemNameStyles(), className)}
|
|
20
|
+
data-slot="file-upload-item-name"
|
|
21
|
+
{...restProps}
|
|
22
|
+
>
|
|
23
|
+
{#if children}
|
|
24
|
+
{@render children()}
|
|
25
|
+
{:else}
|
|
26
|
+
{itemState.opts.file.current.name}
|
|
27
|
+
{/if}
|
|
28
|
+
</div>
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveItemPreviewImageStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveItemPreviewImageProps } from '../types.js';
|
|
5
|
+
import { FileUploadItemContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let { ref = $bindable(null), class: className, ...restProps }: FileUploadPrimitiveItemPreviewImageProps = $props();
|
|
8
|
+
|
|
9
|
+
const itemState = FileUploadItemContext.get();
|
|
10
|
+
|
|
11
|
+
let url = $state<string | undefined>(undefined);
|
|
12
|
+
|
|
13
|
+
$effect(() => {
|
|
14
|
+
const file = itemState.opts.file.current;
|
|
15
|
+
const objectUrl = URL.createObjectURL(file);
|
|
16
|
+
url = objectUrl;
|
|
17
|
+
|
|
18
|
+
return () => {
|
|
19
|
+
URL.revokeObjectURL(objectUrl);
|
|
20
|
+
};
|
|
21
|
+
});
|
|
22
|
+
</script>
|
|
23
|
+
|
|
24
|
+
{#if url}
|
|
25
|
+
<img
|
|
26
|
+
bind:this={ref}
|
|
27
|
+
src={url}
|
|
28
|
+
alt={itemState.opts.file.current.name}
|
|
29
|
+
class={cn(fileUploadPrimitiveItemPreviewImageStyles(), className)}
|
|
30
|
+
data-slot="file-upload-item-preview-image"
|
|
31
|
+
{...restProps}
|
|
32
|
+
/>
|
|
33
|
+
{/if}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveItemPreviewStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveItemPreviewProps } from '../types.js';
|
|
5
|
+
import { FileUploadItemContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
type = '.*',
|
|
10
|
+
children,
|
|
11
|
+
class: className,
|
|
12
|
+
...restProps
|
|
13
|
+
}: FileUploadPrimitiveItemPreviewProps = $props();
|
|
14
|
+
|
|
15
|
+
const itemState = FileUploadItemContext.get();
|
|
16
|
+
|
|
17
|
+
const isMatch = $derived(Boolean(itemState.opts.file.current.type.match(type)));
|
|
18
|
+
</script>
|
|
19
|
+
|
|
20
|
+
{#if isMatch}
|
|
21
|
+
<div
|
|
22
|
+
bind:this={ref}
|
|
23
|
+
class={cn(fileUploadPrimitiveItemPreviewStyles(), className)}
|
|
24
|
+
data-slot="file-upload-item-preview"
|
|
25
|
+
{...restProps}
|
|
26
|
+
>
|
|
27
|
+
{@render children?.()}
|
|
28
|
+
</div>
|
|
29
|
+
{/if}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveItemSizeTextStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveItemSizeTextProps } from '../types.js';
|
|
5
|
+
import { FileUploadItemContext, formatFileSize } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
children,
|
|
10
|
+
class: className,
|
|
11
|
+
...restProps
|
|
12
|
+
}: FileUploadPrimitiveItemSizeTextProps = $props();
|
|
13
|
+
|
|
14
|
+
const itemState = FileUploadItemContext.get();
|
|
15
|
+
</script>
|
|
16
|
+
|
|
17
|
+
<div
|
|
18
|
+
bind:this={ref}
|
|
19
|
+
class={cn(fileUploadPrimitiveItemSizeTextStyles(), className)}
|
|
20
|
+
data-slot="file-upload-item-size-text"
|
|
21
|
+
{...restProps}
|
|
22
|
+
>
|
|
23
|
+
{#if children}
|
|
24
|
+
{@render children()}
|
|
25
|
+
{:else}
|
|
26
|
+
{formatFileSize(itemState.opts.file.current.size)}
|
|
27
|
+
{/if}
|
|
28
|
+
</div>
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { box } from 'svelte-toolbelt';
|
|
4
|
+
import { fileUploadPrimitiveItemStyles } from '../styles.js';
|
|
5
|
+
import type { FileUploadPrimitiveItemProps } from '../types.js';
|
|
6
|
+
import { FileUploadItemState } from './file-upload.svelte.js';
|
|
7
|
+
|
|
8
|
+
let {
|
|
9
|
+
ref = $bindable(null),
|
|
10
|
+
file,
|
|
11
|
+
children,
|
|
12
|
+
class: className,
|
|
13
|
+
variant = 'default',
|
|
14
|
+
...restProps
|
|
15
|
+
}: FileUploadPrimitiveItemProps = $props();
|
|
16
|
+
|
|
17
|
+
FileUploadItemState.create({
|
|
18
|
+
file: box.with(() => file),
|
|
19
|
+
});
|
|
20
|
+
</script>
|
|
21
|
+
|
|
22
|
+
<li
|
|
23
|
+
bind:this={ref}
|
|
24
|
+
class={cn(fileUploadPrimitiveItemStyles({ variant }), className)}
|
|
25
|
+
data-slot="file-upload-item"
|
|
26
|
+
{...restProps}
|
|
27
|
+
>
|
|
28
|
+
{@render children?.()}
|
|
29
|
+
</li>
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { box } from 'svelte-toolbelt';
|
|
4
|
+
import { fileUploadPrimitiveRootStyles } from '../styles.js';
|
|
5
|
+
import type { FileUploadPrimitiveRootProps } from '../types.js';
|
|
6
|
+
import { FileUploadRootState } from './file-upload.svelte.js';
|
|
7
|
+
|
|
8
|
+
let {
|
|
9
|
+
ref = $bindable(null),
|
|
10
|
+
accept,
|
|
11
|
+
maxFiles = 1,
|
|
12
|
+
maxFileSize = Infinity,
|
|
13
|
+
disabled = false,
|
|
14
|
+
invalid = false,
|
|
15
|
+
onFileAccept,
|
|
16
|
+
onFileReject,
|
|
17
|
+
onFileChange,
|
|
18
|
+
children,
|
|
19
|
+
class: className,
|
|
20
|
+
...restProps
|
|
21
|
+
}: FileUploadPrimitiveRootProps = $props();
|
|
22
|
+
|
|
23
|
+
const rootState = FileUploadRootState.create({
|
|
24
|
+
accept: box.with(() => accept),
|
|
25
|
+
maxFiles: box.with(() => maxFiles),
|
|
26
|
+
maxFileSize: box.with(() => maxFileSize),
|
|
27
|
+
disabled: box.with(() => disabled),
|
|
28
|
+
invalid: box.with(() => invalid),
|
|
29
|
+
});
|
|
30
|
+
|
|
31
|
+
$effect(() => {
|
|
32
|
+
rootState.onFileAccept = onFileAccept;
|
|
33
|
+
rootState.onFileReject = onFileReject;
|
|
34
|
+
rootState.onFileChange = onFileChange;
|
|
35
|
+
});
|
|
36
|
+
</script>
|
|
37
|
+
|
|
38
|
+
<div
|
|
39
|
+
bind:this={ref}
|
|
40
|
+
class={cn(fileUploadPrimitiveRootStyles({ disabled }), className)}
|
|
41
|
+
data-slot="file-upload-root"
|
|
42
|
+
data-disabled={disabled || undefined}
|
|
43
|
+
data-dragging={rootState.dragging || undefined}
|
|
44
|
+
{...restProps}
|
|
45
|
+
>
|
|
46
|
+
{@render children?.()}
|
|
47
|
+
</div>
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { Context } from 'runed';
|
|
2
|
+
import type { ReadableBoxedValues } from 'svelte-toolbelt';
|
|
3
|
+
import type { FileAcceptDetails, FileChangeDetails, FileRejectDetails, RejectedFile } from '../types.js';
|
|
4
|
+
export declare const FileUploadRootContext: Context<FileUploadRootState>;
|
|
5
|
+
type FileUploadRootStateOpts = ReadableBoxedValues<{
|
|
6
|
+
accept: string | undefined;
|
|
7
|
+
maxFiles: number;
|
|
8
|
+
maxFileSize: number;
|
|
9
|
+
disabled: boolean;
|
|
10
|
+
invalid: boolean;
|
|
11
|
+
}>;
|
|
12
|
+
export declare class FileUploadRootState {
|
|
13
|
+
static create(opts: FileUploadRootStateOpts): FileUploadRootState;
|
|
14
|
+
readonly opts: FileUploadRootStateOpts;
|
|
15
|
+
acceptedFiles: File[];
|
|
16
|
+
rejectedFiles: RejectedFile[];
|
|
17
|
+
dragging: boolean;
|
|
18
|
+
onFileAccept?: (details: FileAcceptDetails) => void;
|
|
19
|
+
onFileReject?: (details: FileRejectDetails) => void;
|
|
20
|
+
onFileChange?: (details: FileChangeDetails) => void;
|
|
21
|
+
private hiddenInputRef;
|
|
22
|
+
constructor(opts: FileUploadRootStateOpts);
|
|
23
|
+
setHiddenInput(input: HTMLInputElement | null): void;
|
|
24
|
+
openFilePicker(): void;
|
|
25
|
+
addFiles(files: FileList | File[]): void;
|
|
26
|
+
removeFile(file: File): void;
|
|
27
|
+
clearFiles(): void;
|
|
28
|
+
private validateFile;
|
|
29
|
+
private matchesAccept;
|
|
30
|
+
}
|
|
31
|
+
export declare const FileUploadItemContext: Context<FileUploadItemState>;
|
|
32
|
+
type FileUploadItemStateOpts = ReadableBoxedValues<{
|
|
33
|
+
file: File;
|
|
34
|
+
}>;
|
|
35
|
+
export declare class FileUploadItemState {
|
|
36
|
+
static create(opts: FileUploadItemStateOpts): FileUploadItemState;
|
|
37
|
+
readonly opts: FileUploadItemStateOpts;
|
|
38
|
+
constructor(opts: FileUploadItemStateOpts);
|
|
39
|
+
}
|
|
40
|
+
export declare function formatFileSize(bytes: number): string;
|
|
41
|
+
export {};
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
import { keyWithPrefix } from '../../../internal/utils/common.js';
|
|
2
|
+
import { Context } from 'runed';
|
|
3
|
+
// --- Root State ---
|
|
4
|
+
export const FileUploadRootContext = new Context(keyWithPrefix('file-upload-root'));
|
|
5
|
+
export class FileUploadRootState {
|
|
6
|
+
static create(opts) {
|
|
7
|
+
return FileUploadRootContext.set(new FileUploadRootState(opts));
|
|
8
|
+
}
|
|
9
|
+
opts;
|
|
10
|
+
acceptedFiles = $state([]);
|
|
11
|
+
rejectedFiles = $state([]);
|
|
12
|
+
dragging = $state(false);
|
|
13
|
+
onFileAccept;
|
|
14
|
+
onFileReject;
|
|
15
|
+
onFileChange;
|
|
16
|
+
hiddenInputRef = null;
|
|
17
|
+
constructor(opts) {
|
|
18
|
+
this.opts = opts;
|
|
19
|
+
}
|
|
20
|
+
setHiddenInput(input) {
|
|
21
|
+
this.hiddenInputRef = input;
|
|
22
|
+
}
|
|
23
|
+
openFilePicker() {
|
|
24
|
+
this.hiddenInputRef?.click();
|
|
25
|
+
}
|
|
26
|
+
addFiles(files) {
|
|
27
|
+
const fileArray = Array.from(files);
|
|
28
|
+
const maxFiles = this.opts.maxFiles.current;
|
|
29
|
+
const accepted = [];
|
|
30
|
+
const rejected = [];
|
|
31
|
+
for (const file of fileArray) {
|
|
32
|
+
const errors = this.validateFile(file);
|
|
33
|
+
if (errors.length > 0) {
|
|
34
|
+
rejected.push({ file, errors });
|
|
35
|
+
}
|
|
36
|
+
else {
|
|
37
|
+
accepted.push(file);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
if (accepted.length > 0) {
|
|
41
|
+
const incoming = accepted.slice(0, maxFiles);
|
|
42
|
+
const overLimit = accepted.slice(maxFiles);
|
|
43
|
+
for (const file of overLimit) {
|
|
44
|
+
rejected.push({ file, errors: ['TOO_MANY_FILES'] });
|
|
45
|
+
}
|
|
46
|
+
this.acceptedFiles = this.acceptedFiles.length + incoming.length > maxFiles ? incoming : [...this.acceptedFiles, ...incoming];
|
|
47
|
+
this.onFileAccept?.({ files: incoming });
|
|
48
|
+
}
|
|
49
|
+
if (rejected.length > 0) {
|
|
50
|
+
this.rejectedFiles = [...this.rejectedFiles, ...rejected];
|
|
51
|
+
this.onFileReject?.({ files: rejected });
|
|
52
|
+
}
|
|
53
|
+
this.onFileChange?.({
|
|
54
|
+
acceptedFiles: this.acceptedFiles,
|
|
55
|
+
rejectedFiles: this.rejectedFiles,
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
removeFile(file) {
|
|
59
|
+
this.acceptedFiles = this.acceptedFiles.filter((f) => f !== file);
|
|
60
|
+
this.onFileChange?.({
|
|
61
|
+
acceptedFiles: this.acceptedFiles,
|
|
62
|
+
rejectedFiles: this.rejectedFiles,
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
clearFiles() {
|
|
66
|
+
this.acceptedFiles = [];
|
|
67
|
+
this.rejectedFiles = [];
|
|
68
|
+
this.onFileChange?.({
|
|
69
|
+
acceptedFiles: this.acceptedFiles,
|
|
70
|
+
rejectedFiles: this.rejectedFiles,
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
validateFile(file) {
|
|
74
|
+
const errors = [];
|
|
75
|
+
const maxFileSize = this.opts.maxFileSize.current;
|
|
76
|
+
if (file.size > maxFileSize) {
|
|
77
|
+
errors.push('FILE_TOO_LARGE');
|
|
78
|
+
}
|
|
79
|
+
const accept = this.opts.accept.current;
|
|
80
|
+
if (accept && !this.matchesAccept(file, accept)) {
|
|
81
|
+
errors.push('FILE_INVALID_TYPE');
|
|
82
|
+
}
|
|
83
|
+
return errors;
|
|
84
|
+
}
|
|
85
|
+
matchesAccept(file, accept) {
|
|
86
|
+
const acceptTokens = accept
|
|
87
|
+
.split(',')
|
|
88
|
+
.map((t) => t.trim())
|
|
89
|
+
.filter(Boolean);
|
|
90
|
+
return acceptTokens.some((token) => {
|
|
91
|
+
if (token.startsWith('.')) {
|
|
92
|
+
return file.name.toLowerCase().endsWith(token.toLowerCase());
|
|
93
|
+
}
|
|
94
|
+
if (token.endsWith('/*')) {
|
|
95
|
+
const prefix = token.slice(0, -1);
|
|
96
|
+
return file.type.startsWith(prefix);
|
|
97
|
+
}
|
|
98
|
+
return file.type === token;
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
// --- Item State ---
|
|
103
|
+
export const FileUploadItemContext = new Context(keyWithPrefix('file-upload-item'));
|
|
104
|
+
export class FileUploadItemState {
|
|
105
|
+
static create(opts) {
|
|
106
|
+
return FileUploadItemContext.set(new FileUploadItemState(opts));
|
|
107
|
+
}
|
|
108
|
+
opts;
|
|
109
|
+
constructor(opts) {
|
|
110
|
+
this.opts = opts;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
// --- Utils ---
|
|
114
|
+
export function formatFileSize(bytes) {
|
|
115
|
+
if (bytes < 1024)
|
|
116
|
+
return `${bytes} B`;
|
|
117
|
+
if (bytes < 1024 * 1024)
|
|
118
|
+
return `${(bytes / 1024).toFixed(1)} KB`;
|
|
119
|
+
return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
|
|
120
|
+
}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../internal/utils/common.js';
|
|
3
|
+
import { fileUploadPrimitiveTriggerStyles } from '../styles.js';
|
|
4
|
+
import type { FileUploadPrimitiveTriggerProps } from '../types.js';
|
|
5
|
+
import { FileUploadRootContext } from './file-upload.svelte.js';
|
|
6
|
+
|
|
7
|
+
let {
|
|
8
|
+
ref = $bindable(null),
|
|
9
|
+
children,
|
|
10
|
+
class: className,
|
|
11
|
+
...restProps
|
|
12
|
+
}: FileUploadPrimitiveTriggerProps = $props();
|
|
13
|
+
|
|
14
|
+
const rootState = FileUploadRootContext.get();
|
|
15
|
+
|
|
16
|
+
function handleClick(e: MouseEvent) {
|
|
17
|
+
e.stopPropagation();
|
|
18
|
+
rootState.openFilePicker();
|
|
19
|
+
}
|
|
20
|
+
</script>
|
|
21
|
+
|
|
22
|
+
<button
|
|
23
|
+
bind:this={ref}
|
|
24
|
+
type="button"
|
|
25
|
+
class={cn(fileUploadPrimitiveTriggerStyles(), className)}
|
|
26
|
+
data-slot="file-upload-trigger"
|
|
27
|
+
onclick={handleClick}
|
|
28
|
+
{...restProps}
|
|
29
|
+
>
|
|
30
|
+
{@render children?.()}
|
|
31
|
+
</button>
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export { default as Root } from './file-upload.root.svelte';
|
|
2
|
+
export { default as Context } from './file-upload.context.svelte';
|
|
3
|
+
export { default as Dropzone } from './file-upload.dropzone.svelte';
|
|
4
|
+
export { default as Trigger } from './file-upload.trigger.svelte';
|
|
5
|
+
export { default as HiddenInput } from './file-upload.hidden-input.svelte';
|
|
6
|
+
export { default as ItemGroup } from './file-upload.item-group.svelte';
|
|
7
|
+
export { default as Item } from './file-upload.item.svelte';
|
|
8
|
+
export { default as ItemPreview } from './file-upload.item-preview.svelte';
|
|
9
|
+
export { default as ItemPreviewImage } from './file-upload.item-preview-image.svelte';
|
|
10
|
+
export { default as ItemName } from './file-upload.item-name.svelte';
|
|
11
|
+
export { default as ItemSizeText } from './file-upload.item-size-text.svelte';
|
|
12
|
+
export { default as ItemDeleteTrigger } from './file-upload.item-delete-trigger.svelte';
|
|
13
|
+
export { default as ClearTrigger } from './file-upload.clear-trigger.svelte';
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export { default as Root } from './file-upload.root.svelte';
|
|
2
|
+
export { default as Context } from './file-upload.context.svelte';
|
|
3
|
+
export { default as Dropzone } from './file-upload.dropzone.svelte';
|
|
4
|
+
export { default as Trigger } from './file-upload.trigger.svelte';
|
|
5
|
+
export { default as HiddenInput } from './file-upload.hidden-input.svelte';
|
|
6
|
+
export { default as ItemGroup } from './file-upload.item-group.svelte';
|
|
7
|
+
export { default as Item } from './file-upload.item.svelte';
|
|
8
|
+
export { default as ItemPreview } from './file-upload.item-preview.svelte';
|
|
9
|
+
export { default as ItemPreviewImage } from './file-upload.item-preview-image.svelte';
|
|
10
|
+
export { default as ItemName } from './file-upload.item-name.svelte';
|
|
11
|
+
export { default as ItemSizeText } from './file-upload.item-size-text.svelte';
|
|
12
|
+
export { default as ItemDeleteTrigger } from './file-upload.item-delete-trigger.svelte';
|
|
13
|
+
export { default as ClearTrigger } from './file-upload.clear-trigger.svelte';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { Root } from './root/index.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { Root } from './root/index.js';
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import * as FileUploadPrimitive from '../../components/index.js';
|
|
3
|
+
import type { FileUploadRootProps } from '../../types.js';
|
|
4
|
+
|
|
5
|
+
let {
|
|
6
|
+
ref = $bindable(null),
|
|
7
|
+
accept,
|
|
8
|
+
maxFiles = 1,
|
|
9
|
+
maxFileSize = Infinity,
|
|
10
|
+
disabled = false,
|
|
11
|
+
invalid = false,
|
|
12
|
+
onFileAccept,
|
|
13
|
+
onFileReject,
|
|
14
|
+
onFileChange,
|
|
15
|
+
children,
|
|
16
|
+
class: className,
|
|
17
|
+
...restProps
|
|
18
|
+
}: FileUploadRootProps = $props();
|
|
19
|
+
</script>
|
|
20
|
+
|
|
21
|
+
<FileUploadPrimitive.Root
|
|
22
|
+
bind:ref
|
|
23
|
+
{accept}
|
|
24
|
+
{maxFiles}
|
|
25
|
+
{maxFileSize}
|
|
26
|
+
{disabled}
|
|
27
|
+
{invalid}
|
|
28
|
+
{onFileAccept}
|
|
29
|
+
{onFileReject}
|
|
30
|
+
{onFileChange}
|
|
31
|
+
class={className}
|
|
32
|
+
{...restProps}
|
|
33
|
+
>
|
|
34
|
+
<FileUploadPrimitive.HiddenInput />
|
|
35
|
+
{@render children?.()}
|
|
36
|
+
</FileUploadPrimitive.Root>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { default as Root } from './file-upload.root.svelte';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { default as Root } from './file-upload.root.svelte';
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import type { VariantProps } from 'tailwind-variants';
|
|
2
|
+
export declare const fileUploadPrimitiveRootStyles: import("tailwind-variants").TVReturnType<{
|
|
3
|
+
disabled: {
|
|
4
|
+
true: string;
|
|
5
|
+
};
|
|
6
|
+
}, undefined, string[], {
|
|
7
|
+
disabled: {
|
|
8
|
+
true: string;
|
|
9
|
+
};
|
|
10
|
+
}, undefined, import("tailwind-variants").TVReturnType<{
|
|
11
|
+
disabled: {
|
|
12
|
+
true: string;
|
|
13
|
+
};
|
|
14
|
+
}, undefined, string[], unknown, unknown, undefined>>;
|
|
15
|
+
export declare const fileUploadPrimitiveDropzoneStyles: import("tailwind-variants").TVReturnType<{
|
|
16
|
+
dragging: {
|
|
17
|
+
true: string;
|
|
18
|
+
};
|
|
19
|
+
invalid: {
|
|
20
|
+
true: string;
|
|
21
|
+
};
|
|
22
|
+
disabled: {
|
|
23
|
+
true: string;
|
|
24
|
+
};
|
|
25
|
+
}, undefined, string[], {
|
|
26
|
+
dragging: {
|
|
27
|
+
true: string;
|
|
28
|
+
};
|
|
29
|
+
invalid: {
|
|
30
|
+
true: string;
|
|
31
|
+
};
|
|
32
|
+
disabled: {
|
|
33
|
+
true: string;
|
|
34
|
+
};
|
|
35
|
+
}, undefined, import("tailwind-variants").TVReturnType<{
|
|
36
|
+
dragging: {
|
|
37
|
+
true: string;
|
|
38
|
+
};
|
|
39
|
+
invalid: {
|
|
40
|
+
true: string;
|
|
41
|
+
};
|
|
42
|
+
disabled: {
|
|
43
|
+
true: string;
|
|
44
|
+
};
|
|
45
|
+
}, undefined, string[], unknown, unknown, undefined>>;
|
|
46
|
+
export declare const fileUploadPrimitiveTriggerStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
47
|
+
export declare const fileUploadPrimitiveItemGroupStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
48
|
+
export declare const fileUploadPrimitiveItemStyles: import("tailwind-variants").TVReturnType<{
|
|
49
|
+
variant: {
|
|
50
|
+
default: string;
|
|
51
|
+
clean: string;
|
|
52
|
+
};
|
|
53
|
+
}, undefined, string[], {
|
|
54
|
+
variant: {
|
|
55
|
+
default: string;
|
|
56
|
+
clean: string;
|
|
57
|
+
};
|
|
58
|
+
}, undefined, import("tailwind-variants").TVReturnType<{
|
|
59
|
+
variant: {
|
|
60
|
+
default: string;
|
|
61
|
+
clean: string;
|
|
62
|
+
};
|
|
63
|
+
}, undefined, string[], unknown, unknown, undefined>>;
|
|
64
|
+
export declare const fileUploadPrimitiveItemPreviewStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
65
|
+
export declare const fileUploadPrimitiveItemPreviewImageStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
66
|
+
export declare const fileUploadPrimitiveItemNameStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
67
|
+
export declare const fileUploadPrimitiveItemSizeTextStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
68
|
+
export declare const fileUploadPrimitiveItemDeleteTriggerStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
69
|
+
export declare const fileUploadPrimitiveClearTriggerStyles: import("tailwind-variants").TVReturnType<{} | {} | {}, undefined, string[], {} | {}, undefined, import("tailwind-variants").TVReturnType<unknown, undefined, string[], unknown, unknown, undefined>>;
|
|
70
|
+
export type FileUploadPrimitiveRootVariants = VariantProps<typeof fileUploadPrimitiveRootStyles>;
|
|
71
|
+
export type FileUploadPrimitiveDropzoneVariants = VariantProps<typeof fileUploadPrimitiveDropzoneStyles>;
|
|
72
|
+
export type FileUploadPrimitiveTriggerVariants = VariantProps<typeof fileUploadPrimitiveTriggerStyles>;
|
|
73
|
+
export type FileUploadPrimitiveItemGroupVariants = VariantProps<typeof fileUploadPrimitiveItemGroupStyles>;
|
|
74
|
+
export type FileUploadPrimitiveItemVariants = VariantProps<typeof fileUploadPrimitiveItemStyles>;
|
|
75
|
+
export type FileUploadPrimitiveItemPreviewVariants = VariantProps<typeof fileUploadPrimitiveItemPreviewStyles>;
|
|
76
|
+
export type FileUploadPrimitiveItemPreviewImageVariants = VariantProps<typeof fileUploadPrimitiveItemPreviewImageStyles>;
|
|
77
|
+
export type FileUploadPrimitiveItemNameVariants = VariantProps<typeof fileUploadPrimitiveItemNameStyles>;
|
|
78
|
+
export type FileUploadPrimitiveItemSizeTextVariants = VariantProps<typeof fileUploadPrimitiveItemSizeTextStyles>;
|
|
79
|
+
export type FileUploadPrimitiveItemDeleteTriggerVariants = VariantProps<typeof fileUploadPrimitiveItemDeleteTriggerStyles>;
|
|
80
|
+
export type FileUploadPrimitiveClearTriggerVariants = VariantProps<typeof fileUploadPrimitiveClearTriggerStyles>;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { tv } from '../../internal/utils/tailwindcss.js';
|
|
2
|
+
export const fileUploadPrimitiveRootStyles = tv({
|
|
3
|
+
base: ['cgui:flex cgui:flex-col cgui:gap-3'],
|
|
4
|
+
variants: {
|
|
5
|
+
disabled: {
|
|
6
|
+
true: 'cgui:opacity-50 cgui:pointer-events-none',
|
|
7
|
+
},
|
|
8
|
+
},
|
|
9
|
+
});
|
|
10
|
+
export const fileUploadPrimitiveDropzoneStyles = tv({
|
|
11
|
+
base: [
|
|
12
|
+
'cgui:flex cgui:flex-col cgui:items-center cgui:justify-center cgui:gap-2',
|
|
13
|
+
'cgui:rounded-md cgui:border cgui:border-dashed cgui:border-stroke-default',
|
|
14
|
+
'cgui:cursor-pointer',
|
|
15
|
+
'cgui:transition-colors cgui:duration-200',
|
|
16
|
+
],
|
|
17
|
+
variants: {
|
|
18
|
+
dragging: {
|
|
19
|
+
true: 'cgui:border-stroke-primary cgui:bg-surface-primary/5',
|
|
20
|
+
},
|
|
21
|
+
invalid: {
|
|
22
|
+
true: 'cgui:border-stroke-error',
|
|
23
|
+
},
|
|
24
|
+
disabled: {
|
|
25
|
+
true: 'cgui:cursor-not-allowed',
|
|
26
|
+
},
|
|
27
|
+
},
|
|
28
|
+
});
|
|
29
|
+
export const fileUploadPrimitiveTriggerStyles = tv({
|
|
30
|
+
base: ['cgui:cursor-pointer'],
|
|
31
|
+
});
|
|
32
|
+
export const fileUploadPrimitiveItemGroupStyles = tv({
|
|
33
|
+
base: ['cgui:flex cgui:flex-col cgui:gap-2 cgui:list-none cgui:p-0 cgui:m-0'],
|
|
34
|
+
});
|
|
35
|
+
export const fileUploadPrimitiveItemStyles = tv({
|
|
36
|
+
base: ['cgui:flex cgui:items-center cgui:gap-3'],
|
|
37
|
+
variants: {
|
|
38
|
+
variant: {
|
|
39
|
+
default: 'cgui:rounded-sm cgui:border cgui:border-stroke-default cgui:p-2',
|
|
40
|
+
clean: '',
|
|
41
|
+
},
|
|
42
|
+
},
|
|
43
|
+
});
|
|
44
|
+
export const fileUploadPrimitiveItemPreviewStyles = tv({
|
|
45
|
+
base: [
|
|
46
|
+
'cgui:size-10 cgui:shrink-0 cgui:flex cgui:items-center cgui:justify-center cgui:overflow-hidden cgui:rounded-xs',
|
|
47
|
+
],
|
|
48
|
+
});
|
|
49
|
+
export const fileUploadPrimitiveItemPreviewImageStyles = tv({
|
|
50
|
+
base: ['cgui:size-full cgui:object-cover'],
|
|
51
|
+
});
|
|
52
|
+
export const fileUploadPrimitiveItemNameStyles = tv({
|
|
53
|
+
base: ['cgui:text-body-2 cgui:text-fg-darkest cgui:truncate cgui:flex-1'],
|
|
54
|
+
});
|
|
55
|
+
export const fileUploadPrimitiveItemSizeTextStyles = tv({
|
|
56
|
+
base: ['cgui:text-caption-2 cgui:text-fg-regular cgui:shrink-0'],
|
|
57
|
+
});
|
|
58
|
+
export const fileUploadPrimitiveItemDeleteTriggerStyles = tv({
|
|
59
|
+
base: [
|
|
60
|
+
'cgui:shrink-0 cgui:size-6 cgui:flex cgui:items-center cgui:justify-center',
|
|
61
|
+
'cgui:rounded-xs cgui:cursor-pointer',
|
|
62
|
+
'cgui:text-fg-regular cgui:hover:text-fg-darkest',
|
|
63
|
+
'cgui:transition-colors cgui:duration-200',
|
|
64
|
+
],
|
|
65
|
+
});
|
|
66
|
+
export const fileUploadPrimitiveClearTriggerStyles = tv({
|
|
67
|
+
base: ['cgui:cursor-pointer'],
|
|
68
|
+
});
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import type { Without } from '../../internal/types/common.js';
|
|
2
|
+
import type { WithVariants } from '../../internal/types/composition.js';
|
|
3
|
+
import type { PrimitiveButtonAttributes, PrimitiveDivAttributes, PrimitiveImgAttributes, PrimitiveInputAttributes, PrimitiveLiAttributes, PrimitiveUListAttributes } from '../../internal/types/html-attributes.js';
|
|
4
|
+
import type { WithChildren, WithElementRef } from 'svelte-toolbelt';
|
|
5
|
+
import type { FileUploadPrimitiveClearTriggerVariants, FileUploadPrimitiveDropzoneVariants, FileUploadPrimitiveItemDeleteTriggerVariants, FileUploadPrimitiveItemGroupVariants, FileUploadPrimitiveItemNameVariants, FileUploadPrimitiveItemPreviewImageVariants, FileUploadPrimitiveItemPreviewVariants, FileUploadPrimitiveItemSizeTextVariants, FileUploadPrimitiveItemVariants, FileUploadPrimitiveTriggerVariants } from './styles.js';
|
|
6
|
+
export type FileError = 'TOO_MANY_FILES' | 'FILE_INVALID_TYPE' | 'FILE_TOO_LARGE';
|
|
7
|
+
export type RejectedFile = {
|
|
8
|
+
file: File;
|
|
9
|
+
errors: FileError[];
|
|
10
|
+
};
|
|
11
|
+
export type FileAcceptDetails = {
|
|
12
|
+
files: File[];
|
|
13
|
+
};
|
|
14
|
+
export type FileRejectDetails = {
|
|
15
|
+
files: RejectedFile[];
|
|
16
|
+
};
|
|
17
|
+
export type FileChangeDetails = {
|
|
18
|
+
acceptedFiles: File[];
|
|
19
|
+
rejectedFiles: RejectedFile[];
|
|
20
|
+
};
|
|
21
|
+
type FileUploadPrimitiveRootPropsWithoutHTML = WithElementRef<WithChildren<{
|
|
22
|
+
accept?: string;
|
|
23
|
+
maxFiles?: number;
|
|
24
|
+
maxFileSize?: number;
|
|
25
|
+
disabled?: boolean;
|
|
26
|
+
invalid?: boolean;
|
|
27
|
+
onFileAccept?: (details: FileAcceptDetails) => void;
|
|
28
|
+
onFileReject?: (details: FileRejectDetails) => void;
|
|
29
|
+
onFileChange?: (details: FileChangeDetails) => void;
|
|
30
|
+
}>>;
|
|
31
|
+
export type FileUploadPrimitiveRootProps = FileUploadPrimitiveRootPropsWithoutHTML & Without<PrimitiveDivAttributes, FileUploadPrimitiveRootPropsWithoutHTML>;
|
|
32
|
+
type FileUploadPrimitiveDropzonePropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{
|
|
33
|
+
disableClick?: boolean;
|
|
34
|
+
}>>, FileUploadPrimitiveDropzoneVariants>;
|
|
35
|
+
export type FileUploadPrimitiveDropzoneProps = FileUploadPrimitiveDropzonePropsWithoutHTML & Without<PrimitiveDivAttributes, FileUploadPrimitiveDropzonePropsWithoutHTML>;
|
|
36
|
+
type FileUploadPrimitiveTriggerPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{}>>, FileUploadPrimitiveTriggerVariants>;
|
|
37
|
+
export type FileUploadPrimitiveTriggerProps = FileUploadPrimitiveTriggerPropsWithoutHTML & Without<PrimitiveButtonAttributes, FileUploadPrimitiveTriggerPropsWithoutHTML>;
|
|
38
|
+
type FileUploadPrimitiveHiddenInputPropsWithoutHTML = WithElementRef<{}>;
|
|
39
|
+
export type FileUploadPrimitiveHiddenInputProps = FileUploadPrimitiveHiddenInputPropsWithoutHTML & Without<PrimitiveInputAttributes, FileUploadPrimitiveHiddenInputPropsWithoutHTML>;
|
|
40
|
+
type FileUploadPrimitiveItemGroupPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{}>>, FileUploadPrimitiveItemGroupVariants>;
|
|
41
|
+
export type FileUploadPrimitiveItemGroupProps = FileUploadPrimitiveItemGroupPropsWithoutHTML & Without<PrimitiveUListAttributes, FileUploadPrimitiveItemGroupPropsWithoutHTML>;
|
|
42
|
+
type FileUploadPrimitiveItemPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{
|
|
43
|
+
file: File;
|
|
44
|
+
}>>, FileUploadPrimitiveItemVariants>;
|
|
45
|
+
export type FileUploadPrimitiveItemProps = FileUploadPrimitiveItemPropsWithoutHTML & Without<PrimitiveLiAttributes, FileUploadPrimitiveItemPropsWithoutHTML>;
|
|
46
|
+
type FileUploadPrimitiveItemPreviewPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{
|
|
47
|
+
type?: string;
|
|
48
|
+
}>>, FileUploadPrimitiveItemPreviewVariants>;
|
|
49
|
+
export type FileUploadPrimitiveItemPreviewProps = FileUploadPrimitiveItemPreviewPropsWithoutHTML & Without<PrimitiveDivAttributes, FileUploadPrimitiveItemPreviewPropsWithoutHTML>;
|
|
50
|
+
type FileUploadPrimitiveItemPreviewImagePropsWithoutHTML = WithVariants<WithElementRef<{}>, FileUploadPrimitiveItemPreviewImageVariants>;
|
|
51
|
+
export type FileUploadPrimitiveItemPreviewImageProps = FileUploadPrimitiveItemPreviewImagePropsWithoutHTML & Without<PrimitiveImgAttributes, FileUploadPrimitiveItemPreviewImagePropsWithoutHTML>;
|
|
52
|
+
type FileUploadPrimitiveItemNamePropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{}>>, FileUploadPrimitiveItemNameVariants>;
|
|
53
|
+
export type FileUploadPrimitiveItemNameProps = FileUploadPrimitiveItemNamePropsWithoutHTML & Without<PrimitiveDivAttributes, FileUploadPrimitiveItemNamePropsWithoutHTML>;
|
|
54
|
+
type FileUploadPrimitiveItemSizeTextPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{}>>, FileUploadPrimitiveItemSizeTextVariants>;
|
|
55
|
+
export type FileUploadPrimitiveItemSizeTextProps = FileUploadPrimitiveItemSizeTextPropsWithoutHTML & Without<PrimitiveDivAttributes, FileUploadPrimitiveItemSizeTextPropsWithoutHTML>;
|
|
56
|
+
type FileUploadPrimitiveItemDeleteTriggerPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{}>>, FileUploadPrimitiveItemDeleteTriggerVariants>;
|
|
57
|
+
export type FileUploadPrimitiveItemDeleteTriggerProps = FileUploadPrimitiveItemDeleteTriggerPropsWithoutHTML & Without<PrimitiveButtonAttributes, FileUploadPrimitiveItemDeleteTriggerPropsWithoutHTML>;
|
|
58
|
+
type FileUploadPrimitiveClearTriggerPropsWithoutHTML = WithVariants<WithElementRef<WithChildren<{}>>, FileUploadPrimitiveClearTriggerVariants>;
|
|
59
|
+
export type FileUploadPrimitiveClearTriggerProps = FileUploadPrimitiveClearTriggerPropsWithoutHTML & Without<PrimitiveButtonAttributes, FileUploadPrimitiveClearTriggerPropsWithoutHTML>;
|
|
60
|
+
export type FileUploadContext = {
|
|
61
|
+
readonly acceptedFiles: File[];
|
|
62
|
+
readonly rejectedFiles: RejectedFile[];
|
|
63
|
+
readonly dragging: boolean;
|
|
64
|
+
addFiles(files: FileList | File[]): void;
|
|
65
|
+
removeFile(file: File): void;
|
|
66
|
+
clearFiles(): void;
|
|
67
|
+
openFilePicker(): void;
|
|
68
|
+
};
|
|
69
|
+
export type FileUploadPrimitiveContextProps = {
|
|
70
|
+
children?: import('svelte').Snippet<[FileUploadContext]>;
|
|
71
|
+
};
|
|
72
|
+
type FileUploadRootPropsWithoutHTML = WithElementRef<WithChildren<{
|
|
73
|
+
accept?: string;
|
|
74
|
+
maxFiles?: number;
|
|
75
|
+
maxFileSize?: number;
|
|
76
|
+
disabled?: boolean;
|
|
77
|
+
invalid?: boolean;
|
|
78
|
+
onFileAccept?: (details: FileAcceptDetails) => void;
|
|
79
|
+
onFileReject?: (details: FileRejectDetails) => void;
|
|
80
|
+
onFileChange?: (details: FileChangeDetails) => void;
|
|
81
|
+
}>>;
|
|
82
|
+
export type FileUploadRootProps = FileUploadRootPropsWithoutHTML & Without<PrimitiveDivAttributes, FileUploadRootPropsWithoutHTML>;
|
|
83
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|