|
|
@@ -137,24 +137,30 @@ const PickerStockTake: React.FC<PickerStockTakeProps> = ({ |
|
|
setLoadingDetails(false); |
|
|
setLoadingDetails(false); |
|
|
} |
|
|
} |
|
|
}, [selectedSession, total]); |
|
|
}, [selectedSession, total]); |
|
|
|
|
|
|
|
|
useEffect(() => { |
|
|
useEffect(() => { |
|
|
const inputs: Record<number, { firstQty: string; secondQty: string; firstBadQty: string; secondBadQty: string; remark: string }> = {}; |
|
|
|
|
|
inventoryLotDetails.forEach((detail) => { |
|
|
|
|
|
const firstTotal = detail.firstStockTakeQty != null |
|
|
|
|
|
? (detail.firstStockTakeQty + (detail.firstBadQty ?? 0)).toString() |
|
|
|
|
|
: ""; |
|
|
|
|
|
const secondTotal = detail.secondStockTakeQty != null |
|
|
|
|
|
? (detail.secondStockTakeQty + (detail.secondBadQty ?? 0)).toString() |
|
|
|
|
|
: ""; |
|
|
|
|
|
inputs[detail.id] = { |
|
|
|
|
|
firstQty: firstTotal, |
|
|
|
|
|
secondQty: secondTotal, |
|
|
|
|
|
firstBadQty: detail.firstBadQty?.toString() || "", |
|
|
|
|
|
secondBadQty: detail.secondBadQty?.toString() || "", |
|
|
|
|
|
remark: detail.remarks || "", |
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
setRecordInputs((prev) => { |
|
|
|
|
|
const next: Record<number, { firstQty: string; secondQty: string; firstBadQty: string; secondBadQty: string; remark: string }> = {}; |
|
|
|
|
|
inventoryLotDetails.forEach((detail) => { |
|
|
|
|
|
const hasServerFirst = detail.firstStockTakeQty != null; |
|
|
|
|
|
const hasServerSecond = detail.secondStockTakeQty != null; |
|
|
|
|
|
const firstTotal = hasServerFirst |
|
|
|
|
|
? (detail.firstStockTakeQty! + (detail.firstBadQty ?? 0)).toString() |
|
|
|
|
|
: ""; |
|
|
|
|
|
const secondTotal = hasServerSecond |
|
|
|
|
|
? (detail.secondStockTakeQty! + (detail.secondBadQty ?? 0)).toString() |
|
|
|
|
|
: ""; |
|
|
|
|
|
const existing = prev[detail.id]; |
|
|
|
|
|
next[detail.id] = { |
|
|
|
|
|
firstQty: hasServerFirst ? firstTotal : (existing?.firstQty ?? firstTotal), |
|
|
|
|
|
secondQty: hasServerSecond ? secondTotal : (existing?.secondQty ?? secondTotal), |
|
|
|
|
|
firstBadQty: hasServerFirst ? (detail.firstBadQty?.toString() || "") : (existing?.firstBadQty ?? ""), |
|
|
|
|
|
secondBadQty: hasServerSecond ? (detail.secondBadQty?.toString() || "") : (existing?.secondBadQty ?? ""), |
|
|
|
|
|
remark: hasServerSecond ? (detail.remarks || "") : (existing?.remark ?? detail.remarks ?? ""), |
|
|
|
|
|
}; |
|
|
|
|
|
}); |
|
|
|
|
|
return next; |
|
|
}); |
|
|
}); |
|
|
setRecordInputs(inputs); |
|
|
|
|
|
}, [inventoryLotDetails]); |
|
|
}, [inventoryLotDetails]); |
|
|
useEffect(() => { |
|
|
useEffect(() => { |
|
|
loadDetails(page, pageSize); |
|
|
loadDetails(page, pageSize); |
|
|
@@ -399,7 +405,40 @@ const PickerStockTake: React.FC<PickerStockTakeProps> = ({ |
|
|
} |
|
|
} |
|
|
return false; |
|
|
return false; |
|
|
}, [selectedSession?.status]); |
|
|
}, [selectedSession?.status]); |
|
|
|
|
|
|
|
|
|
|
|
const handleSubmitAllInputted = useCallback(async () => { |
|
|
|
|
|
if (!selectedSession || !currentUserId) return; |
|
|
|
|
|
|
|
|
|
|
|
const toSave = inventoryLotDetails.filter((detail) => { |
|
|
|
|
|
const submitDisabled = isSubmitDisabled(detail); |
|
|
|
|
|
if (submitDisabled) return false; |
|
|
|
|
|
const isFirstSubmit = !detail.stockTakeRecordId || !detail.firstStockTakeQty; |
|
|
|
|
|
const isSecondSubmit = detail.stockTakeRecordId && detail.firstStockTakeQty && !detail.secondStockTakeQty; |
|
|
|
|
|
const totalQtyStr = isFirstSubmit ? recordInputs[detail.id]?.firstQty : recordInputs[detail.id]?.secondQty; |
|
|
|
|
|
return !!totalQtyStr && totalQtyStr.trim() !== ""; |
|
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
|
|
if (toSave.length === 0) { |
|
|
|
|
|
onSnackbar(t("No valid input to submit"), "warning"); |
|
|
|
|
|
return; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
setBatchSaving(true); |
|
|
|
|
|
let successCount = 0; |
|
|
|
|
|
let errorCount = 0; |
|
|
|
|
|
for (const detail of toSave) { |
|
|
|
|
|
try { |
|
|
|
|
|
await handleSaveStockTake(detail); |
|
|
|
|
|
successCount++; |
|
|
|
|
|
} catch { |
|
|
|
|
|
errorCount++; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
setBatchSaving(false); |
|
|
|
|
|
onSnackbar( |
|
|
|
|
|
t("Submit completed: {{success}} success, {{errors}} errors", { success: successCount, errors: errorCount }), |
|
|
|
|
|
errorCount > 0 ? "warning" : "success" |
|
|
|
|
|
); |
|
|
|
|
|
}, [inventoryLotDetails, recordInputs, isSubmitDisabled, handleSaveStockTake, selectedSession, currentUserId, onSnackbar, t]); |
|
|
const uniqueWarehouses = Array.from( |
|
|
const uniqueWarehouses = Array.from( |
|
|
new Set( |
|
|
new Set( |
|
|
inventoryLotDetails |
|
|
inventoryLotDetails |
|
|
@@ -422,6 +461,15 @@ const PickerStockTake: React.FC<PickerStockTakeProps> = ({ |
|
|
<> {t("Warehouse")}: {uniqueWarehouses}</> |
|
|
<> {t("Warehouse")}: {uniqueWarehouses}</> |
|
|
)} |
|
|
)} |
|
|
</Typography> |
|
|
</Typography> |
|
|
|
|
|
{/* |
|
|
|
|
|
<Button |
|
|
|
|
|
variant="contained" |
|
|
|
|
|
onClick={handleSubmitAllInputted} |
|
|
|
|
|
disabled={batchSaving || saving} |
|
|
|
|
|
> |
|
|
|
|
|
{t("Submit All Inputted")} |
|
|
|
|
|
</Button> |
|
|
|
|
|
*/} |
|
|
{/* 如果需要显示快捷键输入,可以把这块注释打开 */} |
|
|
{/* 如果需要显示快捷键输入,可以把这块注释打开 */} |
|
|
{/* |
|
|
{/* |
|
|
{shortcutInput && ( |
|
|
{shortcutInput && ( |
|
|
|