@xcelsior/ui-spreadsheets 1.0.16 → 1.0.17

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.mts CHANGED
@@ -303,6 +303,8 @@ interface SpreadsheetProps<T = any> {
303
303
  defaultZoom?: number;
304
304
  /** Whether to auto-save changes */
305
305
  autoSave?: boolean;
306
+ /** Callback when changes are saved (called for both auto-save and manual save) */
307
+ onSave?: () => void | Promise<void>;
306
308
  /** Whether to use compact mode (smaller cells) */
307
309
  compactMode?: boolean;
308
310
  /** Loading state */
@@ -604,7 +606,7 @@ interface SpreadsheetColumnGroupHeaderProps {
604
606
  * />
605
607
  * ```
606
608
  */
607
- declare function Spreadsheet<T extends Record<string, any>>({ data, columns, columnGroups, getRowId, onCellsEdit, onSelectionChange, onSortChange, onFilterChange, onRowClick, onRowDoubleClick, onRowClone, onRowDelete, onAddCellComment, onRowHighlight, showToolbar, showPagination, showRowIndex, enableRowSelection, enableCellEditing, enableComments, enableHighlighting, enableUndoRedo, defaultPageSize, pageSizeOptions, defaultZoom, autoSave, compactMode, isLoading, className, emptyMessage, rowHighlights: externalRowHighlights, cellComments: externalCellComments, rowActions, toolbarMenuItems, serverSide, totalItems, currentPage: controlledCurrentPage, pageSize: controlledPageSize, onPageChange, sortConfig: controlledSortConfig, filters: controlledFilters, }: SpreadsheetProps<T>): react_jsx_runtime.JSX.Element;
609
+ declare function Spreadsheet<T extends Record<string, any>>({ data, columns, columnGroups, getRowId, onCellsEdit, onSelectionChange, onSortChange, onFilterChange, onRowClick, onRowDoubleClick, onRowClone, onRowDelete, onAddCellComment, onRowHighlight, showToolbar, showPagination, showRowIndex, enableRowSelection, enableCellEditing, enableComments, enableHighlighting, enableUndoRedo, defaultPageSize, pageSizeOptions, defaultZoom, autoSave, onSave, compactMode, isLoading, className, emptyMessage, rowHighlights: externalRowHighlights, cellComments: externalCellComments, rowActions, toolbarMenuItems, serverSide, totalItems, currentPage: controlledCurrentPage, pageSize: controlledPageSize, onPageChange, sortConfig: controlledSortConfig, filters: controlledFilters, }: SpreadsheetProps<T>): react_jsx_runtime.JSX.Element;
608
610
  declare namespace Spreadsheet {
609
611
  var displayName: string;
610
612
  }
package/dist/index.d.ts CHANGED
@@ -303,6 +303,8 @@ interface SpreadsheetProps<T = any> {
303
303
  defaultZoom?: number;
304
304
  /** Whether to auto-save changes */
305
305
  autoSave?: boolean;
306
+ /** Callback when changes are saved (called for both auto-save and manual save) */
307
+ onSave?: () => void | Promise<void>;
306
308
  /** Whether to use compact mode (smaller cells) */
307
309
  compactMode?: boolean;
308
310
  /** Loading state */
@@ -604,7 +606,7 @@ interface SpreadsheetColumnGroupHeaderProps {
604
606
  * />
605
607
  * ```
606
608
  */
607
- declare function Spreadsheet<T extends Record<string, any>>({ data, columns, columnGroups, getRowId, onCellsEdit, onSelectionChange, onSortChange, onFilterChange, onRowClick, onRowDoubleClick, onRowClone, onRowDelete, onAddCellComment, onRowHighlight, showToolbar, showPagination, showRowIndex, enableRowSelection, enableCellEditing, enableComments, enableHighlighting, enableUndoRedo, defaultPageSize, pageSizeOptions, defaultZoom, autoSave, compactMode, isLoading, className, emptyMessage, rowHighlights: externalRowHighlights, cellComments: externalCellComments, rowActions, toolbarMenuItems, serverSide, totalItems, currentPage: controlledCurrentPage, pageSize: controlledPageSize, onPageChange, sortConfig: controlledSortConfig, filters: controlledFilters, }: SpreadsheetProps<T>): react_jsx_runtime.JSX.Element;
609
+ declare function Spreadsheet<T extends Record<string, any>>({ data, columns, columnGroups, getRowId, onCellsEdit, onSelectionChange, onSortChange, onFilterChange, onRowClick, onRowDoubleClick, onRowClone, onRowDelete, onAddCellComment, onRowHighlight, showToolbar, showPagination, showRowIndex, enableRowSelection, enableCellEditing, enableComments, enableHighlighting, enableUndoRedo, defaultPageSize, pageSizeOptions, defaultZoom, autoSave, onSave, compactMode, isLoading, className, emptyMessage, rowHighlights: externalRowHighlights, cellComments: externalCellComments, rowActions, toolbarMenuItems, serverSide, totalItems, currentPage: controlledCurrentPage, pageSize: controlledPageSize, onPageChange, sortConfig: controlledSortConfig, filters: controlledFilters, }: SpreadsheetProps<T>): react_jsx_runtime.JSX.Element;
608
610
  declare namespace Spreadsheet {
609
611
  var displayName: string;
610
612
  }
package/dist/index.js CHANGED
@@ -194,7 +194,7 @@ function cn(...inputs) {
194
194
  // src/components/SpreadsheetCell.tsx
195
195
  var import_react3 = require("react");
196
196
  var import_jsx_runtime = require("react/jsx-runtime");
197
- var cellPaddingCompact = "px-1.5 py-0.5";
197
+ var cellPaddingCompact = "px-1 py-px";
198
198
  var cellPaddingNormal = "px-2 py-1";
199
199
  var SpreadsheetCell = ({
200
200
  value,
@@ -370,7 +370,8 @@ var SpreadsheetCell = ({
370
370
  onKeyDown: handleCellKeyDown,
371
371
  "data-cell-id": `${rowId}-${column.id}`,
372
372
  className: cn(
373
- "border border-gray-200 text-xs group cursor-pointer transition-colors select-none",
373
+ "border border-gray-200 group cursor-pointer transition-colors select-none",
374
+ compactMode ? "text-[10px]" : "text-xs",
374
375
  cellPadding,
375
376
  column.align === "right" && "text-right",
376
377
  column.align === "center" && "text-center",
@@ -1189,7 +1190,7 @@ ColumnHeaderActions.displayName = "ColumnHeaderActions";
1189
1190
 
1190
1191
  // src/components/SpreadsheetHeader.tsx
1191
1192
  var import_jsx_runtime5 = require("react/jsx-runtime");
1192
- var cellPaddingCompact2 = "px-1.5 py-1";
1193
+ var cellPaddingCompact2 = "px-1 py-0.5";
1193
1194
  var cellPaddingNormal2 = "px-2 py-1.5";
1194
1195
  var SpreadsheetHeader = ({
1195
1196
  column,
@@ -1225,7 +1226,8 @@ var SpreadsheetHeader = ({
1225
1226
  {
1226
1227
  onClick: column.sortable ? onClick : void 0,
1227
1228
  className: cn(
1228
- "border border-gray-200 text-xs font-semibold text-gray-700 sticky group",
1229
+ "border border-gray-200 font-semibold text-gray-700 sticky group",
1230
+ compactMode ? "text-[10px]" : "text-xs",
1229
1231
  cellPadding,
1230
1232
  column.align === "right" && "text-right",
1231
1233
  column.align === "center" && "text-center",
@@ -1395,6 +1397,8 @@ function useSpreadsheetPinning({
1395
1397
 
1396
1398
  // src/components/RowIndexColumnHeader.tsx
1397
1399
  var import_jsx_runtime6 = require("react/jsx-runtime");
1400
+ var cellPaddingCompact3 = "px-1 py-0.5";
1401
+ var cellPaddingNormal3 = "px-2 py-1.5";
1398
1402
  function RowIndexColumnHeader({
1399
1403
  enableHighlighting = false,
1400
1404
  highlightColor,
@@ -1402,13 +1406,17 @@ function RowIndexColumnHeader({
1402
1406
  onHighlightClick,
1403
1407
  onPinClick,
1404
1408
  hasColumnGroups = false,
1409
+ compactMode = false,
1405
1410
  className
1406
1411
  }) {
1412
+ const cellPadding = compactMode ? cellPaddingCompact3 : cellPaddingNormal3;
1407
1413
  return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
1408
1414
  "th",
1409
1415
  {
1410
1416
  className: cn(
1411
- "border border-gray-200 px-2 py-1.5 text-center font-bold text-gray-700 group",
1417
+ "border border-gray-200 text-center font-bold text-gray-700 group",
1418
+ compactMode ? "text-[10px]" : "text-xs",
1419
+ cellPadding,
1412
1420
  isPinned ? "z-30" : "z-20",
1413
1421
  className
1414
1422
  ),
@@ -2646,12 +2654,15 @@ var import_react13 = require("react");
2646
2654
  function useSpreadsheetUndoRedo({
2647
2655
  enabled = true,
2648
2656
  maxStackSize = 50,
2649
- autoSave = true
2657
+ autoSave = true,
2658
+ onSave
2650
2659
  }) {
2651
2660
  const [undoStack, setUndoStack] = (0, import_react13.useState)([]);
2652
2661
  const [redoStack, setRedoStack] = (0, import_react13.useState)([]);
2653
2662
  const [hasUnsavedChanges, setHasUnsavedChanges] = (0, import_react13.useState)(false);
2654
2663
  const [saveStatus, setSaveStatus] = (0, import_react13.useState)("saved");
2664
+ const onSaveRef = (0, import_react13.useRef)(onSave);
2665
+ onSaveRef.current = onSave;
2655
2666
  const pushToUndoStack = (0, import_react13.useCallback)(
2656
2667
  (snapshot) => {
2657
2668
  if (!enabled) return;
@@ -2692,19 +2703,36 @@ function useSpreadsheetUndoRedo({
2692
2703
  });
2693
2704
  return nextSnapshot;
2694
2705
  }, [enabled, redoStack, maxStackSize]);
2695
- const handleSave = (0, import_react13.useCallback)(() => {
2696
- if (!hasUnsavedChanges) return;
2706
+ const handleSave = (0, import_react13.useCallback)(async () => {
2707
+ if (!hasUnsavedChanges && !autoSave) return;
2697
2708
  setSaveStatus("saving");
2698
- setTimeout(() => {
2709
+ try {
2710
+ if (onSaveRef.current) {
2711
+ await onSaveRef.current();
2712
+ }
2699
2713
  setSaveStatus("saved");
2700
2714
  setHasUnsavedChanges(false);
2701
- }, 500);
2702
- }, [hasUnsavedChanges]);
2715
+ } catch {
2716
+ setSaveStatus("error");
2717
+ }
2718
+ }, [hasUnsavedChanges, autoSave]);
2703
2719
  const markAsChanged = (0, import_react13.useCallback)(() => {
2704
2720
  setHasUnsavedChanges(true);
2705
2721
  if (autoSave) {
2706
2722
  setSaveStatus("saving");
2707
- setTimeout(() => setSaveStatus("saved"), 500);
2723
+ if (onSaveRef.current) {
2724
+ Promise.resolve(onSaveRef.current()).then(() => {
2725
+ setSaveStatus("saved");
2726
+ setHasUnsavedChanges(false);
2727
+ }).catch(() => {
2728
+ setSaveStatus("error");
2729
+ });
2730
+ } else {
2731
+ setTimeout(() => {
2732
+ setSaveStatus("saved");
2733
+ setHasUnsavedChanges(false);
2734
+ }, 500);
2735
+ }
2708
2736
  } else {
2709
2737
  setSaveStatus("unsaved");
2710
2738
  }
@@ -3356,6 +3384,7 @@ function Spreadsheet({
3356
3384
  pageSizeOptions = [25, 50, 100, 200],
3357
3385
  defaultZoom = 100,
3358
3386
  autoSave = true,
3387
+ onSave,
3359
3388
  compactMode = false,
3360
3389
  isLoading = false,
3361
3390
  className,
@@ -3440,6 +3469,19 @@ function Spreadsheet({
3440
3469
  externalCellComments,
3441
3470
  onAddCellComment
3442
3471
  });
3472
+ const [showSettingsModal, setShowSettingsModal] = (0, import_react16.useState)(false);
3473
+ const [spreadsheetSettings, setSpreadsheetSettings] = (0, import_react16.useState)({
3474
+ defaultPinnedColumns: [],
3475
+ defaultSort: null,
3476
+ defaultPageSize,
3477
+ defaultZoom,
3478
+ autoSave,
3479
+ compactView: compactMode,
3480
+ showRowIndex,
3481
+ pinRowIndex: false,
3482
+ rowIndexHighlightColor: void 0
3483
+ });
3484
+ const effectiveAutoSave = spreadsheetSettings.autoSave ?? autoSave;
3443
3485
  const {
3444
3486
  canUndo,
3445
3487
  canRedo,
@@ -3454,7 +3496,8 @@ function Spreadsheet({
3454
3496
  markAsChanged
3455
3497
  } = useSpreadsheetUndoRedo({
3456
3498
  enabled: enableUndoRedo,
3457
- autoSave
3499
+ autoSave: effectiveAutoSave,
3500
+ onSave
3458
3501
  });
3459
3502
  const [selectedRows, setSelectedRows] = (0, import_react16.useState)(/* @__PURE__ */ new Set());
3460
3503
  const [lastSelectedRow, setLastSelectedRow] = (0, import_react16.useState)(null);
@@ -3485,18 +3528,6 @@ function Spreadsheet({
3485
3528
  },
3486
3529
  [controlledPageSize, controlledCurrentPage, onPageChange]
3487
3530
  );
3488
- const [showSettingsModal, setShowSettingsModal] = (0, import_react16.useState)(false);
3489
- const [spreadsheetSettings, setSpreadsheetSettings] = (0, import_react16.useState)({
3490
- defaultPinnedColumns: [],
3491
- defaultSort: null,
3492
- defaultPageSize,
3493
- defaultZoom,
3494
- autoSave,
3495
- compactView: compactMode,
3496
- showRowIndex,
3497
- pinRowIndex: false,
3498
- rowIndexHighlightColor: void 0
3499
- });
3500
3531
  (0, import_react16.useEffect)(() => {
3501
3532
  setSpreadsheetSettings((prev) => ({
3502
3533
  ...prev,
@@ -3662,6 +3693,7 @@ function Spreadsheet({
3662
3693
  enabled: true
3663
3694
  });
3664
3695
  const effectiveShowRowIndex = spreadsheetSettings.showRowIndex !== false;
3696
+ const effectiveCompactMode = spreadsheetSettings.compactView ?? compactMode;
3665
3697
  const rowIndexHighlightColor = getColumnHighlight(ROW_INDEX_COLUMN_ID);
3666
3698
  const tableRef = (0, import_react16.useRef)(null);
3667
3699
  const effectiveTotalItems = serverSide ? totalItems ?? data.length : filteredData.length;
@@ -3789,7 +3821,7 @@ function Spreadsheet({
3789
3821
  selectedRowCount: selectedRows.size,
3790
3822
  hasUnsavedChanges,
3791
3823
  saveStatus,
3792
- autoSave,
3824
+ autoSave: effectiveAutoSave,
3793
3825
  hasActiveFilters,
3794
3826
  onClearFilters: clearAllFilters,
3795
3827
  onZoomIn: () => setZoom((z) => Math.min(z + 10, 200)),
@@ -3827,7 +3859,8 @@ function Spreadsheet({
3827
3859
  isPinned: isRowIndexPinned,
3828
3860
  onHighlightClick: handleRowIndexHighlightClick,
3829
3861
  onPinClick: handleToggleRowIndexPin,
3830
- hasColumnGroups: true
3862
+ hasColumnGroups: true,
3863
+ compactMode: effectiveCompactMode
3831
3864
  }
3832
3865
  ),
3833
3866
  columnGroups.map((group) => {
@@ -3870,7 +3903,8 @@ function Spreadsheet({
3870
3903
  isPinned: isRowIndexPinned,
3871
3904
  onHighlightClick: handleRowIndexHighlightClick,
3872
3905
  onPinClick: handleToggleRowIndexPin,
3873
- hasColumnGroups: false
3906
+ hasColumnGroups: false,
3907
+ compactMode: effectiveCompactMode
3874
3908
  }
3875
3909
  ),
3876
3910
  visibleColumns.map((column) => {
@@ -3885,7 +3919,7 @@ function Spreadsheet({
3885
3919
  pinSide: getColumnPinSide(column.id),
3886
3920
  leftOffset: isPinnedLeft ? getColumnLeftOffset(column.id) : 0,
3887
3921
  highlightColor: getColumnHighlight(column.id),
3888
- compactMode,
3922
+ compactMode: effectiveCompactMode,
3889
3923
  onClick: () => handleSort(column.id),
3890
3924
  onFilterClick: () => setActiveFilterColumn(
3891
3925
  activeFilterColumn === column.id ? null : column.id
@@ -3947,6 +3981,7 @@ function Spreadsheet({
3947
3981
  onClick: (e) => handleRowSelect(rowId, e),
3948
3982
  className: cn(
3949
3983
  "border border-gray-200 text-center font-semibold cursor-pointer group",
3984
+ effectiveCompactMode ? "text-[10px] px-1 py-px" : "text-xs px-2 py-1",
3950
3985
  isRowIndexPinned ? "z-20" : "z-0",
3951
3986
  isRowSelected && "bg-blue-100",
3952
3987
  !isRowSelected && rowHighlight && "",
@@ -4118,7 +4153,7 @@ function Spreadsheet({
4118
4153
  isRowSelected,
4119
4154
  isRowHovered,
4120
4155
  highlightColor: cellOrRowOrColumnHighlight,
4121
- compactMode,
4156
+ compactMode: effectiveCompactMode,
4122
4157
  isPinned: isColPinned,
4123
4158
  pinSide: colPinSide,
4124
4159
  leftOffset: getColumnLeftOffset(column.id),