ms-react-table 1.0.0 → 2.0.1

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.mjs CHANGED
@@ -1,8 +1,8 @@
1
1
  // src/MsReactTable.tsx
2
- import React5 from "react";
2
+ import React12 from "react";
3
3
 
4
4
  // src/contextAPI/MsTableProvider.tsx
5
- import { useState as useState3, useMemo as useMemo2, useCallback, useEffect as useEffect2, useRef as useRef2 } from "react";
5
+ import { useState as useState3, useMemo as useMemo2, useCallback as useCallback2, useEffect as useEffect2, useRef, forwardRef, useImperativeHandle } from "react";
6
6
 
7
7
  // src/contextAPI/MsTableContext.tsx
8
8
  import { createContext, useContext } from "react";
@@ -17,7 +17,7 @@ var useTable = () => {
17
17
  };
18
18
 
19
19
  // src/components/HeaderActionMenu/HeaderActionMenu.tsx
20
- import { useEffect, useState as useState2 } from "react";
20
+ import { useCallback, useEffect, useState as useState2 } from "react";
21
21
 
22
22
  // src/_assets/icons/index.tsx
23
23
  import { jsx, jsxs } from "react/jsx-runtime";
@@ -35,9 +35,37 @@ var prevIcon = /* @__PURE__ */ jsx("svg", { xmlns: "http://www.w3.org/2000/svg",
35
35
  var nextIcon = /* @__PURE__ */ jsx("svg", { xmlns: "http://www.w3.org/2000/svg", width: "32", height: "32", fill: "currentColor", viewBox: "0 0 256 256", children: /* @__PURE__ */ jsx("path", { d: "M181.66,133.66l-80,80a8,8,0,0,1-11.32-11.32L164.69,128,90.34,53.66a8,8,0,0,1,11.32-11.32l80,80A8,8,0,0,1,181.66,133.66Z" }) });
36
36
  var doublePipeArrow = /* @__PURE__ */ jsx("svg", { xmlns: "http://www.w3.org/2000/svg", width: "32", height: "32", fill: "currentColor", viewBox: "0 0 256 256", children: /* @__PURE__ */ jsx("path", { d: "M112,48V208a8,8,0,0,1-16,0V136H43.31l18.35,18.34a8,8,0,0,1-11.32,11.32l-32-32a8,8,0,0,1,0-11.32l32-32a8,8,0,0,1,11.32,11.32L43.31,120H96V48a8,8,0,0,1,16,0Zm125.66,74.34-32-32a8,8,0,0,0-11.32,11.32L212.69,120H160V48a8,8,0,0,0-16,0V208a8,8,0,0,0,16,0V136h52.69l-18.35,18.34a8,8,0,0,0,11.32,11.32l32-32A8,8,0,0,0,237.66,122.34Z" }) });
37
37
  var hideShow = /* @__PURE__ */ jsx("svg", { xmlns: "http://www.w3.org/2000/svg", width: "32", height: "32", fill: "currentColor", viewBox: "0 0 256 256", children: /* @__PURE__ */ jsx("path", { d: "M64,105V40a8,8,0,0,0-16,0v65a32,32,0,0,0,0,62v49a8,8,0,0,0,16,0V167a32,32,0,0,0,0-62Zm-8,47a16,16,0,1,1,16-16A16,16,0,0,1,56,152Zm80-95V40a8,8,0,0,0-16,0V57a32,32,0,0,0,0,62v97a8,8,0,0,0,16,0V119a32,32,0,0,0,0-62Zm-8,47a16,16,0,1,1,16-16A16,16,0,0,1,128,104Zm104,64a32.06,32.06,0,0,0-24-31V40a8,8,0,0,0-16,0v97a32,32,0,0,0,0,62v17a8,8,0,0,0,16,0V199A32.06,32.06,0,0,0,232,168Zm-32,16a16,16,0,1,1,16-16A16,16,0,0,1,200,184Z" }) });
38
+ var closeIcon = /* @__PURE__ */ jsxs("svg", { xmlns: "http://www.w3.org/2000/svg", viewBox: "0 0 256 256", children: [
39
+ /* @__PURE__ */ jsx("rect", { width: "64", height: "64", fill: "none" }),
40
+ /* @__PURE__ */ jsx("line", { x1: "200", y1: "56", x2: "56", y2: "200", stroke: "currentColor", strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "16" }),
41
+ /* @__PURE__ */ jsx("line", { x1: "200", y1: "200", x2: "56", y2: "56", stroke: "currentColor", strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "16" })
42
+ ] });
43
+ var rangeIcon = /* @__PURE__ */ jsxs("svg", { xmlns: "http://www.w3.org/2000/svg", viewBox: "0 0 256 256", children: [
44
+ /* @__PURE__ */ jsx("rect", { width: "256", height: "256", fill: "none" }),
45
+ /* @__PURE__ */ jsx("line", { x1: "216", y1: "128", x2: "40", y2: "128", fill: "none", stroke: "currentColor", strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "16" }),
46
+ /* @__PURE__ */ jsx("line", { x1: "128", y1: "16", x2: "128", y2: "96", fill: "none", stroke: "currentColor", strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "16" }),
47
+ /* @__PURE__ */ jsx("polyline", { points: "160 64 128 96 96 64", fill: "none", stroke: "currentColor", "stroke-linecap": "round", strokeLinejoin: "round", strokeWidth: "16" }),
48
+ /* @__PURE__ */ jsx("line", { x1: "128", y1: "240", x2: "128", y2: "160", fill: "none", stroke: "currentColor", strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "16" }),
49
+ /* @__PURE__ */ jsx("polyline", { points: "96 192 128 160 160 192", fill: "none", stroke: "currentColor", strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "16" })
50
+ ] });
51
+
52
+ // src/components/FormElements/CheckBox.tsx
53
+ import { memo } from "react";
54
+ import { Fragment, jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
55
+ var CheckBox = (props) => {
56
+ const { id, name, checked, onChange, disabled } = props;
57
+ return /* @__PURE__ */ jsx2(Fragment, { children: /* @__PURE__ */ jsxs2("label", { className: "ms-checkbox-wrapper", children: [
58
+ /* @__PURE__ */ jsx2("input", { type: "checkbox", className: "ms-promoted-input-checkbox", disabled, checked, onChange: disabled ? () => {
59
+ } : onChange }),
60
+ /* @__PURE__ */ jsx2("span", { className: "ms-checkbox-box" }),
61
+ /* @__PURE__ */ jsx2("svg", { children: /* @__PURE__ */ jsx2("use", { xlinkHref: `#${id}` }) }),
62
+ /* @__PURE__ */ jsx2("svg", { xmlns: "http://www.w3.org/2000/svg", style: { display: "none" }, children: /* @__PURE__ */ jsx2("symbol", { id, viewBox: "0 0 24 24", children: /* @__PURE__ */ jsx2("path", { strokeLinecap: "round", strokeMiterlimit: "10", fill: "none", d: "M22.9 3.7l-15.2 16.6-6.6-7.1" }) }) })
63
+ ] }) });
64
+ };
65
+ var CheckBox_default = memo(CheckBox);
38
66
 
39
67
  // src/components/HeaderActionMenu/HeaderActionMenu.tsx
40
- import { jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
68
+ import { jsx as jsx3, jsxs as jsxs3 } from "react/jsx-runtime";
41
69
  var HeaderActionMenu = (props) => {
42
70
  const { state, api: { onColumnPin, onSortColumn, onAutoColumnResize, onColumnReset, updateState } } = useTable();
43
71
  const [showColumnList, toggleColumnList] = useState2(false);
@@ -47,7 +75,7 @@ var HeaderActionMenu = (props) => {
47
75
  setColumnList(state.colConfigs);
48
76
  onSearchHeader(searchkey);
49
77
  }, [state.colConfigs]);
50
- const onCheckboxChange = (dataIndex, e) => {
78
+ const onCheckboxChange = useCallback((dataIndex, e) => {
51
79
  let newConfig = state.colConfigs.map((item) => {
52
80
  return {
53
81
  ...item,
@@ -59,7 +87,7 @@ var HeaderActionMenu = (props) => {
59
87
  colConfigs: newConfig
60
88
  });
61
89
  setColumnList(newConfig);
62
- };
90
+ }, []);
63
91
  const onSearchHeader = (value) => {
64
92
  let newlist = [];
65
93
  if (value) {
@@ -74,31 +102,31 @@ var HeaderActionMenu = (props) => {
74
102
  }
75
103
  setSearchkey(value);
76
104
  };
77
- return /* @__PURE__ */ jsx2("div", { ref: props.ref, className: "header-menu", style: props.style, children: showColumnList ? /* @__PURE__ */ jsxs2("div", { className: "column-list", children: [
78
- /* @__PURE__ */ jsx2("div", { className: "search", children: /* @__PURE__ */ jsx2("input", { type: "text", placeholder: "Search header", className: "search-input", onChange: (e) => onSearchHeader(e.target.value) }) }),
79
- /* @__PURE__ */ jsx2("div", { className: "list", children: columnList.map((item) => /* @__PURE__ */ jsxs2("div", { className: "item", children: [
80
- /* @__PURE__ */ jsx2("input", { className: "ms-checkbox-input", type: "checkbox", id: item.dataIndex, checked: !item.isHidden, onChange: (e) => onCheckboxChange(item.dataIndex, e) }),
81
- /* @__PURE__ */ jsx2("label", { htmlFor: item.dataIndex, children: item.title })
105
+ return /* @__PURE__ */ jsx3("div", { ref: props.ref, className: "header-menu", style: props.style, children: showColumnList ? /* @__PURE__ */ jsxs3("div", { className: "column-list", children: [
106
+ /* @__PURE__ */ jsx3("div", { className: "search", children: /* @__PURE__ */ jsx3("input", { type: "text", placeholder: "Search header", className: "search-input", onChange: (e) => onSearchHeader(e.target.value) }) }),
107
+ /* @__PURE__ */ jsx3("div", { className: "list", children: columnList.map((item) => /* @__PURE__ */ jsxs3("div", { className: "item", children: [
108
+ /* @__PURE__ */ jsx3(CheckBox_default, { id: item.dataIndex, checked: !item.isHidden, onChange: (e) => onCheckboxChange(item.dataIndex, e) }),
109
+ /* @__PURE__ */ jsx3("label", { htmlFor: item.dataIndex, children: item.title })
82
110
  ] }, item.dataIndex + "_item")) })
83
- ] }) : /* @__PURE__ */ jsxs2("ul", { children: [
84
- /* @__PURE__ */ jsxs2("li", { onClick: () => onSortColumn(props.dataIndex, "asc"), children: [
85
- /* @__PURE__ */ jsx2("span", { children: angleUpIcon }),
111
+ ] }) : /* @__PURE__ */ jsxs3("ul", { children: [
112
+ /* @__PURE__ */ jsxs3("li", { onClick: () => onSortColumn(props.dataIndex, "asc"), children: [
113
+ /* @__PURE__ */ jsx3("span", { children: angleUpIcon }),
86
114
  `Sort By Ascending`
87
115
  ] }),
88
- /* @__PURE__ */ jsxs2("li", { onClick: () => onSortColumn(props.dataIndex, "desc"), children: [
89
- /* @__PURE__ */ jsx2("span", { children: angleDownIcon }),
116
+ /* @__PURE__ */ jsxs3("li", { onClick: () => onSortColumn(props.dataIndex, "desc"), children: [
117
+ /* @__PURE__ */ jsx3("span", { children: angleDownIcon }),
90
118
  `Sort By Descending`
91
119
  ] }),
92
- /* @__PURE__ */ jsxs2("li", { onClick: () => onAutoColumnResize("all"), children: [
93
- /* @__PURE__ */ jsx2("span", { children: doublePipeArrow }),
120
+ /* @__PURE__ */ jsxs3("li", { onClick: () => onAutoColumnResize("all"), children: [
121
+ /* @__PURE__ */ jsx3("span", { children: doublePipeArrow }),
94
122
  `Autosize All Column`
95
123
  ] }),
96
- /* @__PURE__ */ jsxs2("li", { onClick: () => toggleColumnList(true), children: [
97
- /* @__PURE__ */ jsx2("span", { children: hideShow }),
124
+ /* @__PURE__ */ jsxs3("li", { onClick: () => toggleColumnList(true), children: [
125
+ /* @__PURE__ */ jsx3("span", { children: hideShow }),
98
126
  `Hide/Show Columns`
99
127
  ] }),
100
- /* @__PURE__ */ jsxs2("li", { onClick: onColumnReset, children: [
101
- /* @__PURE__ */ jsx2("span", { children: reloadIcon }),
128
+ /* @__PURE__ */ jsxs3("li", { onClick: onColumnReset, children: [
129
+ /* @__PURE__ */ jsx3("span", { children: reloadIcon }),
102
130
  `Reset Columns`
103
131
  ] })
104
132
  ] }) });
@@ -106,10 +134,10 @@ var HeaderActionMenu = (props) => {
106
134
  var HeaderActionMenu_default = HeaderActionMenu;
107
135
 
108
136
  // src/components/Overlay.tsx
109
- import { jsx as jsx3 } from "react/jsx-runtime";
137
+ import { jsx as jsx4 } from "react/jsx-runtime";
110
138
  var Overlay = (props) => {
111
- const { message = "No Records to show", style } = props;
112
- return /* @__PURE__ */ jsx3("div", { className: "overlay-message", style, children: message });
139
+ const { message = "No Records to show", style, customComponentForNoRecords } = props;
140
+ return /* @__PURE__ */ jsx4("div", { className: "overlay-message", style, children: customComponentForNoRecords ? customComponentForNoRecords : message });
113
141
  };
114
142
  var Overlay_default = Overlay;
115
143
 
@@ -128,61 +156,190 @@ function sortData(data, dataIndex, sortBy) {
128
156
  return sortBy === "asc" ? comparison : -comparison;
129
157
  });
130
158
  }
159
+ function applyOperation(fieldValue, rule) {
160
+ if (rule.type === "string") {
161
+ const val = String(fieldValue).toLowerCase();
162
+ const target = String(rule.value).toLowerCase();
163
+ switch (rule.operation) {
164
+ case "include":
165
+ return val.includes(target);
166
+ case "not include":
167
+ return !val.includes(target);
168
+ case "=":
169
+ return val === target;
170
+ case "!=":
171
+ return val !== target;
172
+ default:
173
+ return true;
174
+ }
175
+ }
176
+ if (rule.type === "number") {
177
+ const val = Number(fieldValue);
178
+ const target = Number(rule.value);
179
+ switch (rule.operation) {
180
+ case "=":
181
+ return val === target;
182
+ case "!=":
183
+ return val !== target;
184
+ case ">":
185
+ return val > target;
186
+ case "<":
187
+ return val < target;
188
+ default:
189
+ return true;
190
+ }
191
+ }
192
+ if (rule.type === "date") {
193
+ let [fromDate, toDate] = rule.value;
194
+ const val = new Date(fieldValue)?.getTime();
195
+ const target_1 = new Date(fromDate)?.getTime();
196
+ const target_2 = new Date(toDate)?.getTime();
197
+ switch (rule.operation) {
198
+ case "=":
199
+ return val === target_1;
200
+ case "!=":
201
+ return val !== target_1;
202
+ case ">":
203
+ return val >= target_1;
204
+ case "<":
205
+ return val < target_1;
206
+ case "<>":
207
+ return val > target_1 && val < target_2;
208
+ default:
209
+ return true;
210
+ }
211
+ }
212
+ if (rule.type === "boolean") {
213
+ const val = Boolean(fieldValue);
214
+ const target = rule.value == "true" ? true : false;
215
+ return val === target;
216
+ }
217
+ return true;
218
+ }
219
+ function exportToCSV(data, fileName) {
220
+ const headers = Object.keys(data[0]).join(",");
221
+ const rows = data.map((obj) => Object.values(obj).join(",")).join("\n");
222
+ const csvContent = headers + "\n" + rows;
223
+ const blob = new Blob([csvContent], { type: "text/csv;charset=utf-8;" });
224
+ const link = document.createElement("a");
225
+ link.href = URL.createObjectURL(blob);
226
+ link.download = fileName + ".csv";
227
+ link.click();
228
+ }
229
+ function exportToExcel(data, fileName) {
230
+ const headers = Object.keys(data[0]);
231
+ const rows = data.map((obj) => Object.values(obj));
232
+ let html = "<table border='1'><tr>";
233
+ headers.forEach((h) => html += `<th>${h}</th>`);
234
+ html += "</tr>";
235
+ rows.forEach((row) => {
236
+ html += "<tr>";
237
+ row.forEach((val) => html += `<td>${val}</td>`);
238
+ html += "</tr>";
239
+ });
240
+ html += "</table>";
241
+ const blob = new Blob([html], { type: "application/vnd.ms-excel" });
242
+ const link = document.createElement("a");
243
+ link.href = URL.createObjectURL(blob);
244
+ link.download = fileName + ".xls";
245
+ link.click();
246
+ }
131
247
 
132
248
  // src/contextAPI/MsTableProvider.tsx
133
- import { jsx as jsx4, jsxs as jsxs3 } from "react/jsx-runtime";
134
- var TableProvider = (props) => {
135
- const actionMenuRef = useRef2(null);
249
+ import { jsx as jsx5, jsxs as jsxs4 } from "react/jsx-runtime";
250
+ var TableProvider = forwardRef((props, ref) => {
251
+ const actionMenuRef = useRef(null);
136
252
  const {
137
253
  columns,
138
- data,
254
+ data = [],
139
255
  children,
140
256
  pageSizeOptions = [],
141
257
  isClientSideRendering = true,
142
- totalRecords,
143
- tbodyRef,
144
- theadRef,
145
- onRowClick
258
+ hideDefaultFilterButton = false,
259
+ onRowSelect,
260
+ toggleModalFilter,
261
+ customComponentForNoRecords,
262
+ customComponentForFooter,
263
+ setRowData,
264
+ rowSelectConfig,
265
+ showPagination = true
146
266
  } = props;
147
- const tbodyHeight = tbodyRef?.current?.clientHeight;
148
- const theadHeight = theadRef?.current?.clientHeight;
149
267
  const [showActionMenu, setActionMenu] = useState3(false);
150
268
  const [selectedHeaderCell, setHeaderCell] = useState3("");
269
+ const [ssrList, setSSRList] = useState3([]);
270
+ const [totalSSRCount, setTotalSSRCount] = useState3(0);
151
271
  const [menuPosition, setMenuPosition] = useState3({
152
272
  top: 0,
153
273
  right: 0,
154
274
  left: 0
155
275
  });
276
+ const getColumnConfig = useMemo2(() => {
277
+ let list = columns.map((item) => {
278
+ let { title, dataIndex, isHidden = false, width = 80, type = "string", align = "left", sortable = true, resizable = true, pinned = "", isFilterEnabled = false, hideActionMenu = false, cellRenderer, sortKey = "", displayAs } = item;
279
+ return {
280
+ title,
281
+ dataIndex,
282
+ isHidden,
283
+ width,
284
+ type,
285
+ align,
286
+ sortable,
287
+ sortKey,
288
+ resizable,
289
+ pinned,
290
+ isFilterEnabled,
291
+ hideActionMenu,
292
+ displayAs,
293
+ cellRenderer
294
+ };
295
+ });
296
+ return list;
297
+ }, [columns]);
156
298
  const [state, setState] = useState3({
157
- prevColConfig: columns,
158
- colConfigs: columns,
299
+ prevColConfig: getColumnConfig,
300
+ colConfigs: getColumnConfig,
159
301
  rowData: [],
160
302
  allRowData: data,
161
303
  currentPage: 1,
162
304
  pageSize: pageSizeOptions.length > 0 ? pageSizeOptions[0] : 50,
163
305
  totalRecords: isClientSideRendering ? data.length : props?.totalRecords || 0,
164
306
  selectedRows: [],
165
- pageSizeOptions: pageSizeOptions.length > 0 ? pageSizeOptions : [50, 100, 200, 500],
166
- isAutoSizeAllColumns: false
307
+ selectedIndex: [],
308
+ pageSizeOptions: pageSizeOptions.length > 0 ? pageSizeOptions : [20, 50, 100],
309
+ isAutoSizeAllColumns: false,
310
+ filters: {},
311
+ customComponentForFooter,
312
+ hideDefaultFilterButton: hideDefaultFilterButton || false,
313
+ isClientSideRendering,
314
+ rowSelectConfig
167
315
  });
316
+ const [refreshPage, setRefreshPage] = useState3(false);
317
+ useEffect2(() => {
318
+ if (refreshPage) {
319
+ getListFromServer();
320
+ }
321
+ }, [refreshPage]);
168
322
  useEffect2(() => {
169
323
  if (isClientSideRendering) {
170
324
  const { currentPage, pageSize } = state;
171
325
  let list = data.slice(currentPage - 1, pageSize * currentPage - 1);
172
326
  setState((prevState) => ({
173
327
  ...prevState,
174
- rowData: list
328
+ rowData: showPagination ? list : data
175
329
  }));
330
+ } else {
331
+ getListFromServer();
176
332
  }
177
333
  }, []);
178
- const onRowSelect = useCallback((rowData) => {
334
+ const onRowSelectionChange = useCallback2((rowData, selectedIndex) => {
179
335
  setState((prevState) => ({
180
336
  ...prevState,
181
- selectedRows: [...prevState.selectedRows, rowData]
337
+ selectedRows: rowData,
338
+ selectedIndex
182
339
  }));
183
- onRowClick ? onRowClick(rowData) : null;
340
+ onRowSelect ? onRowSelect(rowData) : null;
184
341
  }, []);
185
- const onColumnResize = useCallback((dataIndex, newWidth) => {
342
+ const onColumnResize = useCallback2((dataIndex, newWidth) => {
186
343
  setState((prevState) => ({
187
344
  ...prevState,
188
345
  colConfigs: prevState.colConfigs.map(
@@ -192,36 +349,50 @@ var TableProvider = (props) => {
192
349
  }));
193
350
  }, []);
194
351
  const onPageChange = (direction) => {
195
- const { pageSize, totalRecords: totalRecords2, allRowData, currentPage } = state;
352
+ const { pageSize, totalRecords, allRowData, currentPage } = state;
196
353
  var goToPageNo = 0;
197
354
  if (direction == "first") {
198
355
  goToPageNo = 1;
199
356
  } else if (direction == "last") {
200
- goToPageNo = Math.ceil(totalRecords2 / pageSize);
357
+ goToPageNo = Math.ceil(totalRecords / pageSize);
201
358
  } else if (direction == "next") {
202
359
  goToPageNo = currentPage + 1;
203
360
  } else if (direction == "prev") {
204
361
  goToPageNo = currentPage - 1;
205
362
  }
206
- let list = data.slice(goToPageNo - 1, pageSize * goToPageNo - 1);
207
363
  setState((prevState) => ({
208
364
  ...prevState,
209
- currentPage: goToPageNo,
210
- rowData: list
365
+ currentPage: goToPageNo
211
366
  }));
367
+ if (!isClientSideRendering) {
368
+ setRefreshPage(true);
369
+ }
212
370
  };
213
371
  const onPageSizeChange = (pageSize) => {
372
+ if (!isClientSideRendering) {
373
+ setState((prevState) => ({
374
+ ...prevState,
375
+ selectedIndex: [],
376
+ selectedRows: [],
377
+ currentPage: 1,
378
+ pageSize
379
+ }));
380
+ setRefreshPage(true);
381
+ return;
382
+ }
214
383
  const { allRowData } = state;
215
384
  let list = allRowData.slice(0, pageSize - 1);
216
385
  setState((prevState) => ({
217
386
  ...prevState,
387
+ selectedIndex: [],
388
+ selectedRows: [],
218
389
  currentPage: 1,
219
390
  pageSize,
220
391
  rowData: list
221
392
  }));
222
393
  };
223
- const toggleActionMenu = (dataIndex, showMenu, ref) => {
224
- const position = ref.current.getBoundingClientRect();
394
+ const toggleActionMenu = (dataIndex, showMenu, ref2) => {
395
+ const position = ref2.current.getBoundingClientRect();
225
396
  let left = position.x + position.width;
226
397
  setMenuPosition({
227
398
  top: position.height,
@@ -241,19 +412,22 @@ var TableProvider = (props) => {
241
412
  if (sortBy == "") {
242
413
  setState((prevState) => ({
243
414
  ...prevState,
244
- colConfigs: columns2,
245
- rowData: data
415
+ colConfigs: columns2
246
416
  }));
417
+ if (!isClientSideRendering) {
418
+ setRefreshPage(true);
419
+ }
247
420
  return;
248
421
  }
249
- let sortedList = sortData(data, dataIndex, sortBy);
250
422
  setState((prevState) => ({
251
423
  ...prevState,
252
- colConfigs: columns2,
253
- rowData: sortedList
424
+ colConfigs: columns2
254
425
  }));
255
426
  setActionMenu(false);
256
427
  setHeaderCell("");
428
+ if (!isClientSideRendering) {
429
+ setRefreshPage(true);
430
+ }
257
431
  };
258
432
  const onColumnPin = (pinDirection) => {
259
433
  const { colConfigs } = state;
@@ -288,12 +462,27 @@ var TableProvider = (props) => {
288
462
  pageSize: pageSizeOptions.length > 0 ? pageSizeOptions[0] : 50,
289
463
  totalRecords: isClientSideRendering ? data.length : props?.totalRecords || 0,
290
464
  selectedRows: [],
291
- pageSizeOptions: pageSizeOptions.length > 0 ? pageSizeOptions : [50, 100, 200, 500],
292
- isAutoSizeAllColumns: false
465
+ selectedIndex: [],
466
+ pageSizeOptions: pageSizeOptions.length > 0 ? pageSizeOptions : [20, 50, 100],
467
+ isAutoSizeAllColumns: false,
468
+ hideDefaultFilterButton,
469
+ filters: {}
293
470
  });
294
471
  setActionMenu(false);
295
472
  };
296
- const updateState = useCallback((newState) => {
473
+ const onFilterApply = (filters) => {
474
+ setState((prev) => ({
475
+ ...prev,
476
+ filters
477
+ }));
478
+ toggleModalFilter(false);
479
+ if (!isClientSideRendering) {
480
+ setRefreshPage(true);
481
+ }
482
+ };
483
+ const onFilterReset = () => {
484
+ };
485
+ const updateState = useCallback2((newState) => {
297
486
  setState((prev) => ({
298
487
  ...prev,
299
488
  ...newState
@@ -301,7 +490,7 @@ var TableProvider = (props) => {
301
490
  }, []);
302
491
  const api = useMemo2(
303
492
  () => ({
304
- onRowSelect,
493
+ onRowSelectionChange,
305
494
  onColumnResize,
306
495
  onAutoColumnResize,
307
496
  onPageChange,
@@ -310,14 +499,14 @@ var TableProvider = (props) => {
310
499
  onColumnPin,
311
500
  onSortColumn,
312
501
  updateState,
313
- onColumnReset
502
+ onColumnReset,
503
+ onFilterApply,
504
+ onFilterReset,
505
+ toggleModalFilter
314
506
  }),
315
- [onRowSelect, onColumnResize, onAutoColumnResize, onPageChange, onPageSizeChange, toggleActionMenu, onColumnPin, onSortColumn, updateState, onColumnReset]
316
- );
317
- const contextValue = useMemo2(
318
- () => ({ state, api }),
319
- [state, api]
507
+ [onRowSelectionChange, onColumnResize, onAutoColumnResize, onPageChange, onPageSizeChange, toggleActionMenu, onColumnPin, onSortColumn, updateState, onColumnReset]
320
508
  );
509
+ const contextValue = { state, api, ssrList, totalSSRCount };
321
510
  useEffect2(() => {
322
511
  function handleClickOutside(event) {
323
512
  if (actionMenuRef && "current" in actionMenuRef && actionMenuRef.current && !actionMenuRef.current.contains(event.target)) {
@@ -327,23 +516,99 @@ var TableProvider = (props) => {
327
516
  document.addEventListener("mousedown", handleClickOutside);
328
517
  return () => document.removeEventListener("mousedown", handleClickOutside);
329
518
  }, [actionMenuRef, setActionMenu]);
330
- return /* @__PURE__ */ jsx4(MsTableContext_default.Provider, { value: contextValue, children: /* @__PURE__ */ jsxs3("div", { className: `table-wrapper ${state.isAutoSizeAllColumns ? "ms-auto-width" : ""}`, children: [
519
+ const reformData = () => {
520
+ let list = data;
521
+ const { filters, colConfigs, pageSize, currentPage } = state;
522
+ if (Object.keys(filters).length > 0) {
523
+ list = data.filter(
524
+ (row) => Object.entries(filters).every(
525
+ ([key, rule]) => applyOperation(row[key], rule)
526
+ )
527
+ );
528
+ }
529
+ let sortedCol = colConfigs.filter((item) => item.sortKey != "");
530
+ if (sortedCol.length > 0) {
531
+ list = sortData(list, sortedCol[0].dataIndex, sortedCol[0].sortKey || "");
532
+ }
533
+ let x = showPagination ? list.slice((currentPage - 1) * pageSize, pageSize * currentPage) : list;
534
+ setState((prev) => ({
535
+ ...prev,
536
+ rowData: x,
537
+ totalRecords: list.length
538
+ }));
539
+ };
540
+ const getListFromServer = () => {
541
+ const { filters, colConfigs, pageSize, currentPage } = state;
542
+ let sortedCol = colConfigs.filter((item) => item.sortKey != "");
543
+ let sortBy = {};
544
+ if (sortedCol.length > 0) {
545
+ sortBy.key = sortedCol[0]?.dataIndex;
546
+ sortBy.sortBy = sortedCol[0]?.sortKey;
547
+ }
548
+ if (typeof setRowData === "function") {
549
+ setRowData(currentPage, pageSize, filters, sortBy);
550
+ setRefreshPage(false);
551
+ }
552
+ };
553
+ useEffect2(() => {
554
+ if (isClientSideRendering) {
555
+ reformData();
556
+ }
557
+ }, [state.pageSize, state.colConfigs, state.filters, state.currentPage]);
558
+ useImperativeHandle(ref, () => ({
559
+ showFilterModal(status) {
560
+ toggleModalFilter(status);
561
+ },
562
+ setRowData(list, totalCount) {
563
+ const { rowSelectConfig: rowSelectConfig2 } = state;
564
+ let defaultCheckedIndex = [];
565
+ let defaultSelectedRows = [];
566
+ if (rowSelectConfig2 && rowSelectConfig2?.isChecked) {
567
+ list.map((row, index) => {
568
+ if (rowSelectConfig2?.isChecked?.(row)) {
569
+ defaultSelectedRows.push(row);
570
+ defaultCheckedIndex.push(index);
571
+ }
572
+ });
573
+ }
574
+ setState((prev) => ({
575
+ ...prev,
576
+ selectedIndex: defaultCheckedIndex,
577
+ selectedRows: defaultSelectedRows,
578
+ rowData: list,
579
+ totalRecords: totalCount
580
+ }));
581
+ },
582
+ exportToCSV(fileName) {
583
+ exportToCSV(state.rowData, fileName);
584
+ },
585
+ exportToExcel(fileName) {
586
+ exportToExcel(state.rowData, fileName);
587
+ },
588
+ getSelectedRows() {
589
+ return state.selectedRows;
590
+ }
591
+ }), [refreshPage]);
592
+ return /* @__PURE__ */ jsx5(MsTableContext_default.Provider, { value: contextValue, children: /* @__PURE__ */ jsxs4("div", { className: `ms-table-wrapper ${props.className} ${state.isAutoSizeAllColumns ? "ms-auto-width" : ""}`, children: [
331
593
  children,
332
- state.rowData.length == 0 && /* @__PURE__ */ jsx4(Overlay_default, { style: { height: tbodyHeight, top: theadHeight } }),
333
- showActionMenu && /* @__PURE__ */ jsx4(HeaderActionMenu_default, { ref: actionMenuRef, dataIndex: selectedHeaderCell, style: { top: menuPosition.top, left: menuPosition.left } })
594
+ state.rowData.length == 0 && /* @__PURE__ */ jsx5(Overlay_default, { customComponentForNoRecords }),
595
+ showActionMenu && /* @__PURE__ */ jsx5(HeaderActionMenu_default, { ref: actionMenuRef, dataIndex: selectedHeaderCell, style: { top: menuPosition.top, left: menuPosition.left } })
334
596
  ] }) });
335
- };
597
+ });
598
+
599
+ // src/components/Header/msTableHeader.tsx
600
+ import { useEffect as useEffect4, useState as useState5 } from "react";
336
601
 
337
602
  // src/components/Header/HeaderCell.tsx
338
- import { useEffect as useEffect3, useRef as useRef3, useState as useState4 } from "react";
339
- import { jsx as jsx5, jsxs as jsxs4 } from "react/jsx-runtime";
603
+ import { memo as memo2, useEffect as useEffect3, useRef as useRef2, useState as useState4 } from "react";
604
+ import { jsx as jsx6, jsxs as jsxs5 } from "react/jsx-runtime";
340
605
  var HeaderCell = (props) => {
341
- const thRef = useRef3(null);
606
+ const thRef = useRef2(null);
342
607
  const { title, cellRenderer, hideActionMenu, dataIndex, width: defaultWidth, resizable = true, pinned } = props;
343
608
  const minWidth = title === "" ? 30 : 50;
344
609
  const [width, setWidth] = useState4(defaultWidth || 80);
345
- const startX = useRef3(0);
346
- const startWidth = useRef3(0);
610
+ const startX = useRef2(0);
611
+ const startWidth = useRef2(0);
347
612
  const { state: { isAutoSizeAllColumns, ...rest }, api } = useTable();
348
613
  useEffect3(() => {
349
614
  if (isAutoSizeAllColumns) {
@@ -356,7 +621,6 @@ var HeaderCell = (props) => {
356
621
  const onMouseDown = (e) => {
357
622
  startX.current = e.clientX;
358
623
  startWidth.current = thRef.current?.offsetWidth || width;
359
- console.log("Start Width:", startWidth.current);
360
624
  document.addEventListener("mousemove", onMouseMove);
361
625
  document.addEventListener("mouseup", onMouseUp);
362
626
  };
@@ -375,106 +639,566 @@ var HeaderCell = (props) => {
375
639
  document.removeEventListener("mousemove", onMouseMove);
376
640
  document.removeEventListener("mouseup", onMouseUp);
377
641
  };
378
- return /* @__PURE__ */ jsxs4(
642
+ return /* @__PURE__ */ jsx6(
379
643
  "th",
380
644
  {
381
645
  className: `${props.headerCellClassName} ${pinned ? pinned + "-pinned" : ""}`,
382
646
  ref: thRef,
383
- style: { width: width || 80 },
384
- children: [
385
- /* @__PURE__ */ jsxs4("span", { className: "ms-table-header-cell ", children: [
386
- /* @__PURE__ */ jsxs4("span", { className: "ms-table-header-cell-title", onClick: () => api.onSortColumn(dataIndex, !props.sortKey ? "asc" : props.sortKey == "asc" ? "desc" : ""), children: [
647
+ style: { width },
648
+ children: /* @__PURE__ */ jsxs5("div", { className: "header-cell-wrapper", children: [
649
+ /* @__PURE__ */ jsxs5("div", { className: "ms-table-header-cell ", children: [
650
+ /* @__PURE__ */ jsxs5("div", { className: "ms-table-header-cell-title", onClick: () => api.onSortColumn(dataIndex, !props.sortKey ? "asc" : props.sortKey == "asc" ? "desc" : ""), children: [
387
651
  title,
652
+ " ",
653
+ rest.filters[dataIndex] ? /* @__PURE__ */ jsx6("sup", { children: "*" }) : "",
388
654
  props.sortKey == "asc" ? angleUpIcon : props.sortKey == "desc" ? angleDownIcon : null
389
655
  ] }),
390
- !hideActionMenu && /* @__PURE__ */ jsx5("span", { className: "ms-table-header-action", title: "View Menu", onClick: () => api.toggleActionMenu(dataIndex, true, thRef), children: verticleThreeDotsIcon })
656
+ !hideActionMenu && /* @__PURE__ */ jsx6("span", { className: "ms-table-header-action", title: "View Menu", onClick: () => api.toggleActionMenu(dataIndex, true, thRef), children: verticleThreeDotsIcon })
391
657
  ] }),
392
- resizable && /* @__PURE__ */ jsx5("span", { className: "ms-table-column-resizer", onMouseDown })
393
- ]
658
+ /* @__PURE__ */ jsx6("div", { className: `ms-table-column-resizer ${resizable ? "" : "disabled"}`, onMouseDown: resizable ? onMouseDown : void 0 })
659
+ ] })
394
660
  },
395
661
  dataIndex
396
662
  );
397
663
  };
398
- var HeaderCell_default = HeaderCell;
664
+ var HeaderCell_default = memo2(HeaderCell);
399
665
 
400
666
  // src/components/Header/msTableHeader.tsx
401
- import { Fragment, jsx as jsx6, jsxs as jsxs5 } from "react/jsx-runtime";
667
+ import { Fragment as Fragment2, jsx as jsx7, jsxs as jsxs6 } from "react/jsx-runtime";
402
668
  var msTableHeader = (props) => {
403
- const { state, api } = useTable();
404
- return /* @__PURE__ */ jsxs5(Fragment, { children: [
405
- /* @__PURE__ */ jsx6("colgroup", { children: state.colConfigs.map((col) => !col.isHidden && /* @__PURE__ */ jsx6("col", { width: col.width || 80 }, col.dataIndex)) }),
406
- /* @__PURE__ */ jsx6("thead", { ref: props.ref, children: /* @__PURE__ */ jsx6("tr", { children: state.colConfigs.map((col) => {
407
- if (!col.isHidden) {
408
- return /* @__PURE__ */ jsx6(HeaderCell_default, { ...col }, col.dataIndex);
409
- }
410
- }) }) })
669
+ const { state: { rowSelectConfig, rowData, colConfigs, selectedIndex, ...rest }, api } = useTable();
670
+ const [isAllChecked, setIsAllChecked] = useState5(false);
671
+ useEffect4(() => {
672
+ if (selectedIndex.length > 0) {
673
+ setIsAllChecked(rowData.length == selectedIndex.length);
674
+ } else {
675
+ setIsAllChecked(false);
676
+ }
677
+ }, [selectedIndex]);
678
+ const handleAllSelection = (isChecked) => {
679
+ let nextIndex = [];
680
+ let rows = [];
681
+ if (isChecked) {
682
+ rowData.map((item, key) => {
683
+ let isDisabled = rowSelectConfig?.isDisabled?.(item) || false;
684
+ let isDefaultChecked = rowSelectConfig?.isChecked?.(item) || false;
685
+ if (isDisabled && isDefaultChecked) {
686
+ nextIndex.push(key);
687
+ rows.push(item);
688
+ } else if (!isDisabled) {
689
+ nextIndex.push(key);
690
+ rows.push(item);
691
+ }
692
+ });
693
+ } else {
694
+ rowData.map((item, key) => {
695
+ let isDisabled = rowSelectConfig?.isDisabled?.(item) || false;
696
+ let isDefaultChecked = rowSelectConfig?.isChecked?.(item) || false;
697
+ if (isDisabled && isDefaultChecked) {
698
+ nextIndex.push(key);
699
+ rows.push(item);
700
+ }
701
+ });
702
+ }
703
+ api.onRowSelectionChange(rows, nextIndex);
704
+ setIsAllChecked(isChecked);
705
+ };
706
+ return /* @__PURE__ */ jsxs6(Fragment2, { children: [
707
+ /* @__PURE__ */ jsxs6("colgroup", { children: [
708
+ rowSelectConfig && /* @__PURE__ */ jsx7("col", { width: 50 }, "all_checkbox"),
709
+ colConfigs.map((col) => !col.isHidden && /* @__PURE__ */ jsx7("col", { width: col.width }, col.dataIndex))
710
+ ] }),
711
+ /* @__PURE__ */ jsx7("thead", { ref: props.ref, children: /* @__PURE__ */ jsxs6("tr", { children: [
712
+ rowSelectConfig && /* @__PURE__ */ jsx7("th", { children: /* @__PURE__ */ jsxs6("div", { className: "header-cell-wrapper ", children: [
713
+ rowSelectConfig.selectionMode == "multiple" && /* @__PURE__ */ jsx7(Fragment2, { children: /* @__PURE__ */ jsx7(CheckBox_default, { id: "all", checked: isAllChecked, onChange: (e) => handleAllSelection(e.target.checked) }) }),
714
+ /* @__PURE__ */ jsx7("div", { className: `ms-table-column-resizer ${rowSelectConfig?.isResizable ? "" : "disabled"}` })
715
+ ] }) }, "all_checkbox"),
716
+ colConfigs.map((col) => {
717
+ if (!col.isHidden) {
718
+ return /* @__PURE__ */ jsx7(HeaderCell_default, { ...col }, col.dataIndex);
719
+ }
720
+ })
721
+ ] }) })
411
722
  ] });
412
723
  };
413
724
  var msTableHeader_default = msTableHeader;
414
725
 
415
726
  // src/components/Body/DataRowCell.tsx
416
- import { jsx as jsx7 } from "react/jsx-runtime";
417
- var DataRowCell = ({ dataIndex, value, cellRenderer, width, pinned }) => {
418
- return /* @__PURE__ */ jsx7("td", { style: dataIndex !== "name" ? { width: width || "80" } : { width: "80" }, className: `${pinned ? pinned + "-pinned" : ""}`, children: cellRenderer ? cellRenderer(value) : value });
727
+ import { jsx as jsx8 } from "react/jsx-runtime";
728
+ var DataRowCell = ({ rowData, dataIndex, value, cellRenderer, width, pinned, ...rest }) => {
729
+ const renderData = () => {
730
+ switch (rest.type) {
731
+ case "string":
732
+ return value;
733
+ case "boolean":
734
+ return rest?.displayAs ? value ? rest.displayAs.true : rest.displayAs.false : JSON.stringify(value);
735
+ case "object":
736
+ return JSON.stringify(value);
737
+ default:
738
+ return value;
739
+ }
740
+ };
741
+ return /* @__PURE__ */ jsx8("td", { style: { width }, className: `${pinned ? pinned + "-pinned" : ""}`, children: cellRenderer ? cellRenderer(rowData, dataIndex) : renderData() });
419
742
  };
420
743
  var DataRowCell_default = DataRowCell;
421
744
 
422
745
  // src/components/Body/msTableBody.tsx
423
- import { jsx as jsx8 } from "react/jsx-runtime";
746
+ import { jsx as jsx9, jsxs as jsxs7 } from "react/jsx-runtime";
424
747
  var msTableBody = (props) => {
425
- const { state, api } = useTable();
426
- return /* @__PURE__ */ jsx8("tbody", { ref: props.ref, children: state.rowData?.map((row, rowIndex) => /* @__PURE__ */ jsx8("tr", { onClick: () => api.onRowSelect(row), children: state.colConfigs?.map((col, colIndex) => !col.isHidden && /* @__PURE__ */ jsx8(DataRowCell_default, { dataIndex: col.dataIndex, value: row[col.dataIndex], width: col.width, cellRenderer: col.cellRenderer, pinned: col.pinned })) }, rowIndex)) });
748
+ const { state: { rowData, rowSelectConfig, colConfigs, selectedIndex, ...rest }, api } = useTable();
749
+ const onCheckboxSelectionChange = (currentSelectedRow, index, isChecked) => {
750
+ let prevIndexes = [...selectedIndex];
751
+ let rows = [];
752
+ if (rowSelectConfig?.selectionMode == "multiple") {
753
+ if (isChecked) {
754
+ prevIndexes = [...prevIndexes, index];
755
+ rows = [...rest.selectedRows, currentSelectedRow];
756
+ } else {
757
+ prevIndexes = selectedIndex.filter((key) => index != key);
758
+ rows = rowData.filter((row, key) => prevIndexes.includes(key));
759
+ }
760
+ } else {
761
+ if (isChecked) {
762
+ prevIndexes = [index];
763
+ rows = [currentSelectedRow];
764
+ } else {
765
+ prevIndexes = [];
766
+ }
767
+ }
768
+ api.onRowSelectionChange(rows, prevIndexes);
769
+ };
770
+ return /* @__PURE__ */ jsx9("tbody", { ref: props.ref, children: rowData?.map((row, rowIndex) => /* @__PURE__ */ jsxs7("tr", { children: [
771
+ rowSelectConfig && rowSelectConfig.selectionMode && /* @__PURE__ */ jsx9("td", { style: { width: "50px" }, children: /* @__PURE__ */ jsx9("div", { className: "text-center d-flex", children: /* @__PURE__ */ jsx9(CheckBox_default, { id: `checkbox_${rowIndex}`, checked: selectedIndex.includes(rowIndex), onChange: (e) => onCheckboxSelectionChange(row, rowIndex, e.target.checked), disabled: rowSelectConfig.isDisabled?.(row) }) }) }),
772
+ colConfigs?.map((col, colIndex) => !col.isHidden && /* @__PURE__ */ jsx9(DataRowCell_default, { type: col.type, dataIndex: col.dataIndex, rowData: row, value: row[col.dataIndex], width: col.width, cellRenderer: col.cellRenderer, pinned: col.pinned, displayAs: col.displayAs }, colIndex + "_col_" + rowIndex))
773
+ ] }, rowIndex + "_row")) });
427
774
  };
428
775
  var msTableBody_default = msTableBody;
429
776
 
777
+ // src/components/FormElements/Button.tsx
778
+ import { jsx as jsx10 } from "react/jsx-runtime";
779
+ var Button = (props) => {
780
+ const { className, label, ...rest } = props;
781
+ return /* @__PURE__ */ jsx10("button", { className: `ms-table-btn ${className}`, ...rest, children: label });
782
+ };
783
+ var Button_default = Button;
784
+
430
785
  // src/components/Footer/msTableFooter.tsx
431
- import { jsx as jsx9, jsxs as jsxs6 } from "react/jsx-runtime";
432
- var MsTableFooter = () => {
786
+ import { jsx as jsx11, jsxs as jsxs8 } from "react/jsx-runtime";
787
+ var MsTableFooter = (props) => {
433
788
  const { state, api } = useTable();
434
- const { pageSizeOptions, currentPage, pageSize, totalRecords } = state;
789
+ const { pageSizeOptions, currentPage, pageSize, totalRecords, filters, hideDefaultFilterButton, customComponentForFooter } = state;
790
+ let filterCount = Object.keys(filters).length;
435
791
  const lastPageNo = Math.ceil(totalRecords / pageSize);
436
- return /* @__PURE__ */ jsxs6("div", { className: "table-footer", children: [
437
- /* @__PURE__ */ jsx9("div", { className: "extra-actions" }),
438
- /* @__PURE__ */ jsxs6("div", { className: "pagination-controls", children: [
439
- /* @__PURE__ */ jsx9("div", { className: "pagination-info", children: /* @__PURE__ */ jsxs6("div", { className: "page-size", children: [
440
- /* @__PURE__ */ jsx9("label", { children: "Rows Per Page:" }),
441
- /* @__PURE__ */ jsx9("select", { onChange: (e) => api.onPageSizeChange(parseInt(e.target.value)), value: pageSize, children: state.pageSizeOptions.map((size) => /* @__PURE__ */ jsx9("option", { value: size, children: size }, size)) })
792
+ return /* @__PURE__ */ jsxs8("div", { className: "table-footer", children: [
793
+ /* @__PURE__ */ jsxs8("div", { className: "extra-actions", children: [
794
+ hideDefaultFilterButton == false && /* @__PURE__ */ jsx11(Button_default, { label: `Filters ${filterCount > 0 ? `(${filterCount})` : ""}`, className: "", onClick: () => props.toggleFilterModal(true) }),
795
+ customComponentForFooter
796
+ ] }),
797
+ /* @__PURE__ */ jsxs8("div", { className: "pagination-controls", children: [
798
+ /* @__PURE__ */ jsx11("div", { className: "pagination-info", children: /* @__PURE__ */ jsxs8("div", { className: "page-size", children: [
799
+ /* @__PURE__ */ jsx11("label", { children: "Rows Per Page:" }),
800
+ /* @__PURE__ */ jsx11("select", { onChange: (e) => api.onPageSizeChange(parseInt(e.target.value)), value: pageSize, children: state.pageSizeOptions.map((size) => /* @__PURE__ */ jsx11("option", { value: size, children: size }, size)) })
442
801
  ] }) }),
443
- /* @__PURE__ */ jsx9("div", { className: "record-info", children: /* @__PURE__ */ jsx9("label", { children: `${(currentPage - 1) * pageSize + 1} to ${Math.min(currentPage * pageSize, totalRecords)} of ${totalRecords}` }) }),
444
- /* @__PURE__ */ jsxs6("div", { className: "pagination-buttons", children: [
445
- /* @__PURE__ */ jsx9("span", { className: `${currentPage == 1 ? "cursor-disabled" : ""}`, title: "Go to First Page", onClick: () => api.onPageChange("first"), children: angleLeftIcon }),
446
- /* @__PURE__ */ jsx9("span", { className: `${currentPage == 1 ? "cursor-disabled" : ""}`, title: "Previous Page", onClick: () => api.onPageChange("prev"), children: prevIcon }),
447
- /* @__PURE__ */ jsxs6("span", { className: "current-page", children: [
802
+ /* @__PURE__ */ jsx11("div", { className: "record-info", children: /* @__PURE__ */ jsx11("label", { children: `${(currentPage - 1) * pageSize + 1} to ${Math.min(currentPage * pageSize, totalRecords)} of ${totalRecords}` }) }),
803
+ /* @__PURE__ */ jsxs8("div", { className: "pagination-buttons", children: [
804
+ /* @__PURE__ */ jsx11("span", { className: `${currentPage == 1 ? "cursor-disabled" : ""}`, title: "Go to First Page", onClick: () => api.onPageChange("first"), children: angleLeftIcon }),
805
+ /* @__PURE__ */ jsx11("span", { className: `${currentPage == 1 ? "cursor-disabled" : ""}`, title: "Previous Page", onClick: () => api.onPageChange("prev"), children: prevIcon }),
806
+ /* @__PURE__ */ jsxs8("span", { className: "current-page", children: [
448
807
  currentPage,
449
808
  " of ",
450
809
  Math.ceil(totalRecords / pageSize)
451
810
  ] }),
452
- /* @__PURE__ */ jsx9("span", { className: `${currentPage == lastPageNo ? "cursor-disabled" : ""}`, title: "Next Page", onClick: () => api.onPageChange("next"), children: nextIcon }),
453
- /* @__PURE__ */ jsx9("span", { className: `${currentPage == lastPageNo ? "cursor-disabled" : ""}`, title: "Go to Last Page", onClick: () => api.onPageChange("last"), children: angleRightIcon })
811
+ /* @__PURE__ */ jsx11("span", { className: `${currentPage == lastPageNo ? "cursor-disabled" : ""}`, title: "Next Page", onClick: () => api.onPageChange("next"), children: nextIcon }),
812
+ /* @__PURE__ */ jsx11("span", { className: `${currentPage == lastPageNo ? "cursor-disabled" : ""}`, title: "Go to Last Page", onClick: () => api.onPageChange("last"), children: angleRightIcon })
454
813
  ] })
455
814
  ] })
456
815
  ] });
457
816
  };
458
817
  var msTableFooter_default = MsTableFooter;
459
818
 
819
+ // src/components/Filter/FilterModal.tsx
820
+ import { memo as memo4, useCallback as useCallback3, useEffect as useEffect9, useRef as useRef3, useState as useState10 } from "react";
821
+
822
+ // src/components/Filter/String/TextFilter.tsx
823
+ import { memo as memo3, useEffect as useEffect5, useState as useState6 } from "react";
824
+
825
+ // src/components/FormElements/Input.tsx
826
+ import { Fragment as Fragment3, jsx as jsx12 } from "react/jsx-runtime";
827
+ var Input = (props) => {
828
+ return /* @__PURE__ */ jsx12(Fragment3, { children: /* @__PURE__ */ jsx12("input", { ...props }) });
829
+ };
830
+ var Input_default = Input;
831
+
832
+ // src/components/FormElements/Select.tsx
833
+ import { Fragment as Fragment4, jsx as jsx13 } from "react/jsx-runtime";
834
+ var Select = (props) => {
835
+ return /* @__PURE__ */ jsx13(Fragment4, { children: /* @__PURE__ */ jsx13("select", { onChange: props.onChange, value: props.value, children: props.option.map((item) => /* @__PURE__ */ jsx13("option", { value: item.value, children: item.label }, props.name + "_" + item.value)) }) });
836
+ };
837
+ var Select_default = Select;
838
+
839
+ // src/components/Filter/String/TextFilter.tsx
840
+ import { jsx as jsx14, jsxs as jsxs9 } from "react/jsx-runtime";
841
+ var TextFilter = (colConfig) => {
842
+ const { title, dataIndex, onChange, filterOps, type } = colConfig;
843
+ const [selectedOps, setSelectedOps] = useState6("include");
844
+ const [value, setValue] = useState6("");
845
+ const options = [
846
+ {
847
+ label: "Contains",
848
+ value: "include"
849
+ },
850
+ {
851
+ label: "Equal to",
852
+ value: "="
853
+ },
854
+ {
855
+ label: "Not Equal to",
856
+ value: "!="
857
+ },
858
+ {
859
+ label: "Does not contain",
860
+ value: "not include"
861
+ }
862
+ ];
863
+ useEffect5(() => {
864
+ if (filterOps === void 0) {
865
+ setSelectedOps("include");
866
+ setValue("");
867
+ } else {
868
+ setSelectedOps(filterOps.operation);
869
+ setValue(filterOps.value);
870
+ }
871
+ }, [filterOps]);
872
+ useEffect5(() => {
873
+ onChange(dataIndex, { type, operation: selectedOps, value });
874
+ }, [selectedOps, value]);
875
+ return /* @__PURE__ */ jsxs9("div", { className: "ms-form-item", children: [
876
+ /* @__PURE__ */ jsx14("label", { children: title }),
877
+ /* @__PURE__ */ jsxs9("div", { className: "", children: [
878
+ /* @__PURE__ */ jsx14(Select_default, { option: options, onChange: (e) => setSelectedOps(e.target.value), value: selectedOps }),
879
+ /* @__PURE__ */ jsx14(Input_default, { name: dataIndex, onChange: (e) => setValue(e.target.value), value })
880
+ ] })
881
+ ] });
882
+ };
883
+ var TextFilter_default = memo3(TextFilter);
884
+
885
+ // src/components/Filter/Number/NumberFilter.tsx
886
+ import { useEffect as useEffect6, useState as useState7 } from "react";
887
+ import { jsx as jsx15, jsxs as jsxs10 } from "react/jsx-runtime";
888
+ var NumberFilter = (colConfig) => {
889
+ const { title, dataIndex, onChange, filterOps } = colConfig;
890
+ const [selectedOps, setSelectedOps] = useState7(filterOps?.operation || "=");
891
+ const [value, setValue] = useState7(filterOps?.value || "");
892
+ const options = [
893
+ {
894
+ label: "Equal to",
895
+ value: "="
896
+ },
897
+ {
898
+ label: "Not Equal to",
899
+ value: "!="
900
+ },
901
+ {
902
+ label: "Greater than",
903
+ value: ">"
904
+ },
905
+ {
906
+ label: "Less than",
907
+ value: "<"
908
+ }
909
+ ];
910
+ useEffect6(() => {
911
+ if (filterOps === void 0) {
912
+ setSelectedOps("=");
913
+ setValue("");
914
+ } else {
915
+ setSelectedOps(filterOps.operation);
916
+ setValue(filterOps.value);
917
+ }
918
+ }, []);
919
+ useEffect6(() => {
920
+ onChange(dataIndex, { type: "number", operation: selectedOps, value });
921
+ }, [selectedOps, value]);
922
+ const handleKeyPress = (e) => {
923
+ const inputEvent = e.nativeEvent;
924
+ if (!/^\d*$/.test(inputEvent.data ?? "")) {
925
+ e.preventDefault();
926
+ }
927
+ };
928
+ return /* @__PURE__ */ jsxs10("div", { className: "ms-form-item", children: [
929
+ /* @__PURE__ */ jsx15("label", { children: title }),
930
+ /* @__PURE__ */ jsxs10("div", { className: "", children: [
931
+ /* @__PURE__ */ jsx15(Select_default, { option: options, onChange: (e) => setSelectedOps(e.target.value), value: selectedOps }),
932
+ /* @__PURE__ */ jsx15(
933
+ Input_default,
934
+ {
935
+ name: dataIndex,
936
+ onChange: (e) => setValue(e.target.value),
937
+ value,
938
+ onBeforeInput: handleKeyPress
939
+ }
940
+ )
941
+ ] })
942
+ ] });
943
+ };
944
+ var NumberFilter_default = NumberFilter;
945
+
946
+ // src/components/Filter/Date/DateFilter.tsx
947
+ import { useEffect as useEffect7, useState as useState8 } from "react";
948
+ import { Fragment as Fragment5, jsx as jsx16, jsxs as jsxs11 } from "react/jsx-runtime";
949
+ var DateFilter = (colConfig) => {
950
+ const { title, dataIndex, onChange, filterOps, type } = colConfig;
951
+ const [selectedOps, setSelectedOps] = useState8("=");
952
+ const [[fromDate, toDate], setValue] = useState8(["", ""]);
953
+ const options = [
954
+ {
955
+ label: "Equal to",
956
+ value: "="
957
+ },
958
+ {
959
+ label: "No Equal to",
960
+ value: "!="
961
+ },
962
+ {
963
+ label: "After",
964
+ value: ">"
965
+ },
966
+ {
967
+ label: "Before",
968
+ value: "<"
969
+ },
970
+ {
971
+ label: "Range",
972
+ value: "<>"
973
+ }
974
+ ];
975
+ useEffect7(() => {
976
+ if (filterOps === void 0) {
977
+ setSelectedOps("=");
978
+ setValue(["", ""]);
979
+ } else {
980
+ setSelectedOps(filterOps.operation);
981
+ setValue(filterOps.value);
982
+ }
983
+ }, [filterOps]);
984
+ const handleChange = (e) => {
985
+ const value = e.target.value;
986
+ setSelectedOps(value);
987
+ onChange(dataIndex, { type, operation: value, value: [fromDate, toDate] });
988
+ };
989
+ const handleDateSelect = (e) => {
990
+ let { name, value } = e.target;
991
+ if (name == "from") {
992
+ setValue([value, toDate]);
993
+ onChange(dataIndex, { type, operation: selectedOps, value: [value, toDate] });
994
+ } else {
995
+ setValue([fromDate, value]);
996
+ onChange(dataIndex, { type, operation: selectedOps, value: [fromDate, value] });
997
+ }
998
+ };
999
+ return /* @__PURE__ */ jsxs11("div", { className: "ms-form-item", children: [
1000
+ /* @__PURE__ */ jsx16("label", { children: title }),
1001
+ /* @__PURE__ */ jsx16(Select_default, { name: dataIndex, option: options, onChange: handleChange }),
1002
+ /* @__PURE__ */ jsx16(Input_default, { name: "from", type: "date", onChange: handleDateSelect, value: fromDate, max: toDate ? new Date(toDate).toISOString().split("T")[0] : void 0 }),
1003
+ selectedOps == "<>" && /* @__PURE__ */ jsxs11(Fragment5, { children: [
1004
+ /* @__PURE__ */ jsx16("div", { className: "text-center ms-range-icon", children: rangeIcon }),
1005
+ /* @__PURE__ */ jsx16(Input_default, { name: `to`, type: "date", onChange: handleDateSelect, value: toDate, min: fromDate ? new Date(fromDate).toISOString().split("T")[0] : void 0 })
1006
+ ] })
1007
+ ] });
1008
+ };
1009
+ var DateFilter_default = DateFilter;
1010
+
1011
+ // src/components/Filter/Boolean/BooleanFilter.tsx
1012
+ import { useEffect as useEffect8, useState as useState9 } from "react";
1013
+ import { jsx as jsx17, jsxs as jsxs12 } from "react/jsx-runtime";
1014
+ var BooleanFilter = (colConfig) => {
1015
+ const { title, dataIndex, onChange, filterOps, displayAs } = colConfig;
1016
+ const [selectedOps, setSelectedOps] = useState9("=");
1017
+ const [value, setValue] = useState9("");
1018
+ useEffect8(() => {
1019
+ if (filterOps === void 0) {
1020
+ setSelectedOps("=");
1021
+ setValue("");
1022
+ } else {
1023
+ setSelectedOps(filterOps.operation);
1024
+ setValue(filterOps.value);
1025
+ }
1026
+ }, []);
1027
+ useEffect8(() => {
1028
+ if (filterOps?.value)
1029
+ setValue(filterOps?.value);
1030
+ }, [filterOps?.value]);
1031
+ const handleSelection = (e) => {
1032
+ setValue(e.target.value);
1033
+ onChange(dataIndex, { type: "boolean", operation: "=", value: e.target.value });
1034
+ };
1035
+ return /* @__PURE__ */ jsxs12("div", { className: "ms-form-item", children: [
1036
+ /* @__PURE__ */ jsx17("label", { children: title }),
1037
+ /* @__PURE__ */ jsxs12("div", { style: { display: "flex", justifyContent: "space-between" }, children: [
1038
+ /* @__PURE__ */ jsxs12("div", { className: "ms-radio-group", children: [
1039
+ /* @__PURE__ */ jsxs12("div", { className: "ms-radio-item", children: [
1040
+ /* @__PURE__ */ jsx17(Input_default, { name: dataIndex, type: "radio", id: dataIndex + "_true", value: "true", className: "ms-table-radio", onChange: handleSelection, checked: value == "true" }),
1041
+ /* @__PURE__ */ jsxs12("label", { htmlFor: dataIndex + "_true", children: [
1042
+ " ",
1043
+ displayAs ? displayAs.true : "True"
1044
+ ] })
1045
+ ] }),
1046
+ /* @__PURE__ */ jsxs12("div", { className: "ms-radio-item", children: [
1047
+ /* @__PURE__ */ jsx17(Input_default, { name: dataIndex, type: "radio", id: dataIndex + "_false", value: "false", className: "ms-table-radio", onChange: handleSelection, checked: value == "false" }),
1048
+ /* @__PURE__ */ jsxs12("label", { htmlFor: dataIndex + "_false", children: [
1049
+ " ",
1050
+ displayAs ? displayAs.false : "False"
1051
+ ] })
1052
+ ] })
1053
+ ] }),
1054
+ value !== "" && /* @__PURE__ */ jsx17("div", { title: "clear", className: "ms-table-clear-item", onClick: () => {
1055
+ setValue("");
1056
+ onChange(dataIndex, { type: "boolean", operation: "=", value: "" });
1057
+ }, children: closeIcon })
1058
+ ] })
1059
+ ] });
1060
+ };
1061
+ var BooleanFilter_default = BooleanFilter;
1062
+
1063
+ // src/components/Filter/FilterModal.tsx
1064
+ import { Fragment as Fragment6, jsx as jsx18, jsxs as jsxs13 } from "react/jsx-runtime";
1065
+ var FilterModal = (props) => {
1066
+ const filterRef = useRef3(null);
1067
+ const headerRef = useRef3(null);
1068
+ const footerRef = useRef3(null);
1069
+ const [height, setHeight] = useState10(0);
1070
+ const [show, toggleShow] = useState10(false);
1071
+ const { state: { colConfigs, filters }, api: { onFilterApply } } = useTable();
1072
+ const [filterValues, setFilterValues] = useState10({});
1073
+ useEffect9(() => {
1074
+ let ref = props.containerRef;
1075
+ let totalHeight = ref?.current.clientHeight || 200;
1076
+ let headerHeight = headerRef?.current.clientHeight || 35;
1077
+ let footerHeight = footerRef?.current.clientHeight || 35;
1078
+ setHeight(totalHeight + 20 - headerHeight - footerHeight);
1079
+ }, []);
1080
+ useEffect9(() => {
1081
+ function handleClickOutside(event) {
1082
+ if (!props.isVisible)
1083
+ return;
1084
+ if (filterRef && "current" in filterRef && filterRef.current && !filterRef.current.contains(event.target)) {
1085
+ toggleShow(false);
1086
+ setTimeout(() => {
1087
+ props.toggleFilterModal(false);
1088
+ setFilterValues({});
1089
+ }, 300);
1090
+ }
1091
+ }
1092
+ document.addEventListener("mousedown", handleClickOutside);
1093
+ return () => document.removeEventListener("mousedown", handleClickOutside);
1094
+ }, [filterRef, props.toggleFilterModal]);
1095
+ const onChangeFilterItems = useCallback3((dataIndex, value) => {
1096
+ if (value.value == "") {
1097
+ let newFilter = {};
1098
+ for (let key in filterValues) {
1099
+ if (key != dataIndex) {
1100
+ newFilter[key] = filterValues[key];
1101
+ }
1102
+ }
1103
+ setFilterValues(newFilter);
1104
+ return;
1105
+ }
1106
+ setFilterValues((prev) => ({
1107
+ ...prev,
1108
+ [dataIndex]: value
1109
+ }));
1110
+ }, []);
1111
+ useEffect9(() => {
1112
+ if (Object.keys(filters).length > 0) {
1113
+ setFilterValues(filters);
1114
+ }
1115
+ }, [filters]);
1116
+ const renderFieldItem = (colConfig) => {
1117
+ if (colConfig.isHidden || !colConfig.isFilterEnabled) {
1118
+ return /* @__PURE__ */ jsx18(Fragment6, {});
1119
+ }
1120
+ switch (colConfig.type) {
1121
+ case "string":
1122
+ return /* @__PURE__ */ jsx18(TextFilter_default, { ...colConfig, onChange: onChangeFilterItems, filterOps: filterValues[colConfig.dataIndex] }, `text_ ${colConfig.dataIndex}`);
1123
+ case "date":
1124
+ return /* @__PURE__ */ jsx18(DateFilter_default, { ...colConfig, onChange: onChangeFilterItems, filterOps: filterValues[colConfig.dataIndex] }, `date_ ${colConfig.dataIndex}`);
1125
+ case "number":
1126
+ return /* @__PURE__ */ jsx18(NumberFilter_default, { ...colConfig, onChange: onChangeFilterItems, filterOps: filterValues[colConfig.dataIndex] }, `numvber_ ${colConfig.dataIndex}`);
1127
+ case "boolean":
1128
+ return /* @__PURE__ */ jsx18(BooleanFilter_default, { ...colConfig, onChange: onChangeFilterItems, filterOps: filterValues[colConfig.dataIndex] }, `numvber_ ${colConfig.dataIndex}`);
1129
+ default:
1130
+ /* @__PURE__ */ jsx18(Fragment6, {});
1131
+ }
1132
+ };
1133
+ const ClearAllFilterItems = () => {
1134
+ setFilterValues({});
1135
+ onFilterApply({});
1136
+ };
1137
+ const handleApply = () => {
1138
+ onFilterApply(filterValues);
1139
+ };
1140
+ useEffect9(() => {
1141
+ if (props.isVisible) {
1142
+ setTimeout(() => toggleShow(true), 100);
1143
+ }
1144
+ }, [props.isVisible]);
1145
+ const onFilterModal = () => {
1146
+ toggleShow(false);
1147
+ setTimeout(() => {
1148
+ props.toggleFilterModal(false);
1149
+ }, 300);
1150
+ };
1151
+ return /* @__PURE__ */ jsxs13("div", { className: "filter-modal", style: show ? { right: "5px" } : {}, ref: filterRef, children: [
1152
+ /* @__PURE__ */ jsxs13("div", { className: "filter-header", ref: headerRef, children: [
1153
+ "Filter",
1154
+ /* @__PURE__ */ jsx18("div", { className: "close", onClick: onFilterModal, children: closeIcon })
1155
+ ] }),
1156
+ /* @__PURE__ */ jsx18("div", { className: "filter-body", style: { height }, children: colConfigs.map((col) => {
1157
+ return renderFieldItem(col);
1158
+ }) }),
1159
+ /* @__PURE__ */ jsxs13("div", { className: "filter-footer", ref: footerRef, children: [
1160
+ /* @__PURE__ */ jsx18(Button_default, { label: "Apply", className: "", disabled: Object.keys(filterValues).length > 0 ? false : true, onClick: handleApply }),
1161
+ /* @__PURE__ */ jsx18(Button_default, { label: "Clear All", className: "ms-table-btn-default", style: { marginLeft: "5px" }, disabled: Object.keys(filterValues).length > 0 ? false : true, onClick: ClearAllFilterItems })
1162
+ ] })
1163
+ ] });
1164
+ };
1165
+ var FilterModal_default = memo4(FilterModal);
1166
+
1167
+ // src/components/Loader.tsx
1168
+ import { jsx as jsx19, jsxs as jsxs14 } from "react/jsx-runtime";
1169
+ var Loader = () => {
1170
+ return /* @__PURE__ */ jsxs14("div", { className: "ms-loader-wrapper", children: [
1171
+ /* @__PURE__ */ jsx19("div", { className: "ms-loader-overlay" }),
1172
+ /* @__PURE__ */ jsx19("div", { className: "ms-loader" }),
1173
+ /* @__PURE__ */ jsx19("span", { children: "Loading..." })
1174
+ ] });
1175
+ };
1176
+ var Loader_default = Loader;
1177
+
460
1178
  // src/MsReactTable.tsx
461
- import { jsx as jsx10, jsxs as jsxs7 } from "react/jsx-runtime";
1179
+ import { jsx as jsx20, jsxs as jsxs15 } from "react/jsx-runtime";
462
1180
  var MsReactTable = (props) => {
463
- const { showPagination = true } = props;
464
- const containerRef = React5.useRef(null);
465
- const tbodyRef = React5.useRef(null);
466
- const theadRef = React5.useRef(null);
467
- return /* @__PURE__ */ jsxs7(TableProvider, { ...props, tbodyRef, theadRef, children: [
468
- /* @__PURE__ */ jsx10("div", { className: "table-container", ref: containerRef, style: { height: props.height || "200px" }, children: /* @__PURE__ */ jsxs7("table", { ref: props.ref, className: `ms-react-table ${props.className}`, border: 0, cellPadding: 0, cellSpacing: 0, style: { width: "100%", ...props.style }, children: [
469
- /* @__PURE__ */ jsx10(msTableHeader_default, { ref: theadRef }),
470
- /* @__PURE__ */ jsx10(msTableBody_default, { ref: tbodyRef })
1181
+ const { showPagination = true, ref, isLoading } = props;
1182
+ const containerRef = React12.useRef(null);
1183
+ const tbodyRef = React12.useRef(null);
1184
+ const theadRef = React12.useRef(null);
1185
+ const [showModalFilter, toggleModalFilter] = React12.useState(false);
1186
+ return /* @__PURE__ */ jsxs15(TableProvider, { ...props, ref, tContainerRef: containerRef, theadRef, toggleModalFilter, children: [
1187
+ /* @__PURE__ */ jsx20("div", { className: "ms-table-container", ref: containerRef, style: { height: props.height || "200px" }, children: /* @__PURE__ */ jsxs15("table", { className: `ms-react-table ${props.className}`, border: 0, cellPadding: 0, cellSpacing: 0, style: { width: "100%", ...props.style }, children: [
1188
+ /* @__PURE__ */ jsx20(msTableHeader_default, { ref: theadRef }),
1189
+ /* @__PURE__ */ jsx20(msTableBody_default, { ref: tbodyRef })
471
1190
  ] }) }),
472
- showPagination && /* @__PURE__ */ jsx10(msTableFooter_default, {})
1191
+ showPagination && /* @__PURE__ */ jsx20(msTableFooter_default, { toggleFilterModal: toggleModalFilter }),
1192
+ /* @__PURE__ */ jsxs15("div", { children: [
1193
+ showModalFilter && /* @__PURE__ */ jsx20(FilterModal_default, { isVisible: showModalFilter, toggleFilterModal: toggleModalFilter, containerRef }),
1194
+ /* @__PURE__ */ jsx20("div", { className: "ms-overlay", style: showModalFilter ? { width: "100%" } : {} }),
1195
+ isLoading && /* @__PURE__ */ jsx20(Loader_default, {})
1196
+ ] })
473
1197
  ] });
474
1198
  };
475
1199
  MsReactTable.displayName = "MsReactTable";
476
1200
  var MsReactTable_default = MsReactTable;
477
1201
  export {
478
- MsReactTable_default as MsReactTable
1202
+ MsReactTable_default as default
479
1203
  };
480
1204
  //# sourceMappingURL=index.mjs.map