import {
  Column as TColumn,
  Table as TTable,
  ExpandedState,
  useReactTable,
  getCoreRowModel,
  getPaginationRowModel,
  getFilteredRowModel,
  getExpandedRowModel,
  ColumnDef,
  flexRender,
} from '@tanstack/react-table';
import React, { useState } from 'react';
import { Checkbox, CheckboxProps } from '../checkbox';
export interface TableProps<T> {
  columns: ColumnDef<T>[];
  data: T[];
  getCoreRowModel?: typeof getCoreRowModel;
}

function Table<T>(props: TableProps<T>) {
  let { columns, data } = props;

  let [expanded, setExpanded] = useState<ExpandedState>({});

  let table = useReactTable({
    data,
    columns,
    state: {
      expanded,
    },
    onExpandedChange: setExpanded,
    getSubRows: (row: any) => row.subIssues,
    getCoreRowModel: getCoreRowModel(),
    getPaginationRowModel: getPaginationRowModel(),
    getFilteredRowModel: getFilteredRowModel(),
    getExpandedRowModel: getExpandedRowModel(),
    debugTable: true,
  });

  return (
    <div className="rounded">
      <table>
        <thead>
          {table.getHeaderGroups().map((headerGroup) => (
            <tr key={headerGroup.id} className="bg-neutral-200 text-neutral-100">
              {headerGroup.headers.map((header) => {
                return (
                  <th
                    key={header.id}
                    colSpan={header.colSpan}
                    className="border-r p-2 text-lg font-semibold text-neutral-950"
                  >
                    {header.isPlaceholder ? null : (
                      <div className="flex">
                        {flexRender(header.column.columnDef.header, header.getContext())}
                      </div>
                    )}
                  </th>
                );
              })}
            </tr>
          ))}
        </thead>
        <tbody>
          {table.getRowModel().rows.map((row) => {
            return (
              <tr key={row.id} className="border">
                {row.getVisibleCells().map((cell) => {
                  return (
                    <td key={cell.id} className="border-r p-2">
                      {flexRender(cell.column.columnDef.cell, cell.getContext())}
                    </td>
                  );
                })}
              </tr>
            );
          })}
        </tbody>
      </table>
    </div>
  );
}

function Filter({ column, table }: { column: TColumn<any, any>; table: TTable<any> }) {
  const firstValue = table.getPreFilteredRowModel().flatRows[0]?.getValue(column.id);

  const columnFilterValue = column.getFilterValue();

  return typeof firstValue === 'number' ? (
    <div className="flex space-x-2">
      <input
        type="number"
        value={(columnFilterValue as [number, number])?.[0] ?? ''}
        onChange={(e) =>
          column.setFilterValue((old: [number, number]) => [e.target.value, old?.[1]])
        }
        placeholder={`Min`}
        className="w-24 rounded border shadow"
      />
      <input
        type="number"
        value={(columnFilterValue as [number, number])?.[1] ?? ''}
        onChange={(e) =>
          column.setFilterValue((old: [number, number]) => [old?.[0], e.target.value])
        }
        placeholder={`Max`}
        className="w-24 rounded border shadow"
      />
    </div>
  ) : (
    <input
      type="text"
      value={(columnFilterValue ?? '') as string}
      onChange={(e) => column.setFilterValue(e.target.value)}
      placeholder={`Search...`}
      className="w-36 rounded border shadow"
    />
  );
}

const IndeterminateCheckbox = ({
  isIndeterminate,
  isSelected,
  className = '',
  ...rest
}: CheckboxProps & React.RefAttributes<HTMLLabelElement>) => {
  return (
    <Checkbox
      isIndeterminate={isIndeterminate}
      isSelected={isSelected}
      className={className + ' cursor-pointer'}
      {...rest}
    />
  );
};

IndeterminateCheckbox.displayName = 'IndeterminateCheckbox';

export { Table, Filter, IndeterminateCheckbox };
