@akcelik/strct 1.0.0 → 1.2.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@akcelik/strct",
3
- "version": "1.0.0",
3
+ "version": "1.2.0",
4
4
  "description": "UIStruct — a standalone Angular component library with a tokenised, multi-palette theme system, built for datacenter / infrastructure management UIs.",
5
5
  "author": "Serkan Akcelik <serkan.akcelik@gmail.com>",
6
6
  "license": "MIT",
@@ -2076,10 +2076,22 @@ interface StrctDatagridLazyState {
2076
2076
  sortKey: string | null;
2077
2077
  sortDir: SortDir;
2078
2078
  }
2079
- /** Persistable user column preferences (widths from resize, hidden from the chooser). */
2079
+ /** Persistable user column preferences (widths from resize, hidden from the
2080
+ * chooser, order from drag-reorder). */
2080
2081
  interface StrctDatagridColumnState {
2081
2082
  widths?: Record<string, number>;
2082
2083
  hidden?: string[];
2084
+ order?: string[];
2085
+ }
2086
+ /** One rendered tbody item: a data row, or a group header. */
2087
+ interface DgItem {
2088
+ row?: StrctRow;
2089
+ group?: {
2090
+ key: unknown;
2091
+ label: string;
2092
+ count: number;
2093
+ collapsed: boolean;
2094
+ };
2083
2095
  }
2084
2096
  /**
2085
2097
  * Marks the expandable-row detail template. The row is the template's implicit
@@ -2200,6 +2212,14 @@ declare class StrctDatagrid {
2200
2212
  readonly stateKey: _angular_core.InputSignal<string | null>;
2201
2213
  /** User column preferences (two-way): widths from resize, hidden from the chooser. */
2202
2214
  readonly columnState: _angular_core.ModelSignal<StrctDatagridColumnState | null>;
2215
+ /** Let the user reorder data columns by dragging their headers. */
2216
+ readonly reorderable: _angular_core.InputSignalWithTransform<boolean, unknown>;
2217
+ /**
2218
+ * Group rows by this column key: the grid renders a collapsible header row
2219
+ * per distinct value (with a count), respecting the current sort within
2220
+ * groups. Paging is bypassed while grouped; not combinable with `virtual`.
2221
+ */
2222
+ readonly groupBy: _angular_core.InputSignal<string | null>;
2203
2223
  /** Emitted when the selection changes. */
2204
2224
  readonly selectionChange: _angular_core.OutputEmitterRef<StrctRow[]>;
2205
2225
  /** Emitted when the refresh button is clicked. */
