@bsol-oss/react-datatable5 8.1.1 → 8.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -304,12 +304,15 @@ interface TableControlsProps {
304
304
  showFilterName?: boolean;
305
305
  showFilterTags?: boolean;
306
306
  showReload?: boolean;
307
+ showPagination?: boolean;
308
+ showPageSizeControl?: boolean;
309
+ showPageCountText?: boolean;
307
310
  filterOptions?: string[];
308
311
  extraItems?: ReactNode;
309
312
  loading?: boolean;
310
313
  hasError?: boolean;
311
314
  }
312
- declare const TableControls: ({ totalText, fitTableWidth, fitTableHeight, isMobile, children, showGlobalFilter, showFilter, showFilterName, showFilterTags, showReload, filterOptions, extraItems, loading, hasError, }: TableControlsProps) => react_jsx_runtime.JSX.Element;
315
+ declare const TableControls: ({ totalText, fitTableWidth, fitTableHeight, isMobile, children, showGlobalFilter, showFilter, showFilterName, showFilterTags, showReload, showPagination, showPageSizeControl, showPageCountText, filterOptions, extraItems, loading, hasError, }: TableControlsProps) => react_jsx_runtime.JSX.Element;
313
316
 
314
317
  interface TableFooterProps {
315
318
  pinnedBgColor?: {
package/dist/index.js CHANGED
@@ -21,12 +21,12 @@ var hi2 = require('react-icons/hi2');
21
21
  var reactTable = require('@tanstack/react-table');
22
22
  var matchSorterUtils = require('@tanstack/match-sorter-utils');
23
23
  var bs = require('react-icons/bs');
24
- var gr = require('react-icons/gr');
25
- var hi = require('react-icons/hi');
24
+ var usehooks = require('@uidotdev/usehooks');
26
25
  var reactQuery = require('@tanstack/react-query');
27
26
  var io5 = require('react-icons/io5');
27
+ var gr = require('react-icons/gr');
28
+ var hi = require('react-icons/hi');
28
29
  var axios = require('axios');
29
- var usehooks = require('@uidotdev/usehooks');
30
30
  var reactHookForm = require('react-hook-form');
31
31
  var dayjs = require('dayjs');
32
32
 
@@ -371,7 +371,7 @@ const ResetFilteringButton = ({ text = "Reset Filtering", }) => {
371
371
  }, children: text }));
372
372
  };
373
373
 
374
- const EditFilterButton$1 = ({ text, title = "Edit Filter", closeText = "Close", resetText = "Reset", icon = jsxRuntime.jsx(md.MdFilterAlt, {}), }) => {
374
+ const EditFilterButton = ({ text, title = "Edit Filter", closeText = "Close", resetText = "Reset", icon = jsxRuntime.jsx(md.MdFilterAlt, {}), }) => {
375
375
  const filterModal = react.useDisclosure();
376
376
  return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: jsxRuntime.jsx(DialogRoot, { size: ["full", "full", "md", "md"], open: filterModal.open, children: jsxRuntime.jsxs(DialogRoot, { children: [jsxRuntime.jsx(DialogTrigger, { asChild: true, children: jsxRuntime.jsxs(react.Button, { as: react.Box, variant: "ghost", onClick: filterModal.onOpen, children: [icon, " ", text] }) }), jsxRuntime.jsxs(DialogContent, { children: [jsxRuntime.jsx(DialogHeader, { children: jsxRuntime.jsx(DialogTitle, { children: title }) }), jsxRuntime.jsx(DialogBody, { children: jsxRuntime.jsxs(react.Flex, { flexFlow: "column", gap: "1rem", children: [jsxRuntime.jsx(TableFilter, {}), jsxRuntime.jsx(ResetFilteringButton, { text: resetText })] }) }), jsxRuntime.jsxs(DialogFooter, { children: [jsxRuntime.jsx(DialogActionTrigger, { asChild: true, children: jsxRuntime.jsx(react.Button, { onClick: filterModal.onClose, children: closeText }) }), jsxRuntime.jsx(react.Button, { children: "Save" })] }), jsxRuntime.jsx(DialogCloseTrigger, {})] })] }) }) }));
377
377
  };
@@ -2450,7 +2450,7 @@ const TableViewer = () => {
2450
2450
  }) }));
2451
2451
  };
2452
2452
 
2453
- const EditViewButton$1 = ({ text, icon = jsxRuntime.jsx(io.IoMdEye, {}), title = "Edit View", }) => {
2453
+ const EditViewButton = ({ text, icon = jsxRuntime.jsx(io.IoMdEye, {}), title = "Edit View", }) => {
2454
2454
  const viewModel = react.useDisclosure();
2455
2455
  return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: jsxRuntime.jsxs(DialogRoot, { children: [jsxRuntime.jsx(react.DialogBackdrop, {}), jsxRuntime.jsx(DialogTrigger, { asChild: true, children: jsxRuntime.jsxs(react.Button, { as: react.Box, variant: "ghost", onClick: viewModel.onOpen, children: [icon, " ", text] }) }), jsxRuntime.jsxs(DialogContent, { children: [jsxRuntime.jsx(DialogCloseTrigger, {}), jsxRuntime.jsxs(DialogHeader, { children: [jsxRuntime.jsx(DialogTitle, {}), title] }), jsxRuntime.jsx(DialogBody, { children: jsxRuntime.jsx(TableViewer, {}) }), jsxRuntime.jsx(DialogFooter, {})] })] }) }));
2456
2456
  };
@@ -3001,12 +3001,90 @@ const Tooltip = React__namespace.forwardRef(function Tooltip(props, ref) {
3001
3001
  return (jsxRuntime.jsxs(react.Tooltip.Root, { ...rest, children: [jsxRuntime.jsx(react.Tooltip.Trigger, { asChild: true, children: children }), jsxRuntime.jsx(react.Portal, { disabled: !portalled, container: portalRef, children: jsxRuntime.jsx(react.Tooltip.Positioner, { children: jsxRuntime.jsxs(react.Tooltip.Content, { ref: ref, ...contentProps, children: [showArrow && (jsxRuntime.jsx(react.Tooltip.Arrow, { children: jsxRuntime.jsx(react.Tooltip.ArrowTip, {}) })), content] }) }) })] }));
3002
3002
  });
