diff options
Diffstat (limited to 'lib/dolce/dialogs/upload-files-to-detail-dialog.tsx')
| -rw-r--r-- | lib/dolce/dialogs/upload-files-to-detail-dialog.tsx | 252 |
1 files changed, 159 insertions, 93 deletions
diff --git a/lib/dolce/dialogs/upload-files-to-detail-dialog.tsx b/lib/dolce/dialogs/upload-files-to-detail-dialog.tsx index e8d82129..f21ccc70 100644 --- a/lib/dolce/dialogs/upload-files-to-detail-dialog.tsx +++ b/lib/dolce/dialogs/upload-files-to-detail-dialog.tsx @@ -55,20 +55,29 @@ export function UploadFilesToDetailDialog({ isDragActive, } = useFileUploadWithProgress(); + const [showConfirmation, setShowConfirmation] = useState(false); + // 다이얼로그 닫을 때 초기화 React.useEffect(() => { if (!open) { clearFiles(); + setShowConfirmation(false); } }, [open, clearFiles]); - // 업로드 처리 + // 업로드 처리 (확인 단계 포함) const handleUpload = async () => { if (selectedFiles.length === 0) { toast.error(t("uploadFilesDialog.selectFilesError")); return; } + // 확인 단계가 아니면 확인 단계로 이동 + if (!showConfirmation) { + setShowConfirmation(true); + return; + } + setIsUploading(true); try { @@ -112,117 +121,169 @@ export function UploadFilesToDetailDialog({ } }; + const handleCancel = () => { + if (showConfirmation) { + setShowConfirmation(false); + } else { + onOpenChange(false); + } + }; + return ( <Dialog open={open} onOpenChange={onOpenChange}> - <DialogContent className="max-w-2xl"> + <DialogContent className="max-w-2xl max-h-[85vh] overflow-y-auto"> <DialogHeader> - <DialogTitle>{t("uploadFilesDialog.title")}</DialogTitle> + <DialogTitle> + {showConfirmation + ? t("uploadFilesDialog.confirmTitle", "파일 업로드 확인") + : t("uploadFilesDialog.title") + } + </DialogTitle> <DialogDescription> {t("uploadFilesDialog.description", { drawingNo, revNo })} </DialogDescription> </DialogHeader> - <div className="space-y-4"> - {/* 안내 메시지 */} - <Alert> - <AlertCircle className="h-4 w-4" /> - <AlertDescription> - {t("uploadFilesDialog.alertMessage")} - </AlertDescription> - </Alert> - - {/* 파일 선택 영역 */} - <div - {...getRootProps()} - className={`border-2 border-dashed rounded-lg p-8 transition-all duration-200 cursor-pointer ${ - isDragActive - ? "border-primary bg-primary/5 scale-[1.02]" - : "border-muted-foreground/30 hover:border-muted-foreground/50" - }`} - > - <input {...getInputProps()} /> - <div className="flex flex-col items-center justify-center"> - <FolderOpen - className={`h-12 w-12 mb-3 transition-colors ${ - isDragActive ? "text-primary" : "text-muted-foreground" - }`} - /> - <p - className={`text-sm transition-colors ${ - isDragActive - ? "text-primary font-medium" - : "text-muted-foreground" - }`} - > - {isDragActive - ? t("uploadFilesDialog.dropHereText") - : t("uploadFilesDialog.dragDropText")} - </p> - <p className="text-xs text-muted-foreground mt-1"> - {t("uploadFilesDialog.fileInfo")} - </p> - </div> - </div> + {showConfirmation ? ( + <div className="space-y-4"> + <Alert> + <AlertCircle className="h-4 w-4" /> + <AlertDescription> + {t("uploadFilesDialog.confirmMessage", "선택한 파일을 업로드하시겠습니까?")} + </AlertDescription> + </Alert> - {/* 선택된 파일 목록 */} - {selectedFiles.length > 0 && ( <div className="border rounded-lg p-4"> - {isUploading ? ( - // 업로드 중: 진행도 표시 - <FileUploadProgressList fileProgresses={fileProgresses} /> - ) : ( - // 대기 중: 삭제 버튼 표시 - <> - <div className="flex items-center justify-between mb-3"> - <h4 className="text-sm font-medium"> - {t("uploadFilesDialog.selectedFiles", { count: selectedFiles.length })} - </h4> - <Button - variant="ghost" - size="sm" - onClick={clearFiles} + <h4 className="text-sm font-medium mb-3"> + {t("uploadFilesDialog.selectedFiles", { count: selectedFiles.length })} + </h4> + <div className="max-h-60 overflow-y-auto space-y-2"> + {isUploading ? ( + <FileUploadProgressList fileProgresses={fileProgresses} /> + ) : ( + selectedFiles.map((file, index) => ( + <div + key={index} + className="flex items-center justify-between p-2 rounded bg-muted/50" > - {t("uploadFilesDialog.removeAll")} - </Button> - </div> - <div className="max-h-60 overflow-y-auto space-y-2"> - {selectedFiles.map((file, index) => ( - <div - key={index} - className="flex items-center justify-between p-2 rounded bg-muted/50" - > - <div className="flex items-center gap-2 flex-1 min-w-0"> - <FileText className="h-4 w-4 text-muted-foreground shrink-0" /> - <div className="flex-1 min-w-0"> - <p className="text-sm truncate">{file.name}</p> - <p className="text-xs text-muted-foreground"> - {(file.size / 1024 / 1024).toFixed(2)} MB - </p> - </div> + <div className="flex items-center gap-2 flex-1 min-w-0"> + <FileText className="h-4 w-4 text-muted-foreground shrink-0" /> + <div className="flex-1 min-w-0"> + <p className="text-sm truncate">{file.name}</p> + <p className="text-xs text-muted-foreground"> + {(file.size / 1024 / 1024).toFixed(2)} MB + </p> </div> - <Button - variant="ghost" - size="sm" - onClick={() => removeFile(index)} - > - <X className="h-4 w-4" /> - </Button> </div> - ))} - </div> - </> - )} + </div> + )) + )} + </div> + </div> + </div> + ) : ( + <div className="space-y-4"> + {/* 안내 메시지 */} + <Alert> + <AlertCircle className="h-4 w-4" /> + <AlertDescription> + {t("uploadFilesDialog.alertMessage")} + </AlertDescription> + </Alert> + + {/* 파일 선택 영역 */} + <div + {...getRootProps()} + className={`border-2 border-dashed rounded-lg p-8 transition-all duration-200 cursor-pointer ${ + isDragActive + ? "border-primary bg-primary/5 scale-[1.02]" + : "border-muted-foreground/30 hover:border-muted-foreground/50" + }`} + > + <input {...getInputProps()} /> + <div className="flex flex-col items-center justify-center"> + <FolderOpen + className={`h-12 w-12 mb-3 transition-colors ${ + isDragActive ? "text-primary" : "text-muted-foreground" + }`} + /> + <p + className={`text-sm transition-colors ${ + isDragActive + ? "text-primary font-medium" + : "text-muted-foreground" + }`} + > + {isDragActive + ? t("uploadFilesDialog.dropHereText") + : t("uploadFilesDialog.dragDropText")} + </p> + <p className="text-xs text-muted-foreground mt-1"> + {t("uploadFilesDialog.fileInfo")} + </p> + </div> </div> - )} - </div> + + {/* 선택된 파일 목록 */} + {selectedFiles.length > 0 && ( + <div className="border rounded-lg p-4"> + {isUploading ? ( + // 업로드 중: 진행도 표시 + <FileUploadProgressList fileProgresses={fileProgresses} /> + ) : ( + // 대기 중: 삭제 버튼 표시 + <> + <div className="flex items-center justify-between mb-3"> + <h4 className="text-sm font-medium"> + {t("uploadFilesDialog.selectedFiles", { count: selectedFiles.length })} + </h4> + <Button + variant="ghost" + size="sm" + onClick={clearFiles} + > + {t("uploadFilesDialog.removeAll")} + </Button> + </div> + <div className="max-h-60 overflow-y-auto space-y-2"> + {selectedFiles.map((file, index) => ( + <div + key={index} + className="flex items-center justify-between p-2 rounded bg-muted/50" + > + <div className="flex items-center gap-2 flex-1 min-w-0"> + <FileText className="h-4 w-4 text-muted-foreground shrink-0" /> + <div className="flex-1 min-w-0"> + <p className="text-sm truncate">{file.name}</p> + <p className="text-xs text-muted-foreground"> + {(file.size / 1024 / 1024).toFixed(2)} MB + </p> + </div> + </div> + <Button + variant="ghost" + size="sm" + onClick={() => removeFile(index)} + > + <X className="h-4 w-4" /> + </Button> + </div> + ))} + </div> + </> + )} + </div> + )} + </div> + )} <DialogFooter> <Button variant="outline" - onClick={() => onOpenChange(false)} + onClick={handleCancel} disabled={isUploading} > - {t("uploadFilesDialog.cancelButton")} + {showConfirmation ? t("uploadFilesDialog.backButton", "뒤로") : t("uploadFilesDialog.cancelButton")} </Button> <Button onClick={handleUpload} @@ -233,10 +294,15 @@ export function UploadFilesToDetailDialog({ <Loader2 className="mr-2 h-4 w-4 animate-spin" /> {t("uploadFilesDialog.uploadingButton")} </> + ) : showConfirmation ? ( + <> + <Upload className="mr-2 h-4 w-4" /> + {t("uploadFilesDialog.confirmUpload", "업로드")} + </> ) : ( <> <Upload className="mr-2 h-4 w-4" /> - {t("uploadFilesDialog.uploadButton", { count: selectedFiles.length })} + {t("uploadFilesDialog.nextButton", "다음")} </> )} </Button> |