@@ -2239,8 +2259,24 @@ declare class StrctDatagrid {
2239
2259
  protected readonly paneOpen: _angular_core.Signal<boolean>;
2240
2260
  /** Whether to render the trailing row-actions (kebab) column. */
2241
2261
  protected readonly canActions: _angular_core.Signal<boolean>;
2262
+ /** User-chosen column order (keys); unknown keys keep declared positions. */
2263
+ private readonly columnOrder;
2264
+ /** Declared columns re-arranged by the user's drag order. */
2265
+ private readonly orderedColumns;
2242
2266
  /** Only the first column is shown while the detail pane is open. */
2243
2267
  protected readonly visibleColumns: _angular_core.Signal<StrctDatagridColumn[]>;
2268
+ protected readonly dragKey: _angular_core.WritableSignal<string | null>;
2269
+ protected readonly dropKey: _angular_core.WritableSignal<string | null>;
2270
+ protected onColDragStart(key: string, event: DragEvent): void;
2271
+ protected onColDragOver(key: string, event: DragEvent): void;
2272
+ protected onColDrop(key: string): void;
2273
+ protected onColDragEnd(): void;
2274
+ private readonly collapsedGroups;
2275
+ /** Collapse / expand one group header. */
2276
+ toggleGroup(key: unknown): void;
2277
+ /** What tbody renders: plain (virtual/paged) rows, or groups + their rows. */
2278
+ protected readonly displayItems: _angular_core.Signal<DgItem[]>;
2279
+ protected itemKey(it: DgItem): unknown;
2244
2280
  protected readonly sorted: _angular_core.Signal<StrctRow[]>;
2245
2281
  protected readonly paged: _angular_core.Signal<StrctRow[]>;
2246
2282
  /** Full count for the pager / footer (server total in lazy mode). */
@@ -2284,6 +2320,14 @@ declare class StrctDatagrid {
2284
2320
  * current order (client mode: the full sorted set, not just the page).
2285
2321
  */
2286
2322
  toCSV(): string;
2323
+ /**
2324
+ * The grid as a real .xlsx workbook (dependency-free SpreadsheetML):
2325
+ * header labels + every non-hidden column in the current order, all rows in
2326
+ * the current sort; numeric cells stay numeric.
2327
+ */
2328
+ toXLSX(): Uint8Array;
2329
+ /** Download the grid as an .xlsx file. */
2330
+ downloadXLSX(filename?: string): void;
2287
2331
  /** Download the grid as a CSV file. */
2288
2332
  downloadCSV(filename?: string): void;
2289
2333
  protected colspan(): number;
@@ -2309,7 +2353,7 @@ declare class StrctDatagrid {
2309
2353
  private commitSelection;
2310
2354
  private compare;
2311
2355
  static ɵfac: _angular_core.ɵɵFactoryDeclaration<StrctDatagrid, never>;
2312
- static ɵcmp: _angular_core.ɵɵComponentDeclaration<StrctDatagrid, "strct-datagrid", never, { "columns": { "alias": "columns"; "required": true; "isSignal": true; }; "rows": { "alias": "rows"; "required": true; "isSignal": true; }; "pageSize": { "alias": "pageSize"; "required": false; "isSignal": true; }; "selectable": { "alias": "selectable"; "required": false; "isSignal": true; }; "expandable": { "alias": "expandable"; "required": false; "isSignal": true; }; "detailPane": { "alias": "detailPane"; "required": false; "isSignal": true; }; "compact": { "alias": "compact"; "required": false; "isSignal": true; }; "singleLine": { "alias": "singleLine"; "required": false; "isSignal": true; }; "emptyText": { "alias": "emptyText"; "required": false; "isSignal": true; }; "loading": { "alias": "loading"; "required": false; "isSignal": true; }; "resizable": { "alias": "resizable"; "required": false; "isSignal": true; }; "columnChooser": { "alias": "columnChooser"; "required": false; "isSignal": true; }; "sync": { "alias": "sync"; "required": false; "isSignal": true; }; "footerActionsDisabled": { "alias": "footerActionsDisabled"; "required": false; "isSignal": true; }; "rowId": { "alias": "rowId"; "required": false; "isSignal": true; }; "rowActions": { "alias": "rowActions"; "required": false; "isSignal": true; }; "initialSelection": { "alias": "initialSelection"; "required": false; "isSignal": true; }; "labels": { "alias": "labels"; "required": false; "isSignal": true; }; "virtual": { "alias": "virtual"; "required": false; "isSignal": true; }; "viewportHeight": { "alias": "viewportHeight"; "required": false; "isSignal": true; }; "rowHeight": { "alias": "rowHeight"; "required": false; "isSignal": true; }; "lazy": { "alias": "lazy"; "required": false; "isSignal": true; }; "total": { "alias": "total"; "required": false; "isSignal": true; }; "stateKey": { "alias": "stateKey"; "required": false; "isSignal": true; }; "columnState": { "alias": "columnState"; "required": false; "isSignal": true; }; }, { "columnState": "columnStateChange"; "selectionChange": "selectionChange"; "syncChange": "syncChange"; "rowAction": "rowAction"; "lazyLoad": "lazyLoad"; }, ["detailDef", "actionBarDef", "cellDefs"], ["[strctDatagridActionBar]"], true, never>;
2356
+ static ɵcmp: _angular_core.ɵɵComponentDeclaration<StrctDatagrid, "strct-datagrid", never, { "columns": { "alias": "columns"; "required": true; "isSignal": true; }; "rows": { "alias": "rows"; "required": true; "isSignal": true; }; "pageSize": { "alias": "pageSize"; "required": false; "isSignal": true; }; "selectable": { "alias": "selectable"; "required": false; "isSignal": true; }; "expandable": { "alias": "expandable"; "required": false; "isSignal": true; }; "detailPane": { "alias": "detailPane"; "required": false; "isSignal": true; }; "compact": { "alias": "compact"; "required": false; "isSignal": true; }; "singleLine": { "alias": "singleLine"; "required": false; "isSignal": true; }; "emptyText": { "alias": "emptyText"; "required": false; "isSignal": true; }; "loading": { "alias": "loading"; "required": false; "isSignal": true; }; "resizable": { "alias": "resizable"; "required": false; "isSignal": true; }; "columnChooser": { "alias": "columnChooser"; "required": false; "isSignal": true; }; "sync": { "alias": "sync"; "required": false; "isSignal": true; }; "footerActionsDisabled": { "alias": "footerActionsDisabled"; "required": false; "isSignal": true; }; "rowId": { "alias": "rowId"; "required": false; "isSignal": true; }; "rowActions": { "alias": "rowActions"; "required": false; "isSignal": true; }; "initialSelection": { "alias": "initialSelection"; "required": false; "isSignal": true; }; "labels": { "alias": "labels"; "required": false; "isSignal": true; }; "virtual": { "alias": "virtual"; "required": false; "isSignal": true; }; "viewportHeight": { "alias": "viewportHeight"; "required": false; "isSignal": true; }; "rowHeight": { "alias": "rowHeight"; "required": false; "isSignal": true; }; "lazy": { "alias": "lazy"; "required": false; "isSignal": true; }; "total": { "alias": "total"; "required": false; "isSignal": true; }; "stateKey": { "alias": "stateKey"; "required": false; "isSignal": true; }; "columnState": { "alias": "columnState"; "required": false; "isSignal": true; }; "reorderable": { "alias": "reorderable"; "required": false; "isSignal": true; }; "groupBy": { "alias": "groupBy"; "required": false; "isSignal": true; }; }, { "columnState": "columnStateChange"; "selectionChange": "selectionChange"; "syncChange": "syncChange"; "rowAction": "rowAction"; "lazyLoad": "lazyLoad"; }, ["detailDef", "actionBarDef", "cellDefs"], ["[strctDatagridActionBar]"], true, never>;
2313
2357
  }
2314
2358
 
2315
2359
  /** Timeline node state colors. */
@@ -2523,6 +2567,19 @@ declare class StrctChart {
2523
2567
  * Double-click, Escape or the reset chip zooms back out.
2524
2568
  */
2525
2569
  readonly zoom: _angular_core.InputSignalWithTransform<boolean, unknown>;
2570
+ /**
2571
+ * Stack multi-series values cumulatively: each series draws its line at the
2572
+ * running total and fills the band down to the series below (nulls break the
2573
+ * stack at that slot). Tooltips keep the original per-series values.
2574
+ */
2575
+ readonly stacked: _angular_core.InputSignalWithTransform<boolean, unknown>;
2576
+ /** Y-axis scale. `log` needs positive values; non-positives clamp to the floor. */
2577
+ readonly scale: _angular_core.InputSignal<"linear" | "log">;
2578
+ /**
2579
+ * Per-point timestamps (ms epoch or Date). When set, x positions map to real
2580
+ * time, so uneven sampling renders honestly instead of equally spaced.
2581
+ */
2582
+ readonly times: _angular_core.InputSignal<(number | Date)[] | null>;
2526
2583
  /** Tooltip text for a gap (null) point. */
2527
2584
  readonly gapText: _angular_core.InputSignal<string>;
2528
2585
  /** Accessible label of the reset-zoom chip (localizable). */
@@ -2576,11 +2633,16 @@ declare class StrctChart {
2576
2633
  private chartH;
2577
2634
  /** Horizontal gap between two data points, in px (of the visible window). */
2578
2635
  private stepX;
2579
- /** Real values inside the visible window (multi-aware; bands included). */
2636
+ /** Real values inside the visible window (multi-aware; bands included;
2637
+ * per-slot totals when stacked). */
2580
2638
  private readonly visibleValues;
2581
2639
  private readonly yMax;
2582
2640
  private readonly yMin;
2641
+ /** Smallest positive visible value — the floor of a log axis. */
2642
+ private readonly logFloor;
2583
2643
  private yOf;
2644
+ /** Timestamps normalized to ms (null when the axis is index-based). */
2645
+ private readonly timesMs;
2584
2646
  protected readonly points: _angular_core.Signal<(Pt | null)[]>;
2585
2647
  /** Non-gap points only (dot rendering). */
2586
2648
  protected readonly dotPts: _angular_core.Signal<Pt[]>;
@@ -2670,7 +2732,8 @@ declare class StrctChart {
2670
2732
  protected readonly chartAria: _angular_core.Signal<string>;
2671
2733
  /** aria-live text announcing the hovered / keyboard-selected point. */
2672
2734
  protected readonly srText: _angular_core.Signal<string>;
2673
- /** Pixel x of a data index (shared by the plot, labels and annotations). */
2735
+ /** Pixel x of a data index (shared by the plot, labels and annotations).
2736
+ * With `times`, positions map to real timestamps — uneven sampling shows. */
2674
2737
  protected xOf(i: number): number;
2675
2738
  /** Set the local hover index, emitting `hoverIndex` on change. */
2676
2739
  private setHover;
@@ -2691,7 +2754,7 @@ declare class StrctChart {
2691
2754
  /** The chart as a PNG data URL at the given scale (default 2×). */
2692
2755
  toPNG(scale?: number): Promise<string>;
2693
2756
  static ɵfac: _angular_core.ɵɵFactoryDeclaration<StrctChart, never>;
2694
- static ɵcmp: _angular_core.ɵɵComponentDeclaration<StrctChart, "strct-chart", never, { "data": { "alias": "data"; "required": false; "isSignal": true; }; "series": { "alias": "series"; "required": false; "isSignal": true; }; "type": { "alias": "type"; "required": false; "isSignal": true; }; "curve": { "alias": "curve"; "required": false; "isSignal": true; }; "area": { "alias": "area"; "required": false; "isSignal": true; }; "glow": { "alias": "glow"; "required": false; "isSignal": true; }; "live": { "alias": "live"; "required": false; "isSignal": true; }; "interval": { "alias": "interval"; "required": false; "isSignal": true; }; "interactive": { "alias": "interactive"; "required": false; "isSignal": true; }; "strokeWidth": { "alias": "strokeWidth"; "required": false; "isSignal": true; }; "grid": { "alias": "grid"; "required": false; "isSignal": true; }; "dots": { "alias": "dots"; "required": false; "isSignal": true; }; "legend": { "alias": "legend"; "required": false; "isSignal": true; }; "labels": { "alias": "labels"; "required": false; "isSignal": true; }; "xTicks": { "alias": "xTicks"; "required": false; "isSignal": true; }; "xFormat": { "alias": "xFormat"; "required": false; "isSignal": true; }; "status": { "alias": "status"; "required": false; "isSignal": true; }; "height": { "alias": "height"; "required": false; "isSignal": true; }; "max": { "alias": "max"; "required": false; "isSignal": true; }; "min": { "alias": "min"; "required": false; "isSignal": true; }; "yAxis": { "alias": "yAxis"; "required": false; "isSignal": true; }; "yTicks": { "alias": "yTicks"; "required": false; "isSignal": true; }; "axisFormat": { "alias": "axisFormat"; "required": false; "isSignal": true; }; "thresholds": { "alias": "thresholds"; "required": false; "isSignal": true; }; "emptyText": { "alias": "emptyText"; "required": false; "isSignal": true; }; "agoFormat": { "alias": "agoFormat"; "required": false; "isSignal": true; }; "valueFormat": { "alias": "valueFormat"; "required": false; "isSignal": true; }; "annotations": { "alias": "annotations"; "required": false; "isSignal": true; }; "activeIndex": { "alias": "activeIndex"; "required": false; "isSignal": true; }; "brush": { "alias": "brush"; "required": false; "isSignal": true; }; "zoom": { "alias": "zoom"; "required": false; "isSignal": true; }; "gapText": { "alias": "gapText"; "required": false; "isSignal": true; }; "resetLabel": { "alias": "resetLabel"; "required": false; "isSignal": true; }; }, { "hoverIndex": "hoverIndex"; "brushChange": "brushChange"; }, never, never, true, never>;
2757
+ static ɵcmp: _angular_core.ɵɵComponentDeclaration<StrctChart, "strct-chart", never, { "data": { "alias": "data"; "required": false; "isSignal": true; }; "series": { "alias": "series"; "required": false; "isSignal": true; }; "type": { "alias": "type"; "required": false; "isSignal": true; }; "curve": { "alias": "curve"; "required": false; "isSignal": true; }; "area": { "alias": "area"; "required": false; "isSignal": true; }; "glow": { "alias": "glow"; "required": false; "isSignal": true; }; "live": { "alias": "live"; "required": false; "isSignal": true; }; "interval": { "alias": "interval"; "required": false; "isSignal": true; }; "interactive": { "alias": "interactive"; "required": false; "isSignal": true; }; "strokeWidth": { "alias": "strokeWidth"; "required": false; "isSignal": true; }; "grid": { "alias": "grid"; "required": false; "isSignal": true; }; "dots": { "alias": "dots"; "required": false; "isSignal": true; }; "legend": { "alias": "legend"; "required": false; "isSignal": true; }; "labels": { "alias": "labels"; "required": false; "isSignal": true; }; "xTicks": { "alias": "xTicks"; "required": false; "isSignal": true; }; "xFormat": { "alias": "xFormat"; "required": false; "isSignal": true; }; "status": { "alias": "status"; "required": false; "isSignal": true; }; "height": { "alias": "height"; "required": false; "isSignal": true; }; "max": { "alias": "max"; "required": false; "isSignal": true; }; "min": { "alias": "min"; "required": false; "isSignal": true; }; "yAxis": { "alias": "yAxis"; "required": false; "isSignal": true; }; "yTicks": { "alias": "yTicks"; "required": false; "isSignal": true; }; "axisFormat": { "alias": "axisFormat"; "required": false; "isSignal": true; }; "thresholds": { "alias": "thresholds"; "required": false; "isSignal": true; }; "emptyText": { "alias": "emptyText"; "required": false; "isSignal": true; }; "agoFormat": { "alias": "agoFormat"; "required": false; "isSignal": true; }; "valueFormat": { "alias": "valueFormat"; "required": false; "isSignal": true; }; "annotations": { "alias": "annotations"; "required": false; "isSignal": true; }; "activeIndex": { "alias": "activeIndex"; "required": false; "isSignal": true; }; "brush": { "alias": "brush"; "required": false; "isSignal": true; }; "zoom": { "alias": "zoom"; "required": false; "isSignal": true; }; "stacked": { "alias": "stacked"; "required": false; "isSignal": true; }; "scale": { "alias": "scale"; "required": false; "isSignal": true; }; "times": { "alias": "times"; "required": false; "isSignal": true; }; "gapText": { "alias": "gapText"; "required": false; "isSignal": true; }; "resetLabel": { "alias": "resetLabel"; "required": false; "isSignal": true; }; }, { "hoverIndex": "hoverIndex"; "brushChange": "brushChange"; }, never, never, true, never>;
2695
2758
  }
2696
2759
 
2697
2760
  /** A single weighted slice of a donut chart. */