3003
3003
 
3004
- const TableControls = ({ totalText = "Total:", fitTableWidth = false, fitTableHeight = false, isMobile = false, children = jsxRuntime.jsx(jsxRuntime.Fragment, {}), showGlobalFilter = false, showFilter = false, showFilterName = false, showFilterTags = false, showReload = false, filterOptions = [], extraItems = jsxRuntime.jsx(jsxRuntime.Fragment, {}), loading = false, hasError = false, }) => {
3004
+ const InputGroup = React__namespace.forwardRef(function InputGroup(props, ref) {
3005
+ const { startElement, startElementProps, endElement, endElementProps, children, startOffset = "6px", endOffset = "6px", ...rest } = props;
3006
+ return (jsxRuntime.jsxs(react.Group, { ref: ref, ...rest, children: [startElement && (jsxRuntime.jsx(react.InputElement, { pointerEvents: "none", ...startElementProps, children: startElement })), React__namespace.cloneElement(children, {
3007
+ ...(startElement && {
3008
+ ps: `calc(var(--input-height) - ${startOffset})`,
3009
+ }),
3010
+ ...(endElement && { pe: `calc(var(--input-height) - ${endOffset})` }),
3011
+ // @ts-expect-error chakra generated files
3012
+ ...children.props,
3013
+ }), endElement && (jsxRuntime.jsx(react.InputElement, { placement: "end", ...endElementProps, children: endElement }))] }));
3014
+ });
3015
+
3016
+ const GlobalFilter = () => {
3017
+ const { table } = useDataTableContext();
3018
+ const [searchTerm, setSearchTerm] = React.useState("");
3019
+ const debouncedSearchTerm = usehooks.useDebounce(searchTerm, 500);
3020
+ React.useEffect(() => {
3021
+ const searchHN = async () => {
3022
+ table.setGlobalFilter(debouncedSearchTerm);
3023
+ };
3024
+ searchHN();
3025
+ }, [debouncedSearchTerm]);
3026
+ return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: jsxRuntime.jsx(InputGroup, { flex: "1", startElement: jsxRuntime.jsx(md.MdSearch, {}), children: jsxRuntime.jsx(react.Input, { placeholder: "Outline", variant: "outline", onChange: (e) => {
3027
+ setSearchTerm(e.target.value);
3028
+ } }) }) }));
3029
+ };
3030
+
3031
+ const useDataTableServerContext = () => {
3032
+ const context = React.useContext(DataTableServerContext);
3033
+ const { query } = context;
3034
+ const isEmpty = (query.data?.count ?? 0) <= 0;
3035
+ return { ...context, isEmpty };
3036
+ };
3037
+
3038
+ const ReloadButton = ({ text = "Reload", variant = "icon", }) => {
3039
+ const { url } = useDataTableServerContext();
3040
+ const queryClient = reactQuery.useQueryClient();
3041
+ if (variant === "icon") {
3042
+ return (jsxRuntime.jsx(Tooltip, { showArrow: true, content: "This is the tooltip content", children: jsxRuntime.jsx(Button, { variant: "ghost", onClick: () => {
3043
+ queryClient.invalidateQueries({ queryKey: [url] });
3044
+ }, "aria-label": "refresh", children: jsxRuntime.jsx(io5.IoReload, {}) }) }));
3045
+ }
3046
+ return (jsxRuntime.jsxs(Button, { variant: "ghost", onClick: () => {
3047
+ queryClient.invalidateQueries({ queryKey: [url] });
3048
+ }, children: [jsxRuntime.jsx(io5.IoReload, {}), " ", text] }));
3049
+ };
3050
+
3051
+ const FilterOptions = ({ column }) => {
3052
+ const { table } = useDataTableContext();
3053
+ const tableColumn = table.getColumn(column);
3054
+ const options = tableColumn?.columnDef.meta?.filterOptions ?? [];
3055
+ return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: options.map((option) => {
3056
+ const selected = table.getColumn(column)?.getFilterValue() === option;
3057
+ return (jsxRuntime.jsxs(react.Button, { size: "sm", onClick: () => {
3058
+ if (selected) {
3059
+ table.setColumnFilters((state) => {
3060
+ return state.filter((filter) => {
3061
+ return filter.id !== column;
3062
+ });
3063
+ });
3064
+ return;
3065
+ }
3066
+ table.getColumn(column)?.setFilterValue(option);
3067
+ }, variant: selected ? "solid" : "outline", display: "flex", gap: "0.25rem", children: [option, selected && jsxRuntime.jsx(md.MdClose, {})] }, option));
3068
+ }) }));
3069
+ };
3070
+
3071
+ const TableFilterTags = () => {
3072
+ const { table } = useDataTableContext();
3073
+ return (jsxRuntime.jsx(react.Flex, { gap: "0.5rem", flexFlow: "wrap", children: table.getState().columnFilters.map(({ id, value }) => {
3074
+ return (jsxRuntime.jsx(Tag, { gap: "0.5rem", closable: true, cursor: "pointer", onClick: () => {
3075
+ table.setColumnFilters(table.getState().columnFilters.filter((filter) => {
3076
+ return filter.value != value;
3077
+ }));
3078
+ }, children: `${id}: ${value}` }, `${id}-${value}`));
3079
+ }) }));
3080
+ };
3081
+
3082
+ const TableControls = ({ totalText = "Total:", fitTableWidth = false, fitTableHeight = false, isMobile = false, children = jsxRuntime.jsx(jsxRuntime.Fragment, {}), showGlobalFilter = false, showFilter = false, showFilterName = false, showFilterTags = false, showReload = false, showPagination = true, showPageSizeControl = true, showPageCountText = true, filterOptions = [], extraItems = jsxRuntime.jsx(jsxRuntime.Fragment, {}), loading = false, hasError = false, }) => {
3005
3083
  return (jsxRuntime.jsxs(react.Grid, { templateRows: "auto 1fr auto", width: fitTableWidth ? "fit-content" : "100%", height: fitTableHeight ? "fit-content" : "100%", gap: "0.5rem", children: [jsxRuntime.jsxs(react.Flex, { flexFlow: "column", gap: 2, children: [jsxRuntime.jsxs(react.Flex, { justifyContent: "space-between", children: [jsxRuntime.jsx(react.Box, { children: jsxRuntime.jsx(EditViewButton, { text: isMobile ? undefined : "View", icon: jsxRuntime.jsx(md.MdOutlineViewColumn, {}) }) }), jsxRuntime.jsxs(react.Flex, { gap: "0.5rem", alignItems: "center", justifySelf: "end", children: [loading && jsxRuntime.jsx(react.Spinner, { size: "sm" }), hasError && (jsxRuntime.jsx(Tooltip, { content: "An error occurred while fetching data", children: jsxRuntime.jsx(react.Icon, { as: bs.BsExclamationCircleFill, color: "red.400" }) })), showGlobalFilter && jsxRuntime.jsx(GlobalFilter, {}), showFilter && (jsxRuntime.jsx(jsxRuntime.Fragment, { children: jsxRuntime.jsx(EditFilterButton, { text: isMobile ? undefined : "Advanced Filter" }) })), showReload && jsxRuntime.jsx(ReloadButton, {}), extraItems] })] }), filterOptions.length > 0 && (jsxRuntime.jsx(react.Flex, { flexFlow: "column", gap: "0.5rem", children: filterOptions.map((column) => {
3006
3084
  return (jsxRuntime.jsxs(react.Flex, { alignItems: "center", flexFlow: "wrap", gap: "0.5rem", children: [showFilterName && jsxRuntime.jsxs(react.Text, { children: [column, ":"] }), jsxRuntime.jsx(FilterOptions, { column: column })] }, column));
3007
3085
  }) })), showFilterTags && (jsxRuntime.jsx(react.Flex, { children: jsxRuntime.jsx(TableFilterTags, {}) }))] }), jsxRuntime.jsx(react.Grid, { overflow: "auto", backgroundColor: "gray.50", _dark: {
3008
3086
  backgroundColor: "gray.900",
3009
- }, children: children }), jsxRuntime.jsxs(react.Flex, { justifyContent: "space-between", children: [jsxRuntime.jsxs(react.Flex, { gap: "1rem", alignItems: "center", children: [jsxRuntime.jsx(PageSizeControl, {}), jsxRuntime.jsxs(react.Flex, { children: [jsxRuntime.jsx(react.Text, { paddingRight: "0.5rem", children: totalText }), jsxRuntime.jsx(RowCountText, {})] })] }), jsxRuntime.jsx(react.Box, { justifySelf: "end", children: jsxRuntime.jsx(TablePagination, {}) })] })] }));
3087
+ }, children: children }), jsxRuntime.jsxs(react.Flex, { justifyContent: "space-between", children: [jsxRuntime.jsxs(react.Flex, { gap: "1rem", alignItems: "center", children: [showPageSizeControl && jsxRuntime.jsx(PageSizeControl, {}), showPageCountText && (jsxRuntime.jsxs(react.Flex, { children: [jsxRuntime.jsx(react.Text, { paddingRight: "0.5rem", children: totalText }), jsxRuntime.jsx(RowCountText, {})] }))] }), jsxRuntime.jsx(react.Box, { justifySelf: "end", children: showPagination && jsxRuntime.jsx(TablePagination, {}) })] })] }));
3010
3088
  };
