@kreativa/ui 0.1.0 → 0.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.js CHANGED
@@ -22,6 +22,7 @@ var index_exports = {};
22
22
  __export(index_exports, {
23
23
  Button: () => Button,
24
24
  Card: () => Card,
25
+ DataTable: () => DataTable,
25
26
  DatePicker: () => DatePicker,
26
27
  EmptyState: () => EmptyState,
27
28
  FormButtonGroup: () => FormButtonGroup,
@@ -37,6 +38,7 @@ __export(index_exports, {
37
38
  Table: () => Table,
38
39
  Tabs: () => Tabs,
39
40
  Timer: () => Timer,
41
+ createFilterOptions: () => createFilterOptions,
40
42
  formatTime: () => formatTime
41
43
  });
42
44
  module.exports = __toCommonJS(index_exports);
@@ -338,10 +340,15 @@ function Table({
338
340
  onRowClick,
339
341
  loading = false,
340
342
  emptyMessage = "No data available",
341
- className = ""
343
+ className = "",
344
+ resizable = false,
345
+ fixedLayout = false
342
346
  }) {
343
347
  const [sortKey, setSortKey] = (0, import_react5.useState)(null);
344
348
  const [sortDirection, setSortDirection] = (0, import_react5.useState)(null);
349
+ const [columnWidths, setColumnWidths] = (0, import_react5.useState)({});
350
+ const tableRef = (0, import_react5.useRef)(null);
351
+ const resizingRef = (0, import_react5.useRef)(null);
345
352
  const handleHeaderClick = (column) => {
346
353
  if (!column.sortable) return;
347
354
  if (sortKey === column.key) {
@@ -370,65 +377,138 @@ function Table({
370
377
  });
371
378
  return sortDirection === "desc" ? sorted.reverse() : sorted;
372
379
  }, [data, columns, sortKey, sortDirection]);
380
+ const handleResizeStart = (0, import_react5.useCallback)(
381
+ (e, columnKey) => {
382
+ e.preventDefault();
383
+ e.stopPropagation();
384
+ const headerCell = e.currentTarget.parentElement;
385
+ if (!headerCell) return;
386
+ const startWidth = headerCell.getBoundingClientRect().width;
387
+ resizingRef.current = {
388
+ columnKey,
389
+ startX: e.clientX,
390
+ startWidth
391
+ };
392
+ document.addEventListener("mousemove", handleResizeMove);
393
+ document.addEventListener("mouseup", handleResizeEnd);
394
+ document.body.style.cursor = "col-resize";
395
+ document.body.style.userSelect = "none";
396
+ },
397
+ []
398
+ );
399
+ const handleResizeMove = (0, import_react5.useCallback)((e) => {
400
+ if (!resizingRef.current) return;
401
+ const { columnKey, startX, startWidth } = resizingRef.current;
402
+ const column = columns.find((c) => c.key === columnKey);
403
+ const minWidth = column?.minWidth ?? 50;
404
+ const newWidth = Math.max(minWidth, startWidth + (e.clientX - startX));
405
+ setColumnWidths((prev) => ({
406
+ ...prev,
407
+ [columnKey]: newWidth
408
+ }));
409
+ }, [columns]);
410
+ const handleResizeEnd = (0, import_react5.useCallback)(() => {
411
+ resizingRef.current = null;
412
+ document.removeEventListener("mousemove", handleResizeMove);
413
+ document.removeEventListener("mouseup", handleResizeEnd);
414
+ document.body.style.cursor = "";
415
+ document.body.style.userSelect = "";
416
+ }, [handleResizeMove]);
373
417
  const getSortIcon = (column) => {
374
418
  if (!column.sortable) return null;
375
419
  if (sortKey !== column.key) {
376
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("svg", { className: "w-4 h-4 text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M7 16V4m0 0L3 8m4-4l4 4m6 0v12m0 0l4-4m-4 4l-4-4" }) });
420
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("svg", { className: "w-4 h-4 text-gray-400 shrink-0", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M7 16V4m0 0L3 8m4-4l4 4m6 0v12m0 0l4-4m-4 4l-4-4" }) });
377
421
  }
378
422
  if (sortDirection === "asc") {
379
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("svg", { className: "w-4 h-4 text-primary-600", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 15l7-7 7 7" }) });
423
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("svg", { className: "w-4 h-4 text-primary-600 shrink-0", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 15l7-7 7 7" }) });
380
424
  }
381
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("svg", { className: "w-4 h-4 text-primary-600", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M19 9l-7 7-7-7" }) });
425
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("svg", { className: "w-4 h-4 text-primary-600 shrink-0", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M19 9l-7 7-7-7" }) });
382
426
  };
383
427
  const alignmentClasses = {
384
428
  left: "text-left",
385
429
  center: "text-center",
386
430
  right: "text-right"
387
431
  };
388
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: `overflow-x-auto ${className}`, children: /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("table", { className: "w-full border-collapse", children: [
389
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("thead", { children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tr", { className: "bg-gray-50 border-b border-gray-200", children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
390
- "th",
391
- {
392
- className: `
393
- px-4 py-3 text-sm font-semibold text-gray-700
432
+ const getColumnStyle = (column) => {
433
+ if (columnWidths[column.key]) {
434
+ return { width: columnWidths[column.key], minWidth: columnWidths[column.key] };
435
+ }
436
+ if (column.width) {
437
+ return { width: column.width, minWidth: column.minWidth ?? 50 };
438
+ }
439
+ return { minWidth: column.minWidth ?? 50 };
440
+ };
441
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: `overflow-x-auto ${className}`, children: /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
442
+ "table",
443
+ {
444
+ ref: tableRef,
445
+ className: "w-full border-collapse",
446
+ style: { tableLayout: fixedLayout || resizable ? "fixed" : "auto" },
447
+ children: [
448
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("thead", { children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tr", { className: "bg-gray-50 border-b border-gray-200", children: columns.map((column, index) => /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
449
+ "th",
450
+ {
451
+ className: `
452
+ px-4 py-3 text-sm font-semibold text-gray-700 relative
394
453
  ${alignmentClasses[column.align ?? "left"]}
395
454
  ${column.sortable ? "cursor-pointer select-none hover:bg-gray-100" : ""}
396
455
  `,
397
- style: { width: column.width },
398
- onClick: () => handleHeaderClick(column),
399
- children: /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("div", { className: `flex items-center gap-1 ${column.align === "right" ? "justify-end" : column.align === "center" ? "justify-center" : ""}`, children: [
400
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { children: column.header }),
401
- getSortIcon(column)
402
- ] })
403
- },
404
- column.key
405
- )) }) }),
406
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tbody", { children: loading ? /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tr", { children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("td", { colSpan: columns.length, className: "px-4 py-8 text-center text-gray-500", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("div", { className: "flex items-center justify-center gap-2", children: [
407
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: "w-5 h-5 border-2 border-primary-200 border-t-primary-600 rounded-full animate-spin" }),
408
- /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { children: "Loading..." })
409
- ] }) }) }) : sortedData.length === 0 ? /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tr", { children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("td", { colSpan: columns.length, className: "px-4 py-8 text-center text-gray-500", children: emptyMessage }) }) : sortedData.map((item) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
410
- "tr",
411
- {
412
- className: `
456
+ style: getColumnStyle(column),
457
+ onClick: () => handleHeaderClick(column),
458
+ children: [
459
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
460
+ "div",
461
+ {
462
+ className: `flex items-center gap-1 overflow-hidden ${column.align === "right" ? "justify-end" : column.align === "center" ? "justify-center" : ""}`,
463
+ children: [
464
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { className: "truncate", children: column.header }),
465
+ getSortIcon(column)
466
+ ]
467
+ }
468
+ ),
469
+ resizable && index < columns.length - 1 && /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
470
+ "div",
471
+ {
472
+ className: "absolute top-0 right-0 w-1 h-full cursor-col-resize bg-transparent hover:bg-primary-300 transition-colors",
473
+ onMouseDown: (e) => handleResizeStart(e, column.key),
474
+ onClick: (e) => e.stopPropagation()
475
+ }
476
+ )
477
+ ]
478
+ },
479
+ column.key
480
+ )) }) }),
481
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tbody", { children: loading ? /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tr", { children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("td", { colSpan: columns.length, className: "px-4 py-8 text-center text-gray-500", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("div", { className: "flex items-center justify-center gap-2", children: [
482
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: "w-5 h-5 border-2 border-primary-200 border-t-primary-600 rounded-full animate-spin" }),
483
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { children: "Loading..." })
484
+ ] }) }) }) : sortedData.length === 0 ? /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("tr", { children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("td", { colSpan: columns.length, className: "px-4 py-8 text-center text-gray-500", children: emptyMessage }) }) : sortedData.map((item) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
485
+ "tr",
486
+ {
487
+ className: `
413
488
  border-b border-gray-100 hover:bg-gray-50 transition-colors
414
489
  ${onRowClick ? "cursor-pointer" : ""}
415
490
  `,
416
- onClick: () => onRowClick?.(item),
417
- children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
418
- "td",
419
- {
420
- className: `px-4 py-3 text-sm text-gray-800 ${alignmentClasses[column.align ?? "left"]}`,
421
- style: { width: column.width },
422
- children: column.render(item)
491
+ onClick: () => onRowClick?.(item),
492
+ children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
493
+ "td",
494
+ {
495
+ className: `px-4 py-3 text-sm text-gray-800 overflow-hidden ${alignmentClasses[column.align ?? "left"]}`,
496
+ style: getColumnStyle(column),
497
+ children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: "truncate", children: column.render(item) })
498
+ },
499
+ column.key
500
+ ))
423
501
  },
424
- column.key
425
- ))
426
- },
427
- getRowKey(item)
428
- )) })
429
- ] }) });
502
+ getRowKey(item)
503
+ )) })
504
+ ]
505
+ }
506
+ ) });
430
507
  }
