feat(file-uploader-drop-container): rework FileUploaderDropContainer (#1125)

- convert `FileList` to `File[]` to be consistent with `FileUploader` and `FileUploaderButton`
- add `files` prop for two-way binding
- dispatch instead of forward the `change` event (detail signature: `File[]`)
This commit is contained in:
metonym 2022-02-21 13:33:11 -08:00 committed by GitHub
commit 8d3ac75170
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 60 additions and 32 deletions

View file

@ -1329,18 +1329,19 @@ None.
### Props
| Prop name | Kind | Reactive | Type | Default value | Description |
| :------------ | :--------------- | :------- | :----------------------------------------- | ------------------------------------------------ | ------------------------------------------------------------------------------------------------------------ |
| ref | <code>let</code> | Yes | <code>null &#124; HTMLInputElement</code> | <code>null</code> | Obtain a reference to the input HTML element |
| accept | <code>let</code> | No | <code>string[]</code> | <code>[]</code> | Specify the accepted file types |
| multiple | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to allow multiple files |
| validateFiles | <code>let</code> | No | <code>(files: FileList) => FileList</code> | <code>(files) => files</code> | Override the default behavior of validating uploaded files<br />The default behavior does not validate files |
| labelText | <code>let</code> | No | <code>string</code> | <code>"Add file"</code> | Specify the label text |
| role | <code>let</code> | No | <code>string</code> | <code>"button"</code> | Specify the `role` attribute of the drop container |
| disabled | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to disable the input |
| tabindex | <code>let</code> | No | <code>string</code> | <code>"0"</code> | Specify `tabindex` attribute |
| id | <code>let</code> | No | <code>string</code> | <code>"ccs-" + Math.random().toString(36)</code> | Set an id for the input element |
| name | <code>let</code> | No | <code>string</code> | <code>""</code> | Specify a name attribute for the input |
| Prop name | Kind | Reactive | Type | Default value | Description |
| :------------ | :--------------- | :------- | :---------------------------------------- | ------------------------------------------------ | ------------------------------------------------------------------------------------------------------------ |
| ref | <code>let</code> | Yes | <code>null &#124; HTMLInputElement</code> | <code>null</code> | Obtain a reference to the input HTML element |
| files | <code>let</code> | Yes | <code>File[]</code> | <code>[]</code> | Obtain a reference to the uploaded files |
| accept | <code>let</code> | No | <code>string[]</code> | <code>[]</code> | Specify the accepted file types |
| multiple | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to allow multiple files |
| validateFiles | <code>let</code> | No | <code>(files: File) => File</code> | <code>(files) => files</code> | Override the default behavior of validating uploaded files<br />The default behavior does not validate files |
| labelText | <code>let</code> | No | <code>string</code> | <code>"Add file"</code> | Specify the label text |
| role | <code>let</code> | No | <code>string</code> | <code>"button"</code> | Specify the `role` attribute of the drop container |
| disabled | <code>let</code> | No | <code>boolean</code> | <code>false</code> | Set to `true` to disable the input |
| tabindex | <code>let</code> | No | <code>string</code> | <code>"0"</code> | Specify `tabindex` attribute |
| id | <code>let</code> | No | <code>string</code> | <code>"ccs-" + Math.random().toString(36)</code> | Set an id for the input element |
| name | <code>let</code> | No | <code>string</code> | <code>""</code> | Specify a name attribute for the input |
### Slots
@ -1350,15 +1351,15 @@ None.
### Events
| Event name | Type | Detail |
| :--------- | :--------- | :-------------------- |
| add | dispatched | <code>FileList</code> |
| dragover | forwarded | -- |
| dragleave | forwarded | -- |
| drop | forwarded | -- |
| keydown | forwarded | -- |
| change | forwarded | -- |
| click | forwarded | -- |
| Event name | Type | Detail |
| :--------- | :--------- | :------------------ |
| add | dispatched | <code>File[]</code> |
| change | dispatched | <code>File[]</code> |
| dragover | forwarded | -- |
| dragleave | forwarded | -- |
| drop | forwarded | -- |
| keydown | forwarded | -- |
| click | forwarded | -- |
## `FileUploaderItem`

View file

@ -3760,6 +3760,17 @@
"constant": false,
"reactive": false
},
{
"name": "files",
"kind": "let",
"description": "Obtain a reference to the uploaded files",
"type": "File[]",
"value": "[]",
"isFunction": false,
"isFunctionDeclaration": false,
"constant": false,
"reactive": true
},
{
"name": "multiple",
"kind": "let",
@ -3775,7 +3786,7 @@
"name": "validateFiles",
"kind": "let",
"description": "Override the default behavior of validating uploaded files\nThe default behavior does not validate files",
"type": "(files: FileList) => FileList",
"type": "(files: File) => File",
"value": "(files) => files",
"isFunction": true,
"isFunctionDeclaration": false,
@ -3869,12 +3880,12 @@
}
],
"events": [
{ "type": "dispatched", "name": "add", "detail": "FileList" },
{ "type": "dispatched", "name": "add", "detail": "File[]" },
{ "type": "dispatched", "name": "change", "detail": "File[]" },
{ "type": "forwarded", "name": "dragover", "element": "div" },
{ "type": "forwarded", "name": "dragleave", "element": "div" },
{ "type": "forwarded", "name": "drop", "element": "div" },
{ "type": "forwarded", "name": "keydown", "element": "label" },
{ "type": "forwarded", "name": "change", "element": "input" },
{ "type": "forwarded", "name": "click", "element": "input" }
],
"typedefs": [],

View file

@ -1,6 +1,7 @@
<script>
/**
* @event {FileList} add
* @event {File[]} add
* @event {File[]} change
*/
/**
@ -9,13 +10,19 @@
*/
export let accept = [];
/**
* Obtain a reference to the uploaded files
* @type {File[]}
*/
export let files = [];
/** Set to `true` to allow multiple files */
export let multiple = false;
/**
* Override the default behavior of validating uploaded files
* The default behavior does not validate files
* @type {(files: FileList) => FileList}
* @type {(files: File) => File}
*/
export let validateFiles = (files) => files;
@ -68,7 +75,9 @@
on:drop|preventDefault|stopPropagation="{({ dataTransfer }) => {
if (!disabled) {
over = false;
dispatch('add', validateFiles(dataTransfer.files));
files = validateFiles([...dataTransfer.files]);
dispatch('add', files);
dispatch('change', files);
}
}}"
>
@ -104,9 +113,10 @@
name="{name}"
multiple="{multiple}"
class:bx--file-input="{true}"
on:change
on:change="{({ target }) => {
dispatch('add', validateFiles(target.files));
files = validateFiles([...target.files]);
dispatch('add', files);
dispatch('change', files);
}}"
on:click
on:click="{({ target }) => {

View file

@ -9,6 +9,12 @@ export interface FileUploaderDropContainerProps
*/
accept?: string[];
/**
* Obtain a reference to the uploaded files
* @default []
*/
files?: File[];
/**
* Set to `true` to allow multiple files
* @default false
@ -20,7 +26,7 @@ export interface FileUploaderDropContainerProps
* The default behavior does not validate files
* @default (files) => files
*/
validateFiles?: (files: FileList) => FileList;
validateFiles?: (files: File) => File;
/**
* Specify the label text
@ -68,12 +74,12 @@ export interface FileUploaderDropContainerProps
export default class FileUploaderDropContainer extends SvelteComponentTyped<
FileUploaderDropContainerProps,
{
add: CustomEvent<FileList>;
add: CustomEvent<File[]>;
change: CustomEvent<File[]>;
dragover: WindowEventMap["dragover"];
dragleave: WindowEventMap["dragleave"];
drop: WindowEventMap["drop"];
keydown: WindowEventMap["keydown"];
change: WindowEventMap["change"];
click: WindowEventMap["click"];
},
{ labelText: {} }