"use client";

import React from "react";
import Paper from "@mui/material/Paper";
import Table from "@mui/material/Table";
import TableBody from "@mui/material/TableBody";
import TableCell from "@mui/material/TableCell";
import TableContainer from "@mui/material/TableContainer";
import TableHead from "@mui/material/TableHead";
import TablePagination, {
  TablePaginationProps,
} from "@mui/material/TablePagination";
import TableRow from "@mui/material/TableRow";
import IconButton, { IconButtonOwnProps, IconButtonPropsColorOverrides } from "@mui/material/IconButton";
import { t } from "i18next";
import { useTranslation } from "react-i18next";
import { convertDateArrayToString, moneyFormatter } from "@/app/utils/formatUtil";

export interface ResultWithId {
  id: string | number;
}

interface BaseColumn<T extends ResultWithId> {
  name: keyof T;
  label: string;
  color?: IconButtonOwnProps["color"];
  needTranslation?: boolean;
  type?: string;
  isHidden?: boolean;
}

interface ColumnWithAction<T extends ResultWithId> extends BaseColumn<T> {
  onClick: (item: T) => void;
  buttonIcon: React.ReactNode;
}

export type Column<T extends ResultWithId> =
  | BaseColumn<T>
  | ColumnWithAction<T>;

interface Props<T extends ResultWithId> {
  items: T[];
  columns: Column<T>[];
  noWrapper?: boolean;
}

function isActionColumn<T extends ResultWithId>(
  column: Column<T>,
): column is ColumnWithAction<T> {
  return Boolean((column as ColumnWithAction<T>).onClick);
}

function SearchResults<T extends ResultWithId>({
  items,
  columns,
  noWrapper,
}: Props<T>) {
  const [page, setPage] = React.useState(0);
  const [rowsPerPage, setRowsPerPage] = React.useState(10);
  const { t } = useTranslation()

  const handleChangePage: TablePaginationProps["onPageChange"] = (
    _event,
    newPage,
  ) => {
    setPage(newPage);
  };

  const handleChangeRowsPerPage: TablePaginationProps["onRowsPerPageChange"] = (
    event,
  ) => {
    setRowsPerPage(+event.target.value);
    setPage(0);
  };

  const table = (
    <>
      <TableContainer sx={{ maxHeight: 440 }}>
        <Table stickyHeader>
          <TableHead>
            <TableRow>
              {columns.filter(item => item.isHidden !== true).map((column, idx) => (
                <TableCell key={`${column.name.toString()}${idx}`}>
                  {column?.type === "money" ? <div style={{display: "flex", justifyContent: "flex-end"}}>{column.label}</div> : column.label}
                </TableCell>
              ))}
            </TableRow>
          </TableHead>
          <TableBody>
            {items
              .slice(page * rowsPerPage, page * rowsPerPage + rowsPerPage)
              .map((item) => {
                return (
                  <TableRow hover tabIndex={-1} key={item.id}>
                    {columns.filter(item => item.isHidden !== true).map((column, idx) => {
                      const columnName = column.name;

                      return (
                        <TableCell key={`${columnName.toString()}-${idx}`}>
                          {isActionColumn(column) ? (
                            <IconButton
                              color={column.color ?? "primary"}
                              onClick={() => column.onClick(item)}
                            >
                              {column.buttonIcon}
                            </IconButton>
                          ) :
                            column?.type === "date" ? (
                              <>{convertDateArrayToString(item[columnName] as number[])}</>
                            ) :
                            column?.type === "money" ? (
                              <div style={{display: "flex", justifyContent: "flex-end"}}>{moneyFormatter.format(item[columnName] as number)}</div>
                            ) :
                              (
                                <>{column?.needTranslation ? t(item[columnName] as string) : item[columnName]}</>
                              )}
                        </TableCell>
                      );
                    })}
                  </TableRow>
                );
              })}
          </TableBody>
        </Table>
      </TableContainer>
      <TablePagination
        rowsPerPageOptions={[10, 25, 100]}
        component="div"
        count={items.length}
        rowsPerPage={rowsPerPage}
        page={page}
        onPageChange={handleChangePage}
        onRowsPerPageChange={handleChangeRowsPerPage}
      />
    </>
  );

  return noWrapper ? table : <Paper sx={{ overflow: "hidden" }}>{table}</Paper>;
}

export default SearchResults;
