UNPKG

@trail-ui/react

Version:
480 lines (477 loc) 18.7 kB
import { table_header_default } from "./chunk-GCE2RD4S.mjs"; import { Lozenge } from "./chunk-5CC46WKN.mjs"; import { _Checkbox } from "./chunk-26XCDXWQ.mjs"; import { _Button } from "./chunk-YXFZGEMT.mjs"; import { _AvatarGroup } from "./chunk-STWU4DVS.mjs"; import { _Avatar } from "./chunk-OKWXKKQQ.mjs"; // src/tanstackTable/tanstackTable.tsx import { ArrowDownIcon, ArrowUpIcon, ChevronLeftIcon, ChevronRightIcon } from "@trail-ui/icons"; import { clsx } from "@trail-ui/shared-utils"; import { commonColors } from "@trail-ui/theme"; import { flexRender, getCoreRowModel, getFacetedRowModel, getFacetedUniqueValues, getFilteredRowModel, getPaginationRowModel, getSortedRowModel, useReactTable } from "@tanstack/react-table"; import React, { useEffect, useState } from "react"; import { jsx, jsxs } from "react/jsx-runtime"; import { createElement } from "react"; var includesString = (row, columnId, filterValue) => { const rowValue = row.getValue(columnId); if (typeof rowValue !== "string" || typeof filterValue !== "string") { return false; } return rowValue.toLowerCase().includes(filterValue.toLowerCase()); }; var multiSelectFilter = (row, columnId, filterValue) => { if (!Array.isArray(filterValue)) return true; const rowValue = row.getValue(columnId); return filterValue.includes(rowValue); }; function TanstackTable({ columns, data, tableData, showName = true, defaultSortingHeader, tableName, checkBoxSelectedName, WithoutCheckbox, tableHeight, showFilter = true }) { var _a; const tableColumns = columns.map((column) => { return { id: column.id, size: column.width, header: () => { switch (column.type) { case "id": return !WithoutCheckbox && /* @__PURE__ */ jsx("div", { className: "text-center", children: /* @__PURE__ */ jsx( _Checkbox, { "aria-label": `Select All ${tableName}`, classNames: { control: "mr-0" }, ...{ isSelected: Object.keys(rowSelection).length === data.length, isIndeterminate: Object.keys(rowSelection).length > 0 && Object.keys(rowSelection).length < data.length, checked: Object.keys(rowSelection).length === data.length, onChange: () => { const allSelected = Object.keys(rowSelection).length === data.length; const newSelection = allSelected ? {} : data.reduce((acc, row) => { acc[row.id] = true; return acc; }, {}); setRowSelection(newSelection); } } } ) }); default: return column.name; } }, accessorKey: column.accessor, filterFn: column.type === "text" ? multiSelectFilter : multiSelectFilter, cell: ({ cell }) => { switch (column.type) { case "id": return !WithoutCheckbox && /* @__PURE__ */ jsx("div", { className: "text-center", children: /* @__PURE__ */ jsx( _Checkbox, { classNames: { control: "mr-0" }, "aria-label": `${cell.row.original[checkBoxSelectedName != null ? checkBoxSelectedName : ""]}`, ...{ isSelected: cell.row.getIsSelected(), onChange: () => cell.row.toggleSelected() } } ) }); case "text": return cell.getValue(); case "date": return new Date(cell.getValue()).toLocaleDateString(); case "number": return cell.getValue(); case "status": return /* @__PURE__ */ jsx("p", { className: "w-max", children: /* @__PURE__ */ jsx( Lozenge, { size: "sm", variant: "light", value: cell.getValue(), color: cell.getValue() === "Completed" ? "green" : cell.getValue() === "Regression" ? "red" : "yellow" } ) }); case "percentage": return /* @__PURE__ */ jsx( Lozenge, { size: "sm", variant: "light", value: `${cell.getValue()}`, color: cell.getValue() > 0 ? "green" : cell.getValue() < 0 ? "red" : "yellow" } ); case "image": return /* @__PURE__ */ jsx("figure", { className: "min-w-36", children: /* @__PURE__ */ jsx( "img", { className: "h-10", src: cell.getValue(), style: { objectFit: column.objectFit ? column.objectFit : "cover", width: column.objectFit === "contain" ? "max-content" : "100%" }, alt: "" } ) }); case "profileImage": return /* @__PURE__ */ jsx("figure", { children: /* @__PURE__ */ jsx( "img", { className: "h-10", src: cell.getValue(), style: { objectFit: column.objectFit ? column.objectFit : "cover", width: column.objectFit === "contain" ? "max-content" : "100%" }, alt: "" } ) }); case "username": return /* @__PURE__ */ jsxs("p", { className: "flex items-center gap-1 text-sm text-neutral-900", children: [ /* @__PURE__ */ jsx( _Avatar, { size: "md", is: "span", name: cell.getValue(), getInitials: (name) => name.toUpperCase().slice(0, 2), showFallback: true, color: ["green", "red", "yellow", "default", "purple", "blue"][Math.floor(Math.random() * 6)] } ), showName && /* @__PURE__ */ jsx("span", { id: cell.getValue(), className: "text-sm text-neutral-900", children: cell.getValue() }) ] }); case "usersList": return /* @__PURE__ */ jsx(_AvatarGroup, { size: "md", max: 2, children: (cell.getValue() || []).map((user) => /* @__PURE__ */ jsx( _Avatar, { size: "md", is: "span", src: user.avatar, name: user.name, getInitials: (name) => name.toUpperCase().slice(0, 2), showFallback: true, color: ["green", "red", "yellow", "default", "purple", "blue"][Math.floor(Math.random() * 6)] }, user.id )) }); default: return cell.getValue(); } } }; }); const [sorting, setSorting] = useState([]); const [rowSelection, setRowSelection] = useState({}); const [columnFilters, setColumnFilters] = React.useState([]); const [globalFilter, setGlobalFilter] = React.useState(""); const table = useReactTable({ enableRowSelection: true, columns: tableColumns, data, defaultColumn: { size: 100 }, getCoreRowModel: getCoreRowModel(), getSortedRowModel: getSortedRowModel(), onColumnFiltersChange: setColumnFilters, onRowSelectionChange: setRowSelection, onSortingChange: setSorting, getPaginationRowModel: getPaginationRowModel(), getFacetedRowModel: getFacetedRowModel(), getFacetedUniqueValues: getFacetedUniqueValues(), getFilteredRowModel: getFilteredRowModel(), filterFns: { includesString, multiSelectFilter }, state: { sorting, rowSelection, columnFilters, globalFilter }, initialState: { pagination: { pageSize: tableData ? tableData : 10, pageIndex: 0 } } }); const currentPage = table.getState().pagination.pageIndex + 1; const pageCount = table.getPageCount(); const pageNumbers = []; const maxButtonsToShow = 5; if (pageCount <= maxButtonsToShow) { for (let i = 1; i <= pageCount; i++) { pageNumbers.push(i); } } else { let startPage, endPage; const middleButtonsToShow = maxButtonsToShow - 2; const halfMiddleButtonsToShow = Math.floor(middleButtonsToShow / 2); if (currentPage <= halfMiddleButtonsToShow + 1) { startPage = 2; endPage = middleButtonsToShow + 1; } else if (currentPage + halfMiddleButtonsToShow >= pageCount) { startPage = pageCount - middleButtonsToShow; endPage = pageCount - 1; } else { startPage = currentPage - halfMiddleButtonsToShow; endPage = currentPage + halfMiddleButtonsToShow; } pageNumbers.push(1); if (startPage > 2) { pageNumbers.push("..."); } for (let i = startPage; i <= endPage; i++) { pageNumbers.push(i); } if (endPage < pageCount - 1) { pageNumbers.push("..."); } pageNumbers.push(pageCount); } const alignRightData = [ "salesHours", "plannedHours", "teamSize", "plannedVsActual", "actualVsPlanned", "salesVsActual", "actualHours", "noOfHours", "noOfUnits", "report", "support", "fixing", "meeting", "qualityAssurance", "bbMeeting", "documentation", "training", "offProduction", "peerReview", "projects", "reported", "perfectIssues", "perfectIssuesPercentage" ]; const [currentSort, setCurrentSort] = useState( defaultSortingHeader ? defaultSortingHeader : "projectName" ); function toggleSort(header) { const sortingHandler = header.column.getToggleSortingHandler(); if (sortingHandler) { sortingHandler({ persist: () => { } }); } setCurrentSort(header.id); } const stateSorting = table.getState().sorting; useEffect(() => { const sortedHeader = table.getHeaderGroups().flatMap((headerGroup) => headerGroup.headers).find((header) => header.column.getIsSorted()); if (sortedHeader) { setCurrentSort(sortedHeader.id); } else { setCurrentSort(null); } }, [stateSorting, table]); const [openFilter, setOpenFilter] = useState(false); return /* @__PURE__ */ jsxs("div", { className: "rounded", children: [ showFilter && /* @__PURE__ */ jsx( table_header_default, { openFilter, setOpenFilter, table, globalFilter, setGlobalFilter, data, columns, tableName } ), /* @__PURE__ */ jsxs("div", { className: "p-6", children: [ /* @__PURE__ */ jsx("div", { className: "h-full overflow-auto rounded border border-neutral-200", children: /* @__PURE__ */ jsx("div", { className: `${tableHeight ? tableHeight : ""}`, children: /* @__PURE__ */ jsxs("table", { className: "w-full overflow-auto bg-white ", children: [ /* @__PURE__ */ jsx("thead", { className: "sticky top-0 z-10 border-b border-b-neutral-200", children: /* @__PURE__ */ jsx("tr", { children: table.getHeaderGroups().map( (headerGroup) => headerGroup.headers.map((header) => { var _a2; return /* @__PURE__ */ createElement( "th", { id: header.id, ...header.id === "id" ? { "aria-label": `Select All ${tableName}` } : {}, "aria-sort": header.column.getIsSorted() === "asc" ? "ascending" : header.column.getIsSorted() === "desc" ? "descending" : "none", key: header.id, scope: "col", colSpan: header.colSpan, className: `${alignRightData.includes(header.id) ? "text-right" : "text-left"} ${WithoutCheckbox ? "first:auto" : "first:w-10"} h-10 min-h-10 border-r border-r-neutral-200 bg-neutral-100 p-2 text-sm font-semibold text-neutral-900 first:text-center last:border-r-0` }, header.isPlaceholder && header.column.getIndex() === 0 ? null : header.id == "id" ? /* @__PURE__ */ jsx("span", { children: flexRender(header.column.columnDef.header, header.getContext()) }) : /* @__PURE__ */ jsx( _Button, { appearance: "transparent", className: clsx( header.column.getCanSort() ? "cursor-pointer select-none" : "", `${alignRightData.includes(header.id) ? "justify-end" : "justify-start"} w-full items-center px-0 text-sm font-semibold text-neutral-900` ), onPress: () => toggleSort(header), onKeyDown: (event) => { if (event.key === "Enter" || event.key === " ") { header.column.getToggleSortingHandler(); } }, children: /* @__PURE__ */ jsxs( "span", { className: `${alignRightData.includes(header.id) ? "justify-end" : "justify-between"} flex w-full items-center gap-4`, children: [ flexRender(header.column.columnDef.header, header.getContext()), header.column.getCanSort() && header.id !== "id" && (currentSort === header.id ? /* @__PURE__ */ jsx("span", { className: "sort-icon", children: (_a2 = { asc: /* @__PURE__ */ jsx( ArrowUpIcon, { color: commonColors.neutral[800], width: 16, height: 16 } ), desc: /* @__PURE__ */ jsx( ArrowDownIcon, { color: commonColors.neutral[800], width: 16, height: 16 } ) }[header.column.getIsSorted()]) != null ? _a2 : null }) : null) ] } ) } ) ); }) ) }) }), /* @__PURE__ */ jsx("tbody", { children: ((_a = table.getRowModel().rows) == null ? void 0 : _a.length) ? table.getRowModel().rows.map((row) => /* @__PURE__ */ jsx("tr", { "data-state": row.getIsSelected() && "selected", children: row.getVisibleCells().map( (cell) => cell.column.id === checkBoxSelectedName ? /* @__PURE__ */ jsx( "th", { id: `head-${row.id}`, className: `${alignRightData.includes(cell.column.id) ? "text-right" : "text-left"} ${WithoutCheckbox ? "first:auto" : "first:w-10"} h-10 border-b border-l border-b-neutral-200 border-l-neutral-200 !bg-neutral-50 px-2 py-2 text-sm font-normal text-neutral-900 first:border-l-0`, children: flexRender(cell.column.columnDef.cell, cell.getContext()) }, cell.id ) : /* @__PURE__ */ jsx( "td", { headers: `head-${row.id} ${cell.column.id}`, className: `${alignRightData.includes(cell.column.id) ? "text-right" : "text-left"} ${WithoutCheckbox ? "first:auto" : "first:w-10"} h-10 border-b border-l border-b-neutral-200 border-l-neutral-200 px-2 py-2 text-sm font-normal text-neutral-900 first:border-l-0`, children: flexRender(cell.column.columnDef.cell, cell.getContext()) }, cell.id ) ) }, row.id)) : /* @__PURE__ */ jsx("tr", { children: /* @__PURE__ */ jsx("td", { colSpan: columns.length, className: "h-24 text-center", children: "No results." }) }) }) ] }) }) }), /* @__PURE__ */ jsxs("div", { className: "mt-2 flex items-center justify-between space-x-2 p-2", children: [ /* @__PURE__ */ jsx("div", { children: /* @__PURE__ */ jsxs("p", { className: "text-sm text-neutral-600", children: [ "Showing ", table.getRowModel().rows.length, " out of ", data.length, " results" ] }) }), /* @__PURE__ */ jsx("nav", { "aria-label": "Pagination", className: "flex justify-end", children: /* @__PURE__ */ jsxs("ul", { className: "justtify-end flex gap-2", children: [ /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsx( _Button, { className: "px-1", "aria-label": "Previous page", appearance: "transparent", isDisabled: !table.getCanPreviousPage(), onPress: () => table.previousPage(), children: /* @__PURE__ */ jsx( ChevronLeftIcon, { color: `${currentPage === 1 ? "#B0ACBB" : "#302E38"}`, width: 24, height: 24 } ) } ) }), pageNumbers.map((pageNumber, index) => /* @__PURE__ */ jsx("li", { className: "h-8 w-8", children: pageNumber === "..." ? /* @__PURE__ */ jsx("span", { children: "..." }) : /* @__PURE__ */ jsx( "button", { ...pageNumber === currentPage ? { "aria-current": "page" } : {}, "aria-current": pageNumber === currentPage ? "page" : void 0, onClick: () => { if (pageNumber !== "...") { table.setPageIndex(pageNumber - 1); } }, className: `h-full w-full text-sm font-normal text-neutral-800 ${pageNumber === currentPage ? "rounded border border-purple-600 bg-purple-100" : "bg-white"} ${pageNumber !== "..." ? "underline" : ""}`, children: pageNumber } ) }, index)), /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsx( _Button, { className: "px-1", appearance: "transparent", isDisabled: !table.getCanNextPage(), onPress: () => table.nextPage(), "aria-label": "Next page", children: /* @__PURE__ */ jsx( ChevronRightIcon, { color: !table.getCanNextPage() ? "#B0ACBB" : "#302E38", width: 24, height: 24 } ) } ) }) ] }) }) ] }) ] }) ] }); } export { TanstackTable };