@ganttloom/gantt-core 0.2.1 → 0.4.3

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/README.md CHANGED
@@ -5,10 +5,13 @@
5
5
 
6
6
  Framework-agnostic Gantt chart engine: layout, SVG rendering, drag/resize/link
7
7
  interactions, grouping, critical path, undo/redo, and more — zero runtime
8
- dependencies. If you're using React, prefer
9
- [`@ganttloom/gantt-react`](../gantt-react); use this package directly if
10
- you're integrating with something else (Vue, Svelte, vanilla JS) or want full
11
- control over the DOM lifecycle.
8
+ dependencies. If you're using React or Vue, prefer
9
+ [`@ganttloom/gantt-react`](../gantt-react) or
10
+ [`@ganttloom/gantt-vue`](../gantt-vue); use this package directly if you're
11
+ integrating with something else (Svelte, vanilla JS) or want full control
12
+ over the DOM lifecycle.
13
+
14
+ ![ganttloom overview — day-view Gantt chart with dependencies, critical path, and baselines](https://raw.githubusercontent.com/santhoshkumarhari/ganttLoom/master/docs/screenshots/overview.png)
12
15
 
13
16
  ## Install
14
17
 
@@ -189,6 +192,30 @@ reorder columns. The chart applies the change to its own internal copy of
189
192
  `columns` immediately (so the drag feels live) and calls back so you can
190
193
  persist it — same pattern as a task drag and `onDateChange`.
191
194
 
195
+ ## Grid column sorting
196
+
197
+ Mark a column `sortable: true` and clicking its header cycles ascending →
198
+ descending → none, with a `▲`/`▼` indicator:
199
+
200
+ ```ts
201
+ new GanttChart(container, tasks, deps, {
202
+ columns: [
203
+ { id: "name", title: "Task", sortable: true },
204
+ { id: "assignee", title: "Assignee", accessor: (t) => t.assignees?.[0]?.name, sortable: true },
205
+ ],
206
+ onSortChange: (sort) => console.log(sort), // { columnId, direction } | null
207
+ });
208
+
209
+ chart.setSort("assignee", "desc"); // or null to clear
210
+ chart.getSort(); // { columnId: "assignee", direction: "desc" } | null
211
+ ```
212
+
213
+ Sorting reorders **siblings at every tree level** by the column's value (via
214
+ `accessor`, or `task.name` for the conventional unaccessored "name" column)
215
+ — the group/parent hierarchy itself is never reshuffled, only the order
216
+ within it. A column with neither `accessor` nor the id `"name"` has nothing
217
+ sortable to read and is a no-op if marked sortable.
218
+
192
219
  ## Task search/filter
193
220
 
194
221
  ```ts
@@ -249,6 +276,39 @@ link fires `onDependencyDblClick` — the engine has no built-in "edit link"
249
276
  popover (keeping with zero-dependency, minimal-UI scope), so build your own
250
277
  and call `chart.updateDependency(...)` (undoable) to apply the result.
251
278
 
279
+ Double-clicking a task bar itself (not a link) fires the separate
280
+ `onTaskDblClick(task)` — also off by default until you supply a handler.
281
+
282
+ ## Filling the viewport at any zoom level
283
+
284
+ A short project at month/year zoom, or a chart with just a handful of
285
+ tasks, naturally renders narrow — the timeline's pixel width is purely a
286
+ function of the task date range and the current zoom, with no awareness of
287
+ how much horizontal space is actually available. Set
288
+ `autoFitToViewport: true` to stretch (never shrink) the timeline so it
289
+ fills the container instead of leaving empty space to the right:
290
+
291
+ ```ts
292
+ new GanttChart(container, tasks, deps, { autoFitToViewport: true });
293
+ ```
294
+
295
+ Re-evaluated on view-mode/task changes and on container resize (via
296
+ `ResizeObserver`). It never applies if the content is already wider than
297
+ the container — that's what normal horizontal scrolling is for. Off by
298
+ default, so upgrading doesn't silently change an existing chart's pixel
299
+ layout for anyone who hasn't opted in.
300
+
301
+ Separately, and always on: a short project at a coarse zoom no longer
302
+ renders as one or two lonely ticks. The visible date range is padded out to
303
+ a sensible minimum column count per zoom level (year: 5, quarter: 4,
304
+ month/week: 6, day: 7, hour: 8), so a 3-month project at year zoom still
305
+ shows a real multi-year timeline instead of a cramped sliver. Wider ranges
306
+ are unaffected — this only ever pads, never trims.
307
+
308
+ The timeline's date header also stays pinned to the top of the chart while
309
+ you scroll a tall task list vertically (it still scrolls horizontally in
310
+ sync with the bars), instead of scrolling out of view along with the rows.
311
+
252
312
  ## Multi-select and bulk actions
253
313
 
254
314
  ```ts
@@ -280,10 +340,39 @@ Dragging the whole task shifts every segment together; resizing an edge
280
340
  only adjusts the first (left) or last (right) segment's outer edge, leaving
281
341
  any gap untouched.
282
342
 
343
+ ## Hover tooltips
344
+
345
+ Every bar shows a floating, CSS-customizable tooltip on hover (name, dates,
346
+ progress, assignees, and `task.notes` if set) — not the browser's native
347
+ `title` tooltip, so it's fully styleable:
348
+
349
+ ```css
350
+ .gantt-tooltip { background: #111827; border-radius: 8px; }
351
+ .gantt-tooltip-title { font-weight: 700; }
352
+ ```
353
+
354
+ For full control over markup, `renderTooltip` works exactly like
355
+ `GanttColumn.render` — return an `HTMLElement` to mount directly, a string
356
+ (rendered as text, never parsed as HTML), or `null`/`undefined` to suppress
357
+ the tooltip for that specific task:
358
+
359
+ ```ts
360
+ new GanttChart(el, tasks, deps, {
361
+ renderTooltip: (task) => {
362
+ if (task.isMilestone) return null; // no tooltip on milestones
363
+ const div = document.createElement("div");
364
+ div.textContent = `${task.name} — ${task.progress ?? 0}%`;
365
+ return div;
366
+ },
367
+ });
368
+ ```
369
+
370
+ Set `showTooltip: false` to disable it entirely.
371
+
283
372
  ## Task notes, auto-color, baseline history, and density presets
284
373
 
285
374
  ```ts
286
- { id: "t1", name: "Ship v2", start, end, notes: "Blocked on legal review" } // hover the bar for a native tooltip
375
+ { id: "t1", name: "Ship v2", start, end, notes: "Blocked on legal review" } // shown as an extra line in the default tooltip
287
376
  ```
288
377
 
289
378
  ```ts
@@ -410,6 +499,8 @@ control, same as any element you'd render yourself:
410
499
  | `.gantt-grid-cell` | A grid body cell |
411
500
  | `.gantt-grid-row` | A grid body row (has a default `:hover` background) |
412
501
  | `.gantt-rename-input` | The inline text input shown while renaming a task |
502
+ | `.gantt-tooltip` | The floating hover tooltip's container (see "Hover tooltips" above) |
503
+ | `.gantt-tooltip-title` / `.gantt-tooltip-row` / `.gantt-tooltip-notes` | Elements inside the *default* tooltip content — irrelevant if you use `renderTooltip` |
413
504
 
414
505
  For example, to make the expand/collapse toggle look like a small round
415
506
  button instead of bare text: