@sbnpmiamldw/ui-library 0.1.1
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/README.md +46 -0
- package/dist/App.d.ts +3 -0
- package/dist/App.js +7 -0
- package/dist/components/Alert/alert.d.ts +10 -0
- package/dist/components/Alert/alert.js +18 -0
- package/dist/components/Alert/index.d.ts +2 -0
- package/dist/components/Alert/index.js +2 -0
- package/dist/components/AutoComplete/autoComplete.d.ts +13 -0
- package/dist/components/AutoComplete/autoComplete.js +82 -0
- package/dist/components/AutoComplete/index.d.ts +2 -0
- package/dist/components/AutoComplete/index.js +2 -0
- package/dist/components/Button/button.d.ts +23 -0
- package/dist/components/Button/button.js +19 -0
- package/dist/components/Button/index.d.ts +2 -0
- package/dist/components/Button/index.js +2 -0
- package/dist/components/Icon/icon.d.ts +8 -0
- package/dist/components/Icon/icon.js +10 -0
- package/dist/components/Icon/index.d.ts +2 -0
- package/dist/components/Icon/index.js +2 -0
- package/dist/components/Input/index.d.ts +2 -0
- package/dist/components/Input/index.js +2 -0
- package/dist/components/Input/input.d.ts +15 -0
- package/dist/components/Input/input.js +13 -0
- package/dist/components/Menu/index.d.ts +10 -0
- package/dist/components/Menu/index.js +7 -0
- package/dist/components/Menu/menu.d.ts +21 -0
- package/dist/components/Menu/menu.js +37 -0
- package/dist/components/Menu/menuItem.d.ts +10 -0
- package/dist/components/Menu/menuItem.js +19 -0
- package/dist/components/Menu/subMenu.d.ts +9 -0
- package/dist/components/Menu/subMenu.js +58 -0
- package/dist/components/Select/index.d.ts +10 -0
- package/dist/components/Select/index.js +7 -0
- package/dist/components/Select/select.d.ts +9 -0
- package/dist/components/Select/select.js +66 -0
- package/dist/components/Select/selectItem.d.ts +9 -0
- package/dist/components/Select/selectItem.js +17 -0
- package/dist/components/Select/selectTag.d.ts +7 -0
- package/dist/components/Select/selectTag.js +12 -0
- package/dist/components/Tabs/index.d.ts +8 -0
- package/dist/components/Tabs/index.js +5 -0
- package/dist/components/Tabs/tabItem.d.ts +10 -0
- package/dist/components/Tabs/tabItem.js +19 -0
- package/dist/components/Tabs/tabs.d.ts +15 -0
- package/dist/components/Tabs/tabs.js +37 -0
- package/dist/components/Transition/index.d.ts +2 -0
- package/dist/components/Transition/index.js +2 -0
- package/dist/components/Transition/transition.d.ts +9 -0
- package/dist/components/Transition/transition.js +19 -0
- package/dist/components/Upload/dragger.d.ts +6 -0
- package/dist/components/Upload/dragger.js +19 -0
- package/dist/components/Upload/index.d.ts +13 -0
- package/dist/components/Upload/index.js +9 -0
- package/dist/components/Upload/progress.d.ts +10 -0
- package/dist/components/Upload/progress.js +8 -0
- package/dist/components/Upload/upload.d.ts +35 -0
- package/dist/components/Upload/upload.js +126 -0
- package/dist/components/Upload/uploadList.d.ts +7 -0
- package/dist/components/Upload/uploadList.js +9 -0
- package/dist/hooks/useClickOutside.d.ts +2 -0
- package/dist/hooks/useClickOutside.js +16 -0
- package/dist/hooks/useDebounce.d.ts +1 -0
- package/dist/hooks/useDebounce.js +13 -0
- package/dist/index.css +801 -0
- package/dist/index.css.map +1 -0
- package/dist/index.d.ts +10 -0
- package/dist/index.js +31 -0
- package/dist/reportWebVitals.d.ts +0 -0
- package/dist/reportWebVitals.js +13 -0
- package/dist/setupTests.d.ts +1 -0
- package/dist/setupTests.js +5 -0
- package/package.json +97 -0
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import Button from '../Button/button';
|
|
3
|
+
import Icon from "../Icon/icon";
|
|
4
|
+
import { faXmark } from "@fortawesome/free-solid-svg-icons";
|
|
5
|
+
const SelectTag = ({ value, handleTagClick, }) => {
|
|
6
|
+
const handleClick = () => {
|
|
7
|
+
if (handleTagClick)
|
|
8
|
+
handleTagClick(value);
|
|
9
|
+
};
|
|
10
|
+
return (_jsxs("div", { className: "select-tag", children: [_jsx("div", { className: "select-tag-value", children: value }), _jsx(Button, { className: "select-tag-button", "aria-label": `select tag button ${value}`, onClick: () => handleClick(), children: _jsx(Icon, { icon: faXmark }) })] }));
|
|
11
|
+
};
|
|
12
|
+
export default SelectTag;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { useContext } from 'react';
|
|
3
|
+
import classNames from 'classnames';
|
|
4
|
+
import { TabContext } from './tabs';
|
|
5
|
+
const TabItem = ({ index, disabled = false, className, label }) => {
|
|
6
|
+
const context = useContext(TabContext);
|
|
7
|
+
const classes = classNames('tab-item', className, {
|
|
8
|
+
'is-disabled': disabled,
|
|
9
|
+
'is-active': index === context.index
|
|
10
|
+
});
|
|
11
|
+
const handleClick = () => {
|
|
12
|
+
if (!disabled && context.onSelect && typeof index == 'number') {
|
|
13
|
+
context.onSelect(index);
|
|
14
|
+
}
|
|
15
|
+
};
|
|
16
|
+
return (_jsx("li", { className: classes, onClick: handleClick, children: label }));
|
|
17
|
+
};
|
|
18
|
+
TabItem.displayName = 'TabItem';
|
|
19
|
+
export default TabItem;
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
type selectCallback = (selectIndex: number) => void;
|
|
3
|
+
export interface TabsProps {
|
|
4
|
+
defaultIndex?: number;
|
|
5
|
+
onSelect?: selectCallback;
|
|
6
|
+
className?: string;
|
|
7
|
+
children: React.ReactNode;
|
|
8
|
+
}
|
|
9
|
+
interface ITabContext {
|
|
10
|
+
index: number;
|
|
11
|
+
onSelect?: selectCallback;
|
|
12
|
+
}
|
|
13
|
+
export declare const TabContext: React.Context<ITabContext>;
|
|
14
|
+
declare const Tabs: React.FC<TabsProps>;
|
|
15
|
+
export default Tabs;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import React, { useState, createContext } from 'react';
|
|
3
|
+
import classNames from 'classnames';
|
|
4
|
+
export const TabContext = createContext({ index: 0 });
|
|
5
|
+
const Tabs = ({ defaultIndex = 0, onSelect, className, children }) => {
|
|
6
|
+
const [currentActive, setActive] = useState(defaultIndex);
|
|
7
|
+
const classes = classNames('tabs', className);
|
|
8
|
+
const ActiveContent = (index) => {
|
|
9
|
+
var _a;
|
|
10
|
+
const tabItems = React.Children.toArray(children);
|
|
11
|
+
return (_a = tabItems.find((tab, i) => i === index)) === null || _a === void 0 ? void 0 : _a.props.children;
|
|
12
|
+
};
|
|
13
|
+
const handleClick = (index) => {
|
|
14
|
+
setActive(index);
|
|
15
|
+
if (onSelect) {
|
|
16
|
+
onSelect(index);
|
|
17
|
+
}
|
|
18
|
+
};
|
|
19
|
+
const renderChildren = () => {
|
|
20
|
+
return React.Children.map(children, (child, index) => {
|
|
21
|
+
const childElement = child;
|
|
22
|
+
if (typeof childElement.type === 'function' &&
|
|
23
|
+
childElement.type.displayName === 'TabItem') {
|
|
24
|
+
return React.cloneElement(childElement, { index });
|
|
25
|
+
}
|
|
26
|
+
else {
|
|
27
|
+
console.error('Warning: Tab has a child which is not a TabItem component');
|
|
28
|
+
}
|
|
29
|
+
});
|
|
30
|
+
};
|
|
31
|
+
const passedContext = {
|
|
32
|
+
index: currentActive,
|
|
33
|
+
onSelect: handleClick
|
|
34
|
+
};
|
|
35
|
+
return (_jsxs("div", { className: classes, children: [_jsx("ul", { className: 'tabs-items', children: _jsx(TabContext.Provider, { value: passedContext, children: renderChildren() }) }), _jsx("div", { className: 'tabs-content', children: ActiveContent(currentActive) })] }));
|
|
36
|
+
};
|
|
37
|
+
export default Tabs;
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { CSSTransitionProps } from 'react-transition-group/CSSTransition';
|
|
3
|
+
type AnimationName = 'zoom-in-top' | 'zoom-in-left' | 'zoom-in-right' | 'zoom-in-bottom';
|
|
4
|
+
type TransitionProps = CSSTransitionProps<HTMLElement> & {
|
|
5
|
+
animation?: AnimationName;
|
|
6
|
+
wrapper?: boolean;
|
|
7
|
+
};
|
|
8
|
+
declare const Transition: React.FC<TransitionProps>;
|
|
9
|
+
export default Transition;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import React, { useRef } from "react";
|
|
3
|
+
import { CSSTransition } from "react-transition-group";
|
|
4
|
+
const Transition = ({ children, classNames, animation, wrapper = false, appear = true, unmountOnExit = true, ...restProps }) => {
|
|
5
|
+
const nodeRef = useRef(null);
|
|
6
|
+
const renderChildren = () => {
|
|
7
|
+
if (React.isValidElement(children)) {
|
|
8
|
+
return React.cloneElement(children, {
|
|
9
|
+
ref: nodeRef
|
|
10
|
+
});
|
|
11
|
+
}
|
|
12
|
+
else
|
|
13
|
+
return children;
|
|
14
|
+
};
|
|
15
|
+
return (_jsx(CSSTransition, { nodeRef: nodeRef, appear: appear, unmountOnExit: unmountOnExit, classNames: classNames ? classNames : animation, ...restProps, children: wrapper ? (
|
|
16
|
+
// 防止transition冲突
|
|
17
|
+
_jsx("div", { ref: nodeRef, children: children })) : renderChildren() }));
|
|
18
|
+
};
|
|
19
|
+
export default Transition;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { useState } from "react";
|
|
3
|
+
import classNames from "classnames";
|
|
4
|
+
export const Dragger = ({ onFile, children, }) => {
|
|
5
|
+
const [dragOver, setDragOver] = useState(false);
|
|
6
|
+
const classes = classNames('upload-dragger', {
|
|
7
|
+
'is-dragOver': dragOver,
|
|
8
|
+
});
|
|
9
|
+
const handleDrop = (e) => {
|
|
10
|
+
e.preventDefault();
|
|
11
|
+
setDragOver(false);
|
|
12
|
+
onFile(e.dataTransfer.files);
|
|
13
|
+
};
|
|
14
|
+
const handleDrag = (e, over) => {
|
|
15
|
+
e.preventDefault();
|
|
16
|
+
setDragOver(over);
|
|
17
|
+
};
|
|
18
|
+
return (_jsx("div", { className: classes, onDragOver: e => handleDrag(e, true), onDragLeave: e => handleDrag(e, false), onDrop: handleDrop, children: children }));
|
|
19
|
+
};
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { FC } from "react";
|
|
2
|
+
import { UploadProps, UploadFile } from "./upload";
|
|
3
|
+
import { UploadListProps } from "./uploadList";
|
|
4
|
+
import { ProgressProps } from "./progress";
|
|
5
|
+
import { DraggerProps } from "./dragger";
|
|
6
|
+
export type IUploadComponent = FC<UploadProps> & {
|
|
7
|
+
List: FC<UploadListProps>;
|
|
8
|
+
Progress: FC<ProgressProps>;
|
|
9
|
+
Dragger: FC<DraggerProps>;
|
|
10
|
+
};
|
|
11
|
+
declare const TransUpload: IUploadComponent;
|
|
12
|
+
export default TransUpload;
|
|
13
|
+
export { UploadFile };
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { Upload } from "./upload";
|
|
2
|
+
import { UploadList } from "./uploadList";
|
|
3
|
+
import { Progress } from "./progress";
|
|
4
|
+
import { Dragger } from "./dragger";
|
|
5
|
+
const TransUpload = Upload;
|
|
6
|
+
TransUpload.List = UploadList;
|
|
7
|
+
TransUpload.Progress = Progress;
|
|
8
|
+
TransUpload.Dragger = Dragger;
|
|
9
|
+
export default TransUpload;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { ThemeProps } from '../Icon/icon';
|
|
3
|
+
export interface ProgressProps {
|
|
4
|
+
percent: number;
|
|
5
|
+
strokeHeight?: number;
|
|
6
|
+
showText?: boolean;
|
|
7
|
+
styles?: React.CSSProperties;
|
|
8
|
+
theme?: ThemeProps;
|
|
9
|
+
}
|
|
10
|
+
export declare const Progress: React.FC<ProgressProps>;
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
export const Progress = ({ percent, strokeHeight = 15, showText = true, styles, theme = 'primary', }) => {
|
|
3
|
+
return (_jsx("div", { className: "progress-bar", style: styles, children: _jsx("div", { className: "progress-bar-outer", style: {
|
|
4
|
+
height: `${strokeHeight}px`
|
|
5
|
+
}, children: _jsx("div", { className: `progress-bar-inner color-${theme}`, style: {
|
|
6
|
+
width: `${percent}%`
|
|
7
|
+
}, children: showText && (_jsx("span", { className: "inner-text", children: `${percent}%` })) }) }) }));
|
|
8
|
+
};
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
export type UploadFileStatus = 'ready' | 'uploading' | 'success' | 'error';
|
|
3
|
+
export interface UploadFile {
|
|
4
|
+
uid: string;
|
|
5
|
+
size: number;
|
|
6
|
+
name: string;
|
|
7
|
+
status?: UploadFileStatus;
|
|
8
|
+
percent?: number;
|
|
9
|
+
raw?: File;
|
|
10
|
+
response?: any;
|
|
11
|
+
error?: any;
|
|
12
|
+
}
|
|
13
|
+
export interface UploadProps {
|
|
14
|
+
action: string;
|
|
15
|
+
defaultFileList?: UploadFile[];
|
|
16
|
+
beforUpload?: (file: UploadFile) => boolean | Promise<UploadFile>;
|
|
17
|
+
onProgress?: (percentage: number, file: UploadFile) => void;
|
|
18
|
+
onSuccess?: (data: any, file: UploadFile) => void;
|
|
19
|
+
onError?: (err: any, file: UploadFile) => void;
|
|
20
|
+
onChange?: (file: UploadFile) => void;
|
|
21
|
+
onRemove?: (file: UploadFile) => void;
|
|
22
|
+
headers?: {
|
|
23
|
+
[key: string]: any;
|
|
24
|
+
};
|
|
25
|
+
name?: string;
|
|
26
|
+
data?: {
|
|
27
|
+
[key: string]: any;
|
|
28
|
+
};
|
|
29
|
+
withCredentials?: boolean;
|
|
30
|
+
accept?: string;
|
|
31
|
+
multiple?: boolean;
|
|
32
|
+
drag?: boolean;
|
|
33
|
+
children: React.ReactNode;
|
|
34
|
+
}
|
|
35
|
+
export declare const Upload: React.FC<UploadProps>;
|
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { useState } from "react";
|
|
3
|
+
import axios from "axios";
|
|
4
|
+
import { UploadList } from "./uploadList";
|
|
5
|
+
import { Dragger } from "./dragger";
|
|
6
|
+
export const Upload = ({ action, defaultFileList, beforUpload, onProgress, onSuccess, onError, onChange, onRemove, headers, name = 'file', data, withCredentials, accept, multiple, drag, children, }) => {
|
|
7
|
+
const [fileList, setFileList] = useState(defaultFileList || []);
|
|
8
|
+
const updateFileList = (updateFile, updateObj) => {
|
|
9
|
+
let targetFile = { ...updateFile, ...updateObj };
|
|
10
|
+
setFileList(prevList => {
|
|
11
|
+
return prevList.map(file => {
|
|
12
|
+
if (file.uid === updateFile.uid) {
|
|
13
|
+
targetFile = { ...file, ...updateObj };
|
|
14
|
+
return { ...file, ...updateObj };
|
|
15
|
+
}
|
|
16
|
+
else
|
|
17
|
+
return file;
|
|
18
|
+
});
|
|
19
|
+
});
|
|
20
|
+
return targetFile;
|
|
21
|
+
};
|
|
22
|
+
const convertFileToUpLoadFile = (file) => {
|
|
23
|
+
return {
|
|
24
|
+
uid: Date.now() + "",
|
|
25
|
+
status: 'ready',
|
|
26
|
+
name: file.name,
|
|
27
|
+
size: file.size,
|
|
28
|
+
percent: 0,
|
|
29
|
+
raw: file,
|
|
30
|
+
};
|
|
31
|
+
};
|
|
32
|
+
const post = (file) => {
|
|
33
|
+
setFileList(prevList => [file, ...prevList]);
|
|
34
|
+
const formData = new FormData();
|
|
35
|
+
if (file.raw)
|
|
36
|
+
formData.append(name || 'file', file.raw);
|
|
37
|
+
else
|
|
38
|
+
console.error('empty file');
|
|
39
|
+
if (data) {
|
|
40
|
+
Object.keys(data).forEach(key => {
|
|
41
|
+
formData.append(key, data[key]);
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
axios.post(action, formData, {
|
|
45
|
+
headers: {
|
|
46
|
+
...headers,
|
|
47
|
+
'Content-Type': 'multipart/form-data',
|
|
48
|
+
},
|
|
49
|
+
withCredentials: withCredentials,
|
|
50
|
+
onUploadProgress(progressEvent) {
|
|
51
|
+
var _a;
|
|
52
|
+
const total = (_a = progressEvent.total) !== null && _a !== void 0 ? _a : 0;
|
|
53
|
+
let percentage = total > 0
|
|
54
|
+
? Math.round(progressEvent.loaded / total * 100)
|
|
55
|
+
: 0;
|
|
56
|
+
if (percentage < 100) {
|
|
57
|
+
const newFile = updateFileList(file, {
|
|
58
|
+
percent: percentage,
|
|
59
|
+
status: 'uploading',
|
|
60
|
+
});
|
|
61
|
+
setFileList(prevList => {
|
|
62
|
+
console.log(prevList);
|
|
63
|
+
return prevList;
|
|
64
|
+
});
|
|
65
|
+
onProgress && onProgress(percentage, newFile);
|
|
66
|
+
}
|
|
67
|
+
},
|
|
68
|
+
}).then(resp => {
|
|
69
|
+
// console.log(resp);
|
|
70
|
+
const newFile = updateFileList(file, {
|
|
71
|
+
status: 'success',
|
|
72
|
+
response: resp.data,
|
|
73
|
+
});
|
|
74
|
+
onSuccess && onSuccess(resp.data, newFile);
|
|
75
|
+
onChange && onChange(newFile);
|
|
76
|
+
// onChange?.(file);
|
|
77
|
+
}).catch(err => {
|
|
78
|
+
// console.error(err);
|
|
79
|
+
const newFile = updateFileList(file, {
|
|
80
|
+
status: 'error',
|
|
81
|
+
error: err,
|
|
82
|
+
});
|
|
83
|
+
onError && onError(err, newFile);
|
|
84
|
+
onChange && onChange(newFile);
|
|
85
|
+
});
|
|
86
|
+
};
|
|
87
|
+
const uploadFiles = (files) => {
|
|
88
|
+
let postFile = Array.from(files);
|
|
89
|
+
postFile.forEach(file => {
|
|
90
|
+
const uploadFile = convertFileToUpLoadFile(file);
|
|
91
|
+
if (!beforUpload) {
|
|
92
|
+
post(uploadFile);
|
|
93
|
+
}
|
|
94
|
+
else {
|
|
95
|
+
const result = beforUpload(uploadFile);
|
|
96
|
+
if (result && result instanceof Promise) {
|
|
97
|
+
result.then(processedFile => {
|
|
98
|
+
post(processedFile);
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
else if (result) {
|
|
102
|
+
post(uploadFile);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
});
|
|
106
|
+
};
|
|
107
|
+
const handleFileChange = (e) => {
|
|
108
|
+
const files = e.target.files;
|
|
109
|
+
if (!files)
|
|
110
|
+
return;
|
|
111
|
+
uploadFiles(files);
|
|
112
|
+
e.target.value = '';
|
|
113
|
+
};
|
|
114
|
+
const handleRemove = (file) => {
|
|
115
|
+
setFileList(prevList => {
|
|
116
|
+
return prevList.filter(item => item.uid !== file.uid);
|
|
117
|
+
});
|
|
118
|
+
if (onRemove) {
|
|
119
|
+
onRemove(file);
|
|
120
|
+
}
|
|
121
|
+
};
|
|
122
|
+
// console.log(fileList);
|
|
123
|
+
return (_jsxs("div", { className: "upload-component", children: [_jsx("label", { className: "upload-input", htmlFor: "fileInput", style: { display: 'inline-block' }, children: drag ?
|
|
124
|
+
_jsx(Dragger, { onFile: uploadFiles, children: children }) :
|
|
125
|
+
children }), _jsx("input", { className: "file-input", id: "fileInput", style: { display: "none" }, type: "file", onChange: handleFileChange, accept: accept, multiple: multiple }), _jsx(UploadList, { fileList: fileList, onRemove: handleRemove })] }));
|
|
126
|
+
};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { Progress } from "./progress";
|
|
3
|
+
import Icon from '../Icon/icon';
|
|
4
|
+
import { faFileAlt, faSpinner, faCheckCircle, faTimesCircle, faTimes } from "@fortawesome/free-solid-svg-icons";
|
|
5
|
+
export const UploadList = ({ fileList, onRemove, }) => {
|
|
6
|
+
return (_jsx("ul", { className: "upload-list", children: fileList.map(item => {
|
|
7
|
+
return (_jsxs("li", { className: "upload-list-item", children: [_jsxs("span", { className: `file-name file-name-${item.status}`, children: [_jsx(Icon, { icon: faFileAlt, theme: "secondary" }), item.name] }), _jsxs("span", { className: "file-status", children: [item.status === 'uploading' && _jsx(Icon, { icon: faSpinner, spin: true, theme: "primary" }), item.status === 'success' && _jsx(Icon, { icon: faCheckCircle, theme: "success" }), item.status === 'error' && _jsx(Icon, { icon: faTimesCircle, theme: "danger" })] }), _jsx("span", { className: "file-actions", children: _jsx(Icon, { icon: faTimes, onClick: () => onRemove(item) }) }), item.status === 'uploading' && (_jsx(Progress, { percent: item.percent || 0 }))] }, item.uid));
|
|
8
|
+
}) }));
|
|
9
|
+
};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
export function useClickOutside(ref, handler) {
|
|
3
|
+
React.useEffect(() => {
|
|
4
|
+
const listener = (e) => {
|
|
5
|
+
if (!ref.current || ref.current.contains(e.target)) {
|
|
6
|
+
return;
|
|
7
|
+
}
|
|
8
|
+
else
|
|
9
|
+
handler(e);
|
|
10
|
+
};
|
|
11
|
+
document.addEventListener('click', listener);
|
|
12
|
+
return () => {
|
|
13
|
+
document.removeEventListener('click', listener);
|
|
14
|
+
};
|
|
15
|
+
}, [ref, handler]);
|
|
16
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function useDebounce<T>(value: T, delay?: number): T;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { useState, useEffect } from 'react';
|
|
2
|
+
export function useDebounce(value, delay = 300) {
|
|
3
|
+
const [debounceValue, setDebounceValue] = useState(value);
|
|
4
|
+
useEffect(() => {
|
|
5
|
+
const handler = setTimeout(() => {
|
|
6
|
+
setDebounceValue(value);
|
|
7
|
+
}, delay);
|
|
8
|
+
return () => {
|
|
9
|
+
clearTimeout(handler);
|
|
10
|
+
};
|
|
11
|
+
}, [value, delay]);
|
|
12
|
+
return debounceValue;
|
|
13
|
+
}
|