react+antd使用自定义上传(七牛上传)多文件组件
import { property } from '@/services/property';
import { LoadingOutlined, PlusOutlined } from '@ant-design/icons';
import { Button, Col, message, Modal, Upload } from 'antd';
import { memo, useCallback, useEffect, useState } from 'react';
import { useRequest } from 'umi';
import styles from './index.less';
// eslint-disable-next-line react-hooks/exhaustive-deps, prefer-const
let tempImg: any = [];
type FileExtension = 'jpg' | 'jpeg' | 'bmp' | 'png' | 'gif' | 'txt' | 'pdf' | 'doc' | 'docx' | 'xls' | 'xlsx' | 'mp3' | 'mp4' | 'ppt' | 'pptx' | 'rar' | 'zip' | 'apk' | 'exe' | 'iso' | 'apk' | 'sql' | 'html' | 'htm' | 'xml' | 'css' | 'js';
let fileNum = 0
const UploadFile = (
{ setUploadUrl, uploadUrl, maxCount, formKey, rowKey, allowFileType, uploadText, useOriginFileName }:
{
setUploadUrl: any;
uploadUrl: string[];
maxCount: number;
formKey?: string | number;
rowKey?: number,
allowFileType?: FileExtension[],
uploadText?: string,
useOriginFileName?: boolean
}
) => {
const [imgUrl, setImgUrl] = useState<string[]>([]);
const [fileList, setFileList] = useState<any>([]);
const [prvieVisible, setPrvieVisible] = useState(false);
const [fileUrl, setFileUrl] = useState('');
useEffect(() => {
tempImg = uploadUrl;
setImgUrl(uploadUrl || []);
setLoading(false)
}, [uploadUrl]);
useEffect(() => {
let temp: any = imgUrl.concat([]) || []
temp = uploadUrl.map((item: any) => {
const name = item.split('/')[item.split('/').length - 1]
return {
uid: item,
name: name,
status: 'done',
url: item,
}
})
setFileList(temp)
}, [imgUrl]);
// eslint-disable-next-line @typescript-eslint/no-unused-vars
const [loading, setLoading] = useState<boolean>(false);
const uploadButton = (
<div className={styles.uploadButton} key={rowKey}>
{loading ? <LoadingOutlined /> : <PlusOutlined />}
<div style={{ marginTop: 8 }}>{uploadText == undefined ? '上传文件' : uploadText}</div>
</div>
);
// const customRequest = useCallback((e) => {
// getMyReceiveLog(e.file, fileNum);
// }, []);
//自定义图片上传处理
const customRequest = async (e: any) => {
const file = e.file;
console.log('fileNum', fileNum)
try {
setLoading(true)
const res: any = await property.getQiniuToken({ manual: true });
let { token, filePath } = res.data;
const index = file.name.lastIndexOf('.');
const name = file.name.substr(index);
filePath += name;
const formData = new FormData();
formData.append('token', token);
formData.append('key', filePath);
formData.append('file', file);
fileNum++
property.upload(formData).then((q: any) => {
console.log('上传', formData)
let { key } = q || {};
const url = `https://cdn-imis.meb.com/${key}`;
if (tempImg.length >= maxCount) {
tempImg.splice(tempImg.length - 1, 1, url);
} else {
tempImg.push(url);
}
setImgUrl([...tempImg]);
setUploadUrl([...tempImg], formKey);
}).catch((error) => {
fileNum--
console.log('fileNum', fileNum, tempImg.length)
message.error('上传失败');
}).finally(() => {
console.log('fileNum', fileNum, tempImg.length)
if (fileNum == tempImg.length) {
setLoading(false)
}
})
} catch (error: any) {
console.log(error);
}
};
const imgDel = (img: any) => {
console.log('fileNum', fileNum)
const bb = JSON.parse(JSON.stringify(imgUrl));
const newImg: any = [];
if (bb && bb.length) {
bb.map((item: any) => {
if (item != img) {
newImg.push(item);
}
});
}
tempImg = newImg;
fileNum--
setImgUrl([...newImg]);
setUploadUrl([...newImg], formKey);
};
return (
<div key={rowKey}>
<div>
{
<Upload name="avatar" className="avatar-uploader" disabled={loading} multiple listType="picture-card" showUploadList={{ showPreviewIcon: false }}
fileList={fileList} customRequest={customRequest} onRemove={(e) => { imgDel(e.url) }}>
{Array.isArray(imgUrl) && imgUrl.length < maxCount && <div>{uploadButton}</div>}
</Upload>
}
</div>
</div>
);
};
export default memo(UploadFile );
在页面中使用此组件
const [urlList, setUrlList] = useState<string[]>([]);
const handerUploadUrl = (e: any) => {
setUrlList(e);
};
<UploadFile
useOriginFileName={true}
setUploadUrl={handerUploadUrl}
allowFileType={['jpg', 'jpeg', 'bmp', 'png', 'gif', 'txt', 'pdf', 'doc', 'docx', 'xls', 'xlsx']}
uploadUrl={urlList}
maxCount={5}
formKey="cover"
uploadText="上传文件"
/>