"use client"

import {
  addDailyWorkData,
  editDailyWorkData,
} from "@/components/label/api/daily"
import { Daily } from "@/components/label/api/daily/typing"
import {
  useAllUserStore,
  usePermissionStore,
} from "@/components/label/store/auth"
import { formatUserTreeOptions } from "@/components/tree-select/libs/util"
import { VirtualTreeSelect } from "@/components/tree-select/tree"
import {
  Button,
  Group,
  Modal,
  NumberInput,
  Paper,
  Select,
  SimpleGrid,
  Stack,
  Text,
  TextInput,
} from "@mantine/core"
import { DateInput } from "@mantine/dates"
import { useForm } from "@mantine/form"
import { notifications } from "@mantine/notifications"
import "dayjs/locale/zh-cn"
import { useEffect, useMemo } from "react"
import {
  accountTypeOpts,
  actualTypeOpts,
  objTypeOpts,
  performanceOpts,
  setTypeOpts,
  workTypeOpts,
} from "../config"
import classes from "./DailyReportModal.module.css"

function normalizeTimeValue(value?: string | null) {
  if (!value) return ""
  return value.length >= 5 ? value.slice(0, 5) : value
}

function toTimeWithSeconds(value?: string) {
  if (!value) return undefined
  return value.length === 5 ? `${value}:00` : value
}

function HourRightSection() {
  return (
    <Text size="xs" c="dimmed">
      小时(H)
    </Text>
  )
}

function getEmptyFormValues(currentUserName?: string) {
  return {
    user_name: currentUserName ?? "",
    date: "",
    start_time: "",
    end_time: "",
    set_type: "",
    actual_type: "",
    project_id: "",
    leader_uid: "",
    work_type: "",
    accounting_type: "",
    performance_accounting: "",
    obj_type: "",
    work_time: undefined as number | undefined,
    rate: undefined as number | undefined,
    standard_size: undefined as number | undefined,
    completed_size: undefined as number | undefined,
    residual_size: undefined as number | undefined,
    residual_work_time: undefined as number | undefined,
    residual_pm: "",
    remarks: "",
  }
}

function getCreateFormValues(currentUserName?: string) {
  return {
    ...getEmptyFormValues(currentUserName),
    date: new Date().toISOString().slice(0, 10),
  }
}

function getRecordFormValues(
  record: Daily.DailyWorkList,
  currentUserName?: string
) {
  return {
    user_name: currentUserName ?? "",
    date: record.date ?? "",
    start_time: normalizeTimeValue(record.start_time),
    end_time: normalizeTimeValue(record.end_time),
    set_type: record.set_type ?? "",
    actual_type: record.actual_type ?? "",
    project_id:
      record.project_id === undefined || record.project_id === null
        ? ""
        : String(record.project_id),
    leader_uid:
      record.leader_uid === undefined || record.leader_uid === null
        ? ""
        : String(record.leader_uid),
    work_type: record.work_type ?? "",
    accounting_type: record.accounting_type ?? "",
    performance_accounting:
      record.performance_accounting === true
        ? "true"
        : record.performance_accounting === false
          ? "false"
          : "",
    obj_type:
      record.obj_type === undefined || record.obj_type === null
        ? ""
        : String(record.obj_type),
    work_time: record.work_time ?? undefined,
    rate: record.rate ?? undefined,
    standard_size: record.standard_size ?? undefined,
    completed_size: record.completed_size ?? undefined,
    residual_size: record.residual_size ?? undefined,
    residual_work_time: record.residual_work_time ?? undefined,
    residual_pm:
      record.residual_pm === true
        ? "正"
        : record.residual_pm === false
          ? "负"
          : "",
    remarks: record.remarks ?? "",
  }
}

