gongxiangp2/hooks/useUploadState.ts
chenpei 0ce59be34e 备份:组织架构设计方案讨论前的代码快照
- 包含所有当前修改和新功能
- 准备开始组织架构优化实施方案
2025-12-30 13:20:26 +08:00

281 lines
8.6 KiB
TypeScript

/**
* 上传状态管理 Hook
* 封装 UploadModal 组件的所有状态定义
*/
import { useState, useRef } from 'react'
import type { BatchFileItem, BatchUploadStatus } from '@/components/upload/upload-types'
/**
* 上传状态接口
*/
export interface UploadState {
// 预览图片
previewImages: File[]
previewUrls: string[]
// 详情页展示图片
displayImage: File | null
displayImageUrl: string
// 模特图片
modelImages: File[]
modelImageUrls: string[]
// 素材文件
zipFile: File | null
// 表单字段
productModel: string
categoryName: string
sceneName: string
platformName: string
productCategoryName: string
materialType: string
renderer: string
// 新建分类输入
showNewCategoryInput: boolean
newCategoryName: string
showNewSceneInput: boolean
newSceneName: string
// 上传状态
uploading: boolean
uploadProgress: number
uploadSpeed: number
isProcessing: boolean
error: string
retryCount: number
// 批量上传
batchFiles: BatchFileItem[]
isBatchMode: boolean
batchUploadStatus: BatchUploadStatus | null
// 拖拽状态
isDragging: boolean
isDisplayImageDragging: boolean
isPreviewDragging: boolean
batchPreviewDragging: Record<string, boolean>
}
/**
* 上传状态操作接口
*/
export interface UploadStateActions {
// 预览图片操作
setPreviewImages: React.Dispatch<React.SetStateAction<File[]>>
setPreviewUrls: React.Dispatch<React.SetStateAction<string[]>>
// 详情页展示图片操作
setDisplayImage: React.Dispatch<React.SetStateAction<File | null>>
setDisplayImageUrl: React.Dispatch<React.SetStateAction<string>>
// 模特图片操作
setModelImages: React.Dispatch<React.SetStateAction<File[]>>
setModelImageUrls: React.Dispatch<React.SetStateAction<string[]>>
// 素材文件操作
setZipFile: React.Dispatch<React.SetStateAction<File | null>>
// 表单字段操作
setProductModel: React.Dispatch<React.SetStateAction<string>>
setCategoryName: React.Dispatch<React.SetStateAction<string>>
setSceneName: React.Dispatch<React.SetStateAction<string>>
setPlatformName: React.Dispatch<React.SetStateAction<string>>
setProductCategoryName: React.Dispatch<React.SetStateAction<string>>
setMaterialType: React.Dispatch<React.SetStateAction<string>>
setRenderer: React.Dispatch<React.SetStateAction<string>>
// 新建分类输入操作
setShowNewCategoryInput: React.Dispatch<React.SetStateAction<boolean>>
setNewCategoryName: React.Dispatch<React.SetStateAction<string>>
setShowNewSceneInput: React.Dispatch<React.SetStateAction<boolean>>
setNewSceneName: React.Dispatch<React.SetStateAction<string>>
// 上传状态操作
setUploading: React.Dispatch<React.SetStateAction<boolean>>
setUploadProgress: React.Dispatch<React.SetStateAction<number>>
setUploadSpeed: React.Dispatch<React.SetStateAction<number>>
setIsProcessing: React.Dispatch<React.SetStateAction<boolean>>
setError: React.Dispatch<React.SetStateAction<string>>
setRetryCount: React.Dispatch<React.SetStateAction<number>>
// 批量上传操作
setBatchFiles: React.Dispatch<React.SetStateAction<BatchFileItem[]>>
setIsBatchMode: React.Dispatch<React.SetStateAction<boolean>>
setBatchUploadStatus: React.Dispatch<React.SetStateAction<BatchUploadStatus | null>>
// 拖拽状态操作
setIsDragging: React.Dispatch<React.SetStateAction<boolean>>
setIsDisplayImageDragging: React.Dispatch<React.SetStateAction<boolean>>
setIsPreviewDragging: React.Dispatch<React.SetStateAction<boolean>>
setBatchPreviewDragging: React.Dispatch<React.SetStateAction<Record<string, boolean>>>
}
/**
* Refs 接口
*/
export interface UploadRefs {
previewInputRef: React.RefObject<HTMLInputElement>
zipInputRef: React.RefObject<HTMLInputElement>
dropZoneRef: React.RefObject<HTMLDivElement>
displayImageDropZoneRef: React.RefObject<HTMLDivElement>
previewDropZoneRef: React.RefObject<HTMLDivElement>
xhrRef: React.MutableRefObject<XMLHttpRequest | null>
batchFileInputRef: React.RefObject<HTMLInputElement>
batchUploadCancelRef: React.MutableRefObject<{ cancelled: boolean }>
batchUploadXhrRefs: React.MutableRefObject<Map<string, XMLHttpRequest>>
batchUploadIdsRef: React.MutableRefObject<Map<string, string>>
}
/**
* 上传状态管理 Hook
*/
export function useUploadState() {
// 预览图片
const [previewImages, setPreviewImages] = useState<File[]>([])
const [previewUrls, setPreviewUrls] = useState<string[]>([])
// 详情页展示图片
const [displayImage, setDisplayImage] = useState<File | null>(null)
const [displayImageUrl, setDisplayImageUrl] = useState<string>('')
// 模特图片
const [modelImages, setModelImages] = useState<File[]>([])
const [modelImageUrls, setModelImageUrls] = useState<string[]>([])
// 素材文件
const [zipFile, setZipFile] = useState<File | null>(null)
// 表单字段
const [productModel, setProductModel] = useState('')
const [categoryName, setCategoryName] = useState('')
const [sceneName, setSceneName] = useState('')
const [platformName, setPlatformName] = useState('')
const [productCategoryName, setProductCategoryName] = useState('')
const [materialType, setMaterialType] = useState('3D场景')
const [renderer, setRenderer] = useState('CR')
// 新建分类输入
const [showNewCategoryInput, setShowNewCategoryInput] = useState(false)
const [newCategoryName, setNewCategoryName] = useState('')
const [showNewSceneInput, setShowNewSceneInput] = useState(false)
const [newSceneName, setNewSceneName] = useState('')
// 上传状态
const [uploading, setUploading] = useState(false)
const [uploadProgress, setUploadProgress] = useState(0)
const [uploadSpeed, setUploadSpeed] = useState(0)
const [isProcessing, setIsProcessing] = useState(false)
const [error, setError] = useState('')
const [retryCount, setRetryCount] = useState(0)
// 批量上传
const [batchFiles, setBatchFiles] = useState<BatchFileItem[]>([])
const [isBatchMode, setIsBatchMode] = useState(false)
const [batchUploadStatus, setBatchUploadStatus] = useState<BatchUploadStatus | null>(null)
// 拖拽状态
const [isDragging, setIsDragging] = useState(false)
const [isDisplayImageDragging, setIsDisplayImageDragging] = useState(false)
const [isPreviewDragging, setIsPreviewDragging] = useState(false)
const [batchPreviewDragging, setBatchPreviewDragging] = useState<Record<string, boolean>>({})
// Refs
const previewInputRef = useRef<HTMLInputElement>(null)
const zipInputRef = useRef<HTMLInputElement>(null)
const dropZoneRef = useRef<HTMLDivElement>(null)
const displayImageDropZoneRef = useRef<HTMLDivElement>(null)
const previewDropZoneRef = useRef<HTMLDivElement>(null)
const xhrRef = useRef<XMLHttpRequest | null>(null)
const batchFileInputRef = useRef<HTMLInputElement>(null)
const batchUploadCancelRef = useRef<{ cancelled: boolean }>({ cancelled: false })
const batchUploadXhrRefs = useRef<Map<string, XMLHttpRequest>>(new Map())
const batchUploadIdsRef = useRef<Map<string, string>>(new Map())
const state: UploadState = {
previewImages,
previewUrls,
displayImage,
displayImageUrl,
modelImages,
modelImageUrls,
zipFile,
productModel,
categoryName,
sceneName,
platformName,
productCategoryName,
materialType,
renderer,
showNewCategoryInput,
newCategoryName,
showNewSceneInput,
newSceneName,
uploading,
uploadProgress,
uploadSpeed,
isProcessing,
error,
retryCount,
batchFiles,
isBatchMode,
batchUploadStatus,
isDragging,
isDisplayImageDragging,
isPreviewDragging,
batchPreviewDragging,
}
const actions: UploadStateActions = {
setPreviewImages,
setPreviewUrls,
setDisplayImage,
setDisplayImageUrl,
setModelImages,
setModelImageUrls,
setZipFile,
setProductModel,
setCategoryName,
setSceneName,
setPlatformName,
setProductCategoryName,
setMaterialType,
setRenderer,
setShowNewCategoryInput,
setNewCategoryName,
setShowNewSceneInput,
setNewSceneName,
setUploading,
setUploadProgress,
setUploadSpeed,
setIsProcessing,
setError,
setRetryCount,
setBatchFiles,
setIsBatchMode,
setBatchUploadStatus,
setIsDragging,
setIsDisplayImageDragging,
setIsPreviewDragging,
setBatchPreviewDragging,
}
const refs: UploadRefs = {
previewInputRef,
zipInputRef,
dropZoneRef,
displayImageDropZoneRef,
previewDropZoneRef,
xhrRef,
batchFileInputRef,
batchUploadCancelRef,
batchUploadXhrRefs,
batchUploadIdsRef,
}
return { state, actions, refs }
}