IT/React
[React] Drag & Drop 파일 업로드
시린스
2024. 9. 26. 14:58
반응형
React에서 Drag & Drop이 필요하여 아래와 같이 만들었습니다.
만들면서 HTML 구조와 React에서 사용 할 수 있게 작업 하였습니다.
자세한 사항은 아래 소스 중간중간에 주석을 남겨 두었으니 참고 바랍니다.
function uploadmodal({...props}) {
const [isTxtActive, setTxtActive] = useState(false);
const [isWavActive, setWavActive] = useState(false);
//Drag & Drop
const handleDragStart = (type) => type == 'txt' ? setTxtActive(true) : setWavActive(true); //Drag를 시작 할 때 이벤트
const handleDragEnd = (type) => type == 'txt' ? setTxtActive(false) : setWavActive(false); //Drag가 끝났을 때 이벤트
const handleDragOver = (event,type) => { //파일을 드래그 하고 놨을 때 (이게 없으면 브라우저에서 실행 되거나 다운로드가 되는 증상이 나타남)
event.preventDefault();
event.stopPropagation();
};
const handelDropFile = (e,type) => { //파일을 놨을 때 이벤트
e.preventDefault();
e.stopPropagation();
const newFiles = e.dataTransfer.files[0];
console.log('[handelDropFile]newFiles :' ,newFiles);
}
//label안에 css인 pointer-events:none를 하지 않으면 내용물 안에 영역으로 들어 갔을 때 DragEnter / DragLeave가 한번씩 타면서 초기화가 되는 증상이 나타남.
return (
<label
className={`${isTxtActive ? 'bg-[#efeef3] border-[#000]' : ''} w-[50vw] max-w-[1000px] min-w-[400px] flex flex-col items-center justify-center border-2 p-[20px] rounded-lg border-dotted mb-[10px] cursor-pointer`}
htmlFor="txt-file"
onDragEnter={() => handleDragStart('txt')}
onDragOver={handleDragOver}
onDragLeave={() => handleDragEnd('txt')}
onDrop={(e) => handelDropFile(e,'txt')}
>
<div className="w-[50px] h-[50px] mb-[20px] pointer-events-none" >
<img src={txtFileIcon} alt={txtFileIcon} />
</div>
<div className="mb-[10px] pointer-events-none" >
<span className="cursor-pointer text-[14px] bg-[#444] text-white px-[10px] py-[5px] rounded-full">파일 선택</span>
</div>
<p className="pointer-events-none">또는</p>
<p className="pointer-events-none">여기로 <span className="font-bold">텍스트(.txt) 파일</span>을 드래그 하세요.</p>
<input type="file" accept=".txt" id="txt-file" name="txtfile" style={{display:'none'}}></input>
</label>
);
}
export default uploadmodal;