import dayjs, { ConfigType, Dayjs } from "dayjs";
import { Uom } from "../api/settings/uom";
import {
  ListIterateeCustom,
  every,
  isArray,
  isNaN,
  isNull,
  isUndefined,
  take,
} from "lodash";
import { Box, BoxProps } from "@mui/material";

export const manhourFormatter = new Intl.NumberFormat("en-HK", {
  minimumFractionDigits: 2,
  maximumFractionDigits: 2,
});

export const moneyFormatter = new Intl.NumberFormat("en-HK", {
  style: "currency",
  currency: "HKD",
});

export const decimalFormatter = new Intl.NumberFormat("en-HK", {
  minimumFractionDigits: 2,
  maximumFractionDigits: 5,
});

export const integerFormatter = new Intl.NumberFormat("en-HK", {});

export const INPUT_DATE_FORMAT = "YYYY-MM-DD";

export const OUTPUT_DATE_FORMAT = "YYYY/MM/DD";

export const INPUT_TIME_FORMAT = "HH:mm:ss";

export const OUTPUT_TIME_FORMAT = "HH:mm:ss";

export const arrayToDayjs = (arr: ConfigType | (number | undefined)[], showTime: boolean = false) => {
  const isValidNumber = (
    item: ListIterateeCustom<number | undefined, boolean>,
  ): boolean => typeof item === "number" && !isNaN(item) && isFinite(item);

  let tempArr = arr;

  if (isArray(arr) && every(arr, isValidNumber) && arr.length >= 3) {
    // [year, month, day]
    // tempArr = take(arr, 3);
    tempArr = `${arr[0]?.toString().padStart(4, "0")}-${arr[1]?.toString().padStart(2, "0")}-${arr[2]?.toString().padStart(2, "0")}`;
    if (showTime) {
      // [year, month, day, hour, minute, second]
      tempArr += ` ${
        arr[3]?.toString().padStart(2, "0")}:${
          arr[4]?.toString().padStart(2, "0")}:${
            (arr[5] ?? 0)?.toString().padStart(2, "0")}`;
    }
  }

  return dayjs(tempArr as ConfigType);
};

export const arrayToDateString = (arr: ConfigType | (number | undefined)[], format: "input"|"output" = "output") => {
  if (format == "output") {
    return arrayToDayjs(arr).format(OUTPUT_DATE_FORMAT);
  }
  else {
    return arrayToDayjs(arr).format(INPUT_DATE_FORMAT);
  }
};

export const arrayToDateTimeString = (arr: ConfigType | (number | undefined)[]) => {
  return arrayToDayjs(arr, true).format(`${OUTPUT_DATE_FORMAT} ${OUTPUT_TIME_FORMAT}`);
};

export const dateStringToDayjs = (date: string) => {
  // Format: YYYY/MM/DD
  return dayjs(date, OUTPUT_DATE_FORMAT);
};

export const dateTimeStringToDayjs = (dateTime: string) => {
  // Format: YYYY/MM/DD HH:mm:ss
  return dayjs(dateTime, `${OUTPUT_DATE_FORMAT} ${OUTPUT_TIME_FORMAT}`);
};

export const dayjsToDateString = (date: Dayjs) => {
  return date.format(OUTPUT_DATE_FORMAT);
};

export const dayjsToInputDateString = (date: Dayjs) => {
  return date.format(INPUT_DATE_FORMAT + "T" + INPUT_TIME_FORMAT);
};

export const dayjsToInputDatetimeString = (date: Dayjs) => {
  return date.format(INPUT_DATE_FORMAT);
};

export const dayjsToInputDateTimeString = (date: Dayjs) => {
  return date.format(`${INPUT_DATE_FORMAT}T${OUTPUT_TIME_FORMAT}`);
};

export const outputDateStringToInputDateString = (date: string) => {
  return dayjsToInputDateString(dateStringToDayjs(date))
}

export const stockInLineStatusMap: { [status: string]: number } = {
  draft: 0,
  pending: 1,
  qc: 2,
  determine1: 3,
  determine2: 4,
  determine3: 5,
  receiving: 6,
  received: 7,
  completed: 8,
  rejected: 9,
};

export const stockOutLineStatusMap: { [status: string]: number } = {
  draft: 0,
  pending: 1, // waiting for qc
  determine1: 2, // waiting for qc
  "lot-change": 3, // waiting for qc
  // after qc = completed
  completed: 4,
  rejected: 5,
};

export const pickOrderStatusMap: { [status: string]: number } = {
  pending: 1,
  consolidated: 2,
  released: 3,
  completed: 4,
};

export const calculateWeight = (qty: number, uom: Uom) => {
  return qty * (uom.unit2Qty || 1) * (uom.unit3Qty || 1) * (uom.unit4Qty || 1);
};

export const returnWeightUnit = (uom: Uom) => {
  return uom.unit4 || uom.unit3 || uom.unit2 || uom.unit1;
};
