@guiexpert/table 1.1.94 → 1.1.97
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 +16 -0
- package/css/main.css +299 -0
- package/css/table-calc.css +7 -0
- package/css/table-color-vars.css +58 -0
- package/css/table-fill-batch.css +58 -0
- package/css/table-master-detail.css +95 -0
- package/css/table-row-drag.css +81 -0
- package/index.cjs +37 -35
- package/index.d.ts +34 -0
- package/index.js +9749 -5000
- package/lib/table/action/action-id.type.d.ts +1 -1
- package/lib/table/aria/aria-ids.d.ts +7 -0
- package/lib/table/aria/aria-texts.d.ts +13 -0
- package/lib/table/aria/aria-texts.if.d.ts +101 -0
- package/lib/table/batch-edit/batch-edit-options.d.ts +21 -0
- package/lib/table/batch-edit/batch-edit-options.if.d.ts +20 -0
- package/lib/table/batch-edit/batch-edit-service.d.ts +104 -0
- package/lib/table/batch-edit/cell-change.if.d.ts +39 -0
- package/lib/table/batch-edit/cell-value-change.if.d.ts +18 -0
- package/lib/table/batch-edit/pending-cell-changes.d.ts +104 -0
- package/lib/table/calc/column-values.d.ts +55 -0
- package/lib/table/calc/show-values-as-internals.d.ts +4 -0
- package/lib/table/calc/show-values-as.d.ts +87 -0
- package/lib/table/calc/show-values-as.type.d.ts +55 -0
- package/lib/table/calc/value-getter-context.if.d.ts +35 -0
- package/lib/table/calc/value-getter.type.d.ts +36 -0
- package/lib/table/data/common/event/ge-batch-edit-event.d.ts +46 -0
- package/lib/table/data/common/event/ge-detail-event.d.ts +40 -0
- package/lib/table/data/common/event/ge-model-change-event.d.ts +27 -1
- package/lib/table/data/common/event/ge-row-drag-event.d.ts +89 -0
- package/lib/table/data/options/auto-restore-options.d.ts +2 -0
- package/lib/table/data/options/auto-restore-options.if.d.ts +6 -0
- package/lib/table/data/options/table-options.d.ts +8 -0
- package/lib/table/data/options/table-options.if.d.ts +62 -0
- package/lib/table/data/tablemodel/areamodel/abstract-area-model.d.ts +66 -0
- package/lib/table/data/tablemodel/areamodel/area-model-aggregate-footer.d.ts +5 -0
- package/lib/table/data/tablemodel/areamodel/area-model-array-of-arrays.d.ts +24 -0
- package/lib/table/data/tablemodel/areamodel/area-model-object-array.d.ts +70 -0
- package/lib/table/data/tablemodel/areamodel/area-model-pivot.d.ts +31 -0
- package/lib/table/data/tablemodel/areamodel/area-model-row-groups.d.ts +23 -1
- package/lib/table/data/tablemodel/areamodel/area-model-tree.d.ts +83 -0
- package/lib/table/data/tablemodel/areamodel/area-model.if.d.ts +55 -0
- package/lib/table/data/tablemodel/column/column-def.d.ts +31 -1
- package/lib/table/data/tablemodel/column/column-def.if.d.ts +86 -0
- package/lib/table/ele-scope.d.ts +14 -0
- package/lib/table/event-adapter.d.ts +10 -0
- package/lib/table/event-listener.if.d.ts +39 -0
- package/lib/table/factory/table-factory.d.ts +11 -0
- package/lib/table/fill/compute-fill-changes.d.ts +67 -0
- package/lib/table/fill/fill-direction.type.d.ts +7 -0
- package/lib/table/fill/fill-handle-options.d.ts +29 -0
- package/lib/table/fill/fill-handle-options.if.d.ts +35 -0
- package/lib/table/fill/fill-handle-service.d.ts +55 -0
- package/lib/table/fill/fill-series.d.ts +60 -0
- package/lib/table/fill/fill-value-context.if.d.ts +36 -0
- package/lib/table/formula/compile-formula.d.ts +86 -0
- package/lib/table/formula/evaluator.d.ts +19 -0
- package/lib/table/formula/formula-ast.if.d.ts +42 -0
- package/lib/table/formula/formula-error.d.ts +59 -0
- package/lib/table/formula/formula-options.if.d.ts +41 -0
- package/lib/table/formula/formula-values.d.ts +13 -0
- package/lib/table/formula/functions.d.ts +18 -0
- package/lib/table/formula/parser.d.ts +10 -0
- package/lib/table/formula/tokenizer.d.ts +22 -0
- package/lib/table/master-detail/detail-renderer.if.d.ts +99 -0
- package/lib/table/master-detail/master-detail-options.d.ts +30 -0
- package/lib/table/master-detail/master-detail-options.if.d.ts +60 -0
- package/lib/table/master-detail/master-detail-service.d.ts +223 -0
- package/lib/table/pivot/pivot-value.type.d.ts +13 -0
- package/lib/table/render-scope.d.ts +154 -0
- package/lib/table/renderer/edit/input-cell-renderer.d.ts +1 -1
- package/lib/table/renderer/edit/select-cell-renderer.d.ts +1 -1
- package/lib/table/row-drag/move-rows.d.ts +157 -0
- package/lib/table/row-drag/row-drag-options.d.ts +28 -0
- package/lib/table/row-drag/row-drag-options.if.d.ts +36 -0
- package/lib/table/row-drag/row-drag-service.d.ts +130 -0
- package/lib/table/row-drag/row-drop-target.if.d.ts +29 -0
- package/lib/table/row-layout/row-layout.d.ts +120 -0
- package/lib/table/service/excel-service.d.ts +6 -0
- package/lib/table/service/excel-service.if.d.ts +35 -0
- package/lib/table/state/table-state.if.d.ts +4 -1
- package/lib/table/state/table-state.service.d.ts +4 -0
- package/lib/table/table-api.d.ts +378 -2
- package/lib/table/table-scope.d.ts +185 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -42,6 +42,22 @@ This is the UI-agnostic table component for your next web app. 😊
|
|
|
42
42
|
= a multi-row header with collapsible groups) × aggregated values, total column and total row, filter before the
|
|
43
43
|
aggregation, pivot again at runtime (`PivotFactory.createTableModel({ rows, rowFields, columnFields, values })`,
|
|
44
44
|
`tableApi.setPivotConfig()`, engine `pivotRows()`) – since 1.1.94
|
|
45
|
+
- Calculated columns (`ColumnDef.valueGetter` – sorting, filter via `tableApi.getRowValue()`, copy, Excel, totals and
|
|
46
|
+
row grouping use the computed value), „Show values as“ (`showValuesAs`: share of the column / row / grand / parent
|
|
47
|
+
total, running total, difference, rank – also per pivot value) and formulas (`formula: "[price] * [quantity] * 1.19"`,
|
|
48
|
+
own parser and interpreter without `eval`, functions like `ROUND`, `IF`, `SUM([x])`, error values `#DIV/0!`,
|
|
49
|
+
`tableApi.setColumnFormula()`) – since 1.1.95
|
|
50
|
+
- Row drag: drag handle per row (`ColumnDef.rowDrag` or `rowDrag: true` in the factory), mouse, touch and pen, ghost,
|
|
51
|
+
drop marker, auto-scroll, Escape, keyboard alternative Ctrl+Alt+↑/↓, several selected rows, trees; the table moves
|
|
52
|
+
the rows (managed) or only reports the drop (`rowDragOptions: { managed: false }`, `onRowDragEnd`) – since 1.1.95
|
|
53
|
+
- Fill handle and batch edit: a square at the corner of the selected range copies values or continues series (numbers,
|
|
54
|
+
dates, `Item 1` → `Item 2`; ⌥/Alt switches, Ctrl/⌘+D, Ctrl/⌘+R), batch edit collects changes (`ge-table-cell-pending`)
|
|
55
|
+
until `tableApi.commitBatchEdit()` / `cancelBatchEdit()`, `ColumnDef.validate`, one `onModelChanged` per change with
|
|
56
|
+
old and new values (`tableOptions.fillHandle`, `tableOptions.batchEdit`) – since 1.1.96
|
|
57
|
+
- Master/detail: expandable rows with a detail row over the full width (nested table, form, framework component),
|
|
58
|
+
created lazily and kept while scrolling, fixed or measured height, keyboard (Enter, Tab) and screen readers
|
|
59
|
+
(`aria-expanded`), `tableApi.setDetailExpanded()` / `expandAllDetails()`, stored with the table state
|
|
60
|
+
(`tableOptions.masterDetail`) – since 1.1.97. Variable row heights use prefix sums (O(log n) per scroll frame)
|
|
45
61
|
- Custom Filtering
|
|
46
62
|
- In-place Cell Editing
|
|
47
63
|
- Userdefined Key and Mouse Events
|
package/css/main.css
CHANGED
|
@@ -1,3 +1,10 @@
|
|
|
1
|
+
/* Calculated columns, „Show values as“, formulas (since 1.1.95) */
|
|
2
|
+
|
|
3
|
+
/* a cell with a formula error (#DIV/0!, #NAME? …): the message is the tooltip */
|
|
4
|
+
.ge-table-col-div.ge-table-cell-error {
|
|
5
|
+
color: var(--ge-table-cell-error-color);
|
|
6
|
+
font-variant-numeric: tabular-nums;
|
|
7
|
+
}
|
|
1
8
|
/* Defaults for the host element. :where() = zero specificity, so the app's own rules always win –
|
|
2
9
|
e.g. ".table-div { height: 500px }" no longer depends on the order in which the stylesheets are bundled. */
|
|
3
10
|
:where(.ge-table) {
|
|
@@ -446,6 +453,9 @@
|
|
|
446
453
|
--ge-table-pivot-total-font-weight: 600;
|
|
447
454
|
--ge-table-pivot-empty-text: #6b7280;
|
|
448
455
|
|
|
456
|
+
/* Formulas: error values #DIV/0!, #NAME? … (since 1.1.95) */
|
|
457
|
+
--ge-table-cell-error-color: #b91c1c;
|
|
458
|
+
|
|
449
459
|
/* Overlays "Loading…" / "No rows" (since 1.1.92) */
|
|
450
460
|
--ge-table-overlay-bg: rgba(255, 255, 255, 0.7);
|
|
451
461
|
--ge-table-overlay-content-bg: #fff;
|
|
@@ -457,6 +467,32 @@
|
|
|
457
467
|
/* Row numbers (since 1.1.93): like the header, muted digits (#555 on the header gray ≈ 6.9 : 1) */
|
|
458
468
|
--ge-table-row-number-bg: var(--ge-table-header-west-bg);
|
|
459
469
|
--ge-table-row-number-color: #555;
|
|
470
|
+
|
|
471
|
+
/* Row drag (since 1.1.95): handle ≥ 3 : 1 against white (WCAG 1.4.11), marker, ghost */
|
|
472
|
+
--ge-table-row-drag-handle-color: #6b7280;
|
|
473
|
+
--ge-table-row-drop-indicator-color: #1a73e8;
|
|
474
|
+
--ge-table-row-drop-inside-bg: rgba(26, 115, 232, 0.12);
|
|
475
|
+
--ge-table-row-drag-ghost-bg: #fff;
|
|
476
|
+
--ge-table-row-drag-ghost-text: #1f2937;
|
|
477
|
+
--ge-table-row-drag-ghost-border: #1a73e8;
|
|
478
|
+
--ge-table-row-dragging-opacity: 0.4;
|
|
479
|
+
|
|
480
|
+
/* Fill handle and batch edit (since 1.1.96): handle and preview like the selection, pending = yellow, invalid = red */
|
|
481
|
+
--ge-table-fill-handle-color: #0a6ebd;
|
|
482
|
+
--ge-table-fill-handle-border: #fff;
|
|
483
|
+
--ge-table-fill-preview-border: #0a6ebd;
|
|
484
|
+
--ge-table-cell-pending-bg: #fff3c4;
|
|
485
|
+
--ge-table-cell-pending-text: #3d2e00;
|
|
486
|
+
--ge-table-cell-pending-marker: #c27c00;
|
|
487
|
+
--ge-table-cell-invalid-bg: #fde2e1;
|
|
488
|
+
--ge-table-cell-invalid-text: #8a1c14;
|
|
489
|
+
--ge-table-cell-invalid-border: #d93025;
|
|
490
|
+
|
|
491
|
+
/* Master/detail (since 1.1.97): the detail row below an expanded master row */
|
|
492
|
+
--ge-table-detail-bg: #f4f6f9;
|
|
493
|
+
--ge-table-detail-border: #c9d1db;
|
|
494
|
+
--ge-table-detail-toggle-color: #5f6368;
|
|
495
|
+
--ge-table-detail-toggle-hover-bg: rgba(128, 128, 128, 0.15);
|
|
460
496
|
}
|
|
461
497
|
|
|
462
498
|
|
|
@@ -544,6 +580,9 @@ html[data-theme="dark"] {
|
|
|
544
580
|
--ge-table-pivot-total-font-weight: 600;
|
|
545
581
|
--ge-table-pivot-empty-text: #9ca3af;
|
|
546
582
|
|
|
583
|
+
/* Formulas: error values #DIV/0!, #NAME? … (since 1.1.95) */
|
|
584
|
+
--ge-table-cell-error-color: #f87171;
|
|
585
|
+
|
|
547
586
|
/* Overlays "Loading…" / "No rows" (since 1.1.92) */
|
|
548
587
|
--ge-table-overlay-bg: rgba(17, 24, 39, 0.7); /* --ge-table-bg of the dark theme */
|
|
549
588
|
--ge-table-overlay-content-bg: #1f2937;
|
|
@@ -555,6 +594,185 @@ html[data-theme="dark"] {
|
|
|
555
594
|
/* Row numbers (since 1.1.93) */
|
|
556
595
|
--ge-table-row-number-bg: var(--ge-table-header-west-bg);
|
|
557
596
|
--ge-table-row-number-color: #aaa;
|
|
597
|
+
|
|
598
|
+
/* Row drag (since 1.1.95) */
|
|
599
|
+
--ge-table-row-drag-handle-color: #9ca3af;
|
|
600
|
+
--ge-table-row-drop-indicator-color: #8ab4f8;
|
|
601
|
+
--ge-table-row-drop-inside-bg: rgba(138, 180, 248, 0.16);
|
|
602
|
+
--ge-table-row-drag-ghost-bg: #1f2937;
|
|
603
|
+
--ge-table-row-drag-ghost-text: #f3f4f6;
|
|
604
|
+
--ge-table-row-drag-ghost-border: #8ab4f8;
|
|
605
|
+
--ge-table-row-dragging-opacity: 0.4;
|
|
606
|
+
|
|
607
|
+
/* Fill handle and batch edit (since 1.1.96) */
|
|
608
|
+
--ge-table-fill-handle-color: #8ab4f8;
|
|
609
|
+
--ge-table-fill-handle-border: #1e1e1e;
|
|
610
|
+
--ge-table-fill-preview-border: #8ab4f8;
|
|
611
|
+
--ge-table-cell-pending-bg: #4a3b0b;
|
|
612
|
+
--ge-table-cell-pending-text: #fde68a;
|
|
613
|
+
--ge-table-cell-pending-marker: #f5b82e;
|
|
614
|
+
--ge-table-cell-invalid-bg: #5c1d1a;
|
|
615
|
+
--ge-table-cell-invalid-text: #fecaca;
|
|
616
|
+
--ge-table-cell-invalid-border: #f28b82;
|
|
617
|
+
|
|
618
|
+
/* Master/detail (since 1.1.97) */
|
|
619
|
+
--ge-table-detail-bg: #1b1f24;
|
|
620
|
+
--ge-table-detail-border: #3c434d;
|
|
621
|
+
--ge-table-detail-toggle-color: #bdc1c6;
|
|
622
|
+
--ge-table-detail-toggle-hover-bg: rgba(255, 255, 255, 0.12);
|
|
623
|
+
}
|
|
624
|
+
/* Fill handle and batch edit (since 1.1.96) – colors in table-color-vars.css (--ge-table-fill-*, --ge-table-cell-*) */
|
|
625
|
+
|
|
626
|
+
/* the square at the bottom right corner of the selected range; its center sits on the corner */
|
|
627
|
+
.ge-table-fill-handle {
|
|
628
|
+
position: absolute;
|
|
629
|
+
z-index: 9000; /* above the cells, below the overlay (10000) */
|
|
630
|
+
width: 7px;
|
|
631
|
+
height: 7px;
|
|
632
|
+
margin: -4px 0 0 -4px;
|
|
633
|
+
box-sizing: border-box;
|
|
634
|
+
background: var(--ge-table-fill-handle-color);
|
|
635
|
+
border: 1px solid var(--ge-table-fill-handle-border);
|
|
636
|
+
cursor: crosshair;
|
|
637
|
+
touch-action: none; /* touch drags the handle instead of scrolling */
|
|
638
|
+
}
|
|
639
|
+
|
|
640
|
+
/* a bigger target for touch and pen (the visible square stays small) */
|
|
641
|
+
.ge-table-fill-handle::after {
|
|
642
|
+
content: "";
|
|
643
|
+
position: absolute;
|
|
644
|
+
inset: -8px;
|
|
645
|
+
}
|
|
646
|
+
|
|
647
|
+
/* the cells a fill will cover */
|
|
648
|
+
.ge-table-fill-preview {
|
|
649
|
+
position: absolute;
|
|
650
|
+
z-index: 8999;
|
|
651
|
+
box-sizing: border-box;
|
|
652
|
+
border: 2px dashed var(--ge-table-fill-preview-border);
|
|
653
|
+
pointer-events: none;
|
|
654
|
+
}
|
|
655
|
+
|
|
656
|
+
.ge-table-fill-active,
|
|
657
|
+
.ge-table-fill-active * {
|
|
658
|
+
cursor: crosshair !important;
|
|
659
|
+
user-select: none;
|
|
660
|
+
}
|
|
661
|
+
|
|
662
|
+
/* batch edit: a value that is not saved yet – a colored cell and a small corner mark (not color only, WCAG 1.4.1) */
|
|
663
|
+
.ge-table-col-div.ge-table-cell-pending {
|
|
664
|
+
background-image: linear-gradient(225deg, var(--ge-table-cell-pending-marker) 6px, transparent 6px);
|
|
665
|
+
}
|
|
666
|
+
|
|
667
|
+
/* the color only while the cell is not selected – a selected cell keeps the selection color (and the corner mark) */
|
|
668
|
+
.ge-table-col-div.ge-table-cell-pending:not([class*="-selected-range"]) {
|
|
669
|
+
background-color: var(--ge-table-cell-pending-bg);
|
|
670
|
+
color: var(--ge-table-cell-pending-text);
|
|
671
|
+
}
|
|
672
|
+
|
|
673
|
+
/* an invalid value (ColumnDef.validate): the message is the tooltip */
|
|
674
|
+
.ge-table-col-div.ge-table-cell-invalid:not([class*="-selected-range"]) {
|
|
675
|
+
background-color: var(--ge-table-cell-invalid-bg);
|
|
676
|
+
color: var(--ge-table-cell-invalid-text);
|
|
677
|
+
}
|
|
678
|
+
|
|
679
|
+
.ge-table-col-div.ge-table-cell-invalid {
|
|
680
|
+
box-shadow: inset 0 0 0 2px var(--ge-table-cell-invalid-border);
|
|
681
|
+
}
|
|
682
|
+
/* Master/detail (since 1.1.97) – colors in table-color-vars.css (--ge-table-detail-*) */
|
|
683
|
+
|
|
684
|
+
/* the layer over the visible body (full width, fixed columns included, without the scroll bars); positioned by the
|
|
685
|
+
table. Only the detail rows take pointer events – the body cells between them stay clickable. */
|
|
686
|
+
.ge-table-detail-layer {
|
|
687
|
+
position: absolute;
|
|
688
|
+
z-index: 1000; /* above .ge-table-body-east (999), below the fill preview (8999), focus frame (9999), overlay (10000) */
|
|
689
|
+
overflow: hidden;
|
|
690
|
+
pointer-events: none;
|
|
691
|
+
}
|
|
692
|
+
|
|
693
|
+
.ge-table-detail-row {
|
|
694
|
+
position: absolute;
|
|
695
|
+
inset-inline: 0;
|
|
696
|
+
box-sizing: border-box;
|
|
697
|
+
pointer-events: auto;
|
|
698
|
+
background: var(--ge-table-detail-bg);
|
|
699
|
+
border-top: 1px solid var(--ge-table-detail-border);
|
|
700
|
+
border-bottom: 1px solid var(--ge-table-detail-border);
|
|
701
|
+
}
|
|
702
|
+
|
|
703
|
+
/* scrolled out of view: hidden, not destroyed – the content keeps its state (inputs, scroll positions) */
|
|
704
|
+
.ge-table-detail-row.ge-table-detail-row-parked {
|
|
705
|
+
visibility: hidden;
|
|
706
|
+
content-visibility: hidden;
|
|
707
|
+
}
|
|
708
|
+
|
|
709
|
+
.ge-table-detail-cell {
|
|
710
|
+
box-sizing: border-box;
|
|
711
|
+
width: 100%;
|
|
712
|
+
height: 100%;
|
|
713
|
+
padding-block: 8px;
|
|
714
|
+
padding-inline: 32px 12px;
|
|
715
|
+
overflow: auto;
|
|
716
|
+
}
|
|
717
|
+
|
|
718
|
+
/* detailHeight "auto": the row is as high as its content (measured) */
|
|
719
|
+
.ge-table-detail-row-auto .ge-table-detail-cell {
|
|
720
|
+
height: auto;
|
|
721
|
+
overflow: visible;
|
|
722
|
+
}
|
|
723
|
+
|
|
724
|
+
/* a nested table (context.createTable) */
|
|
725
|
+
.ge-table-detail-table {
|
|
726
|
+
width: 100%;
|
|
727
|
+
position: relative;
|
|
728
|
+
}
|
|
729
|
+
|
|
730
|
+
/* the cell with the expand icon: room for the icon at the start */
|
|
731
|
+
.ge-table-detail-toggle-cell {
|
|
732
|
+
box-sizing: border-box;
|
|
733
|
+
padding-inline-start: 22px;
|
|
734
|
+
}
|
|
735
|
+
|
|
736
|
+
/* behind a row drag handle */
|
|
737
|
+
.ge-table-row-drag-cell.ge-table-detail-toggle-cell {
|
|
738
|
+
padding-inline-start: 36px;
|
|
739
|
+
}
|
|
740
|
+
|
|
741
|
+
.ge-table-detail-toggle {
|
|
742
|
+
position: absolute;
|
|
743
|
+
inset-inline-start: 3px;
|
|
744
|
+
top: 50%;
|
|
745
|
+
width: 16px;
|
|
746
|
+
height: 16px;
|
|
747
|
+
margin-top: -8px;
|
|
748
|
+
border-radius: 3px;
|
|
749
|
+
cursor: pointer;
|
|
750
|
+
}
|
|
751
|
+
|
|
752
|
+
.ge-table-row-drag-cell .ge-table-detail-toggle {
|
|
753
|
+
inset-inline-start: 17px;
|
|
754
|
+
}
|
|
755
|
+
|
|
756
|
+
.ge-table-detail-toggle:hover {
|
|
757
|
+
background-color: var(--ge-table-detail-toggle-hover-bg);
|
|
758
|
+
}
|
|
759
|
+
|
|
760
|
+
/* a chevron drawn with CSS: ▸ collapsed, ▾ expanded */
|
|
761
|
+
.ge-table-detail-toggle::before {
|
|
762
|
+
content: "";
|
|
763
|
+
position: absolute;
|
|
764
|
+
inset-inline-start: 5px;
|
|
765
|
+
top: 4px;
|
|
766
|
+
width: 0;
|
|
767
|
+
height: 0;
|
|
768
|
+
border-style: solid;
|
|
769
|
+
border-width: 4px 0 4px 6px;
|
|
770
|
+
border-color: transparent transparent transparent var(--ge-table-detail-toggle-color);
|
|
771
|
+
transition: transform 0.12s ease-out;
|
|
772
|
+
}
|
|
773
|
+
|
|
774
|
+
.ge-table-detail-toggle.ge-table-detail-toggle-expanded::before {
|
|
775
|
+
transform: rotate(90deg);
|
|
558
776
|
}
|
|
559
777
|
/* Pivot tables (PivotFactory / AreaModelPivot, since 1.1.94) */
|
|
560
778
|
|
|
@@ -598,6 +816,87 @@ html[data-theme="dark"] {
|
|
|
598
816
|
.ge-table-pivot-header.ge-table-pivot-header-column {
|
|
599
817
|
text-align: end;
|
|
600
818
|
}
|
|
819
|
+
/* Row drag (since 1.1.95): handle, ghost, drop marker – colors in table-color-vars.css (--ge-table-row-drag-*) */
|
|
820
|
+
|
|
821
|
+
/* the cell with the handle: room for the grip at the start (a tree cell has its indent already) */
|
|
822
|
+
.ge-table-row-drag-cell:not(.ge-table-col-tree) {
|
|
823
|
+
box-sizing: border-box;
|
|
824
|
+
padding-inline-start: 16px;
|
|
825
|
+
}
|
|
826
|
+
|
|
827
|
+
/* the grip: 2 × 3 dots, drawn with CSS (no text, no image); touch-action: none = touch drags instead of scrolling */
|
|
828
|
+
.ge-table-row-drag-handle {
|
|
829
|
+
position: absolute;
|
|
830
|
+
inset-inline-start: 2px;
|
|
831
|
+
top: 50%;
|
|
832
|
+
width: 12px;
|
|
833
|
+
height: 18px;
|
|
834
|
+
margin-top: -9px;
|
|
835
|
+
cursor: grab;
|
|
836
|
+
touch-action: none;
|
|
837
|
+
border-radius: 3px;
|
|
838
|
+
background-image: radial-gradient(circle, var(--ge-table-row-drag-handle-color) 1.5px, transparent 1.6px);
|
|
839
|
+
background-size: 6px 6px;
|
|
840
|
+
background-position: 0 0;
|
|
841
|
+
}
|
|
842
|
+
|
|
843
|
+
.ge-table-row-drag-handle:hover {
|
|
844
|
+
background-color: rgba(128, 128, 128, 0.15);
|
|
845
|
+
}
|
|
846
|
+
|
|
847
|
+
/* managed drag while the table is sorted or filtered */
|
|
848
|
+
.ge-table-row-drag-handle.ge-table-row-drag-handle-disabled {
|
|
849
|
+
cursor: not-allowed;
|
|
850
|
+
opacity: 0.35;
|
|
851
|
+
}
|
|
852
|
+
|
|
853
|
+
/* the dragged rows while the drag runs */
|
|
854
|
+
.ge-table-row-dragging {
|
|
855
|
+
opacity: var(--ge-table-row-dragging-opacity);
|
|
856
|
+
}
|
|
857
|
+
|
|
858
|
+
.ge-table-row-drag-active,
|
|
859
|
+
.ge-table-row-drag-active * {
|
|
860
|
+
cursor: grabbing !important;
|
|
861
|
+
}
|
|
862
|
+
|
|
863
|
+
.ge-table-row-drag-active.ge-table-row-drag-invalid,
|
|
864
|
+
.ge-table-row-drag-active.ge-table-row-drag-invalid * {
|
|
865
|
+
cursor: no-drop !important;
|
|
866
|
+
}
|
|
867
|
+
|
|
868
|
+
.ge-table-row-drag-ghost {
|
|
869
|
+
position: absolute;
|
|
870
|
+
z-index: 10001; /* above the overlay (10000) */
|
|
871
|
+
pointer-events: none;
|
|
872
|
+
max-width: 280px;
|
|
873
|
+
padding: 4px 10px;
|
|
874
|
+
overflow: hidden;
|
|
875
|
+
white-space: nowrap;
|
|
876
|
+
text-overflow: ellipsis;
|
|
877
|
+
font-size: 0.9em;
|
|
878
|
+
line-height: 1.5;
|
|
879
|
+
color: var(--ge-table-row-drag-ghost-text);
|
|
880
|
+
background: var(--ge-table-row-drag-ghost-bg);
|
|
881
|
+
border: 1px solid var(--ge-table-row-drag-ghost-border);
|
|
882
|
+
border-radius: 4px;
|
|
883
|
+
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.2);
|
|
884
|
+
}
|
|
885
|
+
|
|
886
|
+
.ge-table-row-drop-indicator {
|
|
887
|
+
position: absolute;
|
|
888
|
+
display: none;
|
|
889
|
+
z-index: 10000;
|
|
890
|
+
pointer-events: none;
|
|
891
|
+
background: var(--ge-table-row-drop-indicator-color);
|
|
892
|
+
}
|
|
893
|
+
|
|
894
|
+
/* tree: drop into the row (becomes its child) */
|
|
895
|
+
.ge-table-row-drop-indicator.ge-table-row-drop-indicator-inside {
|
|
896
|
+
box-sizing: border-box;
|
|
897
|
+
background: var(--ge-table-row-drop-inside-bg);
|
|
898
|
+
border: 2px solid var(--ge-table-row-drop-indicator-color);
|
|
899
|
+
}
|
|
601
900
|
/* Row grouping (RowGroupFactory / AreaModelRowGroups, since 1.1.94) */
|
|
602
901
|
|
|
603
902
|
/* every cell of a group row */
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/* Calculated columns, „Show values as“, formulas (since 1.1.95) */
|
|
2
|
+
|
|
3
|
+
/* a cell with a formula error (#DIV/0!, #NAME? …): the message is the tooltip */
|
|
4
|
+
.ge-table-col-div.ge-table-cell-error {
|
|
5
|
+
color: var(--ge-table-cell-error-color);
|
|
6
|
+
font-variant-numeric: tabular-nums;
|
|
7
|
+
}
|
package/css/table-color-vars.css
CHANGED
|
@@ -96,6 +96,9 @@ html, html[data-theme="light"] {
|
|
|
96
96
|
--ge-table-pivot-total-font-weight: 600;
|
|
97
97
|
--ge-table-pivot-empty-text: #6b7280;
|
|
98
98
|
|
|
99
|
+
/* Formulas: error values #DIV/0!, #NAME? … (since 1.1.95) */
|
|
100
|
+
--ge-table-cell-error-color: #b91c1c;
|
|
101
|
+
|
|
99
102
|
/* Overlays "Loading…" / "No rows" (since 1.1.92) */
|
|
100
103
|
--ge-table-overlay-bg: rgba(255, 255, 255, 0.7);
|
|
101
104
|
--ge-table-overlay-content-bg: #fff;
|
|
@@ -107,6 +110,32 @@ html, html[data-theme="light"] {
|
|
|
107
110
|
/* Row numbers (since 1.1.93): like the header, muted digits (#555 on the header gray ≈ 6.9 : 1) */
|
|
108
111
|
--ge-table-row-number-bg: var(--ge-table-header-west-bg);
|
|
109
112
|
--ge-table-row-number-color: #555;
|
|
113
|
+
|
|
114
|
+
/* Row drag (since 1.1.95): handle ≥ 3 : 1 against white (WCAG 1.4.11), marker, ghost */
|
|
115
|
+
--ge-table-row-drag-handle-color: #6b7280;
|
|
116
|
+
--ge-table-row-drop-indicator-color: #1a73e8;
|
|
117
|
+
--ge-table-row-drop-inside-bg: rgba(26, 115, 232, 0.12);
|
|
118
|
+
--ge-table-row-drag-ghost-bg: #fff;
|
|
119
|
+
--ge-table-row-drag-ghost-text: #1f2937;
|
|
120
|
+
--ge-table-row-drag-ghost-border: #1a73e8;
|
|
121
|
+
--ge-table-row-dragging-opacity: 0.4;
|
|
122
|
+
|
|
123
|
+
/* Fill handle and batch edit (since 1.1.96): handle and preview like the selection, pending = yellow, invalid = red */
|
|
124
|
+
--ge-table-fill-handle-color: #0a6ebd;
|
|
125
|
+
--ge-table-fill-handle-border: #fff;
|
|
126
|
+
--ge-table-fill-preview-border: #0a6ebd;
|
|
127
|
+
--ge-table-cell-pending-bg: #fff3c4;
|
|
128
|
+
--ge-table-cell-pending-text: #3d2e00;
|
|
129
|
+
--ge-table-cell-pending-marker: #c27c00;
|
|
130
|
+
--ge-table-cell-invalid-bg: #fde2e1;
|
|
131
|
+
--ge-table-cell-invalid-text: #8a1c14;
|
|
132
|
+
--ge-table-cell-invalid-border: #d93025;
|
|
133
|
+
|
|
134
|
+
/* Master/detail (since 1.1.97): the detail row below an expanded master row */
|
|
135
|
+
--ge-table-detail-bg: #f4f6f9;
|
|
136
|
+
--ge-table-detail-border: #c9d1db;
|
|
137
|
+
--ge-table-detail-toggle-color: #5f6368;
|
|
138
|
+
--ge-table-detail-toggle-hover-bg: rgba(128, 128, 128, 0.15);
|
|
110
139
|
}
|
|
111
140
|
|
|
112
141
|
|
|
@@ -194,6 +223,9 @@ html[data-theme="dark"] {
|
|
|
194
223
|
--ge-table-pivot-total-font-weight: 600;
|
|
195
224
|
--ge-table-pivot-empty-text: #9ca3af;
|
|
196
225
|
|
|
226
|
+
/* Formulas: error values #DIV/0!, #NAME? … (since 1.1.95) */
|
|
227
|
+
--ge-table-cell-error-color: #f87171;
|
|
228
|
+
|
|
197
229
|
/* Overlays "Loading…" / "No rows" (since 1.1.92) */
|
|
198
230
|
--ge-table-overlay-bg: rgba(17, 24, 39, 0.7); /* --ge-table-bg of the dark theme */
|
|
199
231
|
--ge-table-overlay-content-bg: #1f2937;
|
|
@@ -205,4 +237,30 @@ html[data-theme="dark"] {
|
|
|
205
237
|
/* Row numbers (since 1.1.93) */
|
|
206
238
|
--ge-table-row-number-bg: var(--ge-table-header-west-bg);
|
|
207
239
|
--ge-table-row-number-color: #aaa;
|
|
240
|
+
|
|
241
|
+
/* Row drag (since 1.1.95) */
|
|
242
|
+
--ge-table-row-drag-handle-color: #9ca3af;
|
|
243
|
+
--ge-table-row-drop-indicator-color: #8ab4f8;
|
|
244
|
+
--ge-table-row-drop-inside-bg: rgba(138, 180, 248, 0.16);
|
|
245
|
+
--ge-table-row-drag-ghost-bg: #1f2937;
|
|
246
|
+
--ge-table-row-drag-ghost-text: #f3f4f6;
|
|
247
|
+
--ge-table-row-drag-ghost-border: #8ab4f8;
|
|
248
|
+
--ge-table-row-dragging-opacity: 0.4;
|
|
249
|
+
|
|
250
|
+
/* Fill handle and batch edit (since 1.1.96) */
|
|
251
|
+
--ge-table-fill-handle-color: #8ab4f8;
|
|
252
|
+
--ge-table-fill-handle-border: #1e1e1e;
|
|
253
|
+
--ge-table-fill-preview-border: #8ab4f8;
|
|
254
|
+
--ge-table-cell-pending-bg: #4a3b0b;
|
|
255
|
+
--ge-table-cell-pending-text: #fde68a;
|
|
256
|
+
--ge-table-cell-pending-marker: #f5b82e;
|
|
257
|
+
--ge-table-cell-invalid-bg: #5c1d1a;
|
|
258
|
+
--ge-table-cell-invalid-text: #fecaca;
|
|
259
|
+
--ge-table-cell-invalid-border: #f28b82;
|
|
260
|
+
|
|
261
|
+
/* Master/detail (since 1.1.97) */
|
|
262
|
+
--ge-table-detail-bg: #1b1f24;
|
|
263
|
+
--ge-table-detail-border: #3c434d;
|
|
264
|
+
--ge-table-detail-toggle-color: #bdc1c6;
|
|
265
|
+
--ge-table-detail-toggle-hover-bg: rgba(255, 255, 255, 0.12);
|
|
208
266
|
}
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
/* Fill handle and batch edit (since 1.1.96) – colors in table-color-vars.css (--ge-table-fill-*, --ge-table-cell-*) */
|
|
2
|
+
|
|
3
|
+
/* the square at the bottom right corner of the selected range; its center sits on the corner */
|
|
4
|
+
.ge-table-fill-handle {
|
|
5
|
+
position: absolute;
|
|
6
|
+
z-index: 9000; /* above the cells, below the overlay (10000) */
|
|
7
|
+
width: 7px;
|
|
8
|
+
height: 7px;
|
|
9
|
+
margin: -4px 0 0 -4px;
|
|
10
|
+
box-sizing: border-box;
|
|
11
|
+
background: var(--ge-table-fill-handle-color);
|
|
12
|
+
border: 1px solid var(--ge-table-fill-handle-border);
|
|
13
|
+
cursor: crosshair;
|
|
14
|
+
touch-action: none; /* touch drags the handle instead of scrolling */
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
/* a bigger target for touch and pen (the visible square stays small) */
|
|
18
|
+
.ge-table-fill-handle::after {
|
|
19
|
+
content: "";
|
|
20
|
+
position: absolute;
|
|
21
|
+
inset: -8px;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
/* the cells a fill will cover */
|
|
25
|
+
.ge-table-fill-preview {
|
|
26
|
+
position: absolute;
|
|
27
|
+
z-index: 8999;
|
|
28
|
+
box-sizing: border-box;
|
|
29
|
+
border: 2px dashed var(--ge-table-fill-preview-border);
|
|
30
|
+
pointer-events: none;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
.ge-table-fill-active,
|
|
34
|
+
.ge-table-fill-active * {
|
|
35
|
+
cursor: crosshair !important;
|
|
36
|
+
user-select: none;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
/* batch edit: a value that is not saved yet – a colored cell and a small corner mark (not color only, WCAG 1.4.1) */
|
|
40
|
+
.ge-table-col-div.ge-table-cell-pending {
|
|
41
|
+
background-image: linear-gradient(225deg, var(--ge-table-cell-pending-marker) 6px, transparent 6px);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
/* the color only while the cell is not selected – a selected cell keeps the selection color (and the corner mark) */
|
|
45
|
+
.ge-table-col-div.ge-table-cell-pending:not([class*="-selected-range"]) {
|
|
46
|
+
background-color: var(--ge-table-cell-pending-bg);
|
|
47
|
+
color: var(--ge-table-cell-pending-text);
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
/* an invalid value (ColumnDef.validate): the message is the tooltip */
|
|
51
|
+
.ge-table-col-div.ge-table-cell-invalid:not([class*="-selected-range"]) {
|
|
52
|
+
background-color: var(--ge-table-cell-invalid-bg);
|
|
53
|
+
color: var(--ge-table-cell-invalid-text);
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
.ge-table-col-div.ge-table-cell-invalid {
|
|
57
|
+
box-shadow: inset 0 0 0 2px var(--ge-table-cell-invalid-border);
|
|
58
|
+
}
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
/* Master/detail (since 1.1.97) – colors in table-color-vars.css (--ge-table-detail-*) */
|
|
2
|
+
|
|
3
|
+
/* the layer over the visible body (full width, fixed columns included, without the scroll bars); positioned by the
|
|
4
|
+
table. Only the detail rows take pointer events – the body cells between them stay clickable. */
|
|
5
|
+
.ge-table-detail-layer {
|
|
6
|
+
position: absolute;
|
|
7
|
+
z-index: 1000; /* above .ge-table-body-east (999), below the fill preview (8999), focus frame (9999), overlay (10000) */
|
|
8
|
+
overflow: hidden;
|
|
9
|
+
pointer-events: none;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
.ge-table-detail-row {
|
|
13
|
+
position: absolute;
|
|
14
|
+
inset-inline: 0;
|
|
15
|
+
box-sizing: border-box;
|
|
16
|
+
pointer-events: auto;
|
|
17
|
+
background: var(--ge-table-detail-bg);
|
|
18
|
+
border-top: 1px solid var(--ge-table-detail-border);
|
|
19
|
+
border-bottom: 1px solid var(--ge-table-detail-border);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
/* scrolled out of view: hidden, not destroyed – the content keeps its state (inputs, scroll positions) */
|
|
23
|
+
.ge-table-detail-row.ge-table-detail-row-parked {
|
|
24
|
+
visibility: hidden;
|
|
25
|
+
content-visibility: hidden;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
.ge-table-detail-cell {
|
|
29
|
+
box-sizing: border-box;
|
|
30
|
+
width: 100%;
|
|
31
|
+
height: 100%;
|
|
32
|
+
padding-block: 8px;
|
|
33
|
+
padding-inline: 32px 12px;
|
|
34
|
+
overflow: auto;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/* detailHeight "auto": the row is as high as its content (measured) */
|
|
38
|
+
.ge-table-detail-row-auto .ge-table-detail-cell {
|
|
39
|
+
height: auto;
|
|
40
|
+
overflow: visible;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
/* a nested table (context.createTable) */
|
|
44
|
+
.ge-table-detail-table {
|
|
45
|
+
width: 100%;
|
|
46
|
+
position: relative;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/* the cell with the expand icon: room for the icon at the start */
|
|
50
|
+
.ge-table-detail-toggle-cell {
|
|
51
|
+
box-sizing: border-box;
|
|
52
|
+
padding-inline-start: 22px;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
/* behind a row drag handle */
|
|
56
|
+
.ge-table-row-drag-cell.ge-table-detail-toggle-cell {
|
|
57
|
+
padding-inline-start: 36px;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
.ge-table-detail-toggle {
|
|
61
|
+
position: absolute;
|
|
62
|
+
inset-inline-start: 3px;
|
|
63
|
+
top: 50%;
|
|
64
|
+
width: 16px;
|
|
65
|
+
height: 16px;
|
|
66
|
+
margin-top: -8px;
|
|
67
|
+
border-radius: 3px;
|
|
68
|
+
cursor: pointer;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
.ge-table-row-drag-cell .ge-table-detail-toggle {
|
|
72
|
+
inset-inline-start: 17px;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
.ge-table-detail-toggle:hover {
|
|
76
|
+
background-color: var(--ge-table-detail-toggle-hover-bg);
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
/* a chevron drawn with CSS: ▸ collapsed, ▾ expanded */
|
|
80
|
+
.ge-table-detail-toggle::before {
|
|
81
|
+
content: "";
|
|
82
|
+
position: absolute;
|
|
83
|
+
inset-inline-start: 5px;
|
|
84
|
+
top: 4px;
|
|
85
|
+
width: 0;
|
|
86
|
+
height: 0;
|
|
87
|
+
border-style: solid;
|
|
88
|
+
border-width: 4px 0 4px 6px;
|
|
89
|
+
border-color: transparent transparent transparent var(--ge-table-detail-toggle-color);
|
|
90
|
+
transition: transform 0.12s ease-out;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
.ge-table-detail-toggle.ge-table-detail-toggle-expanded::before {
|
|
94
|
+
transform: rotate(90deg);
|
|
95
|
+
}
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
/* Row drag (since 1.1.95): handle, ghost, drop marker – colors in table-color-vars.css (--ge-table-row-drag-*) */
|
|
2
|
+
|
|
3
|
+
/* the cell with the handle: room for the grip at the start (a tree cell has its indent already) */
|
|
4
|
+
.ge-table-row-drag-cell:not(.ge-table-col-tree) {
|
|
5
|
+
box-sizing: border-box;
|
|
6
|
+
padding-inline-start: 16px;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
/* the grip: 2 × 3 dots, drawn with CSS (no text, no image); touch-action: none = touch drags instead of scrolling */
|
|
10
|
+
.ge-table-row-drag-handle {
|
|
11
|
+
position: absolute;
|
|
12
|
+
inset-inline-start: 2px;
|
|
13
|
+
top: 50%;
|
|
14
|
+
width: 12px;
|
|
15
|
+
height: 18px;
|
|
16
|
+
margin-top: -9px;
|
|
17
|
+
cursor: grab;
|
|
18
|
+
touch-action: none;
|
|
19
|
+
border-radius: 3px;
|
|
20
|
+
background-image: radial-gradient(circle, var(--ge-table-row-drag-handle-color) 1.5px, transparent 1.6px);
|
|
21
|
+
background-size: 6px 6px;
|
|
22
|
+
background-position: 0 0;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
.ge-table-row-drag-handle:hover {
|
|
26
|
+
background-color: rgba(128, 128, 128, 0.15);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/* managed drag while the table is sorted or filtered */
|
|
30
|
+
.ge-table-row-drag-handle.ge-table-row-drag-handle-disabled {
|
|
31
|
+
cursor: not-allowed;
|
|
32
|
+
opacity: 0.35;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
/* the dragged rows while the drag runs */
|
|
36
|
+
.ge-table-row-dragging {
|
|
37
|
+
opacity: var(--ge-table-row-dragging-opacity);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
.ge-table-row-drag-active,
|
|
41
|
+
.ge-table-row-drag-active * {
|
|
42
|
+
cursor: grabbing !important;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
.ge-table-row-drag-active.ge-table-row-drag-invalid,
|
|
46
|
+
.ge-table-row-drag-active.ge-table-row-drag-invalid * {
|
|
47
|
+
cursor: no-drop !important;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
.ge-table-row-drag-ghost {
|
|
51
|
+
position: absolute;
|
|
52
|
+
z-index: 10001; /* above the overlay (10000) */
|
|
53
|
+
pointer-events: none;
|
|
54
|
+
max-width: 280px;
|
|
55
|
+
padding: 4px 10px;
|
|
56
|
+
overflow: hidden;
|
|
57
|
+
white-space: nowrap;
|
|
58
|
+
text-overflow: ellipsis;
|
|
59
|
+
font-size: 0.9em;
|
|
60
|
+
line-height: 1.5;
|
|
61
|
+
color: var(--ge-table-row-drag-ghost-text);
|
|
62
|
+
background: var(--ge-table-row-drag-ghost-bg);
|
|
63
|
+
border: 1px solid var(--ge-table-row-drag-ghost-border);
|
|
64
|
+
border-radius: 4px;
|
|
65
|
+
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.2);
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
.ge-table-row-drop-indicator {
|
|
69
|
+
position: absolute;
|
|
70
|
+
display: none;
|
|
71
|
+
z-index: 10000;
|
|
72
|
+
pointer-events: none;
|
|
73
|
+
background: var(--ge-table-row-drop-indicator-color);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/* tree: drop into the row (becomes its child) */
|
|
77
|
+
.ge-table-row-drop-indicator.ge-table-row-drop-indicator-inside {
|
|
78
|
+
box-sizing: border-box;
|
|
79
|
+
background: var(--ge-table-row-drop-inside-bg);
|
|
80
|
+
border: 2px solid var(--ge-table-row-drop-indicator-color);
|
|
81
|
+
}
|