3011
3089
 
3012
3090
  const TableFooter = ({ pinnedBgColor = { light: "gray.50", dark: "gray.700" }, showSelector = false, alwaysShowSelector = true, }) => {
@@ -3190,26 +3268,6 @@ const DefaultTable = ({ showFooter = false, tableProps = {}, tableHeaderProps =
3190
3268
  return (jsxRuntime.jsx(TableControls, { ...controlProps, children: jsxRuntime.jsxs(Table, { ...tableProps, children: [jsxRuntime.jsx(TableHeader, { ...tableHeaderProps }), jsxRuntime.jsx(TableBody, { ...tableBodyProps }), showFooter && jsxRuntime.jsx(TableFooter, { ...tableFooterProps })] }) }));
3191
3269
  };
3192
3270
 
3193
- const useDataTableServerContext = () => {
3194
- const context = React.useContext(DataTableServerContext);
3195
- const { query } = context;
3196
- const isEmpty = (query.data?.count ?? 0) <= 0;
3197
- return { ...context, isEmpty };
3198
- };
3199
-
3200
- const ReloadButton$1 = ({ text = "Reload", variant = "icon", }) => {
3201
- const { url } = useDataTableServerContext();
3202
- const queryClient = reactQuery.useQueryClient();
3203
- if (variant === "icon") {
3204
- return (jsxRuntime.jsx(Tooltip, { showArrow: true, content: "This is the tooltip content", children: jsxRuntime.jsx(Button, { variant: "ghost", onClick: () => {
3205
- queryClient.invalidateQueries({ queryKey: [url] });
3206
- }, "aria-label": "refresh", children: jsxRuntime.jsx(io5.IoReload, {}) }) }));
3207
- }
3208
- return (jsxRuntime.jsxs(Button, { variant: "ghost", onClick: () => {
3209
- queryClient.invalidateQueries({ queryKey: [url] });
3210
- }, children: [jsxRuntime.jsx(io5.IoReload, {}), " ", text] }));
3211
- };
3212
-
3213
3271
  const TableCardContainer = ({ children, variant = "", ...props }) => {
3214
3272
  if (variant === "carousel") {
3215
3273
  return (jsxRuntime.jsx(react.Flex, { overflow: "scroll", gap: "1rem", children: children }));
@@ -3242,17 +3300,6 @@ const TableComponent = ({ render = () => {
3242
3300
  return render(table);
3243
3301
  };
3244
3302
 
3245
- const TableFilterTags$1 = () => {
3246
- const { table } = useDataTableContext();
3247
- return (jsxRuntime.jsx(react.Flex, { gap: "0.5rem", flexFlow: "wrap", children: table.getState().columnFilters.map(({ id, value }) => {
3248
- return (jsxRuntime.jsx(Tag, { gap: "0.5rem", closable: true, cursor: "pointer", onClick: () => {
3249
- table.setColumnFilters(table.getState().columnFilters.filter((filter) => {
3250
- return filter.value != value;
3251
- }));
3252
- }, children: `${id}: ${value}` }, `${id}-${value}`));
3253
- }) }));
3254
- };
3255
-
3256
3303
  const TableLoadingComponent = ({ render, }) => {
3257
3304
  const { loading } = useDataTableContext();
3258
3305
  return jsxRuntime.jsx(jsxRuntime.Fragment, { children: render(loading) });
@@ -3477,53 +3524,6 @@ const ErrorAlert = ({ showMessage = true }) => {
3477
3524
  return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: isError && (jsxRuntime.jsxs(react.Alert.Root, { status: "error", children: [jsxRuntime.jsx(react.Alert.Indicator, {}), jsxRuntime.jsxs(react.Alert.Content, { children: [jsxRuntime.jsx(react.Alert.Title, { children: error.name }), showMessage && (jsxRuntime.jsx(react.Alert.Description, { children: error.message }))] })] })) }));
3478
3525
  };
3479
3526
 
3480
- const FilterOptions$1 = ({ column }) => {
3481
- const { table } = useDataTableContext();
3482
- const tableColumn = table.getColumn(column);
3483
- const options = tableColumn?.columnDef.meta?.filterOptions ?? [];
3484
- return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: options.map((option) => {
3485
- const selected = table.getColumn(column)?.getFilterValue() === option;
3486
- return (jsxRuntime.jsxs(react.Button, { size: "sm", onClick: () => {
3487
- if (selected) {
3488
- table.setColumnFilters((state) => {
3489
- return state.filter((filter) => {
3490
- return filter.id !== column;
3491
- });
3492
- });
3493
- return;
3494
- }
3495
- table.getColumn(column)?.setFilterValue(option);
3496
- }, variant: selected ? "solid" : "outline", display: "flex", gap: "0.25rem", children: [option, selected && jsxRuntime.jsx(md.MdClose, {})] }, option));
3497
- }) }));
3498
- };
3499
-
3500
- const InputGroup = React__namespace.forwardRef(function InputGroup(props, ref) {
3501
- const { startElement, startElementProps, endElement, endElementProps, children, startOffset = "6px", endOffset = "6px", ...rest } = props;
3502
- return (jsxRuntime.jsxs(react.Group, { ref: ref, ...rest, children: [startElement && (jsxRuntime.jsx(react.InputElement, { pointerEvents: "none", ...startElementProps, children: startElement })), React__namespace.cloneElement(children, {
3503
- ...(startElement && {
3504
- ps: `calc(var(--input-height) - ${startOffset})`,
3505
- }),
3506
- ...(endElement && { pe: `calc(var(--input-height) - ${endOffset})` }),
3507
- // @ts-expect-error chakra generated files
3508
- ...children.props,
3509
- }), endElement && (jsxRuntime.jsx(react.InputElement, { placement: "end", ...endElementProps, children: endElement }))] }));
3510
- });
3511
-
3512
- const GlobalFilter$1 = () => {
3513
- const { table } = useDataTableContext();
3514
- const [searchTerm, setSearchTerm] = React.useState("");
3515
- const debouncedSearchTerm = usehooks.useDebounce(searchTerm, 500);
3516
- React.useEffect(() => {
3517
- const searchHN = async () => {
3518
- table.setGlobalFilter(debouncedSearchTerm);
3519
- };
3520
- searchHN();
3521
- }, [debouncedSearchTerm]);
3522
- return (jsxRuntime.jsx(jsxRuntime.Fragment, { children: jsxRuntime.jsx(InputGroup, { flex: "1", startElement: jsxRuntime.jsx(md.MdSearch, {}), children: jsxRuntime.jsx(react.Input, { placeholder: "Outline", variant: "outline", onChange: (e) => {
3523
- setSearchTerm(e.target.value);
3524
- } }) }) }));
3525
- };
3526
-
3527
3527
  //@ts-expect-error TODO: find appropriate type
3528
3528
  const SchemaFormContext = React.createContext({
3529
3529
  schema: {},
@@ -4796,18 +4796,18 @@ exports.DataTableServer = DataTableServer;
4796
4796
  exports.DefaultCardTitle = DefaultCardTitle;
4797
4797
  exports.DefaultTable = DefaultTable;
4798
4798
  exports.DensityToggleButton = DensityToggleButton;
4799
- exports.EditFilterButton = EditFilterButton$1;
4799
+ exports.EditFilterButton = EditFilterButton;
4800
4800
  exports.EditOrderButton = EditOrderButton;
4801
4801
  exports.EditSortingButton = EditSortingButton;
4802
- exports.EditViewButton = EditViewButton$1;
4802
+ exports.EditViewButton = EditViewButton;
4803
4803
  exports.EmptyState = EmptyState;
4804
4804
  exports.ErrorAlert = ErrorAlert;
4805
- exports.FilterOptions = FilterOptions$1;
4805
+ exports.FilterOptions = FilterOptions;
4806
4806
  exports.Form = Form;
4807
- exports.GlobalFilter = GlobalFilter$1;
4807
+ exports.GlobalFilter = GlobalFilter;
4808
4808
  exports.PageSizeControl = PageSizeControl;
4809
4809
  exports.RecordDisplay = RecordDisplay;
4810
- exports.ReloadButton = ReloadButton$1;
4810
+ exports.ReloadButton = ReloadButton;
4811
4811
  exports.ResetFilteringButton = ResetFilteringButton;
4812
4812
  exports.ResetSelectionButton = ResetSelectionButton;
4813
4813
  exports.ResetSortingButton = ResetSortingButton;
@@ -4819,7 +4819,7 @@ exports.TableCards = TableCards;
4819
4819
  exports.TableComponent = TableComponent;
4820
4820
  exports.TableControls = TableControls;
4821
4821
  exports.TableFilter = TableFilter;
4822
- exports.TableFilterTags = TableFilterTags$1;
4822
+ exports.TableFilterTags = TableFilterTags;
4823
4823
  exports.TableFooter = TableFooter;
4824
4824
  exports.TableHeader = TableHeader;
4825
4825
  exports.TableLoadingComponent = TableLoadingComponent;
package/dist/index.mjs CHANGED
@@ -1,9 +1,9 @@
1
1
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
2
- import { Button as Button$1, AbsoluteCenter, Spinner, Span, IconButton, Portal, Dialog, RadioGroup as RadioGroup$1, Grid, Box, Slider as Slider$1, HStack, For, Flex, Text, Tag as Tag$1, Input, useDisclosure, DialogBackdrop, CheckboxCard as CheckboxCard$1, Menu, createRecipeContext, createContext as createContext$1, Pagination, usePaginationContext, Image, Card, DataList, Checkbox as Checkbox$1, Table as Table$1, Tooltip as Tooltip$1, Icon, MenuRoot as MenuRoot$1, MenuTrigger as MenuTrigger$1, EmptyState as EmptyState$2, VStack, List, Alert, Group, InputElement, Popover, Field as Field$1, NumberInput, Accordion, Show, RadioCard, CheckboxGroup, Heading, Center } from '@chakra-ui/react';
2
+ import { Button as Button$1, AbsoluteCenter, Spinner, Span, IconButton, Portal, Dialog, RadioGroup as RadioGroup$1, Grid, Box, Slider as Slider$1, HStack, For, Flex, Text, Tag as Tag$1, Input, useDisclosure, DialogBackdrop, CheckboxCard as CheckboxCard$1, Menu, createRecipeContext, createContext as createContext$1, Pagination, usePaginationContext, Image, Card, DataList, Checkbox as Checkbox$1, Table as Table$1, Tooltip as Tooltip$1, Group, InputElement, Icon, MenuRoot as MenuRoot$1, MenuTrigger as MenuTrigger$1, EmptyState as EmptyState$2, VStack, List, Alert, Popover, Field as Field$1, NumberInput, Accordion, Show, RadioCard, CheckboxGroup, Heading, Center } from '@chakra-ui/react';
3
3
  import { AiOutlineColumnWidth } from 'react-icons/ai';
4
4
  import * as React from 'react';
5
5
  import React__default, { createContext, useContext, useState, useEffect, useRef } from 'react';
6
- import { MdFilterAlt, MdArrowUpward, MdArrowDownward, MdOutlineMoveDown, MdOutlineSort, MdOutlineViewColumn, MdFilterListAlt, MdPushPin, MdCancel, MdClear, MdOutlineChecklist, MdClose, MdSearch } from 'react-icons/md';
6
+ import { MdFilterAlt, MdArrowUpward, MdArrowDownward, MdOutlineMoveDown, MdOutlineSort, MdSearch, MdClose, MdOutlineViewColumn, MdFilterListAlt, MdPushPin, MdCancel, MdClear, MdOutlineChecklist } from 'react-icons/md';
7
7
  import { LuX, LuCheck, LuChevronRight, LuChevronDown } from 'react-icons/lu';
8
8
  import Dayzed from '@bsol-oss/dayzed-react19';
9
9
  import { FaUpDown, FaGripLinesVertical } from 'react-icons/fa6';
@@ -20,12 +20,12 @@ import { HiMiniEllipsisHorizontal, HiChevronLeft, HiChevronRight } from 'react-i
20
20
  import { flexRender, makeStateUpdater, functionalUpdate, useReactTable, getCoreRowModel, getFilteredRowModel, getSortedRowModel, getPaginationRowModel, createColumnHelper } from '@tanstack/react-table';
21
21
  import { rankItem } from '@tanstack/match-sorter-utils';
22
22
  import { BsExclamationCircleFill } from 'react-icons/bs';
23
- import { GrAscend, GrDescend } from 'react-icons/gr';
24
- import { HiColorSwatch, HiOutlineInformationCircle } from 'react-icons/hi';
23
+ import { useDebounce } from '@uidotdev/usehooks';
25
24
  import { useQueryClient, useQuery, QueryClient, QueryClientProvider } from '@tanstack/react-query';
26
25
  import { IoReload } from 'react-icons/io5';
26
+ import { GrAscend, GrDescend } from 'react-icons/gr';
27
+ import { HiColorSwatch, HiOutlineInformationCircle } from 'react-icons/hi';
27
28
  import axios from 'axios';
28
- import { useDebounce } from '@uidotdev/usehooks';
29
29
  import { useFormContext, useForm, FormProvider } from 'react-hook-form';
30
30
  import dayjs from 'dayjs';
31
31
 
@@ -351,7 +351,7 @@ const ResetFilteringButton = ({ text = "Reset Filtering", }) => {
351
351
  }, children: text }));
