import RefreshIcon from "@mui/icons-material/Refresh";
import VisibilityIcon from "@mui/icons-material/Visibility";
import {
  IconButton,
  Paper,
  Table,
  TableBody,
  TableCell,
  TableContainer,
  TableHead,
  TableRow,
  Tooltip,
} from "@mui/material";
import React from "react";
import { Link, useNavigate } from "react-router-dom";
import { Device, DeviceApi, DevicesState, DeviceURL } from "../api/DeviceApi";
import { AsyncWidget } from "../widgets/AsyncWidget";
import { BoolText } from "../widgets/BoolText";
import { SolarEnergyRouteContainer } from "../widgets/SolarEnergyRouteContainer";
import { TimeWidget } from "../widgets/TimeWidget";

export function DevicesRoute(p: { homeWidget?: boolean }): React.ReactElement {
  const loadKey = React.useRef(1);

  const [list, setList] = React.useState<Device[] | undefined>();
  const [states, setStates] = React.useState<DevicesState | undefined>();

  const load = async () => {
    setList(await DeviceApi.ValidatedList());
    setStates(await DeviceApi.DevicesState());
  };

  const reload = () => {
    loadKey.current += 1;
    setList(undefined);
    setStates(undefined);
  };

  return (
    <SolarEnergyRouteContainer
      homeWidget={p.homeWidget}
      label="Devices"
      actions={
        <Tooltip title="Refresh table">
          <IconButton onClick={reload}>
            <RefreshIcon />
          </IconButton>
        </Tooltip>
      }
    >
      <AsyncWidget
        loadKey={loadKey.current}
        ready={!!list && !!states}
        errMsg="Failed to load the list of validated devices!"
        load={load}
        build={() => (
          <ValidatedDevicesList
            onReload={reload}
            list={list!}
            states={states!}
          />
        )}
      />
    </SolarEnergyRouteContainer>
  );
}

function ValidatedDevicesList(p: {
  list: Device[];
  states: DevicesState;
  onReload: () => void;
}): React.ReactElement {
  const navigate = useNavigate();

  if (p.list.length === 0) {
    return <p>There is no device validated yet.</p>;
  }

  return (
    <TableContainer component={Paper}>
      <Table sx={{ minWidth: 650 }} aria-label="simple table">
        <TableHead>
          <TableRow>
            <TableCell>Name</TableCell>
            <TableCell align="center">Model</TableCell>
            <TableCell align="center">Version</TableCell>
            <TableCell align="center">Max relays</TableCell>
            <TableCell align="center">Created</TableCell>
            <TableCell align="center">Updated</TableCell>
            <TableCell align="center">Status</TableCell>
            <TableCell></TableCell>
          </TableRow>
        </TableHead>
        <TableBody>
          {p.list.map((dev) => (
            <TableRow
              hover
              key={dev.id}
              onDoubleClick={() => navigate(DeviceURL(dev))}
            >
              <TableCell component="th" scope="row">
                {dev.name}
              </TableCell>
              <TableCell align="center">{dev.info.reference}</TableCell>
              <TableCell align="center">{dev.info.version}</TableCell>
              <TableCell align="center">{dev.info.max_relays}</TableCell>
              <TableCell align="center">
                <TimeWidget time={dev.time_create} />
              </TableCell>
              <TableCell align="center">
                <TimeWidget time={dev.time_update} />
              </TableCell>
              <TableCell align="center">
                <BoolText
                  val={p.states.get(dev.id)!.online}
                  positive="Online"
                  negative="Offline"
                />
                <br />
                <TimeWidget diff time={p.states.get(dev.id)!.last_ping} />
              </TableCell>
              <TableCell>
                <Tooltip title="Open device page">
                  <Link to={DeviceURL(dev)}>
                    <IconButton>
                      <VisibilityIcon />
                    </IconButton>
                  </Link>
                </Tooltip>
              </TableCell>
            </TableRow>
          ))}
        </TableBody>
      </Table>
    </TableContainer>
  );
}
