gantt-lib 0.91.0 → 0.100.0

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
@@ -45,6 +45,7 @@ __export(index_exports, {
45
45
  PopoverContent: () => PopoverContent,
46
46
  PopoverTrigger: () => PopoverTrigger,
47
47
  ResourceTimelineChart: () => ResourceTimelineChart,
48
+ TableMatrix: () => TableMatrix,
48
49
  TaskList: () => TaskList,
49
50
  TaskRow: () => TaskRow_default,
50
51
  TimeScaleHeader: () => TimeScaleHeader_default,
@@ -142,7 +143,7 @@ __export(index_exports, {
142
143
  module.exports = __toCommonJS(index_exports);
143
144
 
144
145
  // src/components/GanttChart/GanttChart.tsx
145
- var import_react15 = require("react");
146
+ var import_react16 = require("react");
146
147
 
147
148
  // src/core/scheduling/dateMath.ts
148
149
  var DAY_MS = 24 * 60 * 60 * 1e3;
@@ -4844,11 +4845,15 @@ var TaskListRow = import_react10.default.memo(
4844
4845
  resolvedColumns,
4845
4846
  isTaskSelected = false,
4846
4847
  onTaskSelectionChange,
4848
+ activeCustomCell,
4849
+ onActiveCustomCellChange,
4847
4850
  taskListMenuCommands = [],
4851
+ hideTaskListRowActions = false,
4848
4852
  taskDateChangeMode = "preserve-duration",
4849
4853
  onTaskDateChangeModeChange
4850
4854
  }) => {
4851
4855
  const [editingColumnId, setEditingColumnId] = (0, import_react10.useState)(null);
4856
+ const [editingColumnStartValue, setEditingColumnStartValue] = (0, import_react10.useState)(void 0);
4852
4857
  const editingName = editingColumnId === "name";
4853
4858
  const editingDuration = editingColumnId === "duration";
4854
4859
  const editingProgress = editingColumnId === "progress";
@@ -4874,12 +4879,15 @@ var TaskListRow = import_react10.default.memo(
4874
4879
  const editTriggerRef = (0, import_react10.useRef)(
4875
4880
  "doubleclick"
4876
4881
  );
4882
+ const rowRef = (0, import_react10.useRef)(null);
4877
4883
  const isSelected = selectedTaskId === task.id;
4878
4884
  const isParent = (0, import_react10.useMemo)(
4879
4885
  () => isTaskParent(task.id, allTasks),
4880
4886
  [task.id, allTasks]
4881
4887
  );
4882
4888
  const isChild = task.parentId !== void 0;
4889
+ const rowFillLevel = Math.min(nestingDepth, 2);
4890
+ const isTotalRow = Boolean(task.isTotal);
4883
4891
  const isMilestoneRow = normalizedTask.type === "milestone";
4884
4892
  const weekendPredicate = (0, import_react10.useMemo)(
4885
4893
  () => createCustomDayPredicate({ customDays, isWeekend: isWeekend3 }),
@@ -5426,7 +5434,7 @@ var TaskListRow = import_react10.default.memo(
5426
5434
  ),
5427
5435
  [taskListMenuCommands, task, isParent, isMilestoneRow]
5428
5436
  );
5429
- const hasContextMenu = visibleCustomMenuCommands.length > 0 || !!onDuplicateTask || !!onDelete || !!onTasksChange || isParent && !!onUngroupTask;
5437
+ const hasContextMenu = !hideTaskListRowActions && (visibleCustomMenuCommands.length > 0 || !!onDuplicateTask || !!onDelete || !!onTasksChange || isParent && !!onUngroupTask);
5430
5438
  const handleCustomMenuCommandClick = (0, import_react10.useCallback)(
5431
5439
  (command) => (e) => {
5432
5440
  e.stopPropagation();
@@ -5665,14 +5673,14 @@ var TaskListRow = import_react10.default.memo(
5665
5673
  className: "gantt-tl-cell gantt-tl-cell-number",
5666
5674
  onClick: handleNumberClick,
5667
5675
  children: [
5668
- /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
5676
+ onDragStart && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
5669
5677
  "span",
5670
5678
  {
5671
5679
  className: "gantt-tl-drag-handle",
5672
5680
  draggable: true,
5673
5681
  onDragStart: (e) => {
5674
5682
  e.stopPropagation();
5675
- onDragStart?.(rowIndex, e);
5683
+ onDragStart(rowIndex, e);
5676
5684
  },
5677
5685
  onDragEnd: (e) => onDragEnd?.(e),
5678
5686
  onClick: (e) => e.stopPropagation(),
@@ -5868,7 +5876,7 @@ var TaskListRow = import_react10.default.memo(
5868
5876
  "aria-hidden": "true"
5869
5877
  }
5870
5878
  ),
5871
- !editingName && (onInsertAfter || onDelete || onPromoteTask || onDemoteTask || onUngroupTask || onDuplicateTask || onTasksChange || hasContextMenu) && /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("div", { className: `gantt-tl-name-actions${contextMenuOpen ? " gantt-tl-name-actions-open" : ""}`, children: [
5879
+ !editingName && !hideTaskListRowActions && (onInsertAfter || onDelete || onPromoteTask || onDemoteTask || onUngroupTask || onDuplicateTask || onTasksChange || hasContextMenu) && /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("div", { className: `gantt-tl-name-actions${contextMenuOpen ? " gantt-tl-name-actions-open" : ""}`, children: [
5872
5880
  onInsertAfter && /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
5873
5881
  "button",
5874
5882
  {
@@ -6387,9 +6395,52 @@ var TaskListRow = import_react10.default.memo(
6387
6395
  progress: progressCell,
6388
6396
  dependencies: dependenciesCell
6389
6397
  };
6398
+ const focusCustomCell = (0, import_react10.useCallback)((taskId, columnId) => {
6399
+ const overlay = rowRef.current?.closest(".gantt-tl-overlay");
6400
+ if (!overlay) {
6401
+ return;
6402
+ }
6403
+ const selector = `[data-gantt-task-row-id="${taskId}"] [data-custom-column-id="${columnId}"]`;
6404
+ const nextCell = overlay.querySelector(selector);
6405
+ nextCell?.focus();
6406
+ }, []);
6407
+ const moveActiveCustomCell = (0, import_react10.useCallback)((columnId, direction) => {
6408
+ const overlay = rowRef.current?.closest(".gantt-tl-overlay");
6409
+ if (!overlay || !resolvedColumns) {
6410
+ return;
6411
+ }
6412
+ const customColumnIds = resolvedColumns.filter((column) => !["selection", "number", "name", "startDate", "endDate", "duration", "progress", "dependencies"].includes(column.id)).map((column) => column.id);
6413
+ const columnIndex = customColumnIds.indexOf(columnId);
6414
+ if (columnIndex === -1) {
6415
+ return;
6416
+ }
6417
+ const rowElements = Array.from(
6418
+ overlay.querySelectorAll(".gantt-tl-row[data-gantt-task-row-id]")
6419
+ );
6420
+ const rowIds = rowElements.map((element) => element.dataset.ganttTaskRowId).filter((value) => Boolean(value));
6421
+ const rowIndex2 = rowIds.indexOf(task.id);
6422
+ if (rowIndex2 === -1) {
6423
+ return;
6424
+ }
6425
+ let nextRowIndex = rowIndex2;
6426
+ let nextColumnIndex = columnIndex;
6427
+ if (direction === "left") nextColumnIndex -= 1;
6428
+ if (direction === "right") nextColumnIndex += 1;
6429
+ if (direction === "up") nextRowIndex -= 1;
6430
+ if (direction === "down") nextRowIndex += 1;
6431
+ if (nextRowIndex < 0 || nextRowIndex >= rowIds.length || nextColumnIndex < 0 || nextColumnIndex >= customColumnIds.length) {
6432
+ return;
6433
+ }
6434
+ const nextCell = { taskId: rowIds[nextRowIndex], columnId: customColumnIds[nextColumnIndex] };
6435
+ onActiveCustomCellChange?.(nextCell);
6436
+ window.requestAnimationFrame(() => {
6437
+ focusCustomCell(nextCell.taskId, nextCell.columnId);
6438
+ });
6439
+ }, [focusCustomCell, onActiveCustomCellChange, resolvedColumns, task.id]);
6390
6440
  return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
6391
6441
  "div",
6392
6442
  {
6443
+ ref: rowRef,
6393
6444
  "data-filter-match": isFilterMatch ? "true" : "false",
6394
6445
  className: [
6395
6446
  "gantt-tl-row",
@@ -6402,9 +6453,11 @@ var TaskListRow = import_react10.default.memo(
6402
6453
  isDragging ? "gantt-tl-row-dragging" : "",
6403
6454
  isDragOver ? "gantt-tl-row-drag-over" : "",
6404
6455
  isChild ? "gantt-tl-row-child" : "",
6405
- isParent ? "gantt-tl-row-parent" : ""
6456
+ isParent ? "gantt-tl-row-parent" : "",
6457
+ `gantt-tl-row-level-${rowFillLevel}`,
6458
+ isTotalRow ? "gantt-tl-row-total" : ""
6406
6459
  ].filter(Boolean).join(" "),
6407
- style: { minHeight: `${rowHeight}px`, position: "relative" },
6460
+ style: { height: `${rowHeight}px`, position: "relative" },
6408
6461
  "data-gantt-task-row-id": task.id,
6409
6462
  onClick: handleRowClickInternal,
6410
6463
  onKeyDown: handleRowKeyDown,
@@ -6416,43 +6469,120 @@ var TaskListRow = import_react10.default.memo(
6416
6469
  if (builtIn) return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(import_react10.default.Fragment, { children: builtIn }, col.id);
6417
6470
  const isEditing = editingColumnId === col.id;
6418
6471
  const editorFn = col.renderEditor;
6472
+ const isActiveCustomCell = activeCustomCell?.taskId === task.id && activeCustomCell?.columnId === col.id;
6473
+ const startEditingCustomCell = (startValue) => {
6474
+ if (!editorFn) return;
6475
+ onActiveCustomCellChange?.({ taskId: task.id, columnId: col.id });
6476
+ setEditingColumnStartValue(startValue);
6477
+ setEditingColumnId(col.id);
6478
+ };
6419
6479
  const columnContext = {
6420
6480
  task,
6421
6481
  rowIndex,
6422
6482
  isEditing,
6483
+ editStartValue: isEditing ? editingColumnStartValue : void 0,
6423
6484
  openEditor: () => {
6424
- if (editorFn) setEditingColumnId(col.id);
6485
+ startEditingCustomCell();
6425
6486
  },
6426
6487
  closeEditor: () => {
6427
- if (editingColumnId === col.id) setEditingColumnId(null);
6488
+ if (editingColumnId === col.id) {
6489
+ setEditingColumnId(null);
6490
+ setEditingColumnStartValue(void 0);
6491
+ onActiveCustomCellChange?.({ taskId: task.id, columnId: col.id });
6492
+ window.requestAnimationFrame(() => {
6493
+ focusCustomCell(task.id, col.id);
6494
+ });
6495
+ }
6428
6496
  },
6429
6497
  updateTask: (patch) => {
6430
6498
  onTasksChange?.([{ ...task, ...patch }]);
6499
+ onActiveCustomCellChange?.({ taskId: task.id, columnId: col.id });
6500
+ setEditingColumnStartValue(void 0);
6431
6501
  setEditingColumnId(null);
6502
+ window.requestAnimationFrame(() => {
6503
+ focusCustomCell(task.id, col.id);
6504
+ });
6432
6505
  }
6433
6506
  };
6434
6507
  return /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
6435
6508
  "div",
6436
6509
  {
6437
- className: "gantt-tl-cell gantt-tl-cell-custom",
6510
+ className: `gantt-tl-cell gantt-tl-cell-custom gantt-tl-cell-align-${col.align ?? "left"}`,
6438
6511
  "data-column-id": `custom:${col.id}`,
6439
6512
  "data-custom-column-id": col.id,
6513
+ "data-custom-column-active": isActiveCustomCell ? "true" : "false",
6440
6514
  "data-custom-column-editing": isEditing ? "true" : "false",
6441
6515
  "data-testid": `custom-cell-${col.id}`,
6442
- onClick: editorFn && !isEditing ? (e) => {
6516
+ tabIndex: editorFn ? 0 : -1,
6517
+ onFocus: editorFn ? () => {
6518
+ onActiveCustomCellChange?.({ taskId: task.id, columnId: col.id });
6519
+ } : void 0,
6520
+ onClick: editorFn ? (e) => {
6443
6521
  e.stopPropagation();
6444
- setEditingColumnId(col.id);
6522
+ onActiveCustomCellChange?.({ taskId: task.id, columnId: col.id });
6523
+ if (isEditing) {
6524
+ return;
6525
+ }
6526
+ e.currentTarget.focus();
6527
+ } : void 0,
6528
+ onDoubleClick: editorFn && !isEditing ? (e) => {
6529
+ e.stopPropagation();
6530
+ startEditingCustomCell();
6531
+ } : void 0,
6532
+ onKeyDown: editorFn && !isEditing ? (e) => {
6533
+ if (e.key === "ArrowLeft") {
6534
+ e.preventDefault();
6535
+ e.stopPropagation();
6536
+ moveActiveCustomCell(col.id, "left");
6537
+ return;
6538
+ }
6539
+ if (e.key === "ArrowRight") {
6540
+ e.preventDefault();
6541
+ e.stopPropagation();
6542
+ moveActiveCustomCell(col.id, "right");
6543
+ return;
6544
+ }
6545
+ if (e.key === "ArrowUp") {
6546
+ e.preventDefault();
6547
+ e.stopPropagation();
6548
+ moveActiveCustomCell(col.id, "up");
6549
+ return;
6550
+ }
6551
+ if (e.key === "ArrowDown") {
6552
+ e.preventDefault();
6553
+ e.stopPropagation();
6554
+ moveActiveCustomCell(col.id, "down");
6555
+ return;
6556
+ }
6557
+ if (e.key === "Enter" || e.key === "F2") {
6558
+ e.preventDefault();
6559
+ e.stopPropagation();
6560
+ startEditingCustomCell();
6561
+ return;
6562
+ }
6563
+ if (e.key === "Backspace" || e.key === "Delete") {
6564
+ e.preventDefault();
6565
+ e.stopPropagation();
6566
+ startEditingCustomCell("");
6567
+ return;
6568
+ }
6569
+ if (e.key.length === 1 && !e.ctrlKey && !e.metaKey && !e.altKey) {
6570
+ e.preventDefault();
6571
+ e.stopPropagation();
6572
+ startEditingCustomCell(e.key);
6573
+ }
6445
6574
  } : void 0,
6446
6575
  style: { width: col.width ?? 120, minWidth: col.width ?? 120, flexShrink: 0 },
6447
6576
  children: isEditing && editorFn ? /* @__PURE__ */ (0, import_jsx_runtime12.jsx)(
6448
6577
  "div",
6449
6578
  {
6579
+ className: "gantt-tl-cell-custom-editor",
6450
6580
  "data-custom-column-editor": col.id,
6451
6581
  onMouseDown: (e) => e.stopPropagation(),
6452
6582
  onClick: (e) => e.stopPropagation(),
6453
6583
  children: editorFn(columnContext)
6454
6584
  }
6455
- ) : col.renderCell(columnContext)
6585
+ ) : /* @__PURE__ */ (0, import_jsx_runtime12.jsx)("div", { className: "gantt-tl-cell-custom-content", children: col.renderCell(columnContext) })
6456
6586
  },
6457
6587
  col.id
6458
6588
  );
@@ -6504,7 +6634,7 @@ var NewTaskRow = ({
6504
6634
  onCancel();
6505
6635
  }
6506
6636
  };
6507
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("div", { className: "gantt-tl-row gantt-tl-row-new", style: { minHeight: `${rowHeight}px` }, children: [
6637
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("div", { className: "gantt-tl-row gantt-tl-row-new", style: { height: `${rowHeight}px` }, children: [
6508
6638
  /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: "gantt-tl-cell gantt-tl-cell-number" }),
6509
6639
  /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: "gantt-tl-cell gantt-tl-cell-name gantt-tl-cell-new-name", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
6510
6640
  Input,
@@ -6738,6 +6868,7 @@ var TaskList = ({
6738
6868
  onDelete,
6739
6869
  onInsertAfter,
6740
6870
  onReorder,
6871
+ disableTaskDrag = false,
6741
6872
  editingTaskId: propEditingTaskId,
6742
6873
  enableAddTask = true,
6743
6874
  defaultTaskDurationDays = DEFAULT_TASK_DURATION_DAYS,
@@ -6759,10 +6890,13 @@ var TaskList = ({
6759
6890
  additionalColumns,
6760
6891
  hiddenTaskListColumns,
6761
6892
  taskListMenuCommands,
6893
+ hideTaskListRowActions = false,
6894
+ rowContentLines = 1,
6762
6895
  taskDateChangeMode = "preserve-duration",
6763
6896
  onTaskDateChangeModeChange
6764
6897
  }) => {
6765
6898
  const [internalSelectedTaskIds, setInternalSelectedTaskIds] = (0, import_react12.useState)(/* @__PURE__ */ new Set());
6899
+ const [activeCustomCell, setActiveCustomCell] = (0, import_react12.useState)(null);
6766
6900
  const effectiveSelectedTaskIds = selectedTaskIds ?? internalSelectedTaskIds;
6767
6901
  const emitSelectedTaskIdsChange = (0, import_react12.useCallback)((nextSelectedTaskIds) => {
6768
6902
  if (!selectedTaskIds) {
@@ -6934,21 +7068,28 @@ var TaskList = ({
6934
7068
  onSelectedChipChange?.(chip);
6935
7069
  }, [onSelectedChipChange]);
6936
7070
  (0, import_react12.useEffect)(() => {
6937
- if (!selectingPredecessorFor && !selectedChip && !selectedTaskId) return;
7071
+ if (!selectingPredecessorFor && !selectedChip && !selectedTaskId && !activeCustomCell) return;
6938
7072
  const handleKeyDown = (e) => {
6939
7073
  if (e.key === "Escape") {
6940
7074
  setSelectingPredecessorFor(null);
6941
7075
  setSelectedChip(null);
7076
+ setActiveCustomCell(null);
6942
7077
  onSelectedChipChange?.(null);
6943
7078
  onTaskSelect?.(null);
6944
7079
  }
6945
7080
  };
6946
7081
  const handleMouseDown = (e) => {
6947
7082
  const target = e.target;
6948
- if (overlayRef.current?.contains(target)) return;
7083
+ if (overlayRef.current?.contains(target)) {
7084
+ if (activeCustomCell && !target.closest?.("[data-custom-column-id]")) {
7085
+ setActiveCustomCell(null);
7086
+ }
7087
+ return;
7088
+ }
6949
7089
  if (target.closest?.(".gantt-popover")) return;
6950
7090
  setSelectingPredecessorFor(null);
6951
7091
  setSelectedChip(null);
7092
+ setActiveCustomCell(null);
6952
7093
  onSelectedChipChange?.(null);
6953
7094
  onTaskSelect?.(null);
6954
7095
  };
@@ -6958,7 +7099,7 @@ var TaskList = ({
6958
7099
  document.removeEventListener("keydown", handleKeyDown);
6959
7100
  document.removeEventListener("mousedown", handleMouseDown, true);
6960
7101
  };
6961
- }, [selectingPredecessorFor, selectedChip, selectedTaskId, onTaskSelect, onSelectedChipChange]);
7102
+ }, [selectingPredecessorFor, selectedChip, selectedTaskId, activeCustomCell, onTaskSelect, onSelectedChipChange]);
6962
7103
  const handleAddDependency = (0, import_react12.useCallback)((successorTaskId, predecessorTaskId, linkType) => {
6963
7104
  if (successorTaskId === predecessorTaskId) return;
6964
7105
  if (areTasksHierarchicallyRelated(successorTaskId, predecessorTaskId, tasks)) {
@@ -7348,7 +7489,10 @@ var TaskList = ({
7348
7489
  {
7349
7490
  ref: overlayRef,
7350
7491
  className: `gantt-tl-overlay${show ? "" : " gantt-tl-hidden"}${hasRightShadow ? " gantt-tl-overlay-shadowed" : ""}`,
7351
- style: { "--tasklist-width": `${effectiveTaskListWidth}px` },
7492
+ style: {
7493
+ "--tasklist-width": `${effectiveTaskListWidth}px`,
7494
+ "--gantt-row-content-lines": String(Math.max(2, Math.floor(rowContentLines)))
7495
+ },
7352
7496
  children: /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "gantt-tl-table", children: [
7353
7497
  /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("div", { className: "gantt-tl-header", style: { height: `${tableHeaderHeight}px` }, children: resolvedColumns.map((col) => {
7354
7498
  if (col.id === "selection") {
@@ -7428,7 +7572,7 @@ var TaskList = ({
7428
7572
  return /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
7429
7573
  "div",
7430
7574
  {
7431
- className: "gantt-tl-headerCell gantt-tl-headerCell-custom",
7575
+ className: `gantt-tl-headerCell gantt-tl-headerCell-custom gantt-tl-cell-align-${col.align ?? "left"}`,
7432
7576
  "data-column-id": `custom:${col.id}`,
7433
7577
  "data-custom-column-id": col.id,
7434
7578
  style: { width: col.width, minWidth: col.width, flexShrink: 0 },
@@ -7470,12 +7614,12 @@ var TaskList = ({
7470
7614
  onAdd,
7471
7615
  onInsertAfter: handleStartInsertAfter,
7472
7616
  editingTaskId: propEditingTaskId,
7473
- isDragging: draggingIndex === index,
7474
- isDragOver: dragOverIndex === index,
7475
- onDragStart: handleDragStart,
7476
- onDragOver: handleDragOver,
7477
- onDrop: handleDrop,
7478
- onDragEnd: handleDragEnd,
7617
+ isDragging: !disableTaskDrag && draggingIndex === index,
7618
+ isDragOver: !disableTaskDrag && dragOverIndex === index,
7619
+ onDragStart: disableTaskDrag ? void 0 : handleDragStart,
7620
+ onDragOver: disableTaskDrag ? void 0 : handleDragOver,
7621
+ onDrop: disableTaskDrag ? void 0 : handleDrop,
7622
+ onDragEnd: disableTaskDrag ? void 0 : handleDragEnd,
7479
7623
  collapsedParentIds,
7480
7624
  onToggleCollapse: handleToggleCollapse,
7481
7625
  onPromoteTask,
@@ -7496,7 +7640,10 @@ var TaskList = ({
7496
7640
  resolvedColumns,
7497
7641
  isTaskSelected: effectiveSelectedTaskIds.has(task.id),
7498
7642
  onTaskSelectionChange: handleToggleTaskSelection,
7643
+ activeCustomCell,
7644
+ onActiveCustomCellChange: setActiveCustomCell,
7499
7645
  taskListMenuCommands,
7646
+ hideTaskListRowActions,
7500
7647
  taskDateChangeMode,
7501
7648
  onTaskDateChangeModeChange
7502
7649
  }
@@ -7524,25 +7671,25 @@ var TaskList = ({
7524
7671
  enableAddTask && onAdd && !isCreating && !pendingInsert && /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
7525
7672
  "button",
7526
7673
  {
7527
- className: `gantt-tl-add-btn${dragOverIndex === visibleTasks.length ? " gantt-tl-add-btn-drag-over" : ""}`,
7674
+ className: `gantt-tl-add-btn${!disableTaskDrag && dragOverIndex === visibleTasks.length ? " gantt-tl-add-btn-drag-over" : ""}`,
7528
7675
  onClick: () => {
7529
7676
  setPendingInsert(null);
7530
7677
  setIsCreating(true);
7531
7678
  },
7532
- onDragEnter: (e) => {
7679
+ onDragEnter: disableTaskDrag ? void 0 : (e) => {
7533
7680
  e.preventDefault();
7534
7681
  setDragOverIndex(visibleTasks.length);
7535
7682
  },
7536
- onDragOver: (e) => {
7683
+ onDragOver: disableTaskDrag ? void 0 : (e) => {
7537
7684
  e.preventDefault();
7538
7685
  e.dataTransfer.dropEffect = "move";
7539
7686
  setDragOverIndex(visibleTasks.length);
7540
7687
  },
7541
- onDragLeave: (e) => {
7688
+ onDragLeave: disableTaskDrag ? void 0 : (e) => {
7542
7689
  e.preventDefault();
7543
7690
  setDragOverIndex(null);
7544
7691
  },
7545
- onDrop: (e) => {
7692
+ onDrop: disableTaskDrag ? void 0 : (e) => {
7546
7693
  e.preventDefault();
7547
7694
  handleDrop(visibleTasks.length, e);
7548
7695
  },
@@ -9235,6 +9382,190 @@ function ResourceTimelineChart({
9235
9382
  ) });
9236
9383
  }
9237
9384
 
9385
+ // src/components/TableMatrix/TableMatrix.tsx
9386
+ var import_react15 = require("react");
9387
+ var import_jsx_runtime16 = require("react/jsx-runtime");
9388
+ function joinClasses(...values) {
9389
+ return values.filter(Boolean).join(" ");
9390
+ }
9391
+ function TableMatrix({
9392
+ tasks,
9393
+ allTasks = tasks,
9394
+ columns,
9395
+ columnGroups,
9396
+ rowHeight,
9397
+ headerHeight,
9398
+ selectedTaskId,
9399
+ onTaskSelect,
9400
+ onCellClick,
9401
+ highlightedTaskIds,
9402
+ filterMode = "highlight"
9403
+ }) {
9404
+ const gridTemplateColumns = (0, import_react15.useMemo)(
9405
+ () => columns.map((column) => `${column.width}px`).join(" "),
9406
+ [columns]
9407
+ );
9408
+ const totalWidth = (0, import_react15.useMemo)(
9409
+ () => columns.reduce((sum, column) => sum + column.width, 0),
9410
+ [columns]
9411
+ );
9412
+ const hasGroupHeader = (0, import_react15.useMemo)(
9413
+ () => columns.some((column) => !!column.groupId) || (columnGroups?.length ?? 0) > 0,
9414
+ [columnGroups, columns]
9415
+ );
9416
+ const groupMap = (0, import_react15.useMemo)(
9417
+ () => new Map((columnGroups ?? []).map((group) => [group.id, group])),
9418
+ [columnGroups]
9419
+ );
9420
+ const headerSpans = (0, import_react15.useMemo)(() => {
9421
+ if (!hasGroupHeader) return [];
9422
+ if (columnGroups?.some((group) => typeof group.width === "number")) {
9423
+ return columnGroups.map((group) => ({
9424
+ id: group.id,
9425
+ header: group.header,
9426
+ width: group.width ?? 0,
9427
+ className: group.className
9428
+ }));
9429
+ }
9430
+ const spans = [];
9431
+ for (const column of columns) {
9432
+ const groupId = column.groupId ?? column.id;
9433
+ const lastSpan = spans[spans.length - 1];
9434
+ if (lastSpan?.id === groupId) {
9435
+ lastSpan.width += column.width;
9436
+ continue;
9437
+ }
9438
+ const group = groupMap.get(groupId);
9439
+ spans.push({
9440
+ id: groupId,
9441
+ header: group?.header ?? column.header,
9442
+ width: column.width,
9443
+ className: group?.className
9444
+ });
9445
+ }
9446
+ return spans;
9447
+ }, [columns, groupMap, hasGroupHeader]);
9448
+ const headerContentHeight = Math.max(0, headerHeight - 1);
9449
+ const topRowHeight = hasGroupHeader ? Math.ceil(headerContentHeight / 2) : headerContentHeight;
9450
+ const bottomRowHeight = hasGroupHeader ? Math.floor(headerContentHeight / 2) : 0;
9451
+ const parentTaskIds = (0, import_react15.useMemo)(() => {
9452
+ const ids = /* @__PURE__ */ new Set();
9453
+ for (const task of allTasks) {
9454
+ if (task.parentId) {
9455
+ ids.add(task.parentId);
9456
+ }
9457
+ }
9458
+ return ids;
9459
+ }, [allTasks]);
9460
+ const nestingDepthMap = (0, import_react15.useMemo)(() => {
9461
+ const depthMap = /* @__PURE__ */ new Map();
9462
+ const taskById = new Map(allTasks.map((task) => [task.id, task]));
9463
+ const getDepth = (taskId, seen = /* @__PURE__ */ new Set()) => {
9464
+ if (depthMap.has(taskId)) return depthMap.get(taskId);
9465
+ if (seen.has(taskId)) return 0;
9466
+ const task = taskById.get(taskId);
9467
+ if (!task?.parentId || !taskById.has(task.parentId)) {
9468
+ depthMap.set(taskId, 0);
9469
+ return 0;
9470
+ }
9471
+ seen.add(taskId);
9472
+ const depth = getDepth(task.parentId, seen) + 1;
9473
+ depthMap.set(taskId, depth);
9474
+ return depth;
9475
+ };
9476
+ for (const task of allTasks) {
9477
+ getDepth(task.id);
9478
+ }
9479
+ return depthMap;
9480
+ }, [allTasks]);
9481
+ return /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { className: "gantt-mx-root", style: { width: `${totalWidth}px` }, children: [
9482
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)("div", { className: "gantt-mx-header", style: { height: `${headerHeight}px` }, children: [
9483
+ hasGroupHeader && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9484
+ "div",
9485
+ {
9486
+ className: "gantt-mx-headerRow gantt-mx-headerGroupRow",
9487
+ style: { gridTemplateColumns: headerSpans.map((span) => `${span.width}px`).join(" "), height: `${topRowHeight}px` },
9488
+ children: headerSpans.map((span) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { className: joinClasses("gantt-mx-groupCell", span.className), children: span.header }, span.id))
9489
+ }
9490
+ ),
9491
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9492
+ "div",
9493
+ {
9494
+ className: "gantt-mx-headerRow",
9495
+ style: { gridTemplateColumns, height: `${hasGroupHeader ? bottomRowHeight : topRowHeight}px` },
9496
+ children: columns.map((column) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9497
+ "div",
9498
+ {
9499
+ className: joinClasses(
9500
+ "gantt-mx-headerCell",
9501
+ column.headerClassName
9502
+ ),
9503
+ children: column.header
9504
+ },
9505
+ column.id
9506
+ ))
9507
+ }
9508
+ )
9509
+ ] }),
9510
+ /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9511
+ "div",
9512
+ {
9513
+ className: "gantt-mx-body",
9514
+ style: { height: `${tasks.length * rowHeight}px` },
9515
+ children: tasks.map((task, index) => {
9516
+ const isHighlighted = filterMode === "highlight" && !!highlightedTaskIds?.has(task.id);
9517
+ const isParent = parentTaskIds.has(task.id);
9518
+ const nestingDepth = nestingDepthMap.get(task.id) ?? 0;
9519
+ const rowFillLevel = Math.min(nestingDepth, 2);
9520
+ const isTotal = Boolean(task.isTotal);
9521
+ return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9522
+ "div",
9523
+ {
9524
+ "data-gantt-task-row-id": task.id,
9525
+ className: joinClasses(
9526
+ "gantt-mx-row",
9527
+ task.parentId && "gantt-mx-row-child",
9528
+ isParent && "gantt-mx-row-parent",
9529
+ `gantt-mx-row-level-${rowFillLevel}`,
9530
+ isTotal && "gantt-mx-row-total",
9531
+ selectedTaskId === task.id && "gantt-mx-row-selected",
9532
+ isHighlighted && "gantt-mx-row-highlighted"
9533
+ ),
9534
+ style: {
9535
+ gridTemplateColumns,
9536
+ top: `${index * rowHeight}px`,
9537
+ height: `${rowHeight}px`
9538
+ },
9539
+ onClick: () => onTaskSelect?.(task.id),
9540
+ children: columns.map((column, columnIndex) => {
9541
+ const resolvedCellClassName = typeof column.cellClassName === "function" ? column.cellClassName(task) : column.cellClassName;
9542
+ return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9543
+ "div",
9544
+ {
9545
+ className: joinClasses(
9546
+ "gantt-mx-cell",
9547
+ onCellClick && "gantt-mx-cell-clickable",
9548
+ `gantt-mx-cellAlign-${column.align ?? "right"}`,
9549
+ column.className,
9550
+ resolvedCellClassName
9551
+ ),
9552
+ onClick: (event) => {
9553
+ onCellClick?.({ task, column, rowIndex: index, columnIndex, event });
9554
+ },
9555
+ children: column.renderCell(task)
9556
+ },
9557
+ `${task.id}:${column.id}`
9558
+ );
9559
+ })
9560
+ },
9561
+ task.id
9562
+ );
9563
+ })
9564
+ }
9565
+ )
9566
+ ] });
9567
+ }
9568
+
9238
9569
  // src/components/GanttChart/print.ts
9239
9570
  function getPrintDocumentTitle({
9240
9571
  header,
@@ -9573,13 +9904,13 @@ async function printGanttChart({
9573
9904
  }
9574
9905
 
9575
9906
  // src/components/GanttChart/GanttChart.tsx
9576
- var import_jsx_runtime16 = require("react/jsx-runtime");
9907
+ var import_jsx_runtime17 = require("react/jsx-runtime");
9577
9908
  var SCROLL_TO_ROW_CONTEXT_ROWS = 2;
9578
9909
  function GanttChartInner(props, ref) {
9579
9910
  if (props.mode === "resource-planner") {
9580
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(ResourceTimelineChart, { ...props });
9911
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(ResourceTimelineChart, { ...props });
9581
9912
  }
9582
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
9913
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
9583
9914
  TaskGanttChart,
9584
9915
  {
9585
9916
  ...props,
@@ -9588,9 +9919,9 @@ function GanttChartInner(props, ref) {
9588
9919
  );
9589
9920
  }
9590
9921
  function TaskGanttChartInner(props, ref) {
9922
+ const isTableMatrixMode = props.mode === "table-matrix";
9591
9923
  const {
9592
9924
  tasks,
9593
- dayWidth = 40,
9594
9925
  rowHeight = 40,
9595
9926
  headerHeight = 40,
9596
9927
  containerHeight,
@@ -9614,10 +9945,6 @@ function TaskGanttChartInner(props, ref) {
9614
9945
  onUngroupTask,
9615
9946
  enableAddTask = true,
9616
9947
  defaultTaskDurationDays,
9617
- viewMode = "day",
9618
- customDays,
9619
- isWeekend: isWeekend3,
9620
- businessDays = true,
9621
9948
  taskFilter,
9622
9949
  filterMode = "highlight",
9623
9950
  collapsedParentIds: externalCollapsedParentIds,
@@ -9631,28 +9958,43 @@ function TaskGanttChartInner(props, ref) {
9631
9958
  additionalColumns,
9632
9959
  hiddenTaskListColumns,
9633
9960
  taskListMenuCommands,
9961
+ hideTaskListRowActions = false,
9962
+ rowContentLines = 1,
9634
9963
  taskDateChangeMode: externalTaskDateChangeMode,
9635
9964
  onTaskDateChangeModeChange: externalOnTaskDateChangeModeChange
9636
9965
  } = props;
9637
- const containerRef = (0, import_react15.useRef)(null);
9638
- const scrollContainerRef = (0, import_react15.useRef)(null);
9639
- const scrollContentRef = (0, import_react15.useRef)(null);
9640
- const clearSelectedTaskTimeoutRef = (0, import_react15.useRef)(null);
9641
- const [selectedTaskId, setSelectedTaskId] = (0, import_react15.useState)(null);
9642
- const [taskListHasRightShadow, setTaskListHasRightShadow] = (0, import_react15.useState)(false);
9643
- const [internalTaskDateChangeMode, setInternalTaskDateChangeMode] = (0, import_react15.useState)("preserve-duration");
9644
- const [selectedChip, setSelectedChip] = (0, import_react15.useState)(null);
9645
- const [internalCollapsedParentIds, setInternalCollapsedParentIds] = (0, import_react15.useState)(/* @__PURE__ */ new Set());
9966
+ const dayWidth = !isTableMatrixMode ? props.dayWidth ?? 40 : 40;
9967
+ const viewMode = !isTableMatrixMode ? props.viewMode ?? "day" : "day";
9968
+ const customDays = !isTableMatrixMode ? props.customDays : void 0;
9969
+ const isWeekend3 = !isTableMatrixMode ? props.isWeekend : void 0;
9970
+ const businessDays = !isTableMatrixMode ? props.businessDays ?? true : true;
9971
+ const matrixColumns = isTableMatrixMode ? props.matrixColumns : [];
9972
+ const matrixColumnGroups = isTableMatrixMode ? props.matrixColumnGroups : void 0;
9973
+ const onMatrixCellClick = isTableMatrixMode ? props.onMatrixCellClick : void 0;
9974
+ const containerRef = (0, import_react16.useRef)(null);
9975
+ const scrollContainerRef = (0, import_react16.useRef)(null);
9976
+ const scrollContentRef = (0, import_react16.useRef)(null);
9977
+ const clearSelectedTaskTimeoutRef = (0, import_react16.useRef)(null);
9978
+ const [selectedTaskId, setSelectedTaskId] = (0, import_react16.useState)(null);
9979
+ const [taskListHasRightShadow, setTaskListHasRightShadow] = (0, import_react16.useState)(false);
9980
+ const [internalTaskDateChangeMode, setInternalTaskDateChangeMode] = (0, import_react16.useState)("preserve-duration");
9981
+ const [selectedChip, setSelectedChip] = (0, import_react16.useState)(null);
9982
+ const [internalCollapsedParentIds, setInternalCollapsedParentIds] = (0, import_react16.useState)(/* @__PURE__ */ new Set());
9646
9983
  const collapsedParentIds = externalCollapsedParentIds ?? internalCollapsedParentIds;
9647
- const [editingTaskId, setEditingTaskId] = (0, import_react15.useState)(null);
9984
+ const [editingTaskId, setEditingTaskId] = (0, import_react16.useState)(null);
9648
9985
  const taskDateChangeMode = externalTaskDateChangeMode ?? internalTaskDateChangeMode;
9649
9986
  const handleTaskDateChangeMode = externalOnTaskDateChangeModeChange ?? setInternalTaskDateChangeMode;
9650
- const normalizedTasks = (0, import_react15.useMemo)(() => normalizeHierarchyTasks(tasks), [tasks]);
9651
- const isCustomWeekend = (0, import_react15.useMemo)(
9987
+ const resolvedRowContentLines = Math.max(1, Math.floor(rowContentLines));
9988
+ const effectiveRowHeight = (0, import_react16.useMemo)(
9989
+ () => Math.max(rowHeight, 10 + resolvedRowContentLines * 18),
9990
+ [resolvedRowContentLines, rowHeight]
9991
+ );
9992
+ const normalizedTasks = (0, import_react16.useMemo)(() => normalizeHierarchyTasks(tasks), [tasks]);
9993
+ const isCustomWeekend = (0, import_react16.useMemo)(
9652
9994
  () => createCustomDayPredicate({ customDays, isWeekend: isWeekend3 }),
9653
9995
  [customDays, isWeekend3]
9654
9996
  );
9655
- const dateRangeTasks = (0, import_react15.useMemo)(() => {
9997
+ const dateRangeTasks = (0, import_react16.useMemo)(() => {
9656
9998
  if (!showBaseline) {
9657
9999
  return normalizedTasks;
9658
10000
  }
@@ -9662,14 +10004,18 @@ function TaskGanttChartInner(props, ref) {
9662
10004
  endDate: task.baselineEndDate && parseUTCDate(task.baselineEndDate).getTime() > parseUTCDate(task.endDate).getTime() ? task.baselineEndDate : task.endDate
9663
10005
  }));
9664
10006
  }, [normalizedTasks, showBaseline]);
9665
- const dateRange = (0, import_react15.useMemo)(() => getMultiMonthDays(dateRangeTasks), [dateRangeTasks]);
9666
- const [validationResult, setValidationResult] = (0, import_react15.useState)(null);
9667
- const [cascadeOverrides, setCascadeOverrides] = (0, import_react15.useState)(/* @__PURE__ */ new Map());
9668
- const gridWidth = (0, import_react15.useMemo)(
10007
+ const dateRange = (0, import_react16.useMemo)(() => getMultiMonthDays(dateRangeTasks), [dateRangeTasks]);
10008
+ const [validationResult, setValidationResult] = (0, import_react16.useState)(null);
10009
+ const [cascadeOverrides, setCascadeOverrides] = (0, import_react16.useState)(/* @__PURE__ */ new Map());
10010
+ const gridWidth = (0, import_react16.useMemo)(
9669
10011
  () => Math.round(dateRange.length * dayWidth),
9670
10012
  [dateRange.length, dayWidth]
9671
10013
  );
9672
- const visibleTasks = (0, import_react15.useMemo)(() => {
10014
+ const matrixWidth = (0, import_react16.useMemo)(
10015
+ () => matrixColumns.reduce((sum, column) => sum + column.width, 0),
10016
+ [matrixColumns]
10017
+ );
10018
+ const visibleTasks = (0, import_react16.useMemo)(() => {
9673
10019
  const parentMap = new Map(normalizedTasks.map((t) => [t.id, t.parentId]));
9674
10020
  function isAnyAncestorCollapsed(parentId) {
9675
10021
  let current = parentId;
@@ -9685,11 +10031,11 @@ function TaskGanttChartInner(props, ref) {
9685
10031
  }
9686
10032
  return tasks2;
9687
10033
  }, [normalizedTasks, collapsedParentIds, filterMode, taskFilter]);
9688
- const matchedTaskIds = (0, import_react15.useMemo)(() => {
10034
+ const matchedTaskIds = (0, import_react16.useMemo)(() => {
9689
10035
  if (!taskFilter) return /* @__PURE__ */ new Set();
9690
10036
  return new Set(visibleTasks.filter(taskFilter).map((task) => task.id));
9691
10037
  }, [visibleTasks, taskFilter]);
9692
- const taskListHighlightedTaskIds = (0, import_react15.useMemo)(() => {
10038
+ const taskListHighlightedTaskIds = (0, import_react16.useMemo)(() => {
9693
10039
  if (filterMode === "hide") {
9694
10040
  return /* @__PURE__ */ new Set();
9695
10041
  }
@@ -9700,24 +10046,25 @@ function TaskGanttChartInner(props, ref) {
9700
10046
  matchedTaskIds.forEach((taskId) => mergedHighlightedTaskIds.add(taskId));
9701
10047
  return mergedHighlightedTaskIds;
9702
10048
  }, [filterMode, highlightedTaskIds, matchedTaskIds]);
9703
- const totalGridHeight = (0, import_react15.useMemo)(
9704
- () => visibleTasks.length * rowHeight,
9705
- [visibleTasks.length, rowHeight]
10049
+ const totalGridHeight = (0, import_react16.useMemo)(
10050
+ () => visibleTasks.length * effectiveRowHeight,
10051
+ [effectiveRowHeight, visibleTasks.length]
9706
10052
  );
9707
10053
  const timelineHeaderHeight = headerHeight + 1;
9708
- const monthStart = (0, import_react15.useMemo)(() => {
10054
+ const monthStart = (0, import_react16.useMemo)(() => {
9709
10055
  if (dateRange.length === 0) {
9710
10056
  return new Date(Date.UTC((/* @__PURE__ */ new Date()).getUTCFullYear(), (/* @__PURE__ */ new Date()).getUTCMonth(), 1));
9711
10057
  }
9712
10058
  const firstDay = dateRange[0];
9713
10059
  return new Date(Date.UTC(firstDay.getUTCFullYear(), firstDay.getUTCMonth(), 1));
9714
10060
  }, [dateRange]);
9715
- const todayInRange = (0, import_react15.useMemo)(() => {
10061
+ const todayInRange = (0, import_react16.useMemo)(() => {
9716
10062
  const now = /* @__PURE__ */ new Date();
9717
10063
  const today = new Date(Date.UTC(now.getUTCFullYear(), now.getUTCMonth(), now.getUTCDate()));
9718
10064
  return dateRange.some((day) => day.getTime() === today.getTime());
9719
10065
  }, [dateRange]);
9720
- (0, import_react15.useEffect)(() => {
10066
+ (0, import_react16.useEffect)(() => {
10067
+ if (isTableMatrixMode) return;
9721
10068
  const container = scrollContainerRef.current;
9722
10069
  if (!container || dateRange.length === 0) return;
9723
10070
  const now = /* @__PURE__ */ new Date();
@@ -9728,8 +10075,8 @@ function TaskGanttChartInner(props, ref) {
9728
10075
  const containerWidth = container.clientWidth;
9729
10076
  const scrollLeft = Math.round(todayOffset + dayWidth / 2 - containerWidth * 0.3);
9730
10077
  container.scrollLeft = Math.max(0, scrollLeft);
9731
- }, []);
9732
- (0, import_react15.useEffect)(() => {
10078
+ }, [dateRange, dayWidth, isTableMatrixMode]);
10079
+ (0, import_react16.useEffect)(() => {
9733
10080
  const container = scrollContainerRef.current;
9734
10081
  if (!container) return;
9735
10082
  const updateShadow = () => {
@@ -9741,7 +10088,8 @@ function TaskGanttChartInner(props, ref) {
9741
10088
  container.removeEventListener("scroll", updateShadow);
9742
10089
  };
9743
10090
  }, []);
9744
- const scrollToToday = (0, import_react15.useCallback)(() => {
10091
+ const scrollToToday = (0, import_react16.useCallback)(() => {
10092
+ if (isTableMatrixMode) return;
9745
10093
  const container = scrollContainerRef.current;
9746
10094
  if (!container || dateRange.length === 0) return;
9747
10095
  const now = /* @__PURE__ */ new Date();
@@ -9752,8 +10100,18 @@ function TaskGanttChartInner(props, ref) {
9752
10100
  const containerWidth = container.clientWidth;
9753
10101
  const scrollLeft = Math.round(todayOffset + dayWidth / 2 - containerWidth * 0.3);
9754
10102
  container.scrollTo({ left: Math.max(0, scrollLeft), behavior: "smooth" });
9755
- }, [dateRange, dayWidth]);
9756
- const scrollToTask = (0, import_react15.useCallback)((taskId) => {
10103
+ }, [dateRange, dayWidth, isTableMatrixMode]);
10104
+ const scrollToTask = (0, import_react16.useCallback)((taskId) => {
10105
+ if (isTableMatrixMode) {
10106
+ const container2 = scrollContainerRef.current;
10107
+ if (!container2) return;
10108
+ const rowIndex = visibleTasks.findIndex((visibleTask) => visibleTask.id === taskId);
10109
+ if (rowIndex === -1) return;
10110
+ const paddedRowIndex = Math.max(0, rowIndex - SCROLL_TO_ROW_CONTEXT_ROWS);
10111
+ container2.scrollTo({ top: Math.max(0, effectiveRowHeight * paddedRowIndex), behavior: "smooth" });
10112
+ setSelectedTaskId(taskId);
10113
+ return;
10114
+ }
9757
10115
  const container = scrollContainerRef.current;
9758
10116
  if (!container || dateRange.length === 0) return;
9759
10117
  const task = tasks.find((t) => t.id === taskId);
@@ -9769,8 +10127,8 @@ function TaskGanttChartInner(props, ref) {
9769
10127
  const taskOffset = taskIndex * dayWidth;
9770
10128
  const scrollLeft = Math.round(taskOffset - dayWidth * 2);
9771
10129
  container.scrollTo({ left: Math.max(0, scrollLeft), behavior: "smooth" });
9772
- }, [tasks, dateRange, dayWidth]);
9773
- const scrollToRow = (0, import_react15.useCallback)((taskId, options = {}) => {
10130
+ }, [dateRange, dayWidth, effectiveRowHeight, isTableMatrixMode, tasks, visibleTasks]);
10131
+ const scrollToRow = (0, import_react16.useCallback)((taskId, options = {}) => {
9774
10132
  const container = scrollContainerRef.current;
9775
10133
  if (!container) return;
9776
10134
  const task = tasks.find((t) => t.id === taskId);
@@ -9778,7 +10136,7 @@ function TaskGanttChartInner(props, ref) {
9778
10136
  const rowIndex = visibleTasks.findIndex((visibleTask) => visibleTask.id === task.id);
9779
10137
  if (rowIndex === -1) return;
9780
10138
  const paddedRowIndex = Math.max(0, rowIndex - SCROLL_TO_ROW_CONTEXT_ROWS);
9781
- const scrollTop = Math.max(0, rowHeight * paddedRowIndex);
10139
+ const scrollTop = Math.max(0, effectiveRowHeight * paddedRowIndex);
9782
10140
  const {
9783
10141
  select = true,
9784
10142
  behavior = "smooth",
@@ -9798,21 +10156,21 @@ function TaskGanttChartInner(props, ref) {
9798
10156
  }
9799
10157
  }
9800
10158
  container.scrollTo({ top: scrollTop, behavior });
9801
- }, [tasks, visibleTasks, rowHeight]);
9802
- const [dragGuideLines, setDragGuideLines] = (0, import_react15.useState)(null);
9803
- const [draggedTaskOverride, setDraggedTaskOverride] = (0, import_react15.useState)(null);
9804
- const [previewTasksById, setPreviewTasksById] = (0, import_react15.useState)(/* @__PURE__ */ new Map());
9805
- (0, import_react15.useEffect)(() => {
10159
+ }, [effectiveRowHeight, tasks, visibleTasks]);
10160
+ const [dragGuideLines, setDragGuideLines] = (0, import_react16.useState)(null);
10161
+ const [draggedTaskOverride, setDraggedTaskOverride] = (0, import_react16.useState)(null);
10162
+ const [previewTasksById, setPreviewTasksById] = (0, import_react16.useState)(/* @__PURE__ */ new Map());
10163
+ (0, import_react16.useEffect)(() => {
9806
10164
  const result = validateDependencies(tasks);
9807
10165
  setValidationResult(result);
9808
10166
  onValidateDependencies?.(result);
9809
10167
  }, [tasks, onValidateDependencies]);
9810
- (0, import_react15.useEffect)(() => () => {
10168
+ (0, import_react16.useEffect)(() => () => {
9811
10169
  if (clearSelectedTaskTimeoutRef.current !== null) {
9812
10170
  window.clearTimeout(clearSelectedTaskTimeoutRef.current);
9813
10171
  }
9814
10172
  }, []);
9815
- const handleTaskChange = (0, import_react15.useCallback)((updatedTasks) => {
10173
+ const handleTaskChange = (0, import_react16.useCallback)((updatedTasks) => {
9816
10174
  const updatedTask = updatedTasks[0];
9817
10175
  if (!updatedTask) return;
9818
10176
  const originalTask = tasks.find((t) => t.id === updatedTask.id);
@@ -9858,7 +10216,7 @@ function TaskGanttChartInner(props, ref) {
9858
10216
  const cascadedTasks = disableConstraints ? [updatedTask] : universalCascade(updatedTask, newStart, newEnd, sourceTasks, businessDays, isCustomWeekend);
9859
10217
  onTasksChange?.(cascadedTasks);
9860
10218
  }, [tasks, onTasksChange, disableConstraints, editingTaskId, businessDays, isCustomWeekend]);
9861
- const handleDelete = (0, import_react15.useCallback)((taskId) => {
10219
+ const handleDelete = (0, import_react16.useCallback)((taskId) => {
9862
10220
  const toDelete = /* @__PURE__ */ new Set([taskId]);
9863
10221
  function collectDescendants(parentId) {
9864
10222
  const children = getChildren(parentId, tasks);
@@ -9883,10 +10241,10 @@ function TaskGanttChartInner(props, ref) {
9883
10241
  }
9884
10242
  toDelete.forEach((id) => onDelete?.(id));
9885
10243
  }, [tasks, onTasksChange, onDelete]);
9886
- const handleInsertAfter = (0, import_react15.useCallback)((taskId, newTask) => {
10244
+ const handleInsertAfter = (0, import_react16.useCallback)((taskId, newTask) => {
9887
10245
  onInsertAfter?.(taskId, newTask);
9888
10246
  }, [onInsertAfter]);
9889
- const handleReorder = (0, import_react15.useCallback)((reorderedTasks, movedTaskId, inferredParentId) => {
10247
+ const handleReorder = (0, import_react16.useCallback)((reorderedTasks, movedTaskId, inferredParentId) => {
9890
10248
  let updated = reorderedTasks;
9891
10249
  if (movedTaskId) {
9892
10250
  updated = updated.map((t) => {
@@ -9903,7 +10261,7 @@ function TaskGanttChartInner(props, ref) {
9903
10261
  }
9904
10262
  onTasksChange?.(normalized);
9905
10263
  }, [onTasksChange, onReorder]);
9906
- const dependencyOverrides = (0, import_react15.useMemo)(() => {
10264
+ const dependencyOverrides = (0, import_react16.useMemo)(() => {
9907
10265
  const map = new Map(cascadeOverrides);
9908
10266
  if (draggedTaskOverride) {
9909
10267
  map.set(draggedTaskOverride.taskId, {
@@ -9913,32 +10271,32 @@ function TaskGanttChartInner(props, ref) {
9913
10271
  }
9914
10272
  return map;
9915
10273
  }, [cascadeOverrides, draggedTaskOverride]);
9916
- const handleCascadeProgress = (0, import_react15.useCallback)((overrides, previewTasks = []) => {
10274
+ const handleCascadeProgress = (0, import_react16.useCallback)((overrides, previewTasks = []) => {
9917
10275
  setCascadeOverrides(new Map(overrides));
9918
10276
  setPreviewTasksById(new Map(previewTasks.map((task) => [task.id, task])));
9919
10277
  }, []);
9920
- const previewNormalizedTasks = (0, import_react15.useMemo)(() => {
10278
+ const previewNormalizedTasks = (0, import_react16.useMemo)(() => {
9921
10279
  if (previewTasksById.size === 0) return normalizedTasks;
9922
10280
  return normalizedTasks.map((task) => previewTasksById.get(task.id) ?? task);
9923
10281
  }, [normalizedTasks, previewTasksById]);
9924
- const previewVisibleTasks = (0, import_react15.useMemo)(() => {
10282
+ const previewVisibleTasks = (0, import_react16.useMemo)(() => {
9925
10283
  if (previewTasksById.size === 0) return visibleTasks;
9926
10284
  return visibleTasks.map((task) => previewTasksById.get(task.id) ?? task);
9927
10285
  }, [visibleTasks, previewTasksById]);
9928
- const handleCascade = (0, import_react15.useCallback)((cascadedTasks) => {
10286
+ const handleCascade = (0, import_react16.useCallback)((cascadedTasks) => {
9929
10287
  onTasksChange?.(cascadedTasks);
9930
10288
  }, [tasks, onTasksChange]);
9931
- const handleTaskSelect = (0, import_react15.useCallback)((taskId) => {
10289
+ const handleTaskSelect = (0, import_react16.useCallback)((taskId) => {
9932
10290
  setSelectedTaskId(taskId);
9933
10291
  }, []);
9934
- const hoveredRowElementsRef = (0, import_react15.useRef)([]);
9935
- const clearHoveredRows = (0, import_react15.useCallback)(() => {
10292
+ const hoveredRowElementsRef = (0, import_react16.useRef)([]);
10293
+ const clearHoveredRows = (0, import_react16.useCallback)(() => {
9936
10294
  for (const element of hoveredRowElementsRef.current) {
9937
- element.classList.remove("gantt-tl-row-hovered", "gantt-tr-row-hovered");
10295
+ element.classList.remove("gantt-tl-row-hovered", "gantt-tr-row-hovered", "gantt-mx-row-hovered");
9938
10296
  }
9939
10297
  hoveredRowElementsRef.current = [];
9940
10298
  }, []);
9941
- const applyHoveredRows = (0, import_react15.useCallback)((taskId) => {
10299
+ const applyHoveredRows = (0, import_react16.useCallback)((taskId) => {
9942
10300
  const root = scrollContentRef.current;
9943
10301
  if (!root) return;
9944
10302
  clearHoveredRows();
@@ -9952,10 +10310,13 @@ function TaskGanttChartInner(props, ref) {
9952
10310
  if (element.classList.contains("gantt-tr-row")) {
9953
10311
  element.classList.add("gantt-tr-row-hovered");
9954
10312
  }
10313
+ if (element.classList.contains("gantt-mx-row")) {
10314
+ element.classList.add("gantt-mx-row-hovered");
10315
+ }
9955
10316
  }
9956
10317
  hoveredRowElementsRef.current = nextHoveredRows;
9957
10318
  }, [clearHoveredRows]);
9958
- const handleSharedRowHover = (0, import_react15.useCallback)((event) => {
10319
+ const handleSharedRowHover = (0, import_react16.useCallback)((event) => {
9959
10320
  const target = event.target;
9960
10321
  const row = target.closest("[data-gantt-task-row-id]");
9961
10322
  const taskId = row?.dataset.ganttTaskRowId;
@@ -9965,7 +10326,7 @@ function TaskGanttChartInner(props, ref) {
9965
10326
  }
9966
10327
  applyHoveredRows(taskId);
9967
10328
  }, [applyHoveredRows]);
9968
- const handleToggleCollapse = externalOnToggleCollapse ?? (0, import_react15.useCallback)((parentId) => {
10329
+ const handleToggleCollapse = externalOnToggleCollapse ?? (0, import_react16.useCallback)((parentId) => {
9969
10330
  setInternalCollapsedParentIds((prev) => {
9970
10331
  const next = new Set(prev);
9971
10332
  if (next.has(parentId)) {
@@ -9976,20 +10337,20 @@ function TaskGanttChartInner(props, ref) {
9976
10337
  return next;
9977
10338
  });
9978
10339
  }, []);
9979
- const allParentIds = (0, import_react15.useMemo)(() => {
10340
+ const allParentIds = (0, import_react16.useMemo)(() => {
9980
10341
  return new Set(
9981
10342
  normalizedTasks.filter((t) => isTaskParent(t.id, normalizedTasks)).map((t) => t.id)
9982
10343
  );
9983
10344
  }, [normalizedTasks]);
9984
- const handleCollapseAll = (0, import_react15.useCallback)(() => {
10345
+ const handleCollapseAll = (0, import_react16.useCallback)(() => {
9985
10346
  if (externalCollapsedParentIds) return;
9986
10347
  setInternalCollapsedParentIds(allParentIds);
9987
10348
  }, [allParentIds, externalCollapsedParentIds]);
9988
- const handleExpandAll = (0, import_react15.useCallback)(() => {
10349
+ const handleExpandAll = (0, import_react16.useCallback)(() => {
9989
10350
  if (externalCollapsedParentIds) return;
9990
10351
  setInternalCollapsedParentIds(/* @__PURE__ */ new Set());
9991
10352
  }, [externalCollapsedParentIds]);
9992
- const exportToPdf = (0, import_react15.useCallback)(async (options) => {
10353
+ const exportToPdf = (0, import_react16.useCallback)(async (options) => {
9993
10354
  const sourceContainer = containerRef.current;
9994
10355
  const sourceContent = scrollContentRef.current;
9995
10356
  if (!sourceContainer || !sourceContent || typeof window === "undefined" || typeof document === "undefined") {
@@ -10025,7 +10386,7 @@ function TaskGanttChartInner(props, ref) {
10025
10386
  orientation: options?.orientation
10026
10387
  });
10027
10388
  }, [showTaskList, showChart]);
10028
- (0, import_react15.useImperativeHandle)(
10389
+ (0, import_react16.useImperativeHandle)(
10029
10390
  ref,
10030
10391
  () => ({
10031
10392
  scrollToToday,
@@ -10048,7 +10409,7 @@ function TaskGanttChartInner(props, ref) {
10048
10409
  }
10049
10410
  return depth;
10050
10411
  }
10051
- const handlePromoteTask = (0, import_react15.useCallback)((taskId) => {
10412
+ const handlePromoteTask = (0, import_react16.useCallback)((taskId) => {
10052
10413
  if (onPromoteTask) {
10053
10414
  onPromoteTask(taskId);
10054
10415
  return;
@@ -10078,7 +10439,7 @@ function TaskGanttChartInner(props, ref) {
10078
10439
  ]);
10079
10440
  onTasksChange?.(reorderedTasks);
10080
10441
  }, [tasks, onTasksChange, onPromoteTask]);
10081
- const handleDemoteTask = (0, import_react15.useCallback)((taskId, newParentId) => {
10442
+ const handleDemoteTask = (0, import_react16.useCallback)((taskId, newParentId) => {
10082
10443
  if (onDemoteTask) {
10083
10444
  onDemoteTask(taskId, newParentId);
10084
10445
  return;
@@ -10119,7 +10480,7 @@ function TaskGanttChartInner(props, ref) {
10119
10480
  };
10120
10481
  onTasksChange?.([updatedDemotedTask]);
10121
10482
  }, [tasks, onTasksChange, onDemoteTask]);
10122
- const handleUngroupTask = (0, import_react15.useCallback)((taskId) => {
10483
+ const handleUngroupTask = (0, import_react16.useCallback)((taskId) => {
10123
10484
  if (onUngroupTask) {
10124
10485
  onUngroupTask(taskId);
10125
10486
  return;
@@ -10144,8 +10505,8 @@ function TaskGanttChartInner(props, ref) {
10144
10505
  onTasksChange?.(changedTasks);
10145
10506
  }
10146
10507
  }, [tasks, onTasksChange, onUngroupTask]);
10147
- const panStateRef = (0, import_react15.useRef)(null);
10148
- const handlePanStart = (0, import_react15.useCallback)((e) => {
10508
+ const panStateRef = (0, import_react16.useRef)(null);
10509
+ const handlePanStart = (0, import_react16.useCallback)((e) => {
10149
10510
  if (e.button !== 0) return;
10150
10511
  const target = e.target;
10151
10512
  if (target.closest("[data-taskbar]")) return;
@@ -10166,7 +10527,7 @@ function TaskGanttChartInner(props, ref) {
10166
10527
  container.style.cursor = "grabbing";
10167
10528
  e.preventDefault();
10168
10529
  }, []);
10169
- (0, import_react15.useEffect)(() => {
10530
+ (0, import_react16.useEffect)(() => {
10170
10531
  const handlePanMove = (e) => {
10171
10532
  const pan = panStateRef.current;
10172
10533
  if (!pan?.active) return;
@@ -10188,190 +10549,219 @@ function TaskGanttChartInner(props, ref) {
10188
10549
  window.removeEventListener("mouseup", handlePanEnd);
10189
10550
  };
10190
10551
  }, []);
10191
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { ref: containerRef, className: "gantt-container", children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10552
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10192
10553
  "div",
10193
10554
  {
10194
- ref: scrollContainerRef,
10195
- className: "gantt-scrollContainer",
10196
- style: { height: containerHeight ?? "auto", cursor: "grab" },
10197
- onMouseDown: handlePanStart,
10198
- children: /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)(
10555
+ ref: containerRef,
10556
+ className: isTableMatrixMode ? "gantt-container gantt-container-tableMatrix" : "gantt-container",
10557
+ children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10199
10558
  "div",
10200
10559
  {
10201
- ref: scrollContentRef,
10202
- className: "gantt-scrollContent",
10203
- onMouseOver: handleSharedRowHover,
10204
- onMouseLeave: clearHoveredRows,
10205
- children: [
10206
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10207
- TaskList,
10208
- {
10209
- tasks: normalizedTasks,
10210
- rowHeight,
10211
- headerHeight,
10212
- taskListWidth,
10213
- onTasksChange: handleTaskChange,
10214
- selectedTaskId: selectedTaskId ?? void 0,
10215
- onTaskSelect: handleTaskSelect,
10216
- show: showTaskList,
10217
- hasRightShadow: taskListHasRightShadow,
10218
- disableTaskNameEditing,
10219
- disableDependencyEditing,
10220
- onScrollToTask: scrollToTask,
10221
- onSelectedChipChange: setSelectedChip,
10222
- onAdd,
10223
- onDelete: handleDelete,
10224
- onInsertAfter: handleInsertAfter,
10225
- onReorder: handleReorder,
10226
- editingTaskId,
10227
- enableAddTask,
10228
- defaultTaskDurationDays,
10229
- collapsedParentIds,
10230
- onToggleCollapse: handleToggleCollapse,
10231
- onPromoteTask: onPromoteTask ?? handlePromoteTask,
10232
- onDemoteTask: onDemoteTask ?? handleDemoteTask,
10233
- onUngroupTask: onUngroupTask ?? handleUngroupTask,
10234
- highlightedTaskIds: taskListHighlightedTaskIds,
10235
- enableTaskMultiSelect,
10236
- selectedTaskIds,
10237
- onSelectedTaskIdsChange,
10238
- customDays,
10239
- isWeekend: isWeekend3,
10240
- businessDays,
10241
- filterMode,
10242
- filteredTaskIds: matchedTaskIds,
10243
- isFilterActive: !!taskFilter,
10244
- additionalColumns,
10245
- hiddenTaskListColumns,
10246
- taskListMenuCommands,
10247
- taskDateChangeMode,
10248
- onTaskDateChangeModeChange: handleTaskDateChangeMode
10249
- }
10250
- ),
10251
- /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)(
10252
- "div",
10253
- {
10254
- className: showChart ? "gantt-chartSurface" : "gantt-chartSurface gantt-chart-hidden",
10255
- style: { minWidth: `${gridWidth}px`, flex: 1, display: showChart ? void 0 : "none" },
10256
- children: [
10257
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10258
- "div",
10259
- {
10260
- className: "gantt-stickyHeader",
10261
- style: { width: `${gridWidth}px`, height: `${timelineHeaderHeight}px` },
10262
- children: /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10263
- TimeScaleHeader_default,
10560
+ ref: scrollContainerRef,
10561
+ className: "gantt-scrollContainer",
10562
+ style: { height: containerHeight ?? "auto", cursor: "grab" },
10563
+ onMouseDown: handlePanStart,
10564
+ children: /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
10565
+ "div",
10566
+ {
10567
+ ref: scrollContentRef,
10568
+ className: "gantt-scrollContent",
10569
+ onMouseOver: handleSharedRowHover,
10570
+ onMouseLeave: clearHoveredRows,
10571
+ children: [
10572
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10573
+ TaskList,
10574
+ {
10575
+ tasks: normalizedTasks,
10576
+ rowHeight: effectiveRowHeight,
10577
+ headerHeight,
10578
+ taskListWidth,
10579
+ onTasksChange: handleTaskChange,
10580
+ selectedTaskId: selectedTaskId ?? void 0,
10581
+ onTaskSelect: handleTaskSelect,
10582
+ show: showTaskList,
10583
+ hasRightShadow: taskListHasRightShadow,
10584
+ disableTaskNameEditing,
10585
+ disableDependencyEditing,
10586
+ onScrollToTask: scrollToTask,
10587
+ onSelectedChipChange: setSelectedChip,
10588
+ onAdd,
10589
+ onDelete: handleDelete,
10590
+ onInsertAfter: handleInsertAfter,
10591
+ onReorder: handleReorder,
10592
+ disableTaskDrag,
10593
+ editingTaskId,
10594
+ enableAddTask,
10595
+ defaultTaskDurationDays,
10596
+ collapsedParentIds,
10597
+ onToggleCollapse: handleToggleCollapse,
10598
+ onPromoteTask: onPromoteTask ?? handlePromoteTask,
10599
+ onDemoteTask: onDemoteTask ?? handleDemoteTask,
10600
+ onUngroupTask: onUngroupTask ?? handleUngroupTask,
10601
+ highlightedTaskIds: taskListHighlightedTaskIds,
10602
+ enableTaskMultiSelect,
10603
+ selectedTaskIds,
10604
+ onSelectedTaskIdsChange,
10605
+ customDays,
10606
+ isWeekend: isWeekend3,
10607
+ businessDays,
10608
+ filterMode,
10609
+ filteredTaskIds: matchedTaskIds,
10610
+ isFilterActive: !!taskFilter,
10611
+ additionalColumns,
10612
+ hiddenTaskListColumns,
10613
+ taskListMenuCommands,
10614
+ hideTaskListRowActions,
10615
+ rowContentLines: resolvedRowContentLines,
10616
+ taskDateChangeMode,
10617
+ onTaskDateChangeModeChange: handleTaskDateChangeMode
10618
+ }
10619
+ ),
10620
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10621
+ "div",
10622
+ {
10623
+ className: isTableMatrixMode || showChart ? "gantt-chartSurface" : "gantt-chartSurface gantt-chart-hidden",
10624
+ style: {
10625
+ minWidth: `${isTableMatrixMode ? matrixWidth : gridWidth}px`,
10626
+ flex: 1,
10627
+ display: isTableMatrixMode || showChart ? void 0 : "none"
10628
+ },
10629
+ children: isTableMatrixMode ? /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10630
+ TableMatrix,
10631
+ {
10632
+ tasks: visibleTasks,
10633
+ allTasks: normalizedTasks,
10634
+ columns: matrixColumns,
10635
+ columnGroups: matrixColumnGroups,
10636
+ rowHeight: effectiveRowHeight,
10637
+ headerHeight: timelineHeaderHeight,
10638
+ selectedTaskId,
10639
+ onTaskSelect: handleTaskSelect,
10640
+ onCellClick: onMatrixCellClick,
10641
+ highlightedTaskIds: taskListHighlightedTaskIds,
10642
+ filterMode
10643
+ }
10644
+ ) : /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(import_jsx_runtime17.Fragment, { children: [
10645
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10646
+ "div",
10264
10647
  {
10265
- days: dateRange,
10266
- dayWidth,
10267
- headerHeight,
10268
- viewMode,
10269
- isCustomWeekend
10648
+ className: "gantt-stickyHeader",
10649
+ style: { width: `${gridWidth}px`, height: `${timelineHeaderHeight}px` },
10650
+ children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10651
+ TimeScaleHeader_default,
10652
+ {
10653
+ days: dateRange,
10654
+ dayWidth,
10655
+ headerHeight,
10656
+ viewMode,
10657
+ isCustomWeekend
10658
+ }
10659
+ )
10270
10660
  }
10271
- )
10272
- }
10273
- ),
10274
- /* @__PURE__ */ (0, import_jsx_runtime16.jsxs)(
10275
- "div",
10276
- {
10277
- className: "gantt-taskArea",
10278
- style: {
10279
- position: "relative",
10280
- width: `${gridWidth}px`
10281
- },
10282
- children: [
10283
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10284
- GridBackground_default,
10285
- {
10286
- dateRange,
10287
- dayWidth,
10288
- totalHeight: totalGridHeight,
10289
- viewMode,
10290
- isCustomWeekend
10291
- }
10292
- ),
10293
- todayInRange && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(TodayIndicator_default, { monthStart, dayWidth }),
10294
- /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10295
- DependencyLines_default,
10296
- {
10297
- tasks: previewVisibleTasks,
10298
- allTasks: previewNormalizedTasks,
10299
- collapsedParentIds,
10300
- monthStart,
10301
- dayWidth,
10302
- rowHeight,
10303
- gridWidth,
10304
- dragOverrides: dependencyOverrides,
10305
- selectedDep: selectedChip,
10306
- businessDays,
10307
- weekendPredicate: isCustomWeekend
10308
- }
10309
- ),
10310
- dragGuideLines && /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10311
- DragGuideLines_default,
10312
- {
10313
- isDragging: dragGuideLines.isDragging,
10314
- dragMode: dragGuideLines.dragMode,
10315
- left: dragGuideLines.left,
10316
- width: dragGuideLines.width,
10317
- totalHeight: totalGridHeight
10318
- }
10319
- ),
10320
- visibleTasks.map((task, index) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
10321
- TaskRow_default,
10322
- {
10323
- task,
10324
- monthStart,
10325
- dayWidth,
10326
- rowHeight,
10327
- onTasksChange: handleTaskChange,
10328
- onDragStateChange: (state) => {
10329
- if (state.isDragging) {
10330
- setDragGuideLines(state);
10331
- setDraggedTaskOverride({ taskId: task.id, left: state.left, width: state.width });
10332
- } else {
10333
- setDragGuideLines(null);
10334
- setDraggedTaskOverride(null);
10335
- }
10336
- },
10337
- rowIndex: index,
10338
- allTasks: normalizedTasks,
10339
- enableAutoSchedule: enableAutoSchedule ?? false,
10340
- disableConstraints: disableConstraints ?? false,
10341
- overridePosition: cascadeOverrides.get(task.id),
10342
- onCascadeProgress: handleCascadeProgress,
10343
- onCascade: handleCascade,
10344
- highlightExpiredTasks,
10345
- showBaseline,
10346
- isFilterMatch: filterMode === "highlight" ? matchedTaskIds.has(task.id) : false,
10347
- businessDays,
10348
- customDays,
10349
- isWeekend: isWeekend3,
10350
- disableTaskDrag,
10351
- viewMode
10661
+ ),
10662
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
10663
+ "div",
10664
+ {
10665
+ className: "gantt-taskArea",
10666
+ style: {
10667
+ position: "relative",
10668
+ width: `${gridWidth}px`
10352
10669
  },
10353
- task.id
10354
- ))
10355
- ]
10356
- }
10357
- )
10358
- ]
10359
- }
10360
- )
10361
- ]
10670
+ children: [
10671
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10672
+ GridBackground_default,
10673
+ {
10674
+ dateRange,
10675
+ dayWidth,
10676
+ totalHeight: totalGridHeight,
10677
+ viewMode,
10678
+ isCustomWeekend
10679
+ }
10680
+ ),
10681
+ todayInRange && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(TodayIndicator_default, { monthStart, dayWidth }),
10682
+ /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10683
+ DependencyLines_default,
10684
+ {
10685
+ tasks: previewVisibleTasks,
10686
+ allTasks: previewNormalizedTasks,
10687
+ collapsedParentIds,
10688
+ monthStart,
10689
+ dayWidth,
10690
+ rowHeight: effectiveRowHeight,
10691
+ gridWidth,
10692
+ dragOverrides: dependencyOverrides,
10693
+ selectedDep: selectedChip,
10694
+ businessDays,
10695
+ weekendPredicate: isCustomWeekend
10696
+ }
10697
+ ),
10698
+ dragGuideLines && /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10699
+ DragGuideLines_default,
10700
+ {
10701
+ isDragging: dragGuideLines.isDragging,
10702
+ dragMode: dragGuideLines.dragMode,
10703
+ left: dragGuideLines.left,
10704
+ width: dragGuideLines.width,
10705
+ totalHeight: totalGridHeight
10706
+ }
10707
+ ),
10708
+ visibleTasks.map((task, index) => /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
10709
+ TaskRow_default,
10710
+ {
10711
+ task,
10712
+ monthStart,
10713
+ dayWidth,
10714
+ rowHeight: effectiveRowHeight,
10715
+ onTasksChange: handleTaskChange,
10716
+ onDragStateChange: (state) => {
10717
+ if (state.isDragging) {
10718
+ setDragGuideLines(state);
10719
+ setDraggedTaskOverride({ taskId: task.id, left: state.left, width: state.width });
10720
+ } else {
10721
+ setDragGuideLines(null);
10722
+ setDraggedTaskOverride(null);
10723
+ }
10724
+ },
10725
+ rowIndex: index,
10726
+ allTasks: normalizedTasks,
10727
+ enableAutoSchedule: enableAutoSchedule ?? false,
10728
+ disableConstraints: disableConstraints ?? false,
10729
+ overridePosition: cascadeOverrides.get(task.id),
10730
+ onCascadeProgress: handleCascadeProgress,
10731
+ onCascade: handleCascade,
10732
+ highlightExpiredTasks,
10733
+ showBaseline,
10734
+ isFilterMatch: filterMode === "highlight" ? matchedTaskIds.has(task.id) : false,
10735
+ businessDays,
10736
+ customDays,
10737
+ isWeekend: isWeekend3,
10738
+ disableTaskDrag,
10739
+ viewMode
10740
+ },
10741
+ task.id
10742
+ ))
10743
+ ]
10744
+ }
10745
+ )
10746
+ ] })
10747
+ }
10748
+ )
10749
+ ]
10750
+ }
10751
+ )
10362
10752
  }
10363
10753
  )
10364
10754
  }
10365
- ) });
10755
+ );
10366
10756
  }
10367
- var TaskGanttChart = (0, import_react15.forwardRef)(TaskGanttChartInner);
10368
- var GanttChart = (0, import_react15.forwardRef)(GanttChartInner);
10757
+ var TaskGanttChart = (0, import_react16.forwardRef)(TaskGanttChartInner);
10758
+ var GanttChart = (0, import_react16.forwardRef)(GanttChartInner);
10369
10759
  GanttChart.displayName = "GanttChart";
10370
10760
 
10371
10761
  // src/components/ui/Button.tsx
10372
- var import_react16 = __toESM(require("react"));
10373
- var import_jsx_runtime17 = require("react/jsx-runtime");
10374
- var Button = import_react16.default.forwardRef(
10762
+ var import_react17 = __toESM(require("react"));
10763
+ var import_jsx_runtime18 = require("react/jsx-runtime");
10764
+ var Button = import_react17.default.forwardRef(
10375
10765
  ({ className, variant = "default", size = "default", children, ...props }, ref) => {
10376
10766
  const classes = [
10377
10767
  "gantt-btn",
@@ -10379,7 +10769,7 @@ var Button = import_react16.default.forwardRef(
10379
10769
  size !== "default" ? `gantt-btn-${size}` : "",
10380
10770
  className || ""
10381
10771
  ].filter(Boolean).join(" ");
10382
- return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("button", { ref, className: classes, ...props, children });
10772
+ return /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("button", { ref, className: classes, ...props, children });
10383
10773
  }
10384
10774
  );
10385
10775
  Button.displayName = "Button";
@@ -10431,6 +10821,7 @@ var nameContains = (substring, caseSensitive = false) => (task) => {
10431
10821
  PopoverContent,
10432
10822
  PopoverTrigger,
10433
10823
  ResourceTimelineChart,
10824
+ TableMatrix,
10434
10825
  TaskList,
10435
10826
  TaskRow,
10436
10827
  TimeScaleHeader,