352
352
  };
353
353
 
354
- const EditFilterButton$1 = ({ text, title = "Edit Filter", closeText = "Close", resetText = "Reset", icon = jsx(MdFilterAlt, {}), }) => {
354
+ const EditFilterButton = ({ text, title = "Edit Filter", closeText = "Close", resetText = "Reset", icon = jsx(MdFilterAlt, {}), }) => {
355
355
  const filterModal = useDisclosure();
356
356
  return (jsx(Fragment, { children: jsx(DialogRoot, { size: ["full", "full", "md", "md"], open: filterModal.open, children: jsxs(DialogRoot, { children: [jsx(DialogTrigger, { asChild: true, children: jsxs(Button$1, { as: Box, variant: "ghost", onClick: filterModal.onOpen, children: [icon, " ", text] }) }), jsxs(DialogContent, { children: [jsx(DialogHeader, { children: jsx(DialogTitle, { children: title }) }), jsx(DialogBody, { children: jsxs(Flex, { flexFlow: "column", gap: "1rem", children: [jsx(TableFilter, {}), jsx(ResetFilteringButton, { text: resetText })] }) }), jsxs(DialogFooter, { children: [jsx(DialogActionTrigger, { asChild: true, children: jsx(Button$1, { onClick: filterModal.onClose, children: closeText }) }), jsx(Button$1, { children: "Save" })] }), jsx(DialogCloseTrigger, {})] })] }) }) }));
357
357
  };
@@ -2430,7 +2430,7 @@ const TableViewer = () => {
2430
2430
  }) }));
2431
2431
  };
2432
2432
 
2433
- const EditViewButton$1 = ({ text, icon = jsx(IoMdEye, {}), title = "Edit View", }) => {
2433
+ const EditViewButton = ({ text, icon = jsx(IoMdEye, {}), title = "Edit View", }) => {
2434
2434
  const viewModel = useDisclosure();
2435
2435
  return (jsx(Fragment, { children: jsxs(DialogRoot, { children: [jsx(DialogBackdrop, {}), jsx(DialogTrigger, { asChild: true, children: jsxs(Button$1, { as: Box, variant: "ghost", onClick: viewModel.onOpen, children: [icon, " ", text] }) }), jsxs(DialogContent, { children: [jsx(DialogCloseTrigger, {}), jsxs(DialogHeader, { children: [jsx(DialogTitle, {}), title] }), jsx(DialogBody, { children: jsx(TableViewer, {}) }), jsx(DialogFooter, {})] })] }) }));
2436
2436
  };
@@ -2981,12 +2981,90 @@ const Tooltip = React.forwardRef(function Tooltip(props, ref) {
2981
2981
  return (jsxs(Tooltip$1.Root, { ...rest, children: [jsx(Tooltip$1.Trigger, { asChild: true, children: children }), jsx(Portal, { disabled: !portalled, container: portalRef, children: jsx(Tooltip$1.Positioner, { children: jsxs(Tooltip$1.Content, { ref: ref, ...contentProps, children: [showArrow && (jsx(Tooltip$1.Arrow, { children: jsx(Tooltip$1.ArrowTip, {}) })), content] }) }) })] }));
2982
2982
  });
2983
2983
 
2984
- const TableControls = ({ totalText = "Total:", fitTableWidth = false, fitTableHeight = false, isMobile = false, children = jsx(Fragment, {}), showGlobalFilter = false, showFilter = false, showFilterName = false, showFilterTags = false, showReload = false, filterOptions = [], extraItems = jsx(Fragment, {}), loading = false, hasError = false, }) => {
2984
+ const InputGroup = React.forwardRef(function InputGroup(props, ref) {
2985
+ const { startElement, startElementProps, endElement, endElementProps, children, startOffset = "6px", endOffset = "6px", ...rest } = props;
2986
+ return (jsxs(Group, { ref: ref, ...rest, children: [startElement && (jsx(InputElement, { pointerEvents: "none", ...startElementProps, children: startElement })), React.cloneElement(children, {
2987
+ ...(startElement && {
2988
+ ps: `calc(var(--input-height) - ${startOffset})`,
2989
+ }),
2990
+ ...(endElement && { pe: `calc(var(--input-height) - ${endOffset})` }),
2991
+ // @ts-expect-error chakra generated files
2992
+ ...children.props,
2993
+ }), endElement && (jsx(InputElement, { placement: "end", ...endElementProps, children: endElement }))] }));
2994
+ });
2995
+
2996
+ const GlobalFilter = () => {
2997
+ const { table } = useDataTableContext();
2998
+ const [searchTerm, setSearchTerm] = useState("");
2999
+ const debouncedSearchTerm = useDebounce(searchTerm, 500);
3000
+ useEffect(() => {
3001
+ const searchHN = async () => {
3002
+ table.setGlobalFilter(debouncedSearchTerm);
3003
+ };
3004
+ searchHN();
3005
+ }, [debouncedSearchTerm]);
3006
+ return (jsx(Fragment, { children: jsx(InputGroup, { flex: "1", startElement: jsx(MdSearch, {}), children: jsx(Input, { placeholder: "Outline", variant: "outline", onChange: (e) => {
3007
+ setSearchTerm(e.target.value);
3008
+ } }) }) }));
3009
+ };
3010
+
3011
+ const useDataTableServerContext = () => {
3012
+ const context = useContext(DataTableServerContext);
3013
+ const { query } = context;
3014
+ const isEmpty = (query.data?.count ?? 0) <= 0;
3015
+ return { ...context, isEmpty };
3016
+ };
3017
+
3018
+ const ReloadButton = ({ text = "Reload", variant = "icon", }) => {
3019
+ const { url } = useDataTableServerContext();
3020
+ const queryClient = useQueryClient();
3021
+ if (variant === "icon") {
3022
+ return (jsx(Tooltip, { showArrow: true, content: "This is the tooltip content", children: jsx(Button, { variant: "ghost", onClick: () => {
3023
+ queryClient.invalidateQueries({ queryKey: [url] });
3024
+ }, "aria-label": "refresh", children: jsx(IoReload, {}) }) }));
3025
+ }
3026
+ return (jsxs(Button, { variant: "ghost", onClick: () => {
3027
+ queryClient.invalidateQueries({ queryKey: [url] });
3028
+ }, children: [jsx(IoReload, {}), " ", text] }));
3029
+ };
3030
+
3031
+ const FilterOptions = ({ column }) => {
3032
+ const { table } = useDataTableContext();
3033
+ const tableColumn = table.getColumn(column);
3034
+ const options = tableColumn?.columnDef.meta?.filterOptions ?? [];
3035
+ return (jsx(Fragment, { children: options.map((option) => {
3036
+ const selected = table.getColumn(column)?.getFilterValue() === option;
3037
+ return (jsxs(Button$1, { size: "sm", onClick: () => {
3038
+ if (selected) {
3039
+ table.setColumnFilters((state) => {
3040
+ return state.filter((filter) => {
3041
+ return filter.id !== column;
3042
+ });
3043
+ });
3044
+ return;
3045
+ }
3046
+ table.getColumn(column)?.setFilterValue(option);
3047
+ }, variant: selected ? "solid" : "outline", display: "flex", gap: "0.25rem", children: [option, selected && jsx(MdClose, {})] }, option));
3048
+ }) }));
3049
+ };
3050
+
3051
+ const TableFilterTags = () => {
3052
+ const { table } = useDataTableContext();
3053
+ return (jsx(Flex, { gap: "0.5rem", flexFlow: "wrap", children: table.getState().columnFilters.map(({ id, value }) => {
3054
+ return (jsx(Tag, { gap: "0.5rem", closable: true, cursor: "pointer", onClick: () => {
3055
+ table.setColumnFilters(table.getState().columnFilters.filter((filter) => {
3056
+ return filter.value != value;
3057
+ }));
3058
+ }, children: `${id}: ${value}` }, `${id}-${value}`));
3059
+ }) }));
3060
+ };
3061
+
3062
+ const TableControls = ({ totalText = "Total:", fitTableWidth = false, fitTableHeight = false, isMobile = false, children = jsx(Fragment, {}), showGlobalFilter = false, showFilter = false, showFilterName = false, showFilterTags = false, showReload = false, showPagination = true, showPageSizeControl = true, showPageCountText = true, filterOptions = [], extraItems = jsx(Fragment, {}), loading = false, hasError = false, }) => {
2985
3063
  return (jsxs(Grid, { templateRows: "auto 1fr auto", width: fitTableWidth ? "fit-content" : "100%", height: fitTableHeight ? "fit-content" : "100%", gap: "0.5rem", children: [jsxs(Flex, { flexFlow: "column", gap: 2, children: [jsxs(Flex, { justifyContent: "space-between", children: [jsx(Box, { children: jsx(EditViewButton, { text: isMobile ? undefined : "View", icon: jsx(MdOutlineViewColumn, {}) }) }), jsxs(Flex, { gap: "0.5rem", alignItems: "center", justifySelf: "end", children: [loading && jsx(Spinner, { size: "sm" }), hasError && (jsx(Tooltip, { content: "An error occurred while fetching data", children: jsx(Icon, { as: BsExclamationCircleFill, color: "red.400" }) })), showGlobalFilter && jsx(GlobalFilter, {}), showFilter && (jsx(Fragment, { children: jsx(EditFilterButton, { text: isMobile ? undefined : "Advanced Filter" }) })), showReload && jsx(ReloadButton, {}), extraItems] })] }), filterOptions.length > 0 && (jsx(Flex, { flexFlow: "column", gap: "0.5rem", children: filterOptions.map((column) => {
2986
3064
  return (jsxs(Flex, { alignItems: "center", flexFlow: "wrap", gap: "0.5rem", children: [showFilterName && jsxs(Text, { children: [column, ":"] }), jsx(FilterOptions, { column: column })] }, column));
2987
3065
  }) })), showFilterTags && (jsx(Flex, { children: jsx(TableFilterTags, {}) }))] }), jsx(Grid, { overflow: "auto", backgroundColor: "gray.50", _dark: {
2988
3066
  backgroundColor: "gray.900",
2989
- }, children: children }), jsxs(Flex, { justifyContent: "space-between", children: [jsxs(Flex, { gap: "1rem", alignItems: "center", children: [jsx(PageSizeControl, {}), jsxs(Flex, { children: [jsx(Text, { paddingRight: "0.5rem", children: totalText }), jsx(RowCountText, {})] })] }), jsx(Box, { justifySelf: "end", children: jsx(TablePagination, {}) })] })] }));
3067
+ }, children: children }), jsxs(Flex, { justifyContent: "space-between", children: [jsxs(Flex, { gap: "1rem", alignItems: "center", children: [showPageSizeControl && jsx(PageSizeControl, {}), showPageCountText && (jsxs(Flex, { children: [jsx(Text, { paddingRight: "0.5rem", children: totalText }), jsx(RowCountText, {})] }))] }), jsx(Box, { justifySelf: "end", children: showPagination && jsx(TablePagination, {}) })] })] }));
2990
3068
  };