export default function DailyReportModal(props: {
  opened: boolean
  record: Daily.DailyWorkList | null
  projectOptions: Array<{ label: string; value: string }>
  onCloseAction: (refresh?: boolean) => void
}) {
  const { opened, record, onCloseAction, projectOptions } = props

  const user_id = usePermissionStore((s) => s.user_id)
  const user_name = usePermissionStore((s) => s.user_name)
  const treeData = useAllUserStore((s) => s.treeData)

  const leaderOptions = useMemo(
    () => formatUserTreeOptions(treeData ?? []),
    [treeData]
  )

  const form = useForm({
    initialValues: getEmptyFormValues(user_name),
    validate: {
      date: (v) => (v ? null : "请输入日期"),
      set_type: (v) => (v ? null : "请选择规定类型"),
      actual_type: (v) => (v ? null : "请选择出勤类型"),
    },
    validateInputOnChange: true,
    validateInputOnBlur: true,
    clearInputErrorOnChange: true,
  })

  const resetFormState = () => {
    form.setValues(getEmptyFormValues(user_name))
    form.clearErrors()
    form.resetDirty()
  }

  useEffect(() => {
    if (!opened) {
      resetFormState()
      return
    }

    if (!record) {
      form.setValues(getCreateFormValues(user_name))
      form.clearErrors()
      form.resetDirty()
      return
    }

    form.setValues(getRecordFormValues(record, user_name))
    form.clearErrors()
    form.resetDirty()
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [opened, record, user_name])

  useEffect(() => {
    const workTime = form.values.work_time
    const rate = form.values.rate
    if (workTime !== undefined && rate !== undefined) {
      form.setFieldValue("standard_size", Number((workTime * rate).toFixed(1)))
    } else {
      form.setFieldValue("standard_size", undefined)
    }
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [form.values.work_time, form.values.rate])

  useEffect(() => {
    const standardSize = form.values.standard_size
    const completedSize = form.values.completed_size
    const workTime = form.values.work_time

    if (
      standardSize !== undefined &&
      completedSize !== undefined &&
      workTime !== undefined &&
      standardSize !== 0
    ) {
      const residualSize = completedSize - standardSize
      const residualWorkTime = Number(
        ((residualSize / standardSize) * workTime).toFixed(1)
      )
      form.setFieldValue("residual_size", Number(residualSize.toFixed(1)))
      form.setFieldValue("residual_work_time", residualWorkTime)
      form.setFieldValue("residual_pm", residualSize >= 0 ? "正" : "负")
    } else {
      form.setFieldValue("residual_size", undefined)
      form.setFieldValue("residual_work_time", undefined)
      form.setFieldValue("residual_pm", "")
    }
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [
    form.values.standard_size,
    form.values.completed_size,
    form.values.work_time,
  ])

  const handleSubmit = form.onSubmit(async (values) => {
    const uid = typeof user_id === "number" ? user_id : Number(user_id ?? 0)
    if (!uid) {
      notifications.show({
        color: "red",
        title: "提交失败",
        message: "未获取到用户信息",
      })
      return
    }

    const params: Daily.CreateProps = {
      uid,
      date: values.date,
      start_time: toTimeWithSeconds(values.start_time),
      end_time: toTimeWithSeconds(values.end_time),
      set_type: values.set_type,
      actual_type: values.actual_type,
      project_id: values.project_id ? Number(values.project_id) : undefined,
      leader_uid: values.leader_uid ? Number(values.leader_uid) : undefined,
      work_type: values.work_type || undefined,
      accounting_type: values.accounting_type || undefined,
      performance_accounting:
        values.performance_accounting === "true"
          ? true
          : values.performance_accounting === "false"
            ? false
            : undefined,
      obj_type: values.obj_type ? Number(values.obj_type) : undefined,
      work_time: values.work_time || undefined,
      rate: values.rate || undefined,
      standard_size: values.standard_size || undefined,
      completed_size: values.completed_size || undefined,
      residual_size: values.residual_size || undefined,
      residual_work_time: values.residual_work_time || undefined,
      residual_pm:
        values.residual_pm === "正"
          ? true
          : values.residual_pm === "负"
            ? false
            : undefined,
      remarks: values.remarks || undefined,
    }

    try {
      if (record?.id) {
        await editDailyWorkData(params, record.id)
        notifications.show({
          color: "green",
          title: "操作成功",
          message: "已更新日报",
        })
      } else {
        await addDailyWorkData(params)
        notifications.show({
          color: "green",
          title: "操作成功",
          message: "已提交日报",
        })
      }
      resetFormState()
      onCloseAction(true)
    } catch (e) {
      notifications.show({
        color: "red",
        title: "操作失败",
        message: e instanceof Error ? e.message : "请求失败",
      })
    }
  })

  return (
    <Modal
      opened={opened}
      onClose={() => {
        resetFormState()
        onCloseAction()
      }}
      title={record ? "编辑日报" : "填写日报"}
      size={840}
      centered
      classNames={{
        content: classes.modalContent,
        header: classes.modalHeader,
        title: classes.modalTitle,
        body: classes.modalBody,
      }}
      overlayProps={{ backgroundOpacity: 0.22 }}
      transitionProps={{
        transition: "fade",
        duration: 100,
        timingFunction: "ease",
      }}
      closeOnClickOutside={false}>
      <form onSubmit={handleSubmit}>
        <Paper withBorder radius="sm" p="md" className={classes.formSurface}>
          <Stack gap="md" className={classes.formPanel}>
            <SimpleGrid cols={{ base: 1, sm: 3 }} spacing="sm">
              <TextInput label="姓名" value={form.values.user_name} readOnly />
              <DateInput
                label="日期"
                locale="zh-cn"
                withAsterisk
                {...form.getInputProps("date")}
              />
              <div />

              <TextInput
                label="开始时间"
                type="time"
                {...form.getInputProps("start_time")}
              />
              <TextInput
                label="结束时间"
                type="time"
                {...form.getInputProps("end_time")}
              />
              <div />

              <Select
                label="规定类型"
                withAsterisk
                data={setTypeOpts}
                searchable
                clearable
                {...form.getInputProps("set_type")}
                value={form.values.set_type || null}
                onChange={(value) =>
                  form.setFieldValue("set_type", value ?? "")
                }
              />
              <Select
                label="出勤类型"
                withAsterisk
                data={actualTypeOpts}
                searchable
                clearable
                {...form.getInputProps("actual_type")}
                value={form.values.actual_type || null}
                onChange={(value) =>
                  form.setFieldValue("actual_type", value ?? "")
                }
              />
              <div />

              <Select
                label="项目名称"
                data={projectOptions}
                searchable
                clearable
                {...form.getInputProps("project_id")}
                value={form.values.project_id || null}
                onChange={(value) =>
                  form.setFieldValue("project_id", value ?? "")
                }
              />
              <VirtualTreeSelect
                mode="single"
                data={leaderOptions}
                {...form.getInputProps("leader_uid")}
                value={form.values.leader_uid || null}
                onChange={(value) =>
                  form.setFieldValue("leader_uid", value ?? "")
                }
                label="任务组长"
              />
              <Select
                label="工作类别"
                data={workTypeOpts}
                searchable
                clearable
                {...form.getInputProps("work_type")}
                value={form.values.work_type || null}
                onChange={(value) =>
                  form.setFieldValue("work_type", value ?? "")
                }
              />

              <Select
                label="对象类型"
                data={objTypeOpts}
                searchable
                clearable
                {...form.getInputProps("obj_type")}
                value={form.values.obj_type || null}
                onChange={(value) =>
                  form.setFieldValue("obj_type", value ?? "")
                }
              />
              <Select
                label="绩效核算"
                data={performanceOpts}
                searchable
                clearable
                {...form.getInputProps("performance_accounting")}
                value={form.values.performance_accounting || null}
                onChange={(value) =>
                  form.setFieldValue("performance_accounting", value ?? "")
                }
              />
              <Select
                label="核算方式"
                data={accountTypeOpts}
                searchable
                clearable
                {...form.getInputProps("accounting_type")}
                value={form.values.accounting_type || null}
                onChange={(value) =>
                  form.setFieldValue("accounting_type", value ?? "")
                }
              />

              <NumberInput
                label="工时"
                min={0}
                decimalScale={1}
                allowNegative={false}
                hideControls
                rightSection={<HourRightSection />}
                rightSectionWidth={78}
                {...form.getInputProps("work_time")}
              />
              <NumberInput
                label="额定倍速"
                min={0}
                allowNegative={false}
                hideControls
                {...form.getInputProps("rate")}
              />
              <div />

              <NumberInput
                label="标准量"
                value={form.values.standard_size}
                readOnly
                hideControls
              />
              <NumberInput
                label="完成量"
                min={0}
                allowNegative={false}
                hideControls
                {...form.getInputProps("completed_size")}
              />
              <div />

              <NumberInput
                label="余量"
                value={form.values.residual_size}
                readOnly
                hideControls
              />
              <NumberInput
                label="余量工时"
                value={form.values.residual_work_time}
                readOnly
                hideControls
                rightSection={<HourRightSection />}
                rightSectionWidth={78}
              />
              <TextInput
                label="余量正负"
                value={form.values.residual_pm}
                readOnly
              />
            </SimpleGrid>

            <TextInput label="备注" {...form.getInputProps("remarks")} />

            <Group justify="flex-end" gap="sm">
              <Button
                variant="default"
                onClick={() => {
                  resetFormState()
                  onCloseAction()
                }}>
                取消
              </Button>
              <Button type="submit" color="#1874ff">
                提交
              </Button>
            </Group>
          </Stack>
        </Paper>
      </form>
    </Modal>
  )
}
