T.AI / src /components /FileUpload.js
Aaron Meslin
start
c82f7c8
Raw
History Blame Contribute Delete
2.31 kB
import React, { useRef, useState } from 'react';
import './FileUpload.css';
function FileUpload({ label, onFileSelect, acceptedTypes, multiple, maxSize = 10 }) { // maxSize in MB
const fileInputRef = useRef(null);
const [dragActive, setDragActive] = useState(false);
const [error, setError] = useState('');
const validateFile = (file) => {
const sizeInMB = file.size / (1024 * 1024);
if (sizeInMB > maxSize) {
setError(`File size must be less than ${maxSize}MB`);
return false;
}
const fileType = file.type;
const validTypes = acceptedTypes.split(',').map(type => type.replace('.', 'application/'));
if (!validTypes.includes(fileType)) {
setError('Invalid file type');
return false;
}
setError('');
return true;
};
const handleFileChange = (e) => {
const files = Array.from(e.target.files);
if (multiple) {
const validFiles = files.filter(validateFile);
onFileSelect(validFiles);
} else {
const file = files[0];
if (validateFile(file)) {
onFileSelect(file);
}
}
};
const handleDrop = (e) => {
e.preventDefault();
setDragActive(false);
const files = Array.from(e.dataTransfer.files);
if (multiple) {
const validFiles = files.filter(validateFile);
onFileSelect(validFiles);
} else {
const file = files[0];
if (validateFile(file)) {
onFileSelect(file);
}
}
};
return (
<div className="file-upload">
<h3>{label}</h3>
<div
className={`drop-zone ${dragActive ? 'drag-active' : ''}`}
onClick={() => fileInputRef.current.click()}
onDrop={handleDrop}
onDragOver={(e) => {
e.preventDefault();
setDragActive(true);
}}
onDragLeave={() => setDragActive(false)}
>
<p>Drop files here or click to upload</p>
<p className="file-types">Accepted types: {acceptedTypes}</p>
<input
type="file"
ref={fileInputRef}
onChange={handleFileChange}
accept={acceptedTypes}
multiple={multiple}
style={{ display: 'none' }}
/>
</div>
{error && <p className="error-message">{error}</p>}
</div>
);
}
export default FileUpload;