2991
3069
 
2992
3070
  const TableFooter = ({ pinnedBgColor = { light: "gray.50", dark: "gray.700" }, showSelector = false, alwaysShowSelector = true, }) => {
@@ -3170,26 +3248,6 @@ const DefaultTable = ({ showFooter = false, tableProps = {}, tableHeaderProps =
3170
3248
  return (jsx(TableControls, { ...controlProps, children: jsxs(Table, { ...tableProps, children: [jsx(TableHeader, { ...tableHeaderProps }), jsx(TableBody, { ...tableBodyProps }), showFooter && jsx(TableFooter, { ...tableFooterProps })] }) }));
3171
3249
  };
3172
3250
 
3173
- const useDataTableServerContext = () => {
3174
- const context = useContext(DataTableServerContext);
3175
- const { query } = context;
3176
- const isEmpty = (query.data?.count ?? 0) <= 0;
3177
- return { ...context, isEmpty };
3178
- };
3179
-
3180
- const ReloadButton$1 = ({ text = "Reload", variant = "icon", }) => {
3181
- const { url } = useDataTableServerContext();
3182
- const queryClient = useQueryClient();
3183
- if (variant === "icon") {
3184
- return (jsx(Tooltip, { showArrow: true, content: "This is the tooltip content", children: jsx(Button, { variant: "ghost", onClick: () => {
3185
- queryClient.invalidateQueries({ queryKey: [url] });
3186
- }, "aria-label": "refresh", children: jsx(IoReload, {}) }) }));
3187
- }
3188
- return (jsxs(Button, { variant: "ghost", onClick: () => {
3189
- queryClient.invalidateQueries({ queryKey: [url] });
3190
- }, children: [jsx(IoReload, {}), " ", text] }));
3191
- };
3192
-
3193
3251
  const TableCardContainer = ({ children, variant = "", ...props }) => {
3194
3252
  if (variant === "carousel") {
3195
3253
  return (jsx(Flex, { overflow: "scroll", gap: "1rem", children: children }));
@@ -3222,17 +3280,6 @@ const TableComponent = ({ render = () => {
3222
3280
  return render(table);
3223
3281
  };
3224
3282
 
3225
- const TableFilterTags$1 = () => {
3226
- const { table } = useDataTableContext();
3227
- return (jsx(Flex, { gap: "0.5rem", flexFlow: "wrap", children: table.getState().columnFilters.map(({ id, value }) => {
3228
- return (jsx(Tag, { gap: "0.5rem", closable: true, cursor: "pointer", onClick: () => {
3229
- table.setColumnFilters(table.getState().columnFilters.filter((filter) => {
3230
- return filter.value != value;
3231
- }));
3232
- }, children: `${id}: ${value}` }, `${id}-${value}`));
3233
- }) }));
3234
- };
3235
-
3236
3283
  const TableLoadingComponent = ({ render, }) => {
3237
3284
  const { loading } = useDataTableContext();
3238
3285
  return jsx(Fragment, { children: render(loading) });
@@ -3457,53 +3504,6 @@ const ErrorAlert = ({ showMessage = true }) => {
3457
3504
  return (jsx(Fragment, { children: isError && (jsxs(Alert.Root, { status: "error", children: [jsx(Alert.Indicator, {}), jsxs(Alert.Content, { children: [jsx(Alert.Title, { children: error.name }), showMessage && (jsx(Alert.Description, { children: error.message }))] })] })) }));
3458
3505
  };
3459
3506
 
3460
- const FilterOptions$1 = ({ column }) => {
3461
- const { table } = useDataTableContext();
3462
- const tableColumn = table.getColumn(column);
3463
- const options = tableColumn?.columnDef.meta?.filterOptions ?? [];
3464
- return (jsx(Fragment, { children: options.map((option) => {
3465
- const selected = table.getColumn(column)?.getFilterValue() === option;
3466
- return (jsxs(Button$1, { size: "sm", onClick: () => {
3467
- if (selected) {
3468
- table.setColumnFilters((state) => {
3469
- return state.filter((filter) => {
3470
- return filter.id !== column;
3471
- });
3472
- });
3473
- return;
3474
- }
3475
- table.getColumn(column)?.setFilterValue(option);
3476
- }, variant: selected ? "solid" : "outline", display: "flex", gap: "0.25rem", children: [option, selected && jsx(MdClose, {})] }, option));
3477
- }) }));
3478
- };
3479
-
3480
- const InputGroup = React.forwardRef(function InputGroup(props, ref) {
3481
- const { startElement, startElementProps, endElement, endElementProps, children, startOffset = "6px", endOffset = "6px", ...rest } = props;
3482
- return (jsxs(Group, { ref: ref, ...rest, children: [startElement && (jsx(InputElement, { pointerEvents: "none", ...startElementProps, children: startElement })), React.cloneElement(children, {
3483
- ...(startElement && {
3484
- ps: `calc(var(--input-height) - ${startOffset})`,
3485
- }),
3486
- ...(endElement && { pe: `calc(var(--input-height) - ${endOffset})` }),
3487
- // @ts-expect-error chakra generated files
3488
- ...children.props,
3489
- }), endElement && (jsx(InputElement, { placement: "end", ...endElementProps, children: endElement }))] }));
3490
- });
3491
-
3492
- const GlobalFilter$1 = () => {
3493
- const { table } = useDataTableContext();
3494
- const [searchTerm, setSearchTerm] = useState("");
3495
- const debouncedSearchTerm = useDebounce(searchTerm, 500);
3496
- useEffect(() => {
3497
- const searchHN = async () => {
3498
- table.setGlobalFilter(debouncedSearchTerm);
3499
- };
3500
- searchHN();
3501
- }, [debouncedSearchTerm]);
3502
- return (jsx(Fragment, { children: jsx(InputGroup, { flex: "1", startElement: jsx(MdSearch, {}), children: jsx(Input, { placeholder: "Outline", variant: "outline", onChange: (e) => {
3503
- setSearchTerm(e.target.value);
3504
- } }) }) }));
3505
- };
3506
-
3507
3507
  //@ts-expect-error TODO: find appropriate type
3508
3508
  const SchemaFormContext = createContext({
3509
3509
  schema: {},
@@ -4769,4 +4769,4 @@ const getMultiDates = ({ selected, selectedDate, selectedDates, selectable, }) =
4769
4769
  }
4770
4770
  };
4771
4771
 
4772
- export { CardHeader, DataDisplay, DataTable, DataTableServer, DefaultCardTitle, DefaultTable, DensityToggleButton, EditFilterButton$1 as EditFilterButton, EditOrderButton, EditSortingButton, EditViewButton$1 as EditViewButton, EmptyState, ErrorAlert, FilterOptions$1 as FilterOptions, Form, GlobalFilter$1 as GlobalFilter, PageSizeControl, RecordDisplay, ReloadButton$1 as ReloadButton, ResetFilteringButton, ResetSelectionButton, ResetSortingButton, RowCountText, Table, TableBody, TableCardContainer, TableCards, TableComponent, TableControls, TableFilter, TableFilterTags$1 as TableFilterTags, TableFooter, TableHeader, TableLoadingComponent, TableOrderer, TablePagination, TableSelector, TableSorter, TableViewer, TextCell, getColumns, getMultiDates, getRangeDates, useDataTable, useDataTableContext, useDataTableServer, widthSanityCheck };
4772
+ export { CardHeader, DataDisplay, DataTable, DataTableServer, DefaultCardTitle, DefaultTable, DensityToggleButton, EditFilterButton, EditOrderButton, EditSortingButton, EditViewButton, EmptyState, ErrorAlert, FilterOptions, Form, GlobalFilter, PageSizeControl, RecordDisplay, ReloadButton, ResetFilteringButton, ResetSelectionButton, ResetSortingButton, RowCountText, Table, TableBody, TableCardContainer, TableCards, TableComponent, TableControls, TableFilter, TableFilterTags, TableFooter, TableHeader, TableLoadingComponent, TableOrderer, TablePagination, TableSelector, TableSorter, TableViewer, TextCell, getColumns, getMultiDates, getRangeDates, useDataTable, useDataTableContext, useDataTableServer, widthSanityCheck };
@@ -10,9 +10,12 @@ export interface TableControlsProps {
10
10
  showFilterName?: boolean;
11
11
  showFilterTags?: boolean;
12
12
  showReload?: boolean;
13
+ showPagination?: boolean;
14
+ showPageSizeControl?: boolean;
15
+ showPageCountText?: boolean;
13
16
  filterOptions?: string[];
14
17
  extraItems?: ReactNode;
15
18
  loading?: boolean;
16
19
  hasError?: boolean;
17
20
  }
18
- export declare const TableControls: ({ totalText, fitTableWidth, fitTableHeight, isMobile, children, showGlobalFilter, showFilter, showFilterName, showFilterTags, showReload, filterOptions, extraItems, loading, hasError, }: TableControlsProps) => import("react/jsx-runtime").JSX.Element;
21
+ export declare const TableControls: ({ totalText, fitTableWidth, fitTableHeight, isMobile, children, showGlobalFilter, showFilter, showFilterName, showFilterTags, showReload, showPagination, showPageSizeControl, showPageCountText, filterOptions, extraItems, loading, hasError, }: TableControlsProps) => import("react/jsx-runtime").JSX.Element;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@bsol-oss/react-datatable5",
3
- "version": "8.1.1",
3
+ "version": "8.1.2",
4
4
  "type": "module",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",