|
- "use client";
-
- import { PurchaseQcResult, PurchaseQCInput } from "@/app/api/po/actions";
- import {
- Box,
- Card,
- CardContent,
- Checkbox,
- FormControl,
- FormControlLabel,
- Grid,
- Radio,
- RadioGroup,
- Stack,
- Tab,
- Tabs,
- TabsProps,
- TextField,
- Tooltip,
- Typography,
- } from "@mui/material";
- import { useFormContext, Controller } from "react-hook-form";
- import { useTranslation } from "react-i18next";
- import StyledDataGrid from "../StyledDataGrid";
- import { Dispatch, SetStateAction, useCallback, useEffect, useMemo, useState } from "react";
- import {
- GridColDef,
- GridRowIdGetter,
- GridRowModel,
- useGridApiContext,
- GridRenderCellParams,
- GridRenderEditCellParams,
- useGridApiRef,
- GridRowSelectionModel,
- } from "@mui/x-data-grid";
- import InputDataGrid from "../InputDataGrid";
- import { TableRow } from "../InputDataGrid/InputDataGrid";
- import TwoLineCell from "./TwoLineCell";
- import QcSelect from "./QcSelect";
- import { GridEditInputCell } from "@mui/x-data-grid";
- import { StockInLine } from "@/app/api/po";
- import { stockInLineStatusMap } from "@/app/utils/formatUtil";
- import { fetchQcItemCheck, fetchQcResult } from "@/app/api/qc/actions";
- import { QcItemWithChecks } from "@/app/api/qc";
- import axios from "@/app/(main)/axios/axiosInstance";
- import { NEXT_PUBLIC_API_URL } from "@/config/api";
- import axiosInstance from "@/app/(main)/axios/axiosInstance";
- import EscalationComponent from "./EscalationComponent";
- import QcDataGrid from "./QCDatagrid";
- import StockInFormVer2 from "./StockInFormVer2";
- import { dummyEscalationHistory, dummyQCData, QcData } from "./dummyQcTemplate";
- import { ModalFormInput } from "@/app/api/po/actions";
- import { escape } from "lodash";
-
- interface Props {
- itemDetail: StockInLine;
- qc: QcItemWithChecks[];
- disabled: boolean;
- qcItems: QcData[]
- setQcItems: Dispatch<SetStateAction<QcData[]>>
- }
-
- type EntryError =
- | {
- [field in keyof QcData]?: string;
- }
- | undefined;
-
- type QcRow = TableRow<Partial<QcData>, EntryError>;
- // fetchQcItemCheck
- const QcFormVer2: React.FC<Props> = ({ qc, itemDetail, disabled, qcItems, setQcItems }) => {
- const { t } = useTranslation("purchaseOrder");
- const apiRef = useGridApiRef();
- const {
- register,
- formState: { errors, defaultValues, touchedFields },
- watch,
- control,
- setValue,
- getValues,
- reset,
- resetField,
- setError,
- clearErrors,
- } = useFormContext<PurchaseQCInput>();
-
- const [tabIndex, setTabIndex] = useState(0);
- const [rowSelectionModel, setRowSelectionModel] = useState<GridRowSelectionModel>();
- const [escalationHistory, setEscalationHistory] = useState(dummyEscalationHistory);
- const [qcResult, setQcResult] = useState();
- const qcAccept = watch("qcAccept");
- // const [qcAccept, setQcAccept] = useState(true);
- // const [qcItems, setQcItems] = useState(dummyQCData)
-
- const column = useMemo<GridColDef[]>(
- () => [
- {
- field: "escalation",
- headerName: t("escalation"),
- flex: 1,
- },
- {
- field: "supervisor",
- headerName: t("supervisor"),
- flex: 1,
- },
- ], []
- )
- const handleTabChange = useCallback<NonNullable<TabsProps["onChange"]>>(
- (_e, newValue) => {
- setTabIndex(newValue);
- },
- [],
- );
-
- //// validate form
- const accQty = watch("acceptQty");
- const validateForm = useCallback(() => {
- console.log(accQty);
- if (accQty > itemDetail.acceptedQty) {
- setError("acceptQty", {
- message: `${t("acceptQty must not greater than")} ${
- itemDetail.acceptedQty
- }`,
- type: "required",
- });
- }
- if (accQty < 1) {
- setError("acceptQty", {
- message: t("minimal value is 1"),
- type: "required",
- });
- }
- if (isNaN(accQty)) {
- setError("acceptQty", {
- message: t("value must be a number"),
- type: "required",
- });
- }
- }, [accQty]);
-
- useEffect(() => {
- clearErrors();
- validateForm();
- }, [clearErrors, validateForm]);
-
- const columns = useMemo<GridColDef[]>(
- () => [
- {
- field: "escalation",
- headerName: t("escalation"),
- flex: 1,
- },
- {
- field: "supervisor",
- headerName: t("supervisor"),
- flex: 1,
- },
- ],
- [],
- );
- /// validate datagrid
- const validation = useCallback(
- (newRow: GridRowModel<QcRow>): EntryError => {
- const error: EntryError = {};
- // const { qcItemId, failQty } = newRow;
- return Object.keys(error).length > 0 ? error : undefined;
- },
- [],
- );
-
- function BooleanEditCell(params: GridRenderEditCellParams) {
- const apiRef = useGridApiContext();
- const { id, field, value } = params;
-
- const handleChange = (e: React.ChangeEvent<HTMLInputElement>) => {
- apiRef.current.setEditCellValue({ id, field, value: e.target.checked });
- apiRef.current.stopCellEditMode({ id, field }); // commit immediately
- };
-
- return <Checkbox checked={!!value} onChange={handleChange} sx={{ p: 0 }} />;
- }
-
- const qcColumns: GridColDef[] = [
- {
- field: "qcItem",
- headerName: t("qcItem"),
- flex: 2,
- renderCell: (params) => (
- <Box>
- <b>{params.value}</b><br/>
- {params.row.qcDescription}<br/>
- </Box>
- ),
- },
- {
- field: 'isPassed',
- headerName: t("qcResult"),
- flex: 1.5,
- renderCell: (params) => {
- const currentValue = params.value;
- return (
- <FormControl>
- <RadioGroup
- row
- aria-labelledby="demo-radio-buttons-group-label"
- value={currentValue === undefined ? "" : (currentValue ? "true" : "false")}
- onChange={(e) => {
- const value = e.target.value;
- setQcItems((prev) =>
- prev.map((r): QcData => (r.id === params.id ? { ...r, isPassed: value === "true" } : r))
- );
- }}
- name={`isPassed-${params.id}`}
- >
- <FormControlLabel
- value="true"
- control={<Radio />}
- label="合格"
- sx={{
- color: currentValue === true ? "green" : "inherit",
- "& .Mui-checked": {color: "green"}
- }}
- />
- <FormControlLabel
- value="false"
- control={<Radio />}
- label="不合格"
- sx={{
- color: currentValue === false ? "red" : "inherit",
- "& .Mui-checked": {color: "red"}
- }}
- />
- </RadioGroup>
- </FormControl>
- );
- },
- },
- {
- field: "failedQty",
- headerName: t("failedQty"),
- flex: 1,
- // editable: true,
- renderCell: (params) => (
- <TextField
- type="number"
- size="small"
- value={!params.row.isPassed? (params.value ?? '') : '0'}
- disabled={params.row.isPassed}
- onChange={(e) => {
- const v = e.target.value;
- const next = v === '' ? undefined : Number(v);
- if (Number.isNaN(next)) return;
- setQcItems((prev) =>
- prev.map((r) => (r.id === params.id ? { ...r, failedQty: next } : r))
- );
- }}
- onClick={(e) => e.stopPropagation()}
- onMouseDown={(e) => e.stopPropagation()}
- onKeyDown={(e) => e.stopPropagation()}
- inputProps={{ min: 0 }}
- sx={{ width: '100%' }}
- />
- ),
- },
- {
- field: "remarks",
- headerName: t("remarks"),
- flex: 2,
- renderCell: (params) => (
- <TextField
- size="small"
- value={params.value ?? ''}
- onChange={(e) => {
- const remarks = e.target.value;
- // const next = v === '' ? undefined : Number(v);
- // if (Number.isNaN(next)) return;
- setQcItems((prev) =>
- prev.map((r) => (r.id === params.id ? { ...r, remarks: remarks } : r))
- );
- }}
- onClick={(e) => e.stopPropagation()}
- onMouseDown={(e) => e.stopPropagation()}
- onKeyDown={(e) => e.stopPropagation()}
- inputProps={{ min: 0 }}
- sx={{ width: '100%' }}
- />
- ),
- },
- ]
-
- useEffect(() => {
- console.log(itemDetail);
-
- }, [itemDetail]);
-
- // Set initial value for acceptQty
- useEffect(() => {
- if (itemDetail?.acceptedQty !== undefined) {
- setValue("acceptQty", itemDetail.acceptedQty);
- }
- }, [itemDetail?.acceptedQty, setValue]);
-
- // const [openCollapse, setOpenCollapse] = useState(false)
- const [isCollapsed, setIsCollapsed] = useState<boolean>(false);
-
- const onFailedOpenCollapse = useCallback((qcItems: QcData[]) => {
- const isFailed = qcItems.some((qc) => !qc.isPassed)
- console.log(isFailed)
- if (isFailed) {
- setIsCollapsed(true)
- } else {
- setIsCollapsed(false)
- }
- }, [])
-
- // const handleRadioChange = useCallback((event: React.ChangeEvent<HTMLInputElement>) => {
- // const value = event.target.value === 'true';
- // setValue("qcAccept", value);
- // }, [setValue]);
-
-
- useEffect(() => {
- console.log(itemDetail);
-
- }, [itemDetail]);
-
- useEffect(() => {
- // onFailedOpenCollapse(qcItems) // This function is no longer needed
- }, [qcItems]); // Removed onFailedOpenCollapse from dependency array
-
- return (
- <>
- <Grid container justifyContent="flex-start" alignItems="flex-start">
- <Grid
- container
- justifyContent="flex-start"
- alignItems="flex-start"
- spacing={2}
- sx={{ mt: 0.5 }}
- >
- <Grid item xs={12}>
- <Tabs
- value={tabIndex}
- onChange={handleTabChange}
- variant="scrollable"
- >
- <Tab label={t("QC Info")} iconPosition="end" />
- <Tab label={t("Escalation History")} iconPosition="end" />
- </Tabs>
- </Grid>
- {tabIndex == 0 && (
- <>
- <Grid item xs={12}>
- {/* <QcDataGrid<ModalFormInput, QcData, EntryError>
- apiRef={apiRef}
- columns={qcColumns}
- _formKey="qcResult"
- validateRow={validation}
- /> */}
- <StyledDataGrid
- columns={qcColumns}
- rows={qcItems}
- autoHeight
- />
- </Grid>
-
-
- {/* <Grid item xs={12}>
- <EscalationComponent
- forSupervisor={false}
- isCollapsed={isCollapsed}
- setIsCollapsed={setIsCollapsed}
- />
- </Grid> */}
- </>
- )}
- {tabIndex == 1 && (
- <>
- {/* <Grid item xs={12}>
- <StockInFormVer2
- itemDetail={itemDetail}
- disabled={false}
- />
- </Grid> */}
- <Grid item xs={12}>
- <Typography variant="h6" display="block" marginBlockEnd={1}>
- {t("Escalation Info")}
- </Typography>
- </Grid>
- <Grid item xs={12}>
- <StyledDataGrid
- rows={escalationHistory}
- columns={columns}
- onRowSelectionModelChange={(newRowSelectionModel) => {
- setRowSelectionModel(newRowSelectionModel);
- }}
- />
- </Grid>
- </>
- )}
- <Grid item xs={12}>
- <FormControl>
- <Controller
- name="qcAccept"
- control={control}
- defaultValue={true}
- render={({ field }) => (
- <RadioGroup
- row
- aria-labelledby="demo-radio-buttons-group-label"
- {...field}
- value={field.value?.toString() || "true"}
- onChange={(e) => {
- const value = e.target.value === 'true';
- if (!value && Boolean(errors.acceptQty)) {
- setValue("acceptQty", itemDetail.acceptedQty);
- }
- field.onChange(value);
- }}
- >
- <FormControlLabel value="true" control={<Radio />} label="接受" />
- <Box sx={{mr:2}}>
- <TextField
- type="number"
- label={t("acceptQty")}
- sx={{ width: '150px' }}
- defaultValue={accQty}
- disabled={!qcAccept}
- {...register("acceptQty", {
- required: "acceptQty required!",
- })}
- error={Boolean(errors.acceptQty)}
- helperText={errors.acceptQty?.message}
- />
- </Box>
- <FormControlLabel value="false" control={<Radio />} label="不接受及上報" />
- </RadioGroup>
- )}
- />
- </FormControl>
- </Grid>
- {/* <Grid item xs={12}>
- <Typography variant="h6" display="block" marginBlockEnd={1}>
- {t("Escalation Result")}
- </Typography>
- </Grid>
- <Grid item xs={12}>
- <EscalationComponent
- forSupervisor={true}
- isCollapsed={isCollapsed}
- setIsCollapsed={setIsCollapsed}
- />
- </Grid> */}
- </Grid>
- </Grid>
- </>
- );
- };
- export default QcFormVer2;
|