431
508
 
509
+ // src/components/DataTable.tsx
510
+ var import_react7 = require("react");
511
+
432
512
  // src/components/Select.tsx
433
513
  var import_react6 = require("react");
434
514
  var import_jsx_runtime14 = require("react/jsx-runtime");
@@ -612,9 +692,245 @@ function Select({
612
692
  ] });
613
693
  }
614
694
 
615
- // src/components/Tabs.tsx
616
- var import_react7 = require("react");
695
+ // src/components/DataTable.tsx
617
696
  var import_jsx_runtime15 = require("react/jsx-runtime");
697
+ function ColumnFilter({ column, value, onChange }) {
698
+ const filterType = column.filterType ?? "text";
699
+ if (filterType === "none") {
700
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("div", { className: "h-9" });
701
+ }
702
+ if (filterType === "select" && column.filterOptions) {
703
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
704
+ Select,
705
+ {
706
+ options: [{ value: "", label: "Alla" }, ...column.filterOptions],
707
+ value: value || "",
708
+ onChange: (val) => onChange(val),
709
+ placeholder: column.filterPlaceholder || "Alla",
710
+ className: "w-full text-sm"
711
+ }
712
+ );
713
+ }
714
+ if (filterType === "multiselect" && column.filterOptions) {
715
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
716
+ Select,
717
+ {
718
+ options: column.filterOptions,
719
+ value: value || [],
720
+ onChange: (val) => onChange(val),
721
+ placeholder: column.filterPlaceholder || "Alla",
722
+ multiple: true,
723
+ className: "w-full text-sm"
724
+ }
725
+ );
726
+ }
727
+ if (filterType === "boolean") {
728
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
729
+ Select,
730
+ {
731
+ options: [
732
+ { value: "", label: "Alla" },
733
+ { value: "true", label: "Ja" },
734
+ { value: "false", label: "Nej" }
735
+ ],
736
+ value: value || "",
737
+ onChange: (val) => onChange(val),
738
+ className: "w-full text-sm"
739
+ }
740
+ );
741
+ }
742
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
743
+ Input,
744
+ {
745
+ type: "text",
746
+ value: value || "",
747
+ onChange: (e) => onChange(e.target.value),
748
+ placeholder: column.filterPlaceholder || `Filtrera ${column.header.toLowerCase()}...`,
749
+ className: "w-full text-sm h-9"
750
+ }
751
+ );
752
+ }
753
+ function DataTable({
754
+ data,
755
+ columns,
756
+ getRowKey,
757
+ onRowClick,
758
+ loading,
759
+ emptyMessage = "Ingen data att visa.",
760
+ className,
761
+ showFilters = true,
762
+ initialSortKey,
763
+ initialSortDirection = "asc",
764
+ onFilteredDataChange
765
+ }) {
766
+ const [filters, setFilters] = (0, import_react7.useState)({});
767
+ const [sortKey, setSortKey] = (0, import_react7.useState)(initialSortKey || null);
768
+ const [sortDirection, setSortDirection] = (0, import_react7.useState)(initialSortDirection);
769
+ const handleFilterChange = (0, import_react7.useCallback)((columnKey, value) => {
770
+ setFilters((prev) => {
771
+ const next = { ...prev };
772
+ if (value === "" || Array.isArray(value) && value.length === 0) {
773
+ delete next[columnKey];
774
+ } else {
775
+ next[columnKey] = value;
776
+ }
777
+ return next;
778
+ });
779
+ }, []);
780
+ const clearFilters = (0, import_react7.useCallback)(() => {
781
+ setFilters({});
782
+ }, []);
783
+ const filteredData = (0, import_react7.useMemo)(() => {
784
+ let result = [...data];
785
+ for (const [columnKey, filterValue] of Object.entries(filters)) {
786
+ if (!filterValue || Array.isArray(filterValue) && filterValue.length === 0) continue;
787
+ const column = columns.find((c) => c.key === columnKey);
788
+ if (!column) continue;
789
+ const getFilterableValue = column.filterValue || ((item) => {
790
+ return item[columnKey];
791
+ });
792
+ result = result.filter((item) => {
793
+ const itemValue = getFilterableValue(item);
794
+ if (itemValue === null || itemValue === void 0) {
795
+ return filterValue === "";
796
+ }
797
+ const filterType = column.filterType ?? "text";
798
+ if (filterType === "boolean") {
799
+ const boolFilterValue = filterValue === "true";
800
+ return itemValue === boolFilterValue;
801
+ }
802
+ if (filterType === "multiselect" && Array.isArray(filterValue)) {
803
+ return filterValue.includes(String(itemValue));
804
+ }
805
+ if (filterType === "select") {
806
+ return String(itemValue).toLowerCase() === String(filterValue).toLowerCase();
807
+ }
808
+ return String(itemValue).toLowerCase().includes(String(filterValue).toLowerCase());
809
+ });
810
+ }
811
+ return result;
812
+ }, [data, filters, columns]);
813
+ const sortedData = (0, import_react7.useMemo)(() => {
814
+ if (!sortKey) return filteredData;
815
+ const column = columns.find((c) => c.key === sortKey);
816
+ if (!column) return filteredData;
817
+ const sorted = [...filteredData].sort((a, b) => {
818
+ if (column.sortFn) {
819
+ return column.sortFn(a, b);
820
+ }
821
+ const getValueForSort = column.filterValue || ((item) => {
822
+ return item[sortKey];
823
+ });
824
+ const aVal = getValueForSort(a);
825
+ const bVal = getValueForSort(b);
826
+ if (aVal === null || aVal === void 0) return 1;
827
+ if (bVal === null || bVal === void 0) return -1;
828
+ if (typeof aVal === "string" && typeof bVal === "string") {
829
+ return aVal.localeCompare(bVal, "sv");
830
+ }
831
+ if (aVal < bVal) return -1;
832
+ if (aVal > bVal) return 1;
833
+ return 0;
834
+ });
835
+ return sortDirection === "desc" ? sorted.reverse() : sorted;
836
+ }, [filteredData, sortKey, sortDirection, columns]);
837
+ (0, import_react7.useMemo)(() => {
838
+ onFilteredDataChange?.(sortedData);
839
+ }, [sortedData, onFilteredDataChange]);
840
+ const handleSort = (0, import_react7.useCallback)((columnKey) => {
841
+ if (sortKey === columnKey) {
842
+ setSortDirection((prev) => prev === "asc" ? "desc" : "asc");
843
+ } else {
844
+ setSortKey(columnKey);
845
+ setSortDirection("asc");
846
+ }
847
+ }, [sortKey]);
848
+ const tableColumns = (0, import_react7.useMemo)(() => {
849
+ return columns.map((column) => {
850
+ const isSortable = column.sortable !== false && column.filterType !== "none";
851
+ const isCurrentSort = sortKey === column.key;
852
+ return {
853
+ key: column.key,
854
+ header: isSortable ? /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)(
855
+ "button",
856
+ {
857
+ onClick: () => handleSort(column.key),
858
+ className: "flex items-center gap-1 hover:text-gray-900 transition-colors w-full text-left",
859
+ children: [
860
+ column.header,
861
+ isCurrentSort ? /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "text-primary-600", children: sortDirection === "asc" ? "\u2191" : "\u2193" }) : /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { className: "text-gray-400 opacity-50", children: "\u2195" })
862
+ ]
863
+ }
864
+ ) : column.header,
865
+ render: column.render,
866
+ width: column.width,
867
+ align: column.align,
868
+ sortable: false
869
+ // We handle sorting ourselves
870
+ };
871
+ });
872
+ }, [columns, sortKey, sortDirection, handleSort]);
873
+ const hasActiveFilters = Object.keys(filters).length > 0;
874
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className, children: [
875
+ showFilters && /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className: "mb-4", children: [
876
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className: "flex flex-wrap items-center gap-2 mb-2", children: [
877
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("span", { className: "text-sm text-gray-500", children: [
878
+ "Visar ",
879
+ sortedData.length,
880
+ " av ",
881
+ data.length
882
+ ] }),
883
+ hasActiveFilters && /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
884
+ "button",
885
+ {
886
+ onClick: clearFilters,
887
+ className: "text-sm text-primary-600 hover:underline",
888
+ children: "Rensa filter"
889
+ }
890
+ )
891
+ ] }),
892
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("div", { className: "grid grid-cols-1 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-4 xl:grid-cols-6 gap-3 p-3 bg-gray-50 border border-gray-200 rounded-lg", children: columns.filter((col) => col.filterType !== "none").map((column) => /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className: "min-w-0", children: [
893
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("label", { className: "text-xs text-gray-500 mb-1 block truncate", children: column.header }),
894
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
895
+ ColumnFilter,
896
+ {
897
+ column,
898
+ value: filters[column.key] || "",
899
+ onChange: (value) => handleFilterChange(column.key, value)
900
+ }
901
+ )
902
+ ] }, column.key)) })
903
+ ] }),
904
+ /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
905
+ Table,
906
+ {
907
+ data: sortedData,
908
+ columns: tableColumns,
909
+ getRowKey,
910
+ onRowClick,
911
+ loading,
912
+ emptyMessage
913
+ }
914
+ )
915
+ ] });
916
+ }
917
+ function createFilterOptions(data, getValue, labelMap) {
918
+ const uniqueValues = /* @__PURE__ */ new Set();
919
+ for (const item of data) {
920
+ const value = getValue(item);
921
+ if (value !== null && value !== void 0 && value !== "") {
922
+ uniqueValues.add(value);
923
+ }
924
+ }
925
+ return Array.from(uniqueValues).sort((a, b) => a.localeCompare(b, "sv")).map((value) => ({
926
+ value,
927
+ label: labelMap?.[value] || value
928
+ }));
929
+ }
930
+
931
+ // src/components/Tabs.tsx
932
+ var import_react8 = require("react");
933
+ var import_jsx_runtime16 = require("react/jsx-runtime");
618
934
  function Tabs({
619
935
  tabs,
620
936
  activeTab: controlledActiveTab,
@@ -625,7 +941,7 @@ function Tabs({
625
941
  className = ""
626
942
  }) {
627
943
  const isControlled = controlledActiveTab !== void 0;
628
- const [internalActiveTab, setInternalActiveTab] = (0, import_react7.useState)(
944
+ const [internalActiveTab, setInternalActiveTab] = (0, import_react8.useState)(
629
945
  defaultTab || tabs.find((t) => !t.disabled)?.id || tabs[0]?.id
630
946
  );
631
947
  const activeTab = isControlled ? controlledActiveTab : internalActiveTab;
@@ -693,11 +1009,11 @@ function Tabs({
693
1009
  }
694
1010
  };
695
1011
  const styles = variantStyles[variant];
696
- return /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("div", { className, children: [
697
- /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("div", { className: `flex ${styles.container}`, role: "tablist", children: tabs.map((tab, index) => {
1012
+ return /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { className, children: [
1013
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: `flex ${styles.container}`, role: "tablist", children: tabs.map((tab, index) => {
698
1014
  const isActive = tab.id === activeTab;
699
1015
  const isDisabled = tab.disabled ?? false;
700
- return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
1016
+ return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
701
1017
  "button",
702
1018
  {
703
1019
  type: "button",
@@ -709,7 +1025,7 @@ function Tabs({
709
1025
  className: styles.tab(isActive, isDisabled),
710
1026
  onClick: () => handleTabClick(tab),
711
1027
  onKeyDown: (e) => handleKeyDown(e, index),
712
- children: /* @__PURE__ */ (0, import_jsx_runtime15.jsxs)("span", { className: "flex items-center gap-2", children: [
1028
+ children: /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("span", { className: "flex items-center gap-2", children: [
713
1029
  tab.icon,
714
1030
  tab.label
715
1031
  ] })
@@ -717,13 +1033,13 @@ function Tabs({
717
1033
  tab.id
718
1034
  );
719
1035
  }) }),
720
- renderContent && activeContent && /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("div", { className: "pt-4", role: "tabpanel", children: activeContent })
1036
+ renderContent && activeContent && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "pt-4", role: "tabpanel", children: activeContent })
721
1037
  ] });
722
1038
  }
723
1039
 
724
1040
  // src/components/DatePicker.tsx
725
- var import_react8 = require("react");
726
- var import_jsx_runtime16 = require("react/jsx-runtime");
1041
+ var import_react9 = require("react");
1042
+ var import_jsx_runtime17 = require("react/jsx-runtime");
727
1043
  var WEEKDAYS = ["Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"];
728
1044
  var MONTHS = [
729
1045
  "January",
@@ -826,12 +1142,12 @@ function DatePicker({
826
1142
  disabled = false,
827
1143
  className = ""
828
1144
  }) {
829
- const [isOpen, setIsOpen] = (0, import_react8.useState)(false);
830
- const [viewDate, setViewDate] = (0, import_react8.useState)(/* @__PURE__ */ new Date());
831
- const [hoverDate, setHoverDate] = (0, import_react8.useState)(null);
832
- const containerRef = (0, import_react8.useRef)(null);
833
- const [selectingEnd, setSelectingEnd] = (0, import_react8.useState)(false);
834
- (0, import_react8.useEffect)(() => {
1145
+ const [isOpen, setIsOpen] = (0, import_react9.useState)(false);
1146
+ const [viewDate, setViewDate] = (0, import_react9.useState)(/* @__PURE__ */ new Date());
1147
+ const [hoverDate, setHoverDate] = (0, import_react9.useState)(null);
1148
+ const containerRef = (0, import_react9.useRef)(null);
1149
+ const [selectingEnd, setSelectingEnd] = (0, import_react9.useState)(false);
1150
+ (0, import_react9.useEffect)(() => {
835
1151
  const handleClickOutside = (e) => {
836
1152
  if (containerRef.current && !containerRef.current.contains(e.target)) {
837
1153
  setIsOpen(false);
@@ -841,7 +1157,7 @@ function DatePicker({
841
1157
  document.addEventListener("mousedown", handleClickOutside);
842
1158
  return () => document.removeEventListener("mousedown", handleClickOutside);
843
1159
  }, []);
844
- const displayText = (0, import_react8.useMemo)(() => {
1160
+ const displayText = (0, import_react9.useMemo)(() => {
845
1161
  if (!value) return "";
846
1162
  if (range) {
847
1163
  const rangeValue = value;
@@ -858,7 +1174,7 @@ function DatePicker({
858
1174
  }
859
1175
  return formatDate(value);
860
1176
  }, [value, range]);
861
- const calendarDays = (0, import_react8.useMemo)(() => {
1177
+ const calendarDays = (0, import_react9.useMemo)(() => {
862
1178
  const year = viewDate.getFullYear();
863
1179
  const month = viewDate.getMonth();
864
1180
  const firstDay = new Date(year, month, 1);
@@ -941,9 +1257,9 @@ function DatePicker({
941
1257
  };
942
1258
  const today = /* @__PURE__ */ new Date();
943
1259
  today.setHours(0, 0, 0, 0);
944
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { ref: containerRef, className: `relative ${className}`, children: [
945
- label && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("label", { className: "block text-sm font-medium text-gray-700 mb-2", children: label }),
946
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1260
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { ref: containerRef, className: `relative ${className}`, children: [
1261
+ label && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("label", { className: "block text-sm font-medium text-gray-700 mb-2", children: label }),
1262
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
947
1263
  "div",
948
1264
  {
949
1265
  className: `
@@ -953,15 +1269,15 @@ function DatePicker({
953
1269
  transition-all
954
1270
  `,
955
1271
  onClick: () => !disabled && setIsOpen(!isOpen),
956
- children: /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { className: "flex items-center justify-between", children: [
957
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("span", { className: displayText ? "text-gray-800" : "text-gray-400", children: displayText || placeholder }),
958
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("svg", { className: "w-5 h-5 text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v12a2 2 0 002 2z" }) })
1272
+ children: /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "flex items-center justify-between", children: [
1273
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: displayText ? "text-gray-800" : "text-gray-400", children: displayText || placeholder }),
1274
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: "w-5 h-5 text-gray-400", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v12a2 2 0 002 2z" }) })
959
1275
  ] })
960
1276
  }
961
1277
  ),
962
- error && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("p", { className: "mt-1 text-xs text-red-600", children: error }),
963
- isOpen && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "absolute z-50 mt-1 bg-white border border-gray-200 rounded-xl shadow-lg p-4", children: /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { className: range ? "flex gap-4" : "", children: [
964
- range && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "border-r border-gray-100 pr-4 space-y-1", children: PRESET_RANGES.map((preset) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1278
+ error && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("p", { className: "mt-1 text-xs text-red-600", children: error }),
1279
+ isOpen && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "absolute z-50 mt-1 bg-white border border-gray-200 rounded-xl shadow-lg p-4", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: range ? "flex gap-4" : "", children: [
1280
+ range && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "border-r border-gray-100 pr-4 space-y-1", children: PRESET_RANGES.map((preset) => /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
965
1281
  "button",
966
1282
  {
967
1283
  type: "button",
@@ -971,42 +1287,42 @@ function DatePicker({
971
1287
  },
972
1288
  preset.label
973
1289
  )) }),
974
- /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { children: [
975
- /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { className: "flex items-center justify-between mb-4", children: [
976
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1290
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { children: [
1291
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "flex items-center justify-between mb-4", children: [
1292
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
977
1293
  "button",
978
1294
  {
979
1295
  type: "button",
980
1296
  className: "p-1 hover:bg-gray-100 rounded",
981
1297
  onClick: goToPrevMonth,
982
- children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("svg", { className: "w-5 h-5 text-gray-600", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M15 19l-7-7 7-7" }) })
1298
+ children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: "w-5 h-5 text-gray-600", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M15 19l-7-7 7-7" }) })
983
1299
  }
984
1300
  ),
985
- /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("span", { className: "text-sm font-semibold text-gray-800", children: [
1301
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("span", { className: "text-sm font-semibold text-gray-800", children: [
986
1302
  MONTHS[viewDate.getMonth()],
987
1303
  " ",
988
1304
  viewDate.getFullYear()
989
1305
  ] }),
990
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1306
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
991
1307
  "button",
992
1308
  {
993
1309
  type: "button",
994
1310
  className: "p-1 hover:bg-gray-100 rounded",
995
1311
  onClick: goToNextMonth,
996
- children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("svg", { className: "w-5 h-5 text-gray-600", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 5l7 7-7 7" }) })
1312
+ children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: "w-5 h-5 text-gray-600", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M9 5l7 7-7 7" }) })
997
1313
  }
998
1314
  )
999
1315
  ] }),
1000
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "grid grid-cols-7 gap-1 mb-2", children: WEEKDAYS.map((day) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "text-center text-xs font-medium text-gray-500 py-1", children: day }, day)) }),
1001
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "grid grid-cols-7 gap-1", children: calendarDays.map((date, index) => {
1316
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "grid grid-cols-7 gap-1 mb-2", children: WEEKDAYS.map((day) => /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "text-center text-xs font-medium text-gray-500 py-1", children: day }, day)) }),
1317
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "grid grid-cols-7 gap-1", children: calendarDays.map((date, index) => {
1002
1318
  if (!date) {
1003
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: "w-9 h-9" }, `empty-${index}`);
1319
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: "w-9 h-9" }, `empty-${index}`);
1004
1320
  }
1005
1321
  const isDisabled = isDateDisabled(date);
1006
1322
  const isSelected = isDateSelected(date);
1007
1323
  const inRange = isDateInRange(date);
1008
1324
  const isToday = isSameDay(date, today);
1009
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
1325
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1010
1326
  "button",
1011
1327
  {
1012
1328
  type: "button",
@@ -1032,8 +1348,8 @@ function DatePicker({
1032
1348
  }
1033
1349
 
1034
1350
  // src/components/Timer.tsx
1035
- var import_react9 = require("react");
1036
- var import_jsx_runtime17 = require("react/jsx-runtime");
1351
+ var import_react10 = require("react");
1352
+ var import_jsx_runtime18 = require("react/jsx-runtime");
1037
1353
  function formatTime(totalSeconds) {
1038
1354
  const hours = Math.floor(totalSeconds / 3600);
1039
1355
  const minutes = Math.floor(totalSeconds % 3600 / 60);
@@ -1057,20 +1373,20 @@ function Timer({
1057
1373
  elapsedSeconds: controlledElapsedSeconds
1058
1374
  }) {
1059
1375
  const isControlled = controlledIsRunning !== void 0;
1060
- const [internalIsRunning, setInternalIsRunning] = (0, import_react9.useState)(false);
1061
- const [internalElapsedSeconds, setInternalElapsedSeconds] = (0, import_react9.useState)(initialSeconds);
1376
+ const [internalIsRunning, setInternalIsRunning] = (0, import_react10.useState)(false);
1377
+ const [internalElapsedSeconds, setInternalElapsedSeconds] = (0, import_react10.useState)(initialSeconds);
1062
1378
  const isRunning = isControlled ? controlledIsRunning : internalIsRunning;
1063
1379
  const elapsedSeconds = isControlled ? controlledElapsedSeconds ?? 0 : internalElapsedSeconds;
1064
- const intervalRef = (0, import_react9.useRef)(null);
1065
- const startTimeRef = (0, import_react9.useRef)(null);
1066
- (0, import_react9.useEffect)(() => {
1380
+ const intervalRef = (0, import_react10.useRef)(null);
1381
+ const startTimeRef = (0, import_react10.useRef)(null);
1382
+ (0, import_react10.useEffect)(() => {
1067
1383
  return () => {
1068
1384
  if (intervalRef.current) {
1069
1385
  clearInterval(intervalRef.current);
1070
1386
  }
1071
1387
  };
1072
1388
  }, []);
1073
- (0, import_react9.useEffect)(() => {
1389
+ (0, import_react10.useEffect)(() => {
1074
1390
  if (isControlled) return;
1075
1391
  if (isRunning) {
1076
1392
  intervalRef.current = setInterval(() => {
@@ -1093,7 +1409,7 @@ function Timer({
1093
1409
  }
1094
1410
  };
1095
1411
  }, [isRunning, isControlled, onTick]);
1096
- const handleStart = (0, import_react9.useCallback)(() => {
1412
+ const handleStart = (0, import_react10.useCallback)(() => {
1097
1413
  const now = /* @__PURE__ */ new Date();
1098
1414
  startTimeRef.current = now;
1099
1415
  if (!isControlled) {
@@ -1101,13 +1417,13 @@ function Timer({
1101
1417
  }
1102
1418
  onStart?.(now);
1103
1419
  }, [isControlled, onStart]);
1104
- const handleStop = (0, import_react9.useCallback)(() => {
1420
+ const handleStop = (0, import_react10.useCallback)(() => {
1105
1421
  if (!isControlled) {
1106
1422
  setInternalIsRunning(false);
1107
1423
  }
1108
1424
  onStop?.(elapsedSeconds);
1109
1425
  }, [isControlled, elapsedSeconds, onStop]);
1110
- const handleReset = (0, import_react9.useCallback)(() => {
1426
+ const handleReset = (0, import_react10.useCallback)(() => {
1111
1427
  if (!isControlled) {
1112
1428
  setInternalIsRunning(false);
1113
1429
  setInternalElapsedSeconds(0);
@@ -1115,7 +1431,7 @@ function Timer({
1115
1431
  startTimeRef.current = null;
1116
1432
  onReset?.();
1117
1433
  }, [isControlled, onReset]);
1118
- const handleToggle = (0, import_react9.useCallback)(() => {
1434
+ const handleToggle = (0, import_react10.useCallback)(() => {
1119
1435
  if (isRunning) {
1120
1436
  handleStop();
1121
1437
  } else {
@@ -1143,10 +1459,10 @@ function Timer({
1143
1459
  }
1144
1460
  };
1145
1461
  const styles = sizeClasses3[size];
1146
- return /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: `flex items-center ${styles.container} ${className}`, children: [
1147
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: `font-mono font-bold text-gray-800 ${styles.time} tabular-nums`, children: formatTime(elapsedSeconds) }),
1148
- /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "flex items-center gap-2", children: [
1149
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1462
+ return /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: `flex items-center ${styles.container} ${className}`, children: [
1463
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { className: `font-mono font-bold text-gray-800 ${styles.time} tabular-nums`, children: formatTime(elapsedSeconds) }),
1464
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex items-center gap-2", children: [
1465
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1150
1466
  "button",
1151
1467
  {
1152
1468
  type: "button",
@@ -1160,14 +1476,14 @@ function Timer({
1160
1476
  title: isRunning ? "Pause" : "Start",
1161
1477
  children: isRunning ? (
1162
1478
  // Pause icon
1163
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: styles.icon, fill: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { d: "M6 4h4v16H6V4zm8 0h4v16h-4V4z" }) })
1479
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("svg", { className: styles.icon, fill: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("path", { d: "M6 4h4v16H6V4zm8 0h4v16h-4V4z" }) })
1164
1480
  ) : (
1165
1481
  // Play icon
1166
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: styles.icon, fill: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { d: "M8 5v14l11-7z" }) })
1482
+ /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("svg", { className: styles.icon, fill: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("path", { d: "M8 5v14l11-7z" }) })
1167
1483
  )
1168
1484
  }
1169
1485
  ),
1170
- elapsedSeconds > 0 && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1486
+ elapsedSeconds > 0 && /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1171
1487
  "button",
1172
1488
  {
1173
1489
  type: "button",
@@ -1178,10 +1494,10 @@ function Timer({
1178
1494
  transition-colors focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500
1179
1495
  `,
1180
1496
  title: "Stop",
1181
- children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: styles.icon, fill: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { d: "M6 6h12v12H6z" }) })
1497
+ children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("svg", { className: styles.icon, fill: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("path", { d: "M6 6h12v12H6z" }) })
1182
1498
  }
1183
1499
  ),
1184
- showReset && elapsedSeconds > 0 && !isRunning && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
1500
+ showReset && elapsedSeconds > 0 && !isRunning && /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
1185
1501
  "button",
1186
1502
  {
1187
1503
  type: "button",
@@ -1192,7 +1508,7 @@ function Timer({
1192
1508
  transition-colors focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-400
1193
1509
  `,
1194
1510
  title: "Reset",
1195
- children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("svg", { className: styles.icon, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15" }) })
1511
+ children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("svg", { className: styles.icon, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15" }) })
1196
1512
  }
1197
1513
  )
1198
1514
  ] })
@@ -1202,6 +1518,7 @@ function Timer({
1202
1518
  0 && (module.exports = {
1203
1519
  Button,
1204
1520
  Card,
1521
+ DataTable,
1205
1522
  DatePicker,
1206
1523
  EmptyState,
1207
1524
  FormButtonGroup,
@@ -1217,6 +1534,7 @@ function Timer({
1217
1534
  Table,
1218
1535
  Tabs,
1219
1536
  Timer,
1537
+ createFilterOptions,
1220
1538
  formatTime
1221
1539
  });
1222
1540
  //# sourceMappingURL=index.js.map