src/pages/Trash/Trash.tsx
import React, { useEffect, useState, useMemo } from "react";
import { getAllSoftDeletedTrainees } from "../../redux/actions/softDeletedTraineesActions";
import { restoretraine } from "../../redux/actions/restoreDelTrainee";
import { connect } from "react-redux";
import { useTable, usePagination, useRowSelect } from "react-table";
import * as BsIcons from "react-icons/bs";
import * as AiIcons from "react-icons/ai";
import CheckBox from "../../components/CkeckBox";
import Menu from "@mui/material/Menu";
import MenuItem from "@mui/material/MenuItem";
import NavBar from "../../components/sidebar/navHeader";
import { clearTrash } from "../../redux/actions/clearTrash";
import Select from "react-select";
import { customTheme, darkTheme } from "../FilterTeainee/FilterTrainee";
import { useTheme } from "../../hooks/darkmode";
import { TrashSkeleton } from "../../skeletons/skeletonOfTrash";
const Trash = (props: any) => {
const { allTrainees, restore, clearTrashMessage} = props;
const [pageIdx] = useState(1);
const [itemsPerPage] = useState(100);
const [anchorEl, setAnchorEl] = useState<null | HTMLElement>(null);
const [traineid, settraineid] = useState("");
const [filterAttribute, setFilterAttribute] = useState("");
const [wordsEntered, setWordsEntered] = useState("");
const { theme, setTheme } = useTheme();
const open = Boolean(anchorEl);
const [isLoading, setIsLoading] = useState(true);
const handleClose = () => {
setAnchorEl(null);
};
const [activeCycle, setActiveCycle] = useState<number | undefined>(undefined);
useEffect(() => {
const fetchData = async () => {
setIsLoading(true);
const data = {
page: pageIdx,
itemsPerPage,
filterAttribute,
wordEntered: wordsEntered,
};
await props.getAllSoftDeletedTrainees(data);
setIsLoading(false);
};
fetchData();
}, [restore, clearTrashMessage, filterAttribute, wordsEntered]);
const [moredrop, setmoredrop] = useState("");
const trainees = allTrainees.data;
const onSubmitHandler = (e: any) => {
const traine = trainees[activeCycle!];
settraineid(traine.id);
props.restoretraine(traine.id);
setAnchorEl(null);
};
const onSubmitHandle = async (userId: any) => {
setmoredrop("");
};
const COLS = [
{
Header: "First name",
accessor: "firstName",
},
{
Header: "Last name",
accessor: "lastName",
},
{
Header: "Email",
accessor: "email",
},
{
Header: "Actions",
accessor: "",
Cell: ({ row }: any) => {
return (
<div>
<BsIcons.BsThreeDotsVertical
onClick={(event) => {
setActiveCycle(row.id);
setAnchorEl(event.currentTarget as unknown as HTMLElement);
}}
style={{
color: "#000",
fontSize: "20px",
}}
/>
</div>
);
},
},
];
const columns = useMemo(() => COLS, []);
const {
getTableProps,
getTableBodyProps,
headerGroups,
page,
nextPage,
previousPage,
canNextPage,
canPreviousPage,
pageOptions,
gotoPage,
pageCount,
setPageSize,
state,
prepareRow,
rows,
selectedFlatRows,
}: any = useTable(
{
columns,
data: trainees,
},
usePagination,
useRowSelect,
(hooks: any) => {
hooks.visibleColumns.push((columns: any) => {
return [
{
id: "selection",
Header: ({ getToggleAllRowsSelectedProps }: any) => (
<CheckBox {...getToggleAllRowsSelectedProps()} />
),
Cell: ({ row }: any) => (
<CheckBox {...row.getToggleRowSelectedProps()} />
),
},
...columns,
];
});
}
);
const { pageIndex, pageSize } = state;
const emptyRecycleBin = async () => {
await props.clearTrash();
};
const clearInput = () => {
setWordsEntered("");
};
if (isLoading) {
return <TrashSkeleton/>
}
return (
<>
<div className="flex bg-[#F9F9FB] min-h-[100vh] dark:bg-dark-frame-bg dark:text-white w-full">
<div className="min-h-[50vh] w-[100%] block md:w-[100%] md:mt-0 md:pl-0 pt-4">
<div className=" w-[100%] top-[20%] md:top-[10%] md:relative px-8 md:px-[10px]">
<div className="flex justify-between align-center mb-5 relative md:block">
<div className="absolute bottom-0 right-0 md:relative md:mb-3">
<button
onClick={emptyRecycleBin}
className="px-3 rounded-[5px] dark:bg-[#56C870] bg-[#173b3f] text-white flex items-center"
>
Empty trash
</button>
</div>
<div>
<div className="">
<Select
className="test sm:text-sm border bg-cgray border-solid border-bdr w-40 rounded-bt-rd dark:text-ltb"
options={[
{ value: "_id", label: "Trainee ID" },
{ value: "firstName", label: "First Name" },
{ value: "lastName", label: "Last Name" },
{ value: "email", label: "Email" },
{ value: "cycle_id._id", label: "Cycle ID" },
{ value: "cycle_id.name", label: "Cycle Name" },
{ value: "cycle_id.startDate", label: "Start Date" },
{ value: "cycle_id.endDate", label: "End Date" },
{ value: "", label: "Select by" },
]}
defaultValue={{ value: "", label: "Select by" }}
onChange={(e) => setFilterAttribute(`${e?.value}`)}
theme={theme ? customTheme : darkTheme}
/>
</div>
<div className="flex items-center mb-6 semi-sm:flex-wrap">
<div className=" searchInputs relative block">
<span className="absolute inset-y-0 left-0 flex items-center pl-2">
<svg
className="h-5 w-5 fill-slate-300 text-cg cursor-pointer"
onClick={clearInput}
viewBox="-6 -6 20 20"
>
{wordsEntered === "" ? (
<AiIcons.AiOutlineSearch />
) : (
<AiIcons.AiOutlineClose />
)}
</svg>
</span>
<input
onChange={(e) => setWordsEntered(e.target.value)}
className="dark:text-ltb dark:bg-[#293647] dark:border-opacity-5 block bg-row-gray w-50 border border-bdr rounded-bt-rd mt-2 py-2 pl-9 pr-4 focus:outline-none sm:text-sm"
value={wordsEntered}
placeholder="Search"
type="text"
name="search"
/>
</div>
</div>
</div>
</div>
<div>
<div className=" w-[100%] dark:bg-dark-bg max-h-[70vh] m-auto bg-[#fff] shadow-md rounded-[10px] relative pb-[20px] overflow-x-auto overflow-y-scroll md:w-[100%]">
<table
{...getTableProps()}
className="border-collapse w-[100%] m-auto rounded-[15px] whitespace-nowrap "
>
<thead className=" w-full px-32 sticky top-0">
{headerGroups.map((headerGroup: any, index: number) => (
<tr
key={index}
{...headerGroup.getHeaderGroupProps()}
className="border-solid border-[1px] border-white dark:border-dark-tertiary even:bg-[#eef1f1] first:w-[20px]"
>
{headerGroup.headers.map(
(column: any, index: number) => (
<th
key={index}
{...column.getHeaderProps}
className="border-solid pl-[30px] h-[50px] text-left dark:bg-dark-tertiary bg-[#eef1f1] first:rounded-tl-[10px] last:rounded-tr-[10px] border-b-[2px] border-[#c5c5c5] dark:border-dark-tertiary py-6 last:pl-[0px] w-[150px] last:w-[20px] first:w-[20px] "
>
{column.render("Header")}
</th>
)
)}
</tr>
))}
</thead>
<tbody {...getTableBodyProps()}>
{page.map((row: any) => {
prepareRow(row);
return (
<tr
{...row.getRowProps()}
key={row.original.id}
className="border-b dark:border-dark-tertiary border-gray-200 "
// className="even:bg-[#eef1f1] border-b border-gray-200 dark:border-dark-tertiary"
>
{row.cells.map((cell: any) => {
return (
<td
{...cell.getCellProps()}
className="pl-[30px] text-left max-w-[150px] overflow-x-auto p-4 last:w-[2px] last:pl-[0px]"
>
{cell.render("Cell")}
</td>
);
})}
</tr>
);
})}
</tbody>
</table>
</div>{" "}
</div>
<Menu
id="basic-menu"
anchorEl={anchorEl}
open={open}
onClose={handleClose}
MenuListProps={{
"aria-labelledby": "basic-button",
}}
>
<MenuItem
onClick={(e) => {
onSubmitHandler(e);
}}
>
<BsIcons.BsArrowCounterclockwise className="mr-[5px] " />
Restore
</MenuItem>
</Menu>
<div className="block mx-auto my-0 w-[100%] bottom-0 overflow-x-auto">
<div className="w-[100%] flex items-center justify-center my-[30px] mx-auto md:block md:mx-auto">
<span className="flex items-center md:justify-center md:mt-[10px]">
{" "}
<button
className="my-0 mx-[5px] px-[5px] py-0 text-[#333] h-[38px] border-solid border-[1px] border-[#a8a8a8] disabled:bg-[#E7E7E7] disabled:text-[#a8a8a8] dark:border-dark-tertiary dark:bg-dark-bg dark:text-white"
onClick={() => gotoPage(0)}
disabled={!canPreviousPage}
>
<AiIcons.AiOutlineDoubleLeft />
</button>
<button
className=" border-solid border-[1px] border-[#a8a8a8] py-0 px-[10px] text-[#333] rounded-l-[5px] h-[38px] disabled:bg-[#E7E7E7] disabled:text-[#a8a8a8] dark:border-dark-tertiary dark:bg-dark-bg dark:text-white"
onClick={() => previousPage()}
disabled={!canPreviousPage}
>
<AiIcons.AiOutlineLeft />
</button>
<span className="flex flex-wrap md:hidden " id="pages">
{pageOptions?.map((pageOption: any, i: number) => {
return (
<div>
<button
className={`border-solid border-[1px] mx-[2px] dark:border-dark-tertiary dark:bg-dark-bg dark:text-white border-[#a8a8a8] bg-[#fff] w-[35px] h-[38px] active:bg-[#333] active:text-[#fff]-500 ${
pageIndex === i && "bg-[#eef1f1]"
}`}
onClick={(e: any) => {
const pageNumber = e.target.innerText;
gotoPage(pageNumber - 1);
}}
>
{pageOption + 1}
</button>
</div>
);
})}
</span>
<button
className=" border-solid border-[1px] dark:border-dark-tertiary dark:bg-dark-bg dark:text-white border-[#a8a8a8] py-0 px-[10px] text-[#333] rounded-r-[5px] h-[38px] disabled:bg-[#E7E7E7] disabled:text-[#a8a8a8]"
onClick={() => nextPage()}
disabled={!canNextPage}
>
<AiIcons.AiOutlineRight />
</button>
<button
className="my-0 mx-[5px] px-[5px] py-0 dark:border-dark-tertiary dark:bg-dark-bg dark:text-white text-[#333] h-[38px] border-solid border-[1px] border-[#a8a8a8] disabled:bg-[#E7E7E7] disabled:text-[#a8a8a8]"
onClick={() => gotoPage(pageCount - 1)}
disabled={!canNextPage}
>
<AiIcons.AiOutlineDoubleRight />
</button>
</span>{" "}
<span className="flex ml-3 md:justify-center text-center md:mt-3 md:ml-0">
Page <strong>{pageIndex + 1} </strong>of{" "}
<strong>{pageOptions.length}</strong>
</span>
</div>
</div>
</div>
</div>
</div>
</>
);
};
const mapState = (state: any) => ({
allTrainees: state.softDeletedTrainees,
restore: state.restore,
clearTrashMessage: state.clearTrash,
});
export default connect(mapState, {
getAllSoftDeletedTrainees,
restoretraine,
clearTrash,
})(Trash);
function dispatch(arg0: (dispatch: any) => Promise<void>) {
throw new Error("Function not implemented.");
}