@vii7/div-table-widget 1.1.1 → 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/README.md CHANGED
@@ -1,5 +1,14 @@
1
1
  # DivTable Widget
2
2
 
3
+ **v1.2.0** — 2026-02-01
4
+
5
+ **What's new:**
6
+
7
+ - Fixed `.div-table-body` max-height calculation (now uses widget height minus toolbar and header)
8
+ - Row heights between fixed and scroll sections are now always synchronized to the tallest row
9
+ - No more cell overflow: the tallest cell in a row (including composite cells) sets the row height for both fixed and scroll sections
10
+
11
+
3
12
  A modern, flexible table widget built with CSS Grid and Flexbox instead of HTML tables, featuring Monaco Editor integration for advanced query capabilities.
4
13
 
5
14
  ![alt](demo.gif)
@@ -19,6 +28,7 @@ A modern, flexible table widget built with CSS Grid and Flexbox instead of HTML
19
28
  - **Keyboard Navigation**: Full keyboard accessibility with arrow key navigation
20
29
  - **Responsive Design**: Adaptive column sizing and mobile-friendly layout
21
30
  - **Composite Columns**: Stack multiple fields in one column or create two-line headers
31
+ - **Dark Mode Support**: Built-in dark mode with a single class toggle
22
32
 
23
33
  ## Installation
24
34
 
@@ -28,6 +38,153 @@ npm install @vii7/div-table-widget monaco-editor
28
38
 
29
39
  ## Usage Options
30
40
 
41
+ ## CDN Setup
42
+
43
+ You can use DivTable Widget directly from a CDN for quick prototyping or embedding in static sites. The latest version is available via [jsDelivr](https://www.jsdelivr.com/package/npm/@vii7/div-table-widget).
44
+
45
+ **Example (CDN):**
46
+
47
+ ```html
48
+ <!DOCTYPE html>
49
+ <html>
50
+ <head>
51
+ <!-- DivTable CSS from CDN -->
52
+ <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@vii7/div-table-widget@latest/src/div-table.css">
53
+ <!-- Monaco Editor (from CDN) -->
54
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.52.2/min/vs/loader.min.js"></script>
55
+ <!-- DivTable Query Engine (from CDN) -->
56
+ <script src="https://cdn.jsdelivr.net/npm/@vii7/div-table-widget@latest/src/query.js"></script>
57
+ <!-- DivTable Widget JS (from CDN) -->
58
+ <script src="https://cdn.jsdelivr.net/npm/@vii7/div-table-widget@latest/src/div-table.js"></script>
59
+ </head>
60
+ <body>
61
+ <div id="table-container"></div>
62
+ <script>
63
+ require.config({ paths: { vs: 'https://cdnjs.cloudflare.com/ajax/libs/monaco-editor/0.52.2/min/vs' }});
64
+ require(['vs/editor/editor.main'], function() {
65
+ const divTable = new DivTable(monaco, {
66
+ tableWidgetElement: document.getElementById('table-container'),
67
+ columns: [
68
+ { field: 'id', label: 'ID', primaryKey: true },
69
+ { field: 'name', label: 'Name' },
70
+ { field: 'email', label: 'Email' },
71
+ { field: 'status', label: 'Status' }
72
+ ],
73
+ data: [
74
+ { id: 1, name: 'John Doe', email: 'john@example.com', status: 'active' },
75
+ { id: 2, name: 'Jane Smith', email: 'jane@example.com', status: 'inactive' }
76
+ ]
77
+ });
78
+ });
79
+ </script>
80
+ </body>
81
+ </html>
82
+ ```
83
+
84
+ This setup requires no build step—just copy and paste into your HTML file. Always use the latest version by referencing `@latest` in the CDN URL, or pin to a specific version for production stability.
85
+
86
+
87
+ ## Theming & Customization
88
+
89
+ DivTable supports customizable themes via CSS variables. The base (light) theme is included by default; additional themes like dark mode can be enabled by including a theme CSS file and applying a class.
90
+
91
+ ### Available Themes
92
+
93
+ | Theme | File | Class | Description |
94
+ |-------|------|-------|-------------|
95
+ | Light (default) | `div-table.css` | (none) | Default light theme, included automatically |
96
+ | Dark | `div-table-theme-dark.css` | `.theme-dark` or `.dark` | Dark theme for low-light environments |
97
+
98
+ ### Enabling Dark Mode
99
+
100
+ **Option 1: Static (include theme CSS file)**
101
+
102
+ Include the dark theme CSS after the base CSS:
103
+
104
+ ```html
105
+ <link rel="stylesheet" href="node_modules/@vii7/div-table-widget/dist/divtable.min.css">
106
+ <link rel="stylesheet" href="node_modules/@vii7/div-table-widget/dist/divtable-theme-dark.min.css">
107
+ <body class="theme-dark">
108
+ ...
109
+ </body>
110
+ ```
111
+
112
+ **Option 2: Dynamic (toggle via JavaScript)**
113
+
114
+ You can toggle dark mode dynamically by adding or removing the theme class with JavaScript:
115
+
116
+ ```js
117
+ // Enable dark mode
118
+ document.body.classList.add('theme-dark');
119
+
120
+ // Toggle dark mode
121
+ document.body.classList.toggle('theme-dark');
122
+
123
+ // Remove dark mode (back to light)
124
+ document.body.classList.remove('theme-dark');
125
+ ```
126
+
127
+ **CDN Example (Dark Mode):**
128
+
129
+ ```html
130
+ <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@vii7/div-table-widget@latest/src/div-table.css">
131
+ <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@vii7/div-table-widget@latest/src/div-table-theme-dark.css">
132
+ <body class="theme-dark">
133
+ ...
134
+ </body>
135
+ ```
136
+
137
+ ### Creating Custom Themes
138
+
139
+ You can create your own theme by overriding CSS variables. Copy the dark theme file as a starting point and customize the values:
140
+
141
+ ```css
142
+ /* my-custom-theme.css */
143
+ .theme-custom {
144
+ --dt-primary: #8b5cf6;
145
+ --dt-primary-hover: #7c3aed;
146
+ --dt-bg-base: #1e1b2e;
147
+ --dt-bg-light: #2d2a3e;
148
+ --dt-text-primary: #e2e0f0;
149
+ /* ... override more variables as needed */
150
+ }
151
+ ```
152
+
153
+ Then include and activate your custom theme:
154
+
155
+ ```html
156
+ <link rel="stylesheet" href="div-table.css">
157
+ <link rel="stylesheet" href="my-custom-theme.css">
158
+ <body class="theme-custom">
159
+ ...
160
+ </body>
161
+ ```
162
+
163
+ ### CSS Variables Reference
164
+
165
+ All theme colors are defined as CSS custom properties (variables) in `:root`. Override these in your custom theme class:
166
+
167
+ | Variable | Description |
168
+ |----------|-------------|
169
+ | `--dt-primary` | Primary/accent color |
170
+ | `--dt-bg-base` | Base background color |
171
+ | `--dt-bg-light` | Light background (header, toolbar) |
172
+ | `--dt-bg-hover` | Row hover background |
173
+ | `--dt-bg-selected` | Selected row background |
174
+ | `--dt-border-light` | Light border color |
175
+ | `--dt-border-medium` | Medium border color |
176
+ | `--dt-text-primary` | Primary text color |
177
+ | `--dt-text-secondary` | Secondary text color |
178
+ | `--dt-text-muted` | Muted/disabled text |
179
+ | `--dt-button-bg` | Button background |
180
+ | `--dt-button-text` | Button text color |
181
+ | `--dt-error` | Error state color |
182
+ | `--dt-success` | Success state color |
183
+ | `--dt-warning` | Warning state color |
184
+ | `--dt-info` | Info state color |
185
+
186
+ See `src/div-table.css` for the full list of available variables.
187
+
31
188
  ### Option 1: Minified (Production)
32
189
 
33
190
  ```html
@@ -59,9 +216,11 @@ npm install @vii7/div-table-widget monaco-editor
59
216
  | File | Size | Description |
60
217
  |------|------|-------------|
61
218
  | `dist/divtable.min.js` | ~98KB | Minified JavaScript |
62
- | `dist/divtable.min.css` | ~22KB | Minified CSS |
219
+ | `dist/divtable.min.css` | ~22KB | Minified CSS (base theme) |
220
+ | `dist/divtable-theme-dark.min.css` | ~2KB | Minified dark theme (optional) |
63
221
  | `src/div-table.js` | ~220KB | Source JavaScript |
64
222
  | `src/div-table.css` | ~33KB | Source CSS (with CSS variables) |
223
+ | `src/div-table-theme-dark.css` | ~3KB | Source dark theme (optional) |
65
224
  | `src/query.js` | ~78KB | Query language engine (required) |
66
225
 
67
226
  ## Quick Start
@@ -87,10 +246,10 @@ npm install @vii7/div-table-widget monaco-editor
87
246
  const divTable = new DivTable(monaco, {
88
247
  tableWidgetElement: document.getElementById('table-container'),
89
248
  columns: [
90
- { field: 'id', header: 'ID', primaryKey: true },
91
- { field: 'name', header: 'Name' },
92
- { field: 'email', header: 'Email' },
93
- { field: 'status', header: 'Status' }
249
+ { field: 'id', label: 'ID', primaryKey: true },
250
+ { field: 'name', label: 'Name' },
251
+ { field: 'email', label: 'Email' },
252
+ { field: 'status', label: 'Status' }
94
253
  ],
95
254
  data: [
96
255
  { id: 1, name: 'John Doe', email: 'john@example.com', status: 'active' },
@@ -117,9 +276,9 @@ npm install @vii7/div-table-widget monaco-editor
117
276
  const divTable = new DivTable(monaco, {
118
277
  tableWidgetElement: document.getElementById('table-container'),
119
278
  columns: [
120
- { field: 'id', header: 'ID', primaryKey: true },
121
- { field: 'name', header: 'Name' },
122
- { field: 'age', header: 'Age' }
279
+ { field: 'id', label: 'ID', primaryKey: true },
280
+ { field: 'name', label: 'Name' },
281
+ { field: 'age', label: 'Age' }
123
282
  ],
124
283
  virtualScrolling: true,
125
284
  pageSize: 100,
@@ -333,11 +492,11 @@ Keep the first N columns fixed (frozen) on the left side while scrolling horizon
333
492
  const divTable = new DivTable(monaco, {
334
493
  tableWidgetElement: document.getElementById('table-container'),
335
494
  columns: [
336
- { field: 'id', header: 'ID', primaryKey: true },
337
- { field: 'name', header: 'Name' },
338
- { field: 'email', header: 'Email' },
339
- { field: 'department', header: 'Department' },
340
- { field: 'status', header: 'Status' }
495
+ { field: 'id', label: 'ID', primaryKey: true },
496
+ { field: 'name', label: 'Name' },
497
+ { field: 'email', label: 'Email' },
498
+ { field: 'department', label: 'Department' },
499
+ { field: 'status', label: 'Status' }
341
500
  ],
342
501
  data: myData,
343
502
  fixedColumns: 2 // Freeze first 2 columns (ID and Name)
@@ -0,0 +1 @@
1
+ .dark,.theme-dark{--dt-primary:#ffa200;--dt-primary-hover:#cc8100;--dt-primary-light:rgba(255,162,0,.12);--dt-primary-lighter:rgba(255,162,0,.07);--dt-focus-ring:rgba(255,162,0,.18);--dt-bg-base:#171717;--dt-bg-light:#242424;--dt-bg-hover:#2e2e2e;--dt-bg-selected:rgba(255,162,0,.12);--dt-bg-header:#1f1f1f;--dt-bg-summary:#1f1f1f;--dt-bg-disabled:#333;--dt-border-light:#383838;--dt-border-medium:#333;--dt-border-dark:#2e2e2e;--dt-border-row:#383838;--dt-border-focus:#ffa200;--dt-border-hover:#ffa200;--dt-text-primary:#fafafa;--dt-text-secondary:#e6e6e6;--dt-text-muted:#999;--dt-text-light:#e6e6e6;--dt-text-disabled:#8c8c8c;--dt-text-inverse:#171717;--dt-shadow:rgba(0,0,0,.4);--dt-shadow-medium:rgba(0,0,0,.5);--dt-shadow-heavy:rgba(0,0,0,.6);--dt-error:#ef4343;--dt-error-light:rgba(239,67,67,.6);--dt-error-hover:#7c1d1d;--dt-error-active:#531313;--dt-error-bg:#2e1919;--dt-error-border:#f37272;--dt-error-text:#f15b5b;--dt-error-border-hover:rgba(239,67,67,.6);--dt-error-focus-ring:rgba(239,67,67,.25);--dt-success:#24db6a;--dt-success-bg:#1d3024;--dt-success-bg-hover:#2a4635;--dt-warning:#ffb700;--dt-warning-bg:#302a1d;--dt-warning-bg-hover:#463e2a;--dt-info:#3ebdf4;--dt-info-bg:#1d2a30;--dt-info-bg-hover:#2a3e46;--dt-button-bg:#242424;--dt-button-bg-hover:#2e2e2e;--dt-button-text:#fafafa;--dt-scrollbar-track:#242424;--dt-scrollbar-thumb:#383838;--dt-scrollbar-thumb-hover:#474747;--dt-spinner-track:#333;--dt-spinner-active:#e6e6e6;--dt-skeleton-base:#242424;--dt-skeleton-shine:#333;--dt-group-bg:rgba(36,36,36,.5);--dt-summary-border:#2e2e2e}
@@ -0,0 +1 @@
1
+ !function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t():"function"==typeof define&&define.amd?define([],t):"object"==typeof exports?exports.DivTable=t():e.DivTable=t()}(this,()=>(()=>{"use strict";var e={r:e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})}},t={};return e.r(t),t})());
@@ -1 +1 @@
1
- :root{--dt-primary:#007bff;--dt-primary-hover:#0056b3;--dt-primary-light:rgba(0,123,255,.1);--dt-primary-lighter:rgba(0,123,255,.05);--dt-focus-ring:rgba(3,102,214,.1);--dt-bg-base:#fff;--dt-bg-light:#f9f9f7;--dt-bg-hover:#f0f7ff;--dt-bg-selected:rgba(0,123,255,.1);--dt-bg-header:#f9f9f7;--dt-bg-summary:#f9f9f7;--dt-bg-disabled:#f0f0f0;--dt-border-light:#e9ecef;--dt-border-medium:#e1e5e9;--dt-border-dark:#ced4da;--dt-border-row:#f1f3f4;--dt-border-focus:#123a67;--dt-border-hover:#b0b8c1;--dt-text-primary:#374151;--dt-text-secondary:#495057;--dt-text-muted:#6b7280;--dt-text-light:#666;--dt-text-disabled:#999;--dt-text-inverse:#fff;--dt-shadow:rgba(0,0,0,.1);--dt-shadow-medium:rgba(0,0,0,.12);--dt-shadow-heavy:rgba(0,0,0,.15);--dt-error:#dc3545;--dt-error-light:rgba(220,53,69,.6);--dt-error-hover:#c82333;--dt-error-active:#bd2130;--dt-error-bg:#fff5f5;--dt-error-border:#fed7d7;--dt-error-text:#c53030;--dt-error-border-hover:rgba(200,35,51,.6);--dt-error-focus-ring:rgba(220,53,69,.25);--dt-success:#28a745;--dt-success-bg:#e8f5e9;--dt-success-bg-hover:#c8e6c9;--dt-warning:#ffc107;--dt-warning-bg:#fff8e1;--dt-warning-bg-hover:#ffecb3;--dt-info:#0ea5e9;--dt-info-bg:#e0f2fe;--dt-info-bg-hover:#bae6fd;--dt-button-bg:#f0f0f0;--dt-button-bg-hover:#e0e0e0;--dt-button-text:#333;--dt-scrollbar-track:#f1f1f1;--dt-scrollbar-thumb:#c1c1c1;--dt-scrollbar-thumb-hover:#a8a8a8;--dt-spinner-track:#e3e3e3;--dt-spinner-active:#666;--dt-skeleton-base:#e9ecef;--dt-skeleton-shine:#f8f9fa;--dt-group-bg:hsla(60,14%,97%,.5);--dt-summary-border:#adb5bd}.div-table-widget{background:var(--dt-bg-base);border-radius:8px;box-shadow:0 2px 8px var(--dt-shadow);box-sizing:border-box;display:flex;flex-direction:column;overflow:hidden;width:100%}.div-table-toolbar{align-items:center;background:var(--dt-bg-light);border-bottom:1px solid var(--dt-border-light);display:flex;flex-shrink:0;gap:10px;padding:16px}.query-inputfield{background:var(--dt-bg-base);border:2px solid var(--dt-border-medium);border-radius:8px;box-shadow:0 1px 3px var(--dt-shadow);flex:1;min-width:50%;overflow:hidden;padding:10px 5px 4px 10px;transition:all .2s ease-in-out}.query-inputfield:hover{border-color:var(--dt-border-hover);box-shadow:0 2px 4px var(--dt-shadow-medium)}.query-inputfield.focused{border-color:var(--dt-border-focus);box-shadow:0 0 0 3px var(--dt-focus-ring),0 1px 3px var(--dt-shadow);outline:none}.query-inputfield.error{border-color:var(--dt-error-light)}.query-inputfield.error:hover{border-color:var(--dt-error-border-hover)}.query-inputfield.error.focused{border-color:var(--dt-error-light);box-shadow:0 0 0 3px var(--dt-error-focus-ring),0 1px 3px var(--dt-shadow)}.query-inputfield .monaco-editor{height:22px!important;--vscode-focusBorder:transparent}.div-table-toolbar select{appearance:none;-webkit-appearance:none;-moz-appearance:none;background:var(--dt-bg-base);background-image:url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='none' viewBox='0 0 20 20'%3E%3Cpath stroke='%236b7280' stroke-linecap='round' stroke-linejoin='round' stroke-width='1.5' d='m6 8 4 4 4-4'/%3E%3C/svg%3E");background-position:right 8px center;background-repeat:no-repeat;background-size:16px;border:2px solid var(--dt-border-medium);border-radius:8px;box-shadow:0 1px 3px var(--dt-shadow);color:var(--dt-text-secondary);cursor:pointer;font-size:14px;min-width:150px;padding:10px 32px 10px 12px;transition:all .2s ease-in-out}.div-table-toolbar select:hover{border-color:var(--dt-border-hover);box-shadow:0 2px 4px var(--dt-shadow-medium)}.div-table-toolbar select:focus{border-color:var(--dt-border-focus);box-shadow:0 0 0 3px var(--dt-focus-ring),0 1px 3px var(--dt-shadow);outline:none}.div-table-toolbar select:disabled{background-color:var(--dt-bg-light);border-color:var(--dt-border-light);color:var(--dt-text-muted);cursor:not-allowed}.info-section{color:var(--dt-text-light);display:flex;flex-direction:column;font-size:.9em;gap:0;margin-left:auto;min-width:200px;padding:0;text-align:right}.info-line-container{gap:8px}.info-line,.info-line-container{align-items:center;display:flex;justify-content:flex-end}.info-line.secondary{color:var(--dt-text-disabled);font-size:.8em}.refresh-button{align-items:center;background:none;border:none;border-radius:3px;color:var(--dt-text-light);cursor:pointer;display:flex;flex-shrink:0;height:22px;justify-content:center;min-height:22px;min-width:22px;padding:4px;transition:all .2s ease;width:22px}.refresh-button:hover{background-color:var(--dt-button-bg);color:var(--dt-button-text)}.refresh-button:active{background-color:var(--dt-button-bg-hover)}.refresh-button.refreshing{color:var(--dt-primary)}.refresh-button.refreshing svg{animation:spin 1s linear infinite}.refresh-button svg{height:14px;transition:transform .2s ease;width:14px}.auto-fetch-button{align-items:center;background:none;border:none;border-radius:3px;color:var(--dt-text-light);cursor:pointer;display:flex;flex-shrink:0;height:22px;justify-content:center;margin-left:4px;min-height:22px;min-width:22px;padding:4px;transition:all .2s ease;width:22px}.auto-fetch-button:hover{background-color:var(--dt-button-bg);color:var(--dt-button-text)}.auto-fetch-button:active{background-color:var(--dt-button-bg-hover)}.auto-fetch-button.active{background-color:var(--dt-success-bg);color:var(--dt-success)}.auto-fetch-button.active:hover{background-color:var(--dt-success-bg-hover)}.auto-fetch-button.paused{background-color:var(--dt-warning-bg);color:var(--dt-warning)}.auto-fetch-button.paused:hover{background-color:var(--dt-warning-bg-hover)}.auto-fetch-button:disabled{cursor:not-allowed;opacity:.5}.auto-fetch-button svg{height:14px;transition:transform .2s ease;width:14px}.filter-selected-only-toggle-button{align-items:center;background:none;border:none;border-radius:3px;color:var(--dt-text-light);cursor:pointer;display:flex;flex-shrink:0;height:22px;justify-content:center;margin-right:6px;min-height:22px;min-width:22px;padding:4px;transition:all .2s ease;width:22px}.filter-selected-only-toggle-button:hover{background-color:var(--dt-button-bg);color:var(--dt-button-text)}.filter-selected-only-toggle-button:active{background-color:var(--dt-button-bg-hover)}.filter-selected-only-toggle-button.active{background-color:var(--dt-info-bg);color:var(--dt-info)}.filter-selected-only-toggle-button.active:hover{background-color:var(--dt-info-bg-hover)}.filter-selected-only-toggle-button svg{height:14px;transition:transform .2s ease;width:14px}.info-selection{font-weight:600}.info-stats{color:var(--dt-text-light)}.progress-line{align-items:center;display:flex;justify-content:flex-end;margin-top:2px}.loading-progress{background:var(--dt-border-light);border-radius:2px;height:4px;overflow:hidden;position:relative;width:120px}.progress-segment{border-radius:2px;height:100%;position:absolute;top:0;transition:width .3s ease,left .3s ease}.filtered-segment{background:var(--dt-error);z-index:3}.loaded-segment{background:var(--dt-text-secondary);z-index:2}.loading-segment{background:var(--dt-primary);z-index:1}.loading-segment:after{animation:loading-shimmer 1.5s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.8),transparent);bottom:0;content:"";left:0;position:absolute;right:0;top:0}.loading-progress[data-state=filtered-loading],.loading-progress[data-state=sequential-loading]{position:relative}.loading-progress[data-state=filtered] .loaded-segment{background:var(--dt-text-light)}.loading-progress-bar{background:var(--dt-text-secondary);border-radius:2px;height:100%;position:relative;transition:width .3s ease}.loading-progress-bar.loading:after{animation:loading-shimmer 1.5s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.8),transparent);bottom:0;content:"";left:0;position:absolute;right:0;top:0}.loading-progress[data-state=filtered] .loading-progress-bar{background:var(--dt-text-light)}.loading-progress[data-state=filtered] .loading-progress-bar.loading:after{animation:filtered-shimmer 2s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.4),transparent)}.loading-progress[data-state=loading] .loading-progress-bar{background:var(--dt-text-secondary)}@keyframes loading-shimmer{0%{transform:translateX(-100%)}to{transform:translateX(100%)}}@keyframes filtered-shimmer{0%{transform:translateX(-100%)}to{transform:translateX(100%)}}.div-table-container{background:var(--dt-bg-base);display:flex;flex:1;flex-direction:column;min-height:0;overflow:hidden;width:100%}.div-table-header{align-items:auto;backdrop-filter:blur(10px);-webkit-backdrop-filter:blur(10px);background:var(--dt-bg-header);border-bottom:1px solid var(--dt-border-light);color:var(--dt-text-primary);display:grid;flex-shrink:0;min-height:48px;position:sticky;top:0;transition:box-shadow .3s cubic-bezier(.4,0,.2,1);z-index:10}.scrollbar-spacer{background:transparent;pointer-events:none}.div-table-header.scrolled{box-shadow:0 2px 8px var(--dt-shadow)}.div-table-body{background:var(--dt-bg-base);flex:1;min-height:0;overflow-y:auto}.div-table-row{align-items:stretch;border-bottom:1px solid var(--dt-border-row);box-sizing:border-box;cursor:pointer;display:grid;gap:0;min-height:40px;transition:all .2s ease}.div-table-row:hover{background-color:var(--dt-bg-hover)}.div-table-row:last-child{border-bottom:none}.div-table-cell{box-sizing:border-box;min-width:0;text-overflow:ellipsis;white-space:nowrap}.div-table-cell,.div-table-header-cell{align-items:flex-start;display:flex;overflow:hidden;padding:8px 12px}.div-table-header-cell{color:var(--dt-text-primary);cursor:pointer;justify-content:space-between;transition:background-color .2s ease;user-select:none}.header-left-content{align-items:center;display:flex;flex:1 1 auto;font-weight:600;gap:0;min-width:0;overflow:hidden}.header-left-content>span{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.header-right-content{align-items:center;display:flex;flex:0 0 auto;gap:4px;margin-left:8px}.div-table-header-cell:hover{background-color:var(--dt-shadow)}.group-indicator{align-items:center;display:inline-flex;font-size:12px;height:20px;justify-content:center;opacity:0;transition:opacity .2s ease;width:14px}.div-table-header-cell:hover .group-indicator{opacity:.5}.group-indicator:hover{opacity:1!important}.group-indicator.grouped{color:inherit;opacity:1!important}.sort-indicator{align-items:center;display:inline-flex;height:20px;justify-content:center;opacity:0;transition:opacity .2s ease;width:14px}.div-table-header-cell:hover .sort-indicator{opacity:.5}.sort-indicator.active{opacity:1!important}.header-right-content>span:last-child:not(.group-indicator):not(.sort-indicator){opacity:0;transition:opacity .2s ease}.div-table-header-cell:hover .header-right-content>span:last-child:not(.group-indicator):not(.sort-indicator){opacity:.5}.div-table-header-cell.sorted .header-right-content>span:last-child:not(.sort-indicator){opacity:1!important}.sub-sort-indicator{align-items:center;display:inline-flex;height:20px;justify-content:center;opacity:0;transition:opacity .2s ease;width:14px}.composite-header:hover .sub-sort-indicator,.composite-sub-header:hover .sub-sort-indicator{opacity:.5}.sub-sort-indicator.active{opacity:1!important}.div-table-cell.checkbox-column,.div-table-header-cell.checkbox-column{justify-content:center;max-width:40px;min-width:40px;padding:8px 4px;width:40px}.div-table-cell.checkbox-column input[type=checkbox],.div-table-header-cell.checkbox-column input[type=checkbox]{accent-color:var(--dt-primary);cursor:pointer;height:15px;margin:0;width:15px}input[type=checkbox]:indeterminate{background-color:var(--dt-primary);border-color:var(--dt-primary);position:relative}input[type=checkbox]:indeterminate:after{color:var(--dt-text-inverse);content:"━";font-size:10px;font-weight:700;left:50%;position:absolute;top:50%;transform:translate(-50%,-50%)}.div-table-header-cell.checkbox-column input[type=checkbox]:indeterminate{background-color:var(--dt-primary);border-color:var(--dt-primary)}.div-table-row.selected{background-color:var(--dt-bg-selected)!important}.div-table-row.focused{background-color:var(--dt-bg-base);box-shadow:inset 3px 0 0 var(--dt-primary)}.div-table-row.focused:hover{background-color:var(--dt-primary-lighter)!important}.div-table-row.group-header.focused{background-color:var(--dt-bg-base)!important;box-shadow:inset 3px 0 0 var(--dt-primary)!important}.div-table-row.group-header.focused:hover{background-color:var(--dt-bg-hover)!important}.div-table-row.group-header{background:var(--dt-bg-base);border-bottom:1px solid var(--dt-border-row);border-top:1px solid var(--dt-border-row);box-shadow:none;color:var(--dt-text-secondary);font-weight:400;isolation:isolate;position:sticky;top:0;z-index:9}.div-table-row.group-header:first-of-type{border-top:none}.div-table-row.group-header:hover{background-color:var(--dt-bg-hover)}.div-table-row.group-header:first-of-type{box-shadow:0 2px 8px var(--dt-shadow-heavy)}.div-table-row.group-header .div-table-cell span{font-weight:600}.div-table-row.group-header .checkbox-column{align-items:center;display:flex;justify-content:center}.div-table-row.group-header .checkbox-column input[type=checkbox]{accent-color:var(--dt-primary);cursor:pointer;height:15px;width:15px}.div-table-row.group-header .checkbox-column input[type=checkbox]:indeterminate{background-color:var(--dt-primary)}.group-toggle,.group-toggle-all{align-items:center;border-radius:3px;cursor:pointer;display:inline-flex;font-size:.9em;justify-content:center;min-height:20px;min-width:20px;padding:2px;transform:rotate(90deg);transition:transform .2s ease}.group-toggle-all.collapsed,.group-toggle.collapsed{transform:rotate(0deg)}.group-toggle-all{font-size:1em;font-weight:700;margin-right:6px}.group-toggle-all:hover,.group-toggle:hover{background-color:var(--dt-shadow);opacity:.7}.div-table-cell.grouped-column{color:var(--dt-text-disabled);font-style:italic}.div-table-cell.composite-column{align-items:flex-start;display:flex;flex-direction:column;gap:2px;padding:6px 12px;white-space:normal}.composite-sub{color:var(--dt-text-muted);line-height:1.2}.div-table-cell.composite-cell{align-items:stretch;display:flex;flex-direction:column;gap:0;padding:8px 12px}.composite-sub-cell{align-items:center;display:flex;min-width:0;overflow:hidden}.composite-sub-cell:first-child{margin-bottom:4px}.composite-sub-cell:not(:first-child){color:var(--dt-text-muted)}.div-table-header-cell.composite-header{flex-direction:column;gap:4px;justify-content:flex-start;padding:8px 12px}.composite-sub-header{border-radius:4px;cursor:pointer;min-width:0;padding:0;transition:background-color .2s ease;user-select:none;width:100%}.composite-sub-header:first-child{color:var(--dt-text-primary);font-weight:600;margin-bottom:4px}.composite-sub-header:hover{background-color:var(--dt-bg-disabled)}.composite-toggle{cursor:pointer;display:inline-block;font-size:.9em;transition:transform .2s ease;user-select:none}.composite-toggle:hover{opacity:.7}.div-table-row.group-collapsed{display:none}.col-fixed-narrow{grid-column:span 1;max-width:80px;min-width:60px}.col-fixed-medium{grid-column:span 1;max-width:140px;min-width:100px}.col-flexible-small{flex:1;grid-column:span 1;min-width:120px}.col-flexible-medium{flex:2;grid-column:span 2;min-width:150px}.col-flexible-large{flex:3;grid-column:span 3;min-width:200px}.div-table-header.grid-5-cols,.div-table-row.grid-5-cols{grid-template-columns:40px 1fr 100px 200px 100px}.div-table-header.grid-4-cols,.div-table-row.grid-4-cols{grid-template-columns:40px 2fr 200px 100px}.div-table-header,.div-table-row{grid-template-columns:repeat(auto-fit,minmax(100px,1fr))}@media (max-width:768px){.div-table-toolbar{align-items:stretch;flex-direction:column;gap:8px}.query-inputfield{max-width:100%;width:100%}.div-table-cell.hidden-mobile,.div-table-header-cell.hidden-mobile{display:none}.div-table-header.grid-4-cols,.div-table-header.grid-5-cols,.div-table-row.grid-4-cols,.div-table-row.grid-5-cols{grid-template-columns:40px 2fr 1fr}}@media (max-width:480px){.div-table-cell.hidden-small,.div-table-header-cell.hidden-small{display:none}.div-table-header.grid-4-cols,.div-table-header.grid-5-cols,.div-table-row.grid-4-cols,.div-table-row.grid-5-cols{grid-template-columns:40px 1fr}}.div-table-widget.no-checkboxes .checkbox-column{display:none}.div-table-widget.no-checkboxes .div-table-header.grid-5-cols,.div-table-widget.no-checkboxes .div-table-row.grid-5-cols{grid-template-columns:1fr 2fr 2fr 1fr}.div-table-widget.no-checkboxes .div-table-header.grid-4-cols,.div-table-widget.no-checkboxes .div-table-row.grid-4-cols{grid-template-columns:2fr 2fr 1fr}.div-table-body::-webkit-scrollbar{width:8px}.div-table-body::-webkit-scrollbar-track{background:var(--dt-scrollbar-track);border-radius:4px}.div-table-body::-webkit-scrollbar-thumb{background:var(--dt-scrollbar-thumb);border-radius:4px}.div-table-body::-webkit-scrollbar-thumb:hover{background:var(--dt-scrollbar-thumb-hover)}.div-table-empty{color:var(--dt-text-disabled)}.div-table-empty,.div-table-loading{align-items:center;display:flex;font-style:italic;justify-content:center;min-height:200px}.div-table-loading{color:var(--dt-text-light);position:relative}.div-table-loading:before{animation:spin 1s linear infinite;border-top:2px solid var(--dt-spinner-track);border:2px solid var(--dt-spinner-track);border-radius:50%;border-top-color:var(--dt-spinner-active);content:"";height:20px;margin-right:10px;width:20px}@keyframes spin{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.error-indicator{align-items:center;background:var(--dt-error-bg);border:1px solid var(--dt-error-border);border-radius:3px;color:var(--dt-error-text);display:none;font-size:14px;gap:10px;justify-content:center;margin:10px 0;padding:15px}.div-table-row.loading-placeholder{background:var(--dt-group-bg);border-bottom:1px solid var(--dt-border-row);cursor:default;pointer-events:none}.div-table-row.loading-placeholder:hover{background:var(--dt-group-bg)!important}.div-table-cell.loading-cell{align-items:center;display:flex;padding:8px 12px}.loading-shimmer-content{animation:loading-shimmer 1.5s infinite;background:linear-gradient(90deg,var(--dt-skeleton-base) 25%,var(--dt-skeleton-shine) 50%,var(--dt-skeleton-base) 75%);background-size:200% 100%;border-radius:4px;height:16px}.retry-button{align-items:stretch;background:var(--dt-error);border:none;border-radius:4px;color:var(--dt-text-inverse);flex-direction:column;gap:0;padding:8px 12px}.div-table-cell.composite-cell .composite-sub-cell{align-items:flex-start}.retry-button:hover{background:var(--dt-error-hover)}.retry-button:active{background:var(--dt-error-active)}.div-table-container.has-fixed-columns{display:flex;flex-direction:column;overflow:hidden}.div-table-columns-wrapper{display:flex;flex:1;min-height:0;overflow:hidden}.div-table-fixed-section{background:var(--dt-bg-base);border-right:1px solid var(--dt-border-light);display:flex;flex:0 0 auto;flex-direction:column;z-index:5}.div-table-fixed-section.has-scroll-shadow{box-shadow:2px 0 8px var(--dt-shadow)}.div-table-scroll-section{display:flex;flex:1 1 auto;flex-direction:column;min-width:0;overflow:hidden}.div-table-fixed-header{display:grid;z-index:11}.div-table-fixed-header,.div-table-scroll-header{box-sizing:border-box;flex-shrink:0;position:relative}.div-table-scroll-header{overflow-x:scroll;overflow-y:hidden;scrollbar-width:none;z-index:10;-ms-overflow-style:none}.div-table-scroll-header::-webkit-scrollbar{display:none}.div-table-scroll-header-inner{display:grid;min-width:100%;width:max-content}.div-table-fixed-body{flex:1;min-height:0;overflow-x:hidden;overflow-y:auto}.div-table-fixed-body::-webkit-scrollbar{display:none}.div-table-fixed-body{-ms-overflow-style:none;scrollbar-width:none}.div-table-scroll-body{flex:1;min-height:0;overflow:auto;overflow-x:overlay;overflow-y:overlay}@supports (scrollbar-gutter:stable){.div-table-scroll-body{overflow-x:auto;overflow-y:auto}.div-table-fixed-body,.div-table-scroll-body{scrollbar-gutter:stable}}.div-table-fixed-row,.div-table-scroll-row{align-items:flex-start;box-sizing:border-box;min-height:40px}.div-table-fixed-row,.div-table-scroll-row{background:var(--dt-bg-base);display:grid}.div-table-row.hover,.div-table-row:hover{background-color:var(--dt-bg-hover)}.div-table-fixed-row.selected,.div-table-scroll-row.selected{background-color:var(--dt-bg-selected)!important}.div-table-fixed-row.focused,.div-table-scroll-row.focused{background-color:var(--dt-bg-base);box-shadow:inset 3px 0 0 var(--dt-primary)}.div-table-fixed-row.focused.hover,.div-table-fixed-row.focused:hover,.div-table-scroll-row.focused.hover,.div-table-scroll-row.focused:hover{background-color:var(--dt-primary-lighter)!important}.div-table-fixed-row.group-header,.div-table-scroll-row.group-header{background:var(--dt-bg-base);border-bottom:1px solid var(--dt-border-row);border-top:1px solid var(--dt-border-row);position:sticky;top:0;z-index:4}.div-table-fixed-row.group-header.focused,.div-table-scroll-row.group-header.focused{background-color:var(--dt-bg-base)!important;box-shadow:inset 3px 0 0 var(--dt-primary)!important}.div-table-scroll-section .div-table-cell{overflow:visible;text-overflow:clip;white-space:nowrap}.div-table-scroll-section .div-table-header-cell,.div-table-scroll-section .header-left-content{overflow:visible}.div-table-scroll-section .header-left-content>span{overflow:visible;text-overflow:clip;white-space:nowrap}.div-table-scroll-row{min-width:100%;width:max-content}@media (max-width:768px){.div-table-container.has-fixed-columns{display:flex;flex-direction:column}.div-table-columns-wrapper{flex-direction:column}.div-table-fixed-section{border-bottom:1px solid var(--dt-border-light);border-right:none;box-shadow:0 2px 8px var(--dt-shadow);flex:0 0 auto}.div-table-scroll-section{flex:1 1 auto}}.div-table-row.summary-row{background-color:var(--dt-bg-base);border-bottom:2px solid var(--dt-border-dark);font-weight:600;min-height:32px}.div-table-row.header-summary{background-color:var(--dt-bg-summary);border-bottom:1px solid var(--dt-summary-border);position:sticky;top:0;z-index:2}.div-table-row.group-summary{border-bottom:1px solid var(--dt-summary-border);font-size:.95em;font-weight:500}.div-table-cell.summary-cell{color:var(--dt-text-secondary);padding:8px 12px}.aggregate-value{color:var(--dt-text-primary);font-variant-numeric:tabular-nums;font-weight:700}.div-table-row.summary-row:hover{background-color:var(--dt-bg-summary)}.div-table-fixed-row.summary-row{background-color:var(--dt-bg-base);min-height:32px}.div-table-fixed-row.header-summary{background-color:var(--dt-bg-summary)}.div-table-cell.summary-cell:empty{min-height:1em}
1
+ :root{--dt-primary:#007bff;--dt-primary-hover:#0056b3;--dt-primary-light:rgba(0,123,255,.1);--dt-primary-lighter:rgba(0,123,255,.05);--dt-focus-ring:rgba(3,102,214,.1);--dt-bg-base:#fff;--dt-bg-light:#f9f9f7;--dt-bg-hover:#f0f7ff;--dt-bg-selected:rgba(0,123,255,.1);--dt-bg-header:#f9f9f7;--dt-bg-summary:#f9f9f7;--dt-bg-disabled:#f0f0f0;--dt-border-light:#e9ecef;--dt-border-medium:#e1e5e9;--dt-border-dark:#ced4da;--dt-border-row:#f1f3f4;--dt-border-focus:#123a67;--dt-border-hover:#b0b8c1;--dt-text-primary:#374151;--dt-text-secondary:#495057;--dt-text-muted:#6b7280;--dt-text-light:#666;--dt-text-disabled:#999;--dt-text-inverse:#fff;--dt-shadow:rgba(0,0,0,.1);--dt-shadow-medium:rgba(0,0,0,.12);--dt-shadow-heavy:rgba(0,0,0,.15);--dt-error:#dc3545;--dt-error-light:rgba(220,53,69,.6);--dt-error-hover:#c82333;--dt-error-active:#bd2130;--dt-error-bg:#fff5f5;--dt-error-border:#fed7d7;--dt-error-text:#c53030;--dt-error-border-hover:rgba(200,35,51,.6);--dt-error-focus-ring:rgba(220,53,69,.25);--dt-success:#28a745;--dt-success-bg:#e8f5e9;--dt-success-bg-hover:#c8e6c9;--dt-warning:#ffc107;--dt-warning-bg:#fff8e1;--dt-warning-bg-hover:#ffecb3;--dt-info:#0ea5e9;--dt-info-bg:#e0f2fe;--dt-info-bg-hover:#bae6fd;--dt-button-bg:#f0f0f0;--dt-button-bg-hover:#e0e0e0;--dt-button-text:#333;--dt-scrollbar-track:#f1f1f1;--dt-scrollbar-thumb:#c1c1c1;--dt-scrollbar-thumb-hover:#a8a8a8;--dt-spinner-track:#e3e3e3;--dt-spinner-active:#666;--dt-skeleton-base:#e9ecef;--dt-skeleton-shine:#f8f9fa;--dt-group-bg:hsla(60,14%,97%,.5);--dt-summary-border:#adb5bd}.div-table-widget{background:var(--dt-bg-base);border-radius:8px;box-shadow:0 2px 8px var(--dt-shadow);box-sizing:border-box;display:flex;flex-direction:column;height:100%;overflow:hidden;width:100%}.div-table-toolbar{align-items:center;background:var(--dt-bg-light);border-bottom:1px solid var(--dt-border-light);display:flex;flex-shrink:0;gap:10px;padding:16px}.query-inputfield{background:var(--dt-bg-base);border:2px solid var(--dt-border-medium);border-radius:8px;box-shadow:0 1px 3px var(--dt-shadow);flex:1;min-width:50%;overflow:hidden;padding:10px 5px 4px 10px;transition:all .2s ease-in-out}.query-inputfield:hover{border-color:var(--dt-border-hover);box-shadow:0 2px 4px var(--dt-shadow-medium)}.query-inputfield.focused{border-color:var(--dt-border-focus);box-shadow:0 0 0 3px var(--dt-focus-ring),0 1px 3px var(--dt-shadow);outline:none}.query-inputfield.error{border-color:var(--dt-error-light)}.query-inputfield.error:hover{border-color:var(--dt-error-border-hover)}.query-inputfield.error.focused{border-color:var(--dt-error-light);box-shadow:0 0 0 3px var(--dt-error-focus-ring),0 1px 3px var(--dt-shadow)}.query-inputfield .monaco-editor{height:22px!important;--vscode-focusBorder:transparent}.div-table-toolbar select{appearance:none;-webkit-appearance:none;-moz-appearance:none;background:var(--dt-bg-base);background-image:url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='none' viewBox='0 0 20 20'%3E%3Cpath stroke='%236b7280' stroke-linecap='round' stroke-linejoin='round' stroke-width='1.5' d='m6 8 4 4 4-4'/%3E%3C/svg%3E");background-position:right 8px center;background-repeat:no-repeat;background-size:16px;border:2px solid var(--dt-border-medium);border-radius:8px;box-shadow:0 1px 3px var(--dt-shadow);color:var(--dt-text-secondary);cursor:pointer;font-size:14px;min-width:150px;padding:10px 32px 10px 12px;transition:all .2s ease-in-out}.div-table-toolbar select:hover{border-color:var(--dt-border-hover);box-shadow:0 2px 4px var(--dt-shadow-medium)}.div-table-toolbar select:focus{border-color:var(--dt-border-focus);box-shadow:0 0 0 3px var(--dt-focus-ring),0 1px 3px var(--dt-shadow);outline:none}.div-table-toolbar select:disabled{background-color:var(--dt-bg-light);border-color:var(--dt-border-light);color:var(--dt-text-muted);cursor:not-allowed}.info-section{color:var(--dt-text-light);display:flex;flex-direction:column;font-size:.9em;gap:0;margin-left:auto;min-width:200px;padding:0;text-align:right}.info-line-container{gap:8px}.info-line,.info-line-container{align-items:center;display:flex;justify-content:flex-end}.info-line.secondary{color:var(--dt-text-disabled);font-size:.8em}.refresh-button{align-items:center;background:none;border:none;border-radius:3px;color:var(--dt-text-light);cursor:pointer;display:flex;flex-shrink:0;height:22px;justify-content:center;min-height:22px;min-width:22px;padding:4px;transition:all .2s ease;width:22px}.refresh-button:hover{background-color:var(--dt-button-bg);color:var(--dt-button-text)}.refresh-button:active{background-color:var(--dt-button-bg-hover)}.refresh-button.refreshing{color:var(--dt-primary)}.refresh-button.refreshing svg{animation:spin 1s linear infinite}.refresh-button svg{height:14px;transition:transform .2s ease;width:14px}.auto-fetch-button{align-items:center;background:none;border:none;border-radius:3px;color:var(--dt-text-light);cursor:pointer;display:flex;flex-shrink:0;height:22px;justify-content:center;margin-left:4px;min-height:22px;min-width:22px;padding:4px;transition:all .2s ease;width:22px}.auto-fetch-button:hover{background-color:var(--dt-button-bg);color:var(--dt-button-text)}.auto-fetch-button:active{background-color:var(--dt-button-bg-hover)}.auto-fetch-button.active{background-color:var(--dt-success-bg);color:var(--dt-success)}.auto-fetch-button.active:hover{background-color:var(--dt-success-bg-hover)}.auto-fetch-button.paused{background-color:var(--dt-warning-bg);color:var(--dt-warning)}.auto-fetch-button.paused:hover{background-color:var(--dt-warning-bg-hover)}.auto-fetch-button:disabled{cursor:not-allowed;opacity:.5}.auto-fetch-button svg{height:14px;transition:transform .2s ease;width:14px}.filter-selected-only-toggle-button{align-items:center;background:none;border:none;border-radius:3px;color:var(--dt-text-light);cursor:pointer;display:flex;flex-shrink:0;height:22px;justify-content:center;margin-right:6px;min-height:22px;min-width:22px;padding:4px;transition:all .2s ease;width:22px}.filter-selected-only-toggle-button:hover{background-color:var(--dt-button-bg);color:var(--dt-button-text)}.filter-selected-only-toggle-button:active{background-color:var(--dt-button-bg-hover)}.filter-selected-only-toggle-button.active{background-color:var(--dt-info-bg);color:var(--dt-info)}.filter-selected-only-toggle-button.active:hover{background-color:var(--dt-info-bg-hover)}.filter-selected-only-toggle-button svg{height:14px;transition:transform .2s ease;width:14px}.info-selection{font-weight:600}.info-stats{color:var(--dt-text-light)}.progress-line{align-items:center;display:flex;justify-content:flex-end;margin-top:2px}.loading-progress{background:var(--dt-border-light);border-radius:2px;height:4px;overflow:hidden;position:relative;width:120px}.progress-segment{border-radius:2px;height:100%;position:absolute;top:0;transition:width .3s ease,left .3s ease}.filtered-segment{background:var(--dt-error);z-index:3}.loaded-segment{background:var(--dt-text-secondary);z-index:2}.loading-segment{background:var(--dt-primary);z-index:1}.loading-segment:after{animation:loading-shimmer 1.5s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.8),transparent);bottom:0;content:"";left:0;position:absolute;right:0;top:0}.loading-progress[data-state=filtered-loading],.loading-progress[data-state=sequential-loading]{position:relative}.loading-progress[data-state=filtered] .loaded-segment{background:var(--dt-text-light)}.loading-progress-bar{background:var(--dt-text-secondary);border-radius:2px;height:100%;position:relative;transition:width .3s ease}.loading-progress-bar.loading:after{animation:loading-shimmer 1.5s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.8),transparent);bottom:0;content:"";left:0;position:absolute;right:0;top:0}.loading-progress[data-state=filtered] .loading-progress-bar{background:var(--dt-text-light)}.loading-progress[data-state=filtered] .loading-progress-bar.loading:after{animation:filtered-shimmer 2s infinite;background:linear-gradient(90deg,transparent,hsla(0,0%,100%,.4),transparent)}.loading-progress[data-state=loading] .loading-progress-bar{background:var(--dt-text-secondary)}@keyframes loading-shimmer{0%{transform:translateX(-100%)}to{transform:translateX(100%)}}@keyframes filtered-shimmer{0%{transform:translateX(-100%)}to{transform:translateX(100%)}}.div-table-container{background:var(--dt-bg-base);display:flex;flex:1;flex-direction:column;min-height:0;overflow:hidden;width:100%}.div-table-header{align-items:auto;backdrop-filter:blur(10px);-webkit-backdrop-filter:blur(10px);background:var(--dt-bg-header);border-bottom:1px solid var(--dt-border-light);color:var(--dt-text-primary);display:grid;flex-shrink:0;min-height:48px;position:sticky;top:0;transition:box-shadow .3s cubic-bezier(.4,0,.2,1);z-index:10}.scrollbar-spacer{background:transparent;pointer-events:none}.div-table-header.scrolled{box-shadow:0 2px 8px var(--dt-shadow)}.div-table-body{background:var(--dt-bg-base);flex:1;min-height:0;overflow-y:auto}.div-table-row{align-items:stretch;border-bottom:1px solid var(--dt-border-row);box-sizing:border-box;color:var(--dt-text-primary);cursor:pointer;display:grid;gap:0;min-height:40px;transition:all .2s ease}.div-table-row:hover{background-color:var(--dt-bg-hover)}.div-table-row:last-child{border-bottom:none}.div-table-cell{box-sizing:border-box;min-width:0;text-overflow:ellipsis;white-space:nowrap}.div-table-cell,.div-table-header-cell{align-items:flex-start;display:flex;overflow:hidden;padding:8px 12px}.div-table-header-cell{color:var(--dt-text-primary);cursor:pointer;justify-content:space-between;transition:background-color .2s ease;user-select:none}.header-left-content{align-items:center;display:flex;flex:1 1 auto;font-weight:600;gap:0;min-width:0;overflow:hidden}.header-left-content>span{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.header-right-content{align-items:center;display:flex;flex:0 0 auto;gap:4px;margin-left:8px}.div-table-header-cell:hover{background-color:var(--dt-shadow)}.group-indicator{align-items:center;display:inline-flex;font-size:12px;height:20px;justify-content:center;opacity:0;transition:opacity .2s ease;width:14px}.div-table-header-cell:hover .group-indicator{opacity:.5}.group-indicator:hover{opacity:1!important}.group-indicator.grouped{color:inherit;opacity:1!important}.sort-indicator{align-items:center;display:inline-flex;height:20px;justify-content:center;opacity:0;transition:opacity .2s ease;width:14px}.div-table-header-cell:hover .sort-indicator{opacity:.5}.sort-indicator.active{opacity:1!important}.header-right-content>span:last-child:not(.group-indicator):not(.sort-indicator){opacity:0;transition:opacity .2s ease}.div-table-header-cell:hover .header-right-content>span:last-child:not(.group-indicator):not(.sort-indicator){opacity:.5}.div-table-header-cell.sorted .header-right-content>span:last-child:not(.sort-indicator){opacity:1!important}.sub-sort-indicator{align-items:center;display:inline-flex;height:20px;justify-content:center;opacity:0;transition:opacity .2s ease;width:14px}.composite-header:hover .sub-sort-indicator,.composite-sub-header:hover .sub-sort-indicator{opacity:.5}.sub-sort-indicator.active{opacity:1!important}.div-table-cell.checkbox-column,.div-table-header-cell.checkbox-column{justify-content:center;max-width:40px;min-width:40px;padding:8px 4px;width:40px}.div-table-cell.checkbox-column input[type=checkbox],.div-table-header-cell.checkbox-column input[type=checkbox]{accent-color:var(--dt-primary);cursor:pointer;height:15px;margin:0;width:15px}input[type=checkbox]:indeterminate{background-color:var(--dt-primary);border-color:var(--dt-primary);position:relative}input[type=checkbox]:indeterminate:after{color:var(--dt-text-inverse);content:"━";font-size:10px;font-weight:700;left:50%;position:absolute;top:50%;transform:translate(-50%,-50%)}.div-table-header-cell.checkbox-column input[type=checkbox]:indeterminate{background-color:var(--dt-primary);border-color:var(--dt-primary)}.div-table-row.selected{background-color:var(--dt-bg-selected)!important}.div-table-row.focused{background-color:var(--dt-bg-base);box-shadow:inset 3px 0 0 var(--dt-primary)}.div-table-row.focused:hover{background-color:var(--dt-primary-lighter)!important}.div-table-row.group-header.focused{background-color:var(--dt-bg-base)!important;box-shadow:inset 3px 0 0 var(--dt-primary)!important}.div-table-row.group-header.focused:hover{background-color:var(--dt-bg-hover)!important}.div-table-row.group-header{background:var(--dt-bg-base);border-bottom:1px solid var(--dt-border-row);border-top:1px solid var(--dt-border-row);box-shadow:none;color:var(--dt-text-secondary);font-weight:400;isolation:isolate;position:sticky;top:0;z-index:9}.div-table-row.group-header:first-of-type{border-top:none}.div-table-row.group-header:hover{background-color:var(--dt-bg-hover)}.div-table-row.group-header:first-of-type{box-shadow:0 2px 8px var(--dt-shadow-heavy)}.div-table-row.group-header .div-table-cell span{font-weight:600}.div-table-row.group-header .checkbox-column{align-items:center;display:flex;justify-content:center}.div-table-row.group-header .checkbox-column input[type=checkbox]{accent-color:var(--dt-primary);cursor:pointer;height:15px;width:15px}.div-table-row.group-header .checkbox-column input[type=checkbox]:indeterminate{background-color:var(--dt-primary)}.group-toggle,.group-toggle-all{align-items:center;border-radius:3px;cursor:pointer;display:inline-flex;font-size:.9em;justify-content:center;min-height:20px;min-width:20px;padding:2px;transform:rotate(90deg);transition:transform .2s ease}.group-toggle-all.collapsed,.group-toggle.collapsed{transform:rotate(0deg)}.group-toggle-all{font-size:1em;font-weight:700;margin-right:6px}.group-toggle-all:hover,.group-toggle:hover{background-color:var(--dt-shadow);opacity:.7}.div-table-cell.grouped-column{color:var(--dt-text-disabled);font-style:italic}.div-table-cell.composite-column{align-items:flex-start;display:flex;flex-direction:column;gap:2px;padding:6px 12px;white-space:normal}.composite-sub{color:var(--dt-text-muted);line-height:1.2}.div-table-cell.composite-cell{align-items:stretch;display:flex;flex-direction:column;gap:0;padding:8px 12px}.composite-sub-cell{align-items:center;display:flex;min-width:0;overflow:hidden}.composite-sub-cell:first-child{margin-bottom:4px}.composite-sub-cell:not(:first-child){color:var(--dt-text-muted)}.div-table-header-cell.composite-header{flex-direction:column;gap:4px;justify-content:flex-start;padding:8px 12px}.composite-sub-header{border-radius:4px;cursor:pointer;min-width:0;padding:0;transition:background-color .2s ease;user-select:none;width:100%}.composite-sub-header:first-child{color:var(--dt-text-primary);font-weight:600;margin-bottom:4px}.composite-main-header{color:var(--dt-text-primary)}.composite-sub-header:hover{background-color:var(--dt-bg-disabled)}.composite-toggle{cursor:pointer;display:inline-block;font-size:.9em;transition:transform .2s ease;user-select:none}.composite-toggle:hover{opacity:.7}.div-table-row.group-collapsed{display:none}.col-fixed-narrow{grid-column:span 1;max-width:80px;min-width:60px}.col-fixed-medium{grid-column:span 1;max-width:140px;min-width:100px}.col-flexible-small{flex:1;grid-column:span 1;min-width:120px}.col-flexible-medium{flex:2;grid-column:span 2;min-width:150px}.col-flexible-large{flex:3;grid-column:span 3;min-width:200px}.div-table-header.grid-5-cols,.div-table-row.grid-5-cols{grid-template-columns:40px 1fr 100px 200px 100px}.div-table-header.grid-4-cols,.div-table-row.grid-4-cols{grid-template-columns:40px 2fr 200px 100px}.div-table-header,.div-table-row{grid-template-columns:repeat(auto-fit,minmax(100px,1fr))}@media (max-width:768px){.div-table-toolbar{align-items:stretch;flex-direction:column;gap:8px}.query-inputfield{max-width:100%;width:100%}.div-table-cell.hidden-mobile,.div-table-header-cell.hidden-mobile{display:none}.div-table-header.grid-4-cols,.div-table-header.grid-5-cols,.div-table-row.grid-4-cols,.div-table-row.grid-5-cols{grid-template-columns:40px 2fr 1fr}}@media (max-width:480px){.div-table-cell.hidden-small,.div-table-header-cell.hidden-small{display:none}.div-table-header.grid-4-cols,.div-table-header.grid-5-cols,.div-table-row.grid-4-cols,.div-table-row.grid-5-cols{grid-template-columns:40px 1fr}}.div-table-widget.no-checkboxes .checkbox-column{display:none}.div-table-widget.no-checkboxes .div-table-header.grid-5-cols,.div-table-widget.no-checkboxes .div-table-row.grid-5-cols{grid-template-columns:1fr 2fr 2fr 1fr}.div-table-widget.no-checkboxes .div-table-header.grid-4-cols,.div-table-widget.no-checkboxes .div-table-row.grid-4-cols{grid-template-columns:2fr 2fr 1fr}.div-table-body::-webkit-scrollbar{width:8px}.div-table-body::-webkit-scrollbar-track{background:var(--dt-scrollbar-track);border-radius:4px}.div-table-body::-webkit-scrollbar-thumb{background:var(--dt-scrollbar-thumb);border-radius:4px}.div-table-body::-webkit-scrollbar-thumb:hover{background:var(--dt-scrollbar-thumb-hover)}.div-table-empty{color:var(--dt-text-disabled)}.div-table-empty,.div-table-loading{align-items:center;display:flex;font-style:italic;justify-content:center;min-height:200px}.div-table-loading{color:var(--dt-text-light);position:relative}.div-table-loading:before{animation:spin 1s linear infinite;border-top:2px solid var(--dt-spinner-track);border:2px solid var(--dt-spinner-track);border-radius:50%;border-top-color:var(--dt-spinner-active);content:"";height:20px;margin-right:10px;width:20px}@keyframes spin{0%{transform:rotate(0deg)}to{transform:rotate(1turn)}}.error-indicator{align-items:center;background:var(--dt-error-bg);border:1px solid var(--dt-error-border);border-radius:3px;color:var(--dt-error-text);display:none;font-size:14px;gap:10px;justify-content:center;margin:10px 0;padding:15px}.div-table-row.loading-placeholder{background:var(--dt-group-bg);border-bottom:1px solid var(--dt-border-row);cursor:default;pointer-events:none}.div-table-row.loading-placeholder:hover{background:var(--dt-group-bg)!important}.div-table-cell.loading-cell{align-items:center;display:flex;padding:8px 12px}.loading-shimmer-content{animation:loading-shimmer 1.5s infinite;background:linear-gradient(90deg,var(--dt-skeleton-base) 25%,var(--dt-skeleton-shine) 50%,var(--dt-skeleton-base) 75%);background-size:200% 100%;border-radius:4px;height:16px}.retry-button{align-items:stretch;background:var(--dt-error);border:none;border-radius:4px;color:var(--dt-text-inverse);flex-direction:column;gap:0;padding:8px 12px}.div-table-cell.composite-cell .composite-sub-cell{align-items:flex-start}.retry-button:hover{background:var(--dt-error-hover)}.retry-button:active{background:var(--dt-error-active)}.div-table-container.has-fixed-columns{display:flex;flex-direction:column;overflow:hidden}.div-table-columns-wrapper{display:flex;flex:1;min-height:0;overflow:hidden}.div-table-fixed-section{background:var(--dt-bg-base);border-right:1px solid var(--dt-border-light);display:flex;flex:0 0 auto;flex-direction:column;z-index:5}.div-table-fixed-section.has-scroll-shadow{box-shadow:2px 0 8px var(--dt-shadow)}.div-table-scroll-section{display:flex;flex:1 1 auto;flex-direction:column;min-width:0;overflow:hidden}.div-table-fixed-header{display:grid;z-index:11}.div-table-fixed-header,.div-table-scroll-header{box-sizing:border-box;flex-shrink:0;position:relative}.div-table-scroll-header{overflow-x:scroll;overflow-y:hidden;scrollbar-width:none;z-index:10;-ms-overflow-style:none}.div-table-scroll-header::-webkit-scrollbar{display:none}.div-table-scroll-header-inner{display:grid;min-width:100%;width:max-content}.div-table-fixed-body{flex:1;min-height:0;overflow-x:hidden;overflow-y:auto}.div-table-fixed-body::-webkit-scrollbar{display:none}.div-table-fixed-body{-ms-overflow-style:none;scrollbar-width:none}.div-table-scroll-body{flex:1;min-height:0;overflow:auto;overflow-x:overlay;overflow-y:overlay}@supports (scrollbar-gutter:stable){.div-table-scroll-body{overflow-x:auto;overflow-y:auto}.div-table-fixed-body,.div-table-scroll-body{scrollbar-gutter:stable}}.div-table-fixed-row,.div-table-scroll-row{align-items:flex-start;box-sizing:border-box;min-height:40px}.div-table-fixed-row,.div-table-scroll-row{background:var(--dt-bg-base);display:grid}.div-table-row.hover,.div-table-row:hover{background-color:var(--dt-bg-hover)}.div-table-fixed-row.selected,.div-table-scroll-row.selected{background-color:var(--dt-bg-selected)!important}.div-table-fixed-row.focused,.div-table-scroll-row.focused{background-color:var(--dt-bg-base);box-shadow:inset 3px 0 0 var(--dt-primary)}.div-table-fixed-row.focused.hover,.div-table-fixed-row.focused:hover,.div-table-scroll-row.focused.hover,.div-table-scroll-row.focused:hover{background-color:var(--dt-primary-lighter)!important}.div-table-fixed-row.group-header,.div-table-scroll-row.group-header{background:var(--dt-bg-base);border-bottom:1px solid var(--dt-border-row);border-top:1px solid var(--dt-border-row);position:sticky;top:0;z-index:4}.div-table-fixed-row.group-header.focused,.div-table-scroll-row.group-header.focused{background-color:var(--dt-bg-base)!important;box-shadow:inset 3px 0 0 var(--dt-primary)!important}.div-table-scroll-section .div-table-cell{overflow:visible;text-overflow:clip;white-space:nowrap}.div-table-scroll-section .div-table-header-cell,.div-table-scroll-section .header-left-content{overflow:visible}.div-table-scroll-section .header-left-content>span{overflow:visible;text-overflow:clip;white-space:nowrap}.div-table-scroll-row{min-width:100%;width:max-content}@media (max-width:768px){.div-table-container.has-fixed-columns{display:flex;flex-direction:column}.div-table-columns-wrapper{flex-direction:column}.div-table-fixed-section{border-bottom:1px solid var(--dt-border-light);border-right:none;box-shadow:0 2px 8px var(--dt-shadow);flex:0 0 auto}.div-table-scroll-section{flex:1 1 auto}}.div-table-row.summary-row{background-color:var(--dt-bg-base);border-bottom:2px solid var(--dt-border-dark);font-weight:600;min-height:32px}.div-table-row.header-summary{background-color:var(--dt-bg-summary);border-bottom:1px solid var(--dt-summary-border);position:sticky;top:0;z-index:2}.div-table-row.group-summary{border-bottom:1px solid var(--dt-summary-border);font-size:.95em;font-weight:500}.div-table-cell.summary-cell{color:var(--dt-text-secondary);padding:8px 12px}.aggregate-value{color:var(--dt-text-primary);font-variant-numeric:tabular-nums;font-weight:700}.div-table-row.summary-row:hover{background-color:var(--dt-bg-summary)}.div-table-fixed-row.summary-row{background-color:var(--dt-bg-base);min-height:32px}.div-table-fixed-row.header-summary{background-color:var(--dt-bg-summary)}.div-table-cell.summary-cell:empty{min-height:1em}
@@ -1 +1 @@
1
- !function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t():"function"==typeof define&&define.amd?define([],t):"object"==typeof exports?exports.DivTable=t():e.DivTable=t()}(this,()=>(()=>{var e={430:e=>{class t{constructor(e,t){this.monaco=e,this.options=t;const i=void 0!==t.data&&null!==t.data;this.data=i?t.data:[],this.columns=t.columns||[],this.columns.forEach(e=>{(e.subLabel||e.subField||e.subType||e.subRender)&&console.warn(`DivTable: Column '${e.field}' uses deprecated properties (subLabel, subField, subType, subRender). Please migrate to fieldCompositeName approach. See README for migration guide.`)}),this.showCheckboxes=!1!==t.showCheckboxes,this.multiSelect=!1!==t.multiSelect,this.onSelectionChange=t.onSelectionChange||(()=>{}),this.onRowFocus=t.onRowFocus||(()=>{}),this.showLoadingPlaceholder=!1!==t.showLoadingPlaceholder,this.isLoadingState=0===this.data.length&&this.showLoadingPlaceholder,this._shouldLoadFirstPage=!i&&"function"==typeof t.onNextPage,this.showRefreshButton=t.showRefreshButton||!1,this.onRefresh=t.onRefresh||(()=>{}),this.showAutoFetchButton=!1!==t.showAutoFetchButton,this.autoFetchDelay=t.autoFetchDelay||500,this.virtualScrolling=t.virtualScrolling||!1,this.pageSize=t.pageSize||100,this.totalRecords=t.totalRecords||(this.virtualScrolling?10*this.pageSize:this.data.length),this.onNextPage=t.onNextPage||(()=>{}),this.onPreviousPage=t.onPreviousPage||(()=>{}),this.loadingThreshold=t.loadingThreshold||Math.floor(.8*this.pageSize),this.scrollThreshold=t.scrollThreshold||.95,this.filteredData=[...this.data],this.sortColumn=null,this.sortDirection="asc",this.sortMode="value",this.groupByField=null,this.collapsedGroups=new Set,this.selectedRows=new Set,this.focusedRowId=null,this.currentQuery="",this._lastFocusCallback={rowId:null,groupKey:null},this.showOnlySelected=!1,this.currentPage=0,this.isLoading=!1,this.hasMoreData=!0,this.estimatedRowHeight=40,this.visibleStartIndex=0,this.visibleEndIndex=this.pageSize,this.isAutoFetching=!1,this.autoFetchPaused=!1,this.autoFetchTimeout=null,this.fixedColumns=t.fixedColumns||0,this.lazyCellRendering=!1!==t.lazyCellRendering,this.lazyRenderMargin=t.lazyRenderMargin||"200px",this.rowObserver=null,this.showHeaderSummary=t.showHeaderSummary||!1,this.showGroupSummary=t.showGroupSummary||!1,this.primaryKeyField=this.columns.find(e=>e.primaryKey)?.field||"id",this.queryEngine=new s(this.data,this.primaryKeyField),this.init(),t.group&&this.group(t.group),t.sort&&t.sort.field&&this.sort(t.sort.field,t.sort.direction)}init(){const e=this.options.tableWidgetElement;e?(this.showCheckboxes||e.classList.add("no-checkboxes"),this.multiSelect||e.classList.add("no-multiselect"),this.createTableStructure(e),this.setupQueryEditor(),this.render(),this.setupKeyboardNavigation(),this._shouldLoadFirstPage?setTimeout(()=>this.loadFirstPageAutomatically(),100):this.virtualScrolling&&this.data.length<this.totalRecords&&"function"==typeof this.onNextPage&&setTimeout(()=>this.loadNextPage(),100)):console.error("DivTable: tableWidgetElement is required")}async loadFirstPageAutomatically(){try{this.isLoading=!0,this.updateInfoSection();const e=await this.onNextPage(0,this.pageSize);this.isLoading=!1,e&&Array.isArray(e)&&e.length>0?this.replaceData(e):(this.isLoadingState=!1,this.hasMoreData=!1,this.render())}catch(e){console.error("❌ Error loading first page:",e),this.isLoading=!1,this.isLoadingState=!1,this.hasMoreData=!1,this.render()}}getOrderedColumns(){let e=this.columns.filter(e=>!e.hidden);if(!this.groupByField)return e;const t=[...e],s=t.findIndex(e=>e.field===this.groupByField);if(s>0){const[e]=t.splice(s,1);t.unshift(e)}return t}getCompositeColumns(){const e=this.getOrderedColumns(),t=new Map,s=[];return e.forEach(e=>{if(e.fieldCompositeName){if(!t.has(e.fieldCompositeName)){const i={compositeName:e.fieldCompositeName,columns:[]};t.set(e.fieldCompositeName,i),s.push(i)}t.get(e.fieldCompositeName).columns.push(e)}else s.push({compositeName:null,columns:[e]})}),s}getAllColumns(){return this.columns}createTableStructure(e){this.toolbar=e.querySelector(".div-table-toolbar"),this.toolbar||(this.toolbar=document.createElement("div"),this.toolbar.className="div-table-toolbar",e.appendChild(this.toolbar)),this.createToolbarElements(),this.tableContainer=document.createElement("div"),this.tableContainer.className="div-table-container",e.appendChild(this.tableContainer),this.fixedColumns>0?(this.tableContainer.classList.add("has-fixed-columns"),this.createFixedColumnsStructure()):(this.headerContainer=document.createElement("div"),this.headerContainer.className="div-table-header",this.tableContainer.appendChild(this.headerContainer),this.bodyContainer=document.createElement("div"),this.bodyContainer.className="div-table-body",this.tableContainer.appendChild(this.bodyContainer)),this.setupScrollShadow()}createFixedColumnsStructure(){this.columnsWrapper=document.createElement("div"),this.columnsWrapper.className="div-table-columns-wrapper",this.tableContainer.appendChild(this.columnsWrapper),this.fixedSection=document.createElement("div"),this.fixedSection.className="div-table-fixed-section",this.columnsWrapper.appendChild(this.fixedSection),this.fixedHeaderContainer=document.createElement("div"),this.fixedHeaderContainer.className="div-table-header div-table-fixed-header",this.fixedSection.appendChild(this.fixedHeaderContainer),this.fixedBodyContainer=document.createElement("div"),this.fixedBodyContainer.className="div-table-body div-table-fixed-body",this.fixedSection.appendChild(this.fixedBodyContainer),this.scrollSection=document.createElement("div"),this.scrollSection.className="div-table-scroll-section",this.columnsWrapper.appendChild(this.scrollSection),this.scrollHeaderContainer=document.createElement("div"),this.scrollHeaderContainer.className="div-table-header div-table-scroll-header",this.scrollSection.appendChild(this.scrollHeaderContainer),this.scrollBodyContainer=document.createElement("div"),this.scrollBodyContainer.className="div-table-body div-table-scroll-body",this.scrollSection.appendChild(this.scrollBodyContainer),this.headerContainer=this.scrollHeaderContainer,this.bodyContainer=this.scrollBodyContainer,this.setupFixedColumnsScrollSync()}setupFixedColumnsScrollSync(){let e=!1;this.scrollBodyContainer.addEventListener("scroll",()=>{e||(e=!0,this.fixedBodyContainer.scrollTop=this.scrollBodyContainer.scrollTop,this.scrollHeaderContainer.scrollLeft=this.scrollBodyContainer.scrollLeft,requestAnimationFrame(()=>{e=!1}))}),this.fixedBodyContainer.addEventListener("scroll",()=>{e||(e=!0,this.scrollBodyContainer.scrollTop=this.fixedBodyContainer.scrollTop,requestAnimationFrame(()=>{e=!1}))}),this.scrollHeaderContainer.addEventListener("scroll",()=>{e||(e=!0,this.scrollBodyContainer.scrollLeft=this.scrollHeaderContainer.scrollLeft,requestAnimationFrame(()=>{e=!1}))}),this.adjustFixedBodyForHorizontalScrollbar(),window.addEventListener("resize",()=>{this.adjustFixedBodyForHorizontalScrollbar()})}adjustFixedBodyForHorizontalScrollbar(){if(!this.fixedBodyContainer||!this.scrollBodyContainer)return;const e=this.scrollBodyContainer.offsetHeight-this.scrollBodyContainer.clientHeight;this.fixedBodyContainer.style.paddingBottom=e>0?`${e}px`:""}getEffectiveFixedColumnCount(){return this.fixedColumns}splitColumnsForFixedLayout(){const e=this.getCompositeColumns(),t=this.getEffectiveFixedColumnCount();return{fixedColumns:e.slice(0,t),scrollColumns:e.slice(t)}}createToolbarElements(){let e=this.toolbar.querySelector(".query-input-container");e||(e=document.createElement("div"),e.className="query-input-container",e.setAttribute("tabindex","0"),this.toolbar.appendChild(e));let t=this.toolbar.querySelector(".info-section");t||(t=document.createElement("div"),t.className="info-section",this.toolbar.appendChild(t)),this.infoSection=t}setupScrollShadow(){const e=this.fixedColumns>0?this.scrollBodyContainer:this.bodyContainer,t=this.fixedColumns>0?this.scrollHeaderContainer:this.headerContainer;e.addEventListener("scroll",()=>{e.scrollTop>0?(t.classList.add("scrolled"),this.fixedColumns>0&&this.fixedHeaderContainer&&this.fixedHeaderContainer.classList.add("scrolled")):(t.classList.remove("scrolled"),this.fixedColumns>0&&this.fixedHeaderContainer&&this.fixedHeaderContainer.classList.remove("scrolled")),this.virtualScrolling&&!this.isLoading&&this.handleVirtualScroll()})}setupQueryEditor(){const e=this.toolbar.querySelector(".query-input-container");if(!e)return;e.className="query-input-container query-inputfield";const t={},s=new Map;if(this.columns.forEach(e=>{e.field&&s.set(e.field,e)}),this.data.length>0){const e=this.data[0],i=new Set;Object.keys(e).forEach(o=>{if(i.has(o))return;const a=s.get(o);if(!a)return;if(a.hidden)return;let n,l;if(i.add(o),n=a.type?a.type:"boolean"==typeof e[o]?"boolean":"number"==typeof e[o]?"number":"string","string"===n){const e=[];this.data.forEach(t=>{const s=t[o];Array.isArray(s)?e.push(...s):e.push(s)});const t=[...new Set(e)],s=t.filter(e=>null!=e&&""!==e);l=t.some(e=>null==e||""===e)?[...s,"NULL"]:s}t[o]={type:n,values:l}}),this.columns.forEach(s=>{if(s.subField&&!s.hidden&&void 0!==e[s.subField]){const o=s.subField;if(i.has(o))return;let a,n;if(i.add(o),a=s.subType?s.subType:"boolean"==typeof e[o]?"boolean":"number"==typeof e[o]?"number":"string","string"===a){const e=[];this.data.forEach(t=>{const s=t[o];Array.isArray(s)?e.push(...s):e.push(s)});const t=[...new Set(e)],s=t.filter(e=>null!=e&&""!==e);n=t.some(e=>null==e||""===e)?[...s,"NULL"]:s}t[o]={type:a,values:n}}})}else this.columns.forEach(e=>{e.field&&!e.hidden&&(t[e.field]={type:e.type||"string",values:e.values||[]}),e.subField&&!e.hidden&&(t[e.subField]={type:e.subType||e.type||"string",values:e.values||[]})});"function"==typeof createQueryEditor&&(this.queryEditor=createQueryEditor(this.monaco,e,{fieldNames:t,initialValue:this.currentQuery,placeholder:this.generateDynamicPlaceholder(t)}),this.queryEditor.fieldNames=t,this.setupQueryEventHandlers())}handleQueryChange(e){void 0===e&&(e=this.queryEditor.model?.getValue()||"");const t=this.queryEditor.editor?.getModel();if(t){const s=this.monaco.editor.getModelMarkers({resource:t.uri}).some(e=>e.severity===this.monaco.MarkerSeverity.Error),i=this.toolbar.querySelector(".query-input-container");s?i.classList.add("error"):(i.classList.remove("error"),this.applyQuery(e))}else this.applyQuery(e)}_setupQueryListeners(){let e;this.queryEditor.model.onDidChangeContent(()=>{e&&clearTimeout(e),e=setTimeout(()=>this.handleQueryChange(),350)})}_shouldUpdateFieldNames(e,t){if(!e||0===Object.keys(e).length)return Object.keys(t).length>0;if(Object.keys(e).length!==Object.keys(t).length)return!0;for(const s in t){if(!e[s])return!0;if(e[s].type!==t[s].type)return!0;const i=e[s].values||[],o=t[s].values||[];if(i.length!==o.length)return!0;const a=[...i].sort(),n=[...o].sort();if(a.some((e,t)=>e!==n[t]))return!0}for(const s in e)if(!t[s])return!0;return!1}generateDynamicPlaceholder(e){if(!e||0===Object.keys(e).length)return"Filter data... (e.g., column > value)";const t=[],s=Object.keys(e);for(const i of s.slice(0,2)){const s=e[i];if("number"===s.type)t.push(`${i} > 100`);else if("boolean"===s.type)t.push(`${i} = true`);else if("string"===s.type)if(s.values&&s.values.length>0){const e=s.values.find(e=>"NULL"!==e)||s.values[0];e&&"NULL"!==e?t.push(`${i} = "${e}"`):t.push(`${i} LIKE "%text%"`)}else t.push(`${i} LIKE "%text%"`)}if(0===t.length)return"Filter data... (e.g., column = value)";const i="Filter data...";if(1===t.length)return`${i} (e.g., ${t[0]})`;return`${i} (e.g., ${t.slice(0,2).join(" AND ")})`}setupKeyboardNavigation(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer;e.addEventListener("keydown",e=>{this.handleKeyDown(e)});let t=!1;e.addEventListener("keydown",()=>{t=!0},{capture:!0}),e.addEventListener("mousedown",()=>{t=!1},{capture:!0}),e.addEventListener("focusin",s=>{!this.focusedRowId&&t&&s.target===e&&this.focusFirstRecord()})}getCurrentFocusedElement(){const e=document.activeElement;if(e&&"checkbox"===e.type){const t=e.closest(".div-table-row");if(t&&this.bodyContainer.contains(t))return{element:e,row:t,type:"checkbox"}}return e&&e.classList.contains("div-table-row")&&this.bodyContainer.contains(e)?{element:e,row:e,type:"row"}:null}getFocusableElementForRow(e){if(this.showCheckboxes){const t=e.querySelector('input[type="checkbox"]');if(t)return t}return e}handleKeyDown(e){const t=this.getAllFocusableElements();if(0===t.length)return;const s=this.getCurrentFocusedElement();if(!s)return;let i=t.indexOf(s.element);if(-1!==i)switch(e.key){case"ArrowDown":e.preventDefault(),this.focusElementAtIndex(Math.min(i+1,t.length-1));break;case"ArrowUp":e.preventDefault(),this.focusElementAtIndex(Math.max(i-1,0));break;case"ArrowRight":e.preventDefault(),this.handleRightArrow(s.row);break;case"ArrowLeft":e.preventDefault(),this.handleLeftArrow(s.row);break;case" ":case"Enter":e.preventDefault(),this.handleSelectionToggleForElement(s)}}getAllFocusableElements(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer,t=[],s=Array.from(e.querySelectorAll(".div-table-row"));for(const e of s)if(e.classList.contains("group-header"))if(this.showCheckboxes){const s=e.querySelector('input[type="checkbox"]');s&&"0"===s.getAttribute("tabindex")&&t.push(s)}else t.push(e);else if(e.dataset.id){const s=this.getRowGroupKey(e);if(!s||!this.collapsedGroups.has(s))if(this.showCheckboxes){const s=e.querySelector('input[type="checkbox"]');s&&"0"===s.getAttribute("tabindex")&&t.push(s)}else t.push(e)}return t}focusElementAtIndex(e){const t=this.getAllFocusableElements();if(e>=0&&e<t.length){const s=t[e];s.focus();const i=s.closest(".div-table-row");i&&this.updateFocusState(i)}}updateFocusState(e){if(this.fixedColumns>0){this.fixedBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),this.scrollBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),e.classList.add("focused");const t=e.dataset.id||e.dataset.groupKey;if(t){const s=e.dataset.id?`[data-id="${t}"]`:`[data-group-key="${t}"]`;if(e.closest(".div-table-fixed-body")){const e=this.scrollBodyContainer.querySelector(s);e&&e.classList.add("focused")}else if(e.closest(".div-table-scroll-body")){const e=this.fixedBodyContainer.querySelector(s);e&&e.classList.add("focused")}}}else{this.bodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),e.classList.add("focused")}if(e.classList.contains("group-header")){if(this.focusedRowId=null,this.focusedGroupKey=e.dataset.groupKey,this._lastFocusCallback.groupKey!==e.dataset.groupKey){this._lastFocusCallback={rowId:null,groupKey:e.dataset.groupKey};const t=this.groupData(this.filteredData).find(t=>t.key===e.dataset.groupKey);if(t){const e=this.columns.find(e=>e.field===this.groupByField),s={key:t.key,value:t.value,field:this.groupByField,label:e?.label||this.groupByField,itemCount:t.items.length};"function"==typeof this.onRowFocus&&this.onRowFocus(void 0,s)}}}else if(e.dataset.id&&(this.focusedRowId=e.dataset.id,this.focusedGroupKey=null,this._lastFocusCallback.rowId!==e.dataset.id)){this._lastFocusCallback={rowId:e.dataset.id,groupKey:null};const t=this.findRowData(e.dataset.id);"function"==typeof this.onRowFocus&&this.onRowFocus(t,void 0)}}handleSelectionToggleForElement(e){const t=e.row;t.classList.contains("group-header")?this.toggleGroupSelection(t):t.dataset.id&&this.toggleIndividualRowSelection(t)}handleRightArrow(e){if(e&&e.classList.contains("group-header")&&e.classList.contains("collapsed")){const t=e.dataset.groupKey;this.collapsedGroups.delete(t),e.classList.remove("collapsed");const s={key:t};this.render(),this.restoreGroupFocus(s)}}handleLeftArrow(e){if(e&&e.classList.contains("group-header")&&!e.classList.contains("collapsed")){const t=e.dataset.groupKey;this.collapsedGroups.add(t),e.classList.add("collapsed");const s={key:t};this.render(),this.restoreGroupFocus(s)}}restoreGroupFocus(e){const t=this.bodyContainer.querySelector(`[data-group-key="${e.key}"]`);if(t){if(this.showCheckboxes){const e=t.querySelector('input[type="checkbox"]');e&&e.focus()}else t.focus();this.updateFocusState(t)}}getVisibleRows(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer;return Array.from(e.querySelectorAll(".div-table-row[data-id]:not(.group-header):not(.group-collapsed)"))}getAllFocusableRows(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer,t=Array.from(e.querySelectorAll(".div-table-row")),s=[];for(const e of t)if(e.classList.contains("group-header"))s.push(e);else if(e.dataset.id){const t=this.getRowGroupKey(e);t&&this.collapsedGroups.has(t)||s.push(e)}return s}getRowGroupKey(e){let t=e.previousElementSibling;for(;t;){if(t.classList.contains("group-header"))return t.dataset.groupKey;t=t.previousElementSibling}return null}focusRow(e){const t=this.getAllFocusableElements();e>=0&&e<t.length&&this.focusElementAtIndex(e)}focusFirstRecord(){this.getAllFocusableRows().length>0&&this.focusRow(0)}setFocusedRow(e,t=!1){if(this.bodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>{e.classList.remove("focused")}),e){const s=this.bodyContainer.querySelector(`[data-id="${e}"]`);if(s){if(s.classList.add("focused"),s.scrollIntoView({behavior:"smooth",block:"nearest"}),!t){const e=s.querySelector('input[type="checkbox"]');e&&document.activeElement!==e&&e.focus()}if(this._lastFocusCallback.rowId!==e){this._lastFocusCallback={rowId:e,groupKey:null};const t=this.findRowData(e);this.onRowFocus(t)}}}this.focusedRowId=e}setFocusedGroup(e){this.bodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>{e.classList.remove("focused")}),this.focusedRowId=null;const t=this.bodyContainer.querySelector(`[data-group-key="${e.key}"]`);if(t){t.classList.add("focused"),t.scrollIntoView({behavior:"smooth",block:"nearest"});const s=this.columns.find(e=>e.field===this.groupByField),i={key:e.key,value:e.value,field:this.groupByField,label:s?.label||this.groupByField,itemCount:e.items.length};this.onRowFocus(void 0,i)}}findRowData(e){let t=this.filteredData.find(t=>String(t[this.primaryKeyField])===String(e));return t||(t=this.data.find(t=>String(t[this.primaryKeyField])===String(e))),t}handleSelectionToggle(e){const t=this.getAllFocusableRows();if(e<0||e>=t.length)return;const s=t[e];s.classList.contains("group-header")?this.toggleGroupSelection(s):s.dataset.id&&this.toggleIndividualRowSelection(s)}toggleGroupSelection(e){const t=e.dataset.groupKey,s=this.groupData(this.filteredData).find(e=>e.key===t);if(!s)return;const i=s.items.map(e=>String(e[this.primaryKeyField])),o=i.filter(e=>this.selectedRows.has(e)).length<i.length;s.items.forEach(e=>{const t=String(e[this.primaryKeyField]);o?(this.selectedRows.add(t),e.selected=!0):(this.selectedRows.delete(t),e.selected=!1)}),this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}toggleIndividualRowSelection(e){const t=e.dataset.id;if(!t)return void console.warn("DivTable: Row missing data-id attribute");const s=this.findRowData(t);if(!s)return void console.warn("DivTable: Could not find data for row ID:",t);this.selectedRows.has(t)?(this.selectedRows.delete(t),s.selected=!1,e.classList.remove("selected")):(this.multiSelect||this.clearSelection(),this.selectedRows.add(t),s.selected=!0,e.classList.add("selected")),this.updateSelectionStates(),this.updateInfoSection();const i=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(i)}toggleRowSelection(e){const t=this.getVisibleRows();if(e<0||e>=t.length)return;const s=t[e],i=s.dataset.id,o=this.findRowData(i);if(!o)return;this.selectedRows.has(i)?(this.selectedRows.delete(i),o.selected=!1,s.classList.remove("selected")):(this.multiSelect||this.clearSelection(),this.selectedRows.add(i),o.selected=!0,s.classList.add("selected")),this.updateCheckboxes(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}clearSelection(){this.selectedRows.clear(),this.filteredData.forEach(e=>e.selected=!1),this.updateSelectionStates(),this.updateInfoSection()}updateCheckboxes(){this.fixedColumns>0?this.fixedBodyContainer.querySelectorAll('.div-table-row[data-id] input[type="checkbox"]').forEach(e=>{const t=e.closest(".div-table-row").dataset.id;e.checked=this.selectedRows.has(t)}):this.bodyContainer.querySelectorAll('.div-table-row[data-id] input[type="checkbox"]').forEach(e=>{const t=e.closest(".div-table-row").dataset.id;e.checked=this.selectedRows.has(t)})}updateSelectionStates(){if(this.fixedColumns>0)return void this.updateSelectionStatesWithFixedColumns();this.bodyContainer.querySelectorAll(".div-table-row[data-id]").forEach(e=>{const t=e.dataset.id,s=e.querySelector('input[type="checkbox"]');this.selectedRows.has(t)?(e.classList.add("selected"),s&&(s.checked=!0)):(e.classList.remove("selected"),s&&(s.checked=!1))});const e=this.bodyContainer.querySelectorAll(".div-table-row.group-header");if(e.length>0){const t=this.groupData(this.sortData(this.filteredData));e.forEach(e=>{const s=e.querySelector('input[type="checkbox"]');if(!s)return;const i=e.dataset.groupKey,o=t.find(e=>e.key===i);if(!o)return;const a=o.items.map(e=>String(e[this.primaryKeyField])),n=a.filter(e=>this.selectedRows.has(e));0===n.length?(s.indeterminate=!1,s.checked=!1):n.length===a.length?(s.indeterminate=!1,s.checked=!0):(s.indeterminate=!0,s.checked=!1)})}this.updateHeaderCheckbox(),this.updateSummaryRows()}updateSelectionStatesWithFixedColumns(){this.fixedBodyContainer.querySelectorAll(".div-table-row[data-id]").forEach(e=>{const t=e.dataset.id,s=e.querySelector('input[type="checkbox"]');this.selectedRows.has(t)?(e.classList.add("selected"),s&&(s.checked=!0)):(e.classList.remove("selected"),s&&(s.checked=!1))}),this.scrollBodyContainer.querySelectorAll(".div-table-row[data-id]").forEach(e=>{const t=e.dataset.id;this.selectedRows.has(t)?e.classList.add("selected"):e.classList.remove("selected")});const e=this.fixedBodyContainer.querySelectorAll(".div-table-row.group-header");if(e.length>0){const t=this.groupData(this.sortData(this.filteredData));e.forEach(e=>{const s=e.querySelector('input[type="checkbox"]');if(!s)return;const i=e.dataset.groupKey,o=t.find(e=>e.key===i);if(!o)return;const a=o.items.map(e=>String(e[this.primaryKeyField])),n=a.filter(e=>this.selectedRows.has(e));0===n.length?(s.indeterminate=!1,s.checked=!1):n.length===a.length?(s.indeterminate=!1,s.checked=!0):(s.indeterminate=!0,s.checked=!1)})}this.updateHeaderCheckbox(),this.updateSummaryRows()}updateHeaderCheckbox(){let e;if(e=this.fixedColumns>0?this.fixedHeaderContainer.querySelector('input[type="checkbox"]'):this.headerContainer.querySelector('input[type="checkbox"]'),!e)return;const t=this.filteredData.length,s=this.filteredData.filter(e=>this.selectedRows.has(String(e[this.primaryKeyField]))).length;0===s?(e.checked=!1,e.indeterminate=!1):s===t?(e.checked=!0,e.indeterminate=!1):(e.checked=!1,e.indeterminate=!0)}updateTabIndexes(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer,t=Array.from(e.querySelectorAll(".div-table-row"));for(const e of t)if(e.classList.contains("group-header")){if(this.showCheckboxes){const t=e.querySelector('input[type="checkbox"]');t&&t.setAttribute("tabindex","0")}}else if(e.dataset.id){const t=this.getRowGroupKey(e),s=!t||!this.collapsedGroups.has(t);if(this.showCheckboxes){const t=e.querySelector('input[type="checkbox"]');t&&t.setAttribute("tabindex",s?"0":"-1")}}}render(){this.renderHeader(),this.renderBody(),this.updateInfoSection(),this.updateSelectionStates(),this.updateTabIndexes(),"undefined"==typeof process&&setTimeout(()=>this.verifyDataConsistency(),0)}renderHeader(){if(this.fixedColumns>0)return void this.renderHeaderWithFixedColumns();this.headerContainer.innerHTML="";const e=this.getCompositeColumns();let t="";if(this.showCheckboxes&&(t="40px "),e.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":t+="80px ";break;case"fixed-medium":t+="120px ";break;case"flexible-small":default:t+="1fr ";break;case"flexible-medium":t+="2fr ";break;case"flexible-large":t+="3fr "}}),this.headerContainer.style.gridTemplateColumns=t.trim(),this.showCheckboxes){const e=document.createElement("div");if(e.className="div-table-header-cell checkbox-column",this.multiSelect){const t=document.createElement("input");t.type="checkbox",t.addEventListener("change",e=>{e.target.checked?this.selectAll():(this.clearSelection(),this.showOnlySelected&&(this.renderBody(),this.updateInfoSection()))}),e.appendChild(t)}this.headerContainer.appendChild(e)}e.forEach(e=>{const t=document.createElement("div");if(t.className="div-table-header-cell",e.compositeName)t.classList.add("composite-header"),this.renderCompositeHeaderCell(t,e);else{t.classList.add("sortable");const s=e.columns[0];this.renderSingleHeaderCell(t,s)}this.headerContainer.appendChild(t)}),this.updateScrollbarSpacer()}renderHeaderWithFixedColumns(){this.fixedHeaderContainer.innerHTML="",this.scrollHeaderContainer.innerHTML="";const{fixedColumns:e,scrollColumns:t}=this.splitColumnsForFixedLayout();let s="";this.showCheckboxes&&(s="40px "),e.forEach(e=>{s+=this.getColumnGridSize(e)+" "}),this.fixedHeaderContainer.style.gridTemplateColumns=s.trim();let i="";if(t.forEach(e=>{i+=this.getColumnGridSize(e)+" "}),this.scrollHeaderInner=document.createElement("div"),this.scrollHeaderInner.className="div-table-scroll-header-inner",this.scrollHeaderInner.style.gridTemplateColumns=i.trim(),this.scrollHeaderContainer.appendChild(this.scrollHeaderInner),this.showCheckboxes){const e=document.createElement("div");if(e.className="div-table-header-cell checkbox-column",this.multiSelect){const t=document.createElement("input");t.type="checkbox",t.addEventListener("change",e=>{e.target.checked?this.selectAll():(this.clearSelection(),this.showOnlySelected&&(this.renderBody(),this.updateInfoSection()))}),e.appendChild(t)}this.fixedHeaderContainer.appendChild(e)}e.forEach(e=>{const t=this.createHeaderCell(e);this.fixedHeaderContainer.appendChild(t)}),t.forEach(e=>{const t=this.createHeaderCell(e);this.scrollHeaderInner.appendChild(t)}),this.syncFixedColumnsHeaderHeights()}syncFixedColumnsHeaderHeights(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.fixedHeaderContainer||!this.scrollHeaderContainer)return;this.fixedHeaderContainer.style.height="",this.scrollHeaderContainer.style.height="";const e=this.fixedHeaderContainer.offsetHeight,t=this.scrollHeaderContainer.offsetHeight,s=Math.max(e,t);s>0&&(this.fixedHeaderContainer.style.height=`${s}px`,this.scrollHeaderContainer.style.height=`${s}px`)}syncFixedColumnsRowHeights(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.fixedBodyContainer||!this.scrollBodyContainer)return;const e=this.fixedBodyContainer.querySelectorAll(".div-table-row"),t=this.scrollBodyContainer.querySelectorAll(".div-table-row");e.length===t.length&&e.forEach((e,s)=>{const i=t[s];if(!i)return;e.style.height="",i.style.height="";const o=e.offsetHeight,a=i.offsetHeight,n=Math.max(o,a);n>0&&(e.style.height=`${n}px`,i.style.height=`${n}px`)})}syncFixedColumnsColumnWidths(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.scrollHeaderInner||!this.scrollBodyContainer)return;const{scrollColumns:e}=this.splitColumnsForFixedLayout(),t=e.length;if(0===t)return;const s=Array.from(this.scrollHeaderInner.querySelectorAll(".div-table-header-cell")),i=Array.from(this.scrollBodyContainer.querySelectorAll(".div-table-row:not(.group-header)")),o=[];for(let e=0;e<t;e++){let t=0;s[e]&&(s[e].style.minWidth="",s[e].style.width="",t=Math.max(t,s[e].scrollWidth)),i.forEach(s=>{const i=s.querySelectorAll(".div-table-cell");i[e]&&(i[e].style.minWidth="",i[e].style.width="",t=Math.max(t,i[e].scrollWidth))}),o.push(t+4)}const a=o.map(e=>`${e}px`).join(" "),n=o.reduce((e,t)=>e+t,0);this.scrollHeaderInner.style.gridTemplateColumns=a;this.scrollBodyContainer.querySelectorAll(".div-table-row").forEach(e=>{e.classList.contains("group-header")?(e.style.gridTemplateColumns="1fr",e.style.minWidth=`${n}px`):e.classList.contains("summary-row")?(e.style.gridTemplateColumns=a,e.style.minWidth=`${n}px`):e.style.gridTemplateColumns=a}),this.updateFixedColumnsShadow()}updateFixedColumnsShadow(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.scrollBodyContainer||!this.fixedSection)return;this.scrollBodyContainer.scrollWidth>this.scrollBodyContainer.clientWidth?this.fixedSection.classList.add("has-scroll-shadow"):this.fixedSection.classList.remove("has-scroll-shadow")}getColumnGridSize(e){switch((e.columns[0].responsive||{}).size){case"fixed-narrow":return"80px";case"fixed-medium":return"120px";case"flexible-small":default:return"1fr";case"flexible-medium":return"2fr";case"flexible-large":return"3fr"}}createHeaderCell(e){const t=document.createElement("div");if(t.className="div-table-header-cell",e.compositeName)t.classList.add("composite-header"),this.renderCompositeHeaderCell(t,e);else{t.classList.add("sortable");const s=e.columns[0];this.renderSingleHeaderCell(t,s)}return t}updateScrollbarSpacer(){const e=this.headerContainer.querySelector(".scrollbar-spacer");e&&e.remove();if(this.bodyContainer.scrollHeight>this.bodyContainer.clientHeight){const e=this.bodyContainer.offsetWidth-this.bodyContainer.clientWidth,t=document.createElement("div");t.className="scrollbar-spacer",t.style.width=`${e}px`;const s=this.headerContainer.style.gridTemplateColumns;this.headerContainer.style.gridTemplateColumns=`${s} ${e}px`,this.headerContainer.appendChild(t)}}renderSingleHeaderCell(e,t){if(t.subLabel){e.classList.add("composite-header"),e.style.display="flex",e.style.flexDirection="column",e.style.gap="0",e.style.padding="8px 12px",e.style.alignItems="flex-start";const s=document.createElement("div");s.style.display="flex",s.style.alignItems="center",s.style.width="100%",s.style.marginBottom="4px";const i=document.createElement("span");i.className="composite-main-header",i.innerHTML=t.label||t.field,i.style.fontWeight="600",i.style.color="#374151",i.style.textAlign="left",i.style.flex="1",s.appendChild(i);const o=document.createElement("div");if(o.className="header-right-content",o.style.display="flex",o.style.alignItems="center",o.style.gap="4px",o.style.marginLeft="auto",!1!==t.groupable&&!t.hidden){const e=document.createElement("span");e.className="group-indicator",this.groupByField===t.field&&e.classList.add("grouped"),e.textContent=this.groupByField===t.field?"☴":"☷",e.style.cursor="pointer",e.style.fontSize="1em";const s=t.label||t.field;e.title=this.groupByField===t.field?`Grouped by ${s} (click to ungroup)`:`Click to group by ${s}`,e.addEventListener("click",e=>{e.stopPropagation(),this.groupByField===t.field?this.group(""):this.group(t.field)}),o.appendChild(e)}const a=document.createElement("span");a.className="sort-indicator",a.style.marginLeft="4px",this.sortColumn===t.field?(a.classList.add("active"),a.textContent="asc"===this.sortDirection?"↑":"↓"):a.textContent="⇅",o.appendChild(a),s.appendChild(o),e.appendChild(s);const n=document.createElement("div");n.className="composite-sub-header sortable",n.style.display="flex",n.style.alignItems="center",n.style.width="100%",n.style.cursor="pointer",n.style.borderRadius="4px",n.style.transition="background-color 0.2s ease";const l=document.createElement("span");if(l.innerHTML=t.subLabel,l.style.color="#6b7280",l.style.textAlign="left",l.style.flex="1",n.appendChild(l),t.subField){const e=document.createElement("span");e.className="sub-sort-indicator",e.style.marginLeft="4px",this.sortColumn===t.subField?(e.classList.add("active"),e.textContent="asc"===this.sortDirection?"↑":"↓"):e.textContent="⇅",n.appendChild(e),n.addEventListener("mouseenter",()=>{n.style.backgroundColor="#f3f4f6"}),n.addEventListener("mouseleave",()=>{n.style.backgroundColor="transparent"}),n.addEventListener("click",e=>{e.stopPropagation(),this.sort(t.subField)})}return e.appendChild(n),void s.addEventListener("click",e=>{e.target.classList.contains("group-indicator")||e.target.closest(".group-indicator")||this.sort(t.field)})}const s=document.createElement("div");if(s.className="header-left-content",this.groupByField===t.field){const e=this.groupData(this.filteredData),i=e.length,o=t.label||t.field,a=document.createElement("span");a.className="group-toggle-all";const n=e.every(e=>this.collapsedGroups.has(e.key));n&&a.classList.add("collapsed"),a.textContent="❯",a.title=n?"Expand all groups":"Collapse all groups",a.addEventListener("click",t=>{t.stopPropagation(),t.preventDefault(),n?this.collapsedGroups.clear():e.forEach(e=>{this.collapsedGroups.add(e.key)}),this.render()}),s.appendChild(a);const l=document.createElement("span");l.innerHTML=o,s.appendChild(l);const r=document.createElement("span");r.className="group-count",r.innerHTML=`&nbsp;(${i})`,r.style.opacity="0.8",r.style.fontSize="0.9em",r.style.fontWeight="normal",r.title=`${i} distinct value${1===i?"":"s"} in ${o}`,s.appendChild(r)}else{const e=document.createElement("span");e.innerHTML=t.label||t.field,s.appendChild(e)}e.appendChild(s);const i=document.createElement("div");if(i.className="header-right-content",!1!==t.groupable&&!t.hidden){const e=document.createElement("span");e.className="group-indicator",this.groupByField===t.field&&e.classList.add("grouped"),e.textContent=this.groupByField===t.field?"☴":"☷",e.style.cursor="pointer",e.style.fontSize="1em";const s=t.label||t.field;e.title=this.groupByField===t.field?`Grouped by ${s} (click to ungroup)`:`Click to group by ${s}`,e.addEventListener("click",e=>{e.stopPropagation(),this.groupByField===t.field?this.group(""):this.group(t.field)}),i.appendChild(e)}const o=document.createElement("span");if(o.className="sort-indicator",o.style.fontSize="12px",o.style.marginLeft="4px",this.sortColumn===t.field){o.classList.add("active");const s=this.groupByField&&t.field===this.groupByField;s&&"count"===this.sortMode?o.textContent="asc"===this.sortDirection?"↑1":"↓9":s&&"value"===this.sortMode?o.textContent="asc"===this.sortDirection?"↑A":"↓Z":o.textContent="asc"===this.sortDirection?"↑":"↓",e.classList.add("sorted",this.sortDirection)}else o.textContent="⇅";i.appendChild(o),e.appendChild(i),e.addEventListener("click",e=>{e.target.classList.contains("group-indicator")||e.target.classList.contains("group-toggle-all")||e.target.closest(".group-toggle-all")||e.target.closest(".group-indicator")||this.sort(t.field)})}renderCompositeHeaderCell(e,t){e.style.display="flex",e.style.flexDirection="column",e.style.gap="4px",e.style.padding="8px 12px";t.columns.find(e=>this.groupByField===e.field);t.columns.forEach((t,s)=>{const i=document.createElement("div");i.className="composite-sub-header sortable",i.style.display="flex",i.style.alignItems="center",i.style.gap="8px";const o=document.createElement("div");if(o.style.display="flex",o.style.alignItems="center",o.style.gap="8px",o.style.flex="1",this.groupByField===t.field){const e=this.groupData(this.filteredData),s=e.length,i=t.label||t.field,a=document.createElement("span");a.className="group-toggle-all";const n=e.every(e=>this.collapsedGroups.has(e.key));n&&a.classList.add("collapsed"),a.textContent="❯",a.title=n?"Expand all groups":"Collapse all groups",a.addEventListener("click",t=>{t.stopPropagation(),t.preventDefault(),n?this.collapsedGroups.clear():e.forEach(e=>{this.collapsedGroups.add(e.key)}),this.render()}),o.appendChild(a);const l=document.createElement("span");l.innerHTML=i,o.appendChild(l);const r=document.createElement("span");r.className="group-count",r.innerHTML=`&nbsp;(${s})`,r.style.opacity="0.8",r.style.fontSize="0.9em",r.style.fontWeight="normal",r.title=`${s} distinct value${1===s?"":"s"} in ${i}`,o.appendChild(r)}else{const e=document.createElement("span");e.innerHTML=t.label||t.field,o.appendChild(e)}i.appendChild(o);const a=document.createElement("div");if(a.style.display="flex",a.style.alignItems="center",a.style.gap="4px",!1!==t.groupable&&!t.hidden){const e=document.createElement("span");e.className="group-indicator",this.groupByField===t.field&&e.classList.add("grouped"),e.textContent=this.groupByField===t.field?"☴":"☷",e.style.cursor="pointer",e.style.fontSize="1em";const s=t.label||t.field;e.title=this.groupByField===t.field?`Grouped by ${s} (click to ungroup)`:`Click to group by ${s}`,e.addEventListener("click",e=>{e.stopPropagation(),this.groupByField===t.field?this.group(""):this.group(t.field)}),a.appendChild(e)}const n=document.createElement("span");if(n.className="sort-indicator",n.style.marginLeft="4px",this.sortColumn===t.field){n.classList.add("active");const e=this.groupByField&&t.field===this.groupByField;e&&"count"===this.sortMode?n.textContent="asc"===this.sortDirection?"↑1":"↓9":e&&"value"===this.sortMode?n.textContent="asc"===this.sortDirection?"↑A":"↓Z":n.textContent="asc"===this.sortDirection?"↑":"↓",i.classList.add("sorted",this.sortDirection)}else n.textContent="⇅";a.appendChild(n),i.appendChild(a),i.addEventListener("click",e=>{e.target.classList.contains("group-indicator")||e.target.classList.contains("group-toggle-all")||e.target.closest(".group-indicator")||e.target.closest(".group-toggle-all")||this.sort(t.field)}),e.appendChild(i)})}renderBody(){if(this.rowObserver&&this.rowObserver.disconnect(),this.fixedColumns>0)return void this.renderBodyWithFixedColumns();if(this.bodyContainer.innerHTML="",this.isLoadingState)return void this.showLoadingPlaceholders();let e=this.filteredData;if(this.showOnlySelected&&0===this.selectedRows.size&&(this.showOnlySelected=!1,console.log("👁️ No rows selected - automatically showing all rows")),this.showOnlySelected&&this.selectedRows.size>0&&(e=this.filteredData.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)})),0===e.length){const e=document.createElement("div");return e.className="div-table-empty",e.textContent=this.showOnlySelected&&this.selectedRows.size>0?"No selected rows match current filters":"No data to display",void this.bodyContainer.appendChild(e)}if(this.groupByField?this.renderGroupedRows(e):this.renderRegularRows(e),this.showHeaderSummary&&this.hasAggregateColumns()){const t=this.createHeaderSummaryRow(e);this.bodyContainer.insertBefore(t,this.bodyContainer.firstChild)}this.lazyCellRendering&&this.setupLazyRenderingObserver()}renderBodyWithFixedColumns(){const e=this.scrollBodyContainer?.scrollLeft||0;if(this.fixedBodyContainer.innerHTML="",this.scrollBodyContainer.innerHTML="",this.isLoadingState)return void this.showLoadingPlaceholders();let t=this.filteredData;if(this.showOnlySelected&&0===this.selectedRows.size&&(this.showOnlySelected=!1),this.showOnlySelected&&this.selectedRows.size>0&&(t=this.filteredData.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)})),0===t.length){const e=document.createElement("div");return e.className="div-table-empty",e.textContent=this.showOnlySelected&&this.selectedRows.size>0?"No selected rows match current filters":"No data to display",void this.fixedBodyContainer.appendChild(e)}if(this.groupByField?this.renderGroupedRowsWithFixedColumns(t):this.renderRegularRowsWithFixedColumns(t),this.showHeaderSummary&&this.hasAggregateColumns()){const{fixedSummary:e,scrollSummary:s}=this.createHeaderSummaryRowWithFixedColumns(t);this.fixedBodyContainer.insertBefore(e,this.fixedBodyContainer.firstChild),this.scrollBodyContainer.insertBefore(s,this.scrollBodyContainer.firstChild)}this.syncFixedColumnsColumnWidths(),this.syncFixedColumnsRowHeights(),this.lazyCellRendering&&this.setupLazyRenderingObserver(),e>0&&requestAnimationFrame(()=>{this.scrollBodyContainer.scrollLeft=e}),requestAnimationFrame(()=>{this.adjustFixedBodyForHorizontalScrollbar()})}renderRegularRowsWithFixedColumns(e=this.filteredData){this.sortData(e).forEach(e=>{const{fixedRow:t,scrollRow:s}=this.createRowWithFixedColumns(e);this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s)})}renderGroupedRowsWithFixedColumns(e=this.filteredData){let t=this.groupData(e);this.sortColumn===this.groupByField&&(t=t.sort((e,t)=>{if("count"===this.sortMode){const s=e.items.length-t.items.length;return"desc"===this.sortDirection?-s:s}{if(null==e.value&&null==t.value)return 0;if(null==e.value)return"asc"===this.sortDirection?-1:1;if(null==t.value)return"asc"===this.sortDirection?1:-1;let s=0;return s="number"==typeof e.value&&"number"==typeof t.value?e.value-t.value:String(e.value).localeCompare(String(t.value)),"desc"===this.sortDirection?-s:s}})),t.forEach(e=>{this.sortColumn!==this.groupByField&&(e.items=this.sortData(e.items));const{fixedGroupHeader:t,scrollGroupHeader:s}=this.createGroupHeaderWithFixedColumns(e);if(this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s),this.collapsedGroups.has(e.key)||e.items.forEach(e=>{const{fixedRow:t,scrollRow:s}=this.createRowWithFixedColumns(e);this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s)}),this.showGroupSummary&&this.hasAggregateColumns()){const{fixedSummary:t,scrollSummary:s}=this.createGroupSummaryRowWithFixedColumns(e);this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s)}})}setupLazyRenderingObserver(){if(this.rowObserver&&this.rowObserver.disconnect(),"undefined"==typeof IntersectionObserver)return console.warn("DivTable: IntersectionObserver not supported, falling back to eager rendering"),void this.populateAllUnpopulatedRows();const e=this.fixedColumns>0?this.scrollBodyContainer:this.bodyContainer;this.rowObserver=new IntersectionObserver(e=>{e.forEach(e=>{if(e.isIntersecting){const t=e.target;if("true"!==t.dataset.populated){const e=t.dataset.id,s=this.findRowData(e);if(s)if(this.fixedColumns>0){let i,o;t.classList.contains("div-table-fixed-row")?(i=t,o=this.scrollBodyContainer.querySelector(`.div-table-row[data-id="${e}"]`)):(o=t,i=this.fixedBodyContainer.querySelector(`.div-table-row[data-id="${e}"]`)),i&&o&&this.populateRowCellsWithFixedColumns(i,o,s)}else this.populateRowCells(t,s)}this.rowObserver.unobserve(t)}})},{root:e,rootMargin:this.lazyRenderMargin,threshold:0});if((this.fixedColumns>0?this.scrollBodyContainer.querySelectorAll('.div-table-row[data-populated="false"]'):this.bodyContainer.querySelectorAll('.div-table-row[data-populated="false"]')).forEach(e=>{this.rowObserver.observe(e)}),this.fixedColumns>0&&this.fixedBodyContainer){this.fixedBodyContainer.querySelectorAll('.div-table-row[data-populated="false"]').forEach(e=>{this.rowObserver.observe(e)})}}populateAllUnpopulatedRows(){(this.fixedColumns>0?this.scrollBodyContainer:this.bodyContainer).querySelectorAll('.div-table-row[data-populated="false"]').forEach(e=>{const t=e.dataset.id,s=this.findRowData(t);s&&this.populateRowCells(e,s)})}renderRegularRows(e=this.filteredData){this.sortData(e).forEach(e=>{const t=this.createRow(e);this.bodyContainer.appendChild(t)})}renderGroupedRows(e=this.filteredData){let t=this.groupData(e);this.sortColumn===this.groupByField&&(t=t.sort((e,t)=>{if("count"===this.sortMode){const s=e.items.length-t.items.length;return"desc"===this.sortDirection?-s:s}{if(null==e.value&&null==t.value)return 0;if(null==e.value)return"asc"===this.sortDirection?-1:1;if(null==t.value)return"asc"===this.sortDirection?1:-1;let s=0;return s="number"==typeof e.value&&"number"==typeof t.value?e.value-t.value:String(e.value).localeCompare(String(t.value)),"desc"===this.sortDirection?-s:s}})),t.forEach(e=>{this.sortColumn!==this.groupByField&&(e.items=this.sortData(e.items));const t=this.createGroupHeader(e);if(this.bodyContainer.appendChild(t),this.collapsedGroups.has(e.key)||e.items.forEach(e=>{const t=this.createRow(e);this.bodyContainer.appendChild(t)}),this.showGroupSummary&&this.hasAggregateColumns()){const t=this.createGroupSummaryRow(e);this.bodyContainer.appendChild(t)}})}populateRowCells(e,t){if("true"===e.dataset.populated)return;const s=this.getCompositeColumns(),i=String(t[this.primaryKeyField]);if(this.showCheckboxes){const t=document.createElement("div");t.className="div-table-cell checkbox-column";const s=document.createElement("input");s.type="checkbox",s.checked=this.selectedRows.has(i),s.addEventListener("change",t=>{t.stopPropagation();const o=this.findRowData(i);if(!o)return void console.warn("DivTable: Could not find data for row ID:",i);if(s.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(i),o.selected=!0,e.classList.add("selected");else if(this.selectedRows.delete(i),o.selected=!1,e.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const a=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(a)}),s.addEventListener("focus",t=>{this.updateFocusState(e)}),t.appendChild(s),t.addEventListener("click",e=>{e.target!==s&&(e.stopPropagation(),s.click())}),e.appendChild(t)}s.forEach(s=>{const i=document.createElement("div");if(i.className="div-table-cell",s.compositeName)i.classList.add("composite-cell"),i.style.display="flex",i.style.flexDirection="column",i.style.gap="4px",s.columns.forEach((e,s)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",this.groupByField&&e.field===this.groupByField)o.classList.add("grouped-column"),o.textContent="";else if(e.subField){o.classList.add("composite-column"),o.style.display="flex",o.style.flexDirection="column",o.style.gap="2px";const s=document.createElement("div");s.className="composite-main","function"==typeof e.render?s.innerHTML=e.render(t[e.field],t):s.innerHTML=t[e.field]??"";const i=document.createElement("div");i.className="composite-sub","function"==typeof e.subRender?i.innerHTML=e.subRender(t[e.subField],t):i.innerHTML=t[e.subField]??"",o.appendChild(s),o.appendChild(i)}else"function"==typeof e.render?o.innerHTML=e.render(t[e.field],t):o.innerHTML=t[e.field]??"";i.appendChild(o)});else{const e=s.columns[0];if(this.groupByField&&e.field===this.groupByField)i.classList.add("grouped-column"),i.textContent="";else if(e.subField){i.classList.add("composite-column");const s=document.createElement("div");s.className="composite-main","function"==typeof e.render?s.innerHTML=e.render(t[e.field],t):s.innerHTML=t[e.field]??"";const o=document.createElement("div");o.className="composite-sub","function"==typeof e.subRender?o.innerHTML=e.subRender(t[e.subField],t):o.innerHTML=t[e.subField]??"",i.appendChild(s),i.appendChild(o)}else"function"==typeof e.render?i.innerHTML=e.render(t[e.field],t):i.innerHTML=t[e.field]??""}e.appendChild(i)}),e.dataset.populated="true",requestAnimationFrame(()=>{const t=e.offsetHeight;t>0&&(e.style.minHeight=`${t}px`,e.style.height=`${t}px`,t>this.estimatedRowHeight&&(this.estimatedRowHeight=t))}),this.updateTabIndexes()}populateRowCellsWithFixedColumns(e,t,s){if("true"===e.dataset.populated)return;const{fixedColumns:i,scrollColumns:o}=this.splitColumnsForFixedLayout(),a=String(s[this.primaryKeyField]);if(this.showCheckboxes){const s=document.createElement("div");s.className="div-table-cell checkbox-column";const i=document.createElement("input");i.type="checkbox",i.checked=this.selectedRows.has(a),i.addEventListener("change",s=>{s.stopPropagation();const o=this.findRowData(a);if(!o)return void console.warn("DivTable: Could not find data for row ID:",a);if(i.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(a),o.selected=!0,e.classList.add("selected"),t.classList.add("selected");else if(this.selectedRows.delete(a),o.selected=!1,e.classList.remove("selected"),t.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const n=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(n)}),i.addEventListener("focus",s=>{this.updateFocusStateForFixedRows(e,t)}),s.appendChild(i),s.addEventListener("click",e=>{e.target!==i&&(e.stopPropagation(),i.click())}),e.appendChild(s)}i.forEach(t=>{const i=this.createCellForComposite(t,s);e.appendChild(i)}),o.forEach(e=>{const i=this.createCellForComposite(e,s);t.appendChild(i)}),e.dataset.populated="true",t.dataset.populated="true",requestAnimationFrame(()=>{requestAnimationFrame(()=>{e.style.height,t.style.height,e.style.minHeight,t.style.minHeight;e.style.height="",t.style.height="",e.style.minHeight="40px",t.style.minHeight="40px";const s=e.offsetHeight,i=t.offsetHeight,o=Math.max(s,i,40);e.style.minHeight=`${o}px`,e.style.height=`${o}px`,t.style.minHeight=`${o}px`,t.style.height=`${o}px`,o>this.estimatedRowHeight&&(this.estimatedRowHeight=o)})}),this.updateTabIndexes()}createRow(e){const t=document.createElement("div");t.className="div-table-row",t.dataset.id=e[this.primaryKeyField];const s=this.getCompositeColumns();let i="";this.showCheckboxes&&(i="40px "),s.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":i+="80px ";break;case"fixed-medium":i+="120px ";break;case"flexible-small":default:i+="1fr ";break;case"flexible-medium":i+="2fr ";break;case"flexible-large":i+="3fr "}}),t.style.gridTemplateColumns=i.trim();const o=String(e[this.primaryKeyField]);if(this.selectedRows.has(o)&&t.classList.add("selected"),this.focusedRowId===o&&t.classList.add("focused"),this.lazyCellRendering)return t.style.minHeight=this.estimatedRowHeight+"px",t.dataset.populated="false",t.addEventListener("click",s=>{if("true"!==t.dataset.populated&&this.populateRowCells(t,e),s.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const i=this.getFocusableElementForRow(t);if(i){if(this.getCurrentFocusedElement()===i)return;const e=this.getAllFocusableElements().indexOf(i);-1!==e&&this.focusElementAtIndex(e)}}),t.addEventListener("focus",s=>{"true"!==t.dataset.populated&&this.populateRowCells(t,e),this.updateFocusState(t)}),t;if(this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column";const s=document.createElement("input");s.type="checkbox",s.checked=this.selectedRows.has(o),s.addEventListener("change",e=>{e.stopPropagation();const i=this.findRowData(o);if(!i)return void console.warn("DivTable: Could not find data for row ID:",o);if(s.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(o),i.selected=!0,t.classList.add("selected");else if(this.selectedRows.delete(o),i.selected=!1,t.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const a=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(a)}),s.addEventListener("focus",e=>{this.updateFocusState(t)}),s.addEventListener("blur",e=>{}),e.appendChild(s),e.addEventListener("click",e=>{e.target!==s&&(e.stopPropagation(),s.click())}),t.appendChild(e)}return s.forEach(s=>{const i=document.createElement("div");if(i.className="div-table-cell",s.compositeName)i.classList.add("composite-cell"),i.style.display="flex",i.style.flexDirection="column",i.style.gap="4px",s.columns.forEach((t,s)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",this.groupByField&&t.field===this.groupByField)o.classList.add("grouped-column"),o.textContent="";else if(t.subField){o.classList.add("composite-column"),o.style.display="flex",o.style.flexDirection="column",o.style.gap="2px";const s=document.createElement("div");s.className="composite-main","function"==typeof t.render?s.innerHTML=t.render(e[t.field],e):s.innerHTML=e[t.field]??"";const i=document.createElement("div");i.className="composite-sub","function"==typeof t.subRender?i.innerHTML=t.subRender(e[t.subField],e):i.innerHTML=e[t.subField]??"",o.appendChild(s),o.appendChild(i)}else"function"==typeof t.render?o.innerHTML=t.render(e[t.field],e):o.innerHTML=e[t.field]??"";i.appendChild(o)});else{const t=s.columns[0];if(this.groupByField&&t.field===this.groupByField)i.classList.add("grouped-column"),i.textContent="";else if(t.subField){i.classList.add("composite-column");const s=document.createElement("div");s.className="composite-main","function"==typeof t.render?s.innerHTML=t.render(e[t.field],e):s.innerHTML=e[t.field]??"";const o=document.createElement("div");o.className="composite-sub","function"==typeof t.subRender?o.innerHTML=t.subRender(e[t.subField],e):o.innerHTML=e[t.subField]??"",i.appendChild(s),i.appendChild(o)}else"function"==typeof t.render?i.innerHTML=t.render(e[t.field],e):i.innerHTML=e[t.field]??""}t.appendChild(i)}),t.addEventListener("click",e=>{if(e.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const s=this.getFocusableElementForRow(t);if(s){if(this.getCurrentFocusedElement()===s)return;const e=this.getAllFocusableElements().indexOf(s);-1!==e&&this.focusElementAtIndex(e)}}),t.addEventListener("focus",e=>{this.updateFocusState(t)}),t}createRowWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout(),i=String(e[this.primaryKeyField]),o=document.createElement("div");o.className="div-table-row div-table-fixed-row",o.dataset.id=i;let a="";this.showCheckboxes&&(a="40px "),t.forEach(e=>{a+=this.getColumnGridSize(e)+" "}),o.style.gridTemplateColumns=a.trim();const n=document.createElement("div");n.className="div-table-row div-table-scroll-row",n.dataset.id=i;let l="";if(s.forEach(e=>{l+=this.getColumnGridSize(e)+" "}),n.style.gridTemplateColumns=l.trim(),this.selectedRows.has(i)&&(o.classList.add("selected"),n.classList.add("selected")),this.focusedRowId===i&&(o.classList.add("focused"),n.classList.add("focused")),this.lazyCellRendering){o.style.minHeight=this.estimatedRowHeight+"px",n.style.minHeight=this.estimatedRowHeight+"px",o.dataset.populated="false",n.dataset.populated="false";const t=(t,s)=>{if("true"!==o.dataset.populated&&this.populateRowCellsWithFixedColumns(o,n,e),t.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const i=this.getFocusableElementForRow(o);if(i){const e=this.getAllFocusableElements().indexOf(i);-1!==e&&this.focusElementAtIndex(e)}};return o.addEventListener("click",e=>t(e,o)),n.addEventListener("click",e=>t(e,n)),o.addEventListener("focus",t=>{"true"!==o.dataset.populated&&this.populateRowCellsWithFixedColumns(o,n,e),this.updateFocusStateForFixedRows(o,n)}),o.addEventListener("mouseenter",()=>n.classList.add("hover")),o.addEventListener("mouseleave",()=>n.classList.remove("hover")),n.addEventListener("mouseenter",()=>o.classList.add("hover")),n.addEventListener("mouseleave",()=>o.classList.remove("hover")),{fixedRow:o,scrollRow:n}}if(this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column";const t=document.createElement("input");t.type="checkbox",t.checked=this.selectedRows.has(i),t.addEventListener("change",e=>{e.stopPropagation();const s=this.findRowData(i);if(!s)return void console.warn("DivTable: Could not find data for row ID:",i);if(t.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(i),s.selected=!0,o.classList.add("selected"),n.classList.add("selected");else if(this.selectedRows.delete(i),s.selected=!1,o.classList.remove("selected"),n.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const a=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(a)}),t.addEventListener("focus",e=>{this.updateFocusStateForFixedRows(o,n)}),e.appendChild(t),e.addEventListener("click",e=>{e.target!==t&&(e.stopPropagation(),t.click())}),o.appendChild(e)}t.forEach(t=>{const s=this.createCellForComposite(t,e);o.appendChild(s)}),s.forEach(t=>{const s=this.createCellForComposite(t,e);n.appendChild(s)});const r=(e,t)=>{if(e.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const s=this.getFocusableElementForRow(o);if(s){const e=this.getAllFocusableElements().indexOf(s);-1!==e&&this.focusElementAtIndex(e)}};return o.addEventListener("click",e=>r(e)),n.addEventListener("click",e=>r(e)),o.addEventListener("mouseenter",()=>{n.classList.add("hover")}),o.addEventListener("mouseleave",()=>{n.classList.remove("hover")}),n.addEventListener("mouseenter",()=>{o.classList.add("hover")}),n.addEventListener("mouseleave",()=>{o.classList.remove("hover")}),{fixedRow:o,scrollRow:n}}updateFocusStateForFixedRows(e,t){this.fixedBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),this.scrollBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),e.classList.add("focused"),t.classList.add("focused");const s=e.dataset.id;if(s&&(this.focusedRowId=s,this._lastFocusCallback.rowId!==s)){this._lastFocusCallback={rowId:s,groupKey:null};const e=this.findRowData(s);this.onRowFocus(e)}}createCellForComposite(e,t){const s=document.createElement("div");if(s.className="div-table-cell",!e.compositeName&&e.columns[0]?.align&&(s.style.textAlign=e.columns[0].align,s.style.justifyContent="right"===e.columns[0].align?"flex-end":"center"===e.columns[0].align?"center":"flex-start"),e.compositeName)s.classList.add("composite-cell"),s.style.display="flex",s.style.flexDirection="column",s.style.gap="4px",e.columns.forEach((e,i)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",this.groupByField&&e.field===this.groupByField)o.classList.add("grouped-column"),o.textContent="";else if(e.subField){o.classList.add("composite-column"),o.style.display="flex",o.style.flexDirection="column",o.style.gap="2px";const s=document.createElement("div");s.className="composite-main","function"==typeof e.render?s.innerHTML=e.render(t[e.field],t):s.innerHTML=t[e.field]??"";const i=document.createElement("div");i.className="composite-sub","function"==typeof e.subRender?i.innerHTML=e.subRender(t[e.subField],t):i.innerHTML=t[e.subField]??"",o.appendChild(s),o.appendChild(i)}else"function"==typeof e.render?o.innerHTML=e.render(t[e.field],t):o.innerHTML=t[e.field]??"";s.appendChild(o)});else{const i=e.columns[0];if(this.groupByField&&i.field===this.groupByField)s.classList.add("grouped-column"),s.textContent="";else if(i.subField){s.classList.add("composite-column");const e=document.createElement("div");e.className="composite-main","function"==typeof i.render?e.innerHTML=i.render(t[i.field],t):e.innerHTML=t[i.field]??"";const o=document.createElement("div");o.className="composite-sub","function"==typeof i.subRender?o.innerHTML=i.subRender(t[i.subField],t):o.innerHTML=t[i.subField]??"",s.appendChild(e),s.appendChild(o)}else"function"==typeof i.render?s.innerHTML=i.render(t[i.field],t):s.innerHTML=t[i.field]??""}return s}createGroupHeaderWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout(),i=document.createElement("div");i.className="div-table-row group-header div-table-fixed-row",i.dataset.groupKey=e.key;let o="";this.showCheckboxes&&(o="40px "),t.forEach(e=>{o+=this.getColumnGridSize(e)+" "}),i.style.gridTemplateColumns=o.trim();const a=document.createElement("div");a.className="div-table-row group-header div-table-scroll-row",a.dataset.groupKey=e.key;let n="";if(s.forEach(e=>{n+=this.getColumnGridSize(e)+" "}),a.style.gridTemplateColumns=n.trim(),this.collapsedGroups.has(e.key)&&(i.classList.add("collapsed"),a.classList.add("collapsed")),this.showCheckboxes){const t=document.createElement("div");t.className="div-table-cell checkbox-column";const s=document.createElement("input");s.type="checkbox";const o=e.items.map(e=>String(e[this.primaryKeyField])),n=o.filter(e=>this.selectedRows.has(e));0===n.length?(s.checked=!1,s.indeterminate=!1):n.length===o.length?(s.checked=!0,s.indeterminate=!1):(s.checked=!1,s.indeterminate=!0),s.addEventListener("change",t=>{t.stopPropagation();const s=0===o.filter(e=>this.selectedRows.has(e)).length;if(e.items.forEach(e=>{const t=String(e[this.primaryKeyField]);s?(this.selectedRows.add(t),e.selected=!0):(this.selectedRows.delete(t),e.selected=!1)}),this.showOnlySelected)return this.renderBody(),this.updateInfoSection(),void("function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean)));this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}),s.addEventListener("focus",e=>{this.updateFocusStateForFixedRows(i,a)}),t.appendChild(s),i.appendChild(t)}const l=document.createElement("div");l.className="div-table-cell",l.style.gridColumn=this.showCheckboxes?"2 / -1":"1 / -1",l.style.display="flex",l.style.alignItems="center",l.style.gap="8px";const r=document.createElement("span");r.className="group-toggle",this.collapsedGroups.has(e.key)&&r.classList.add("collapsed"),r.textContent="❯",r.title=this.collapsedGroups.has(e.key)?"Expand group":"Collapse group";const d=this.columns.find(e=>e.field===this.groupByField),c=d?.label||this.groupByField;let h;h=null==e.value||""===e.value?`${c} is undefined`:d&&"function"==typeof d.render?d.render(e.value,null):e.value,l.appendChild(r);const u=document.createElement("span");"string"==typeof h?u.innerHTML=h:u.textContent=h,l.appendChild(u);const p=document.createElement("span");p.className="group-item-count",p.innerHTML=`(${e.items.length})`,p.style.opacity="0.8",p.style.fontSize="0.9em",p.style.fontWeight="normal",p.title=`${e.items.length} item${1===e.items.length?"":"s"} in this group`,l.appendChild(p),i.appendChild(l);const m=document.createElement("div");m.className="div-table-cell",m.style.gridColumn="1 / -1",a.appendChild(m);return r.addEventListener("click",t=>{t.stopPropagation(),t.preventDefault(),this.collapsedGroups.has(e.key)?(this.collapsedGroups.delete(e.key),i.classList.remove("collapsed"),a.classList.remove("collapsed")):(this.collapsedGroups.add(e.key),i.classList.add("collapsed"),a.classList.add("collapsed")),this.render()}),i.addEventListener("mouseenter",()=>{a.classList.add("hover")}),i.addEventListener("mouseleave",()=>{a.classList.remove("hover")}),a.addEventListener("mouseenter",()=>{i.classList.add("hover")}),a.addEventListener("mouseleave",()=>{i.classList.remove("hover")}),{fixedGroupHeader:i,scrollGroupHeader:a}}createGroupHeader(e){const t=document.createElement("div");t.className="div-table-row group-header",t.dataset.groupKey=e.key;const s=this.getOrderedColumns();let i="";if(this.showCheckboxes&&(i="40px "),s.forEach(e=>{switch((e.responsive||{}).size){case"fixed-narrow":i+="80px ";break;case"fixed-medium":i+="120px ";break;case"flexible-small":default:i+="1fr ";break;case"flexible-medium":i+="2fr ";break;case"flexible-large":i+="3fr "}}),t.style.gridTemplateColumns=i.trim(),this.collapsedGroups.has(e.key)&&t.classList.add("collapsed"),this.showCheckboxes){const s=document.createElement("div");s.className="div-table-cell checkbox-column";const i=document.createElement("input");i.type="checkbox";const o=e.items.map(e=>String(e[this.primaryKeyField])),a=o.filter(e=>this.selectedRows.has(e));0===a.length?(i.checked=!1,i.indeterminate=!1):a.length===o.length?(i.checked=!0,i.indeterminate=!1):(i.checked=!1,i.indeterminate=!0),i.addEventListener("change",t=>{t.stopPropagation();const s=0===e.items.map(e=>String(e[this.primaryKeyField])).filter(e=>this.selectedRows.has(e)).length;if(e.items.forEach(e=>{const t=String(e[this.primaryKeyField]);s?(this.selectedRows.add(t),e.selected=!0):(this.selectedRows.delete(t),e.selected=!1)}),this.showOnlySelected)return this.renderBody(),this.updateInfoSection(),void("function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean)));this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}),i.addEventListener("focus",e=>{this.updateFocusState(t)}),s.appendChild(i),t.appendChild(s)}const o=document.createElement("div");o.className="div-table-cell",o.style.gridColumn=this.showCheckboxes?"2 / -1":"1 / -1",o.style.display="flex",o.style.alignItems="center",o.style.gap="8px";const a=document.createElement("span");a.className="group-toggle",this.collapsedGroups.has(e.key)&&a.classList.add("collapsed"),a.textContent="❯",a.title=this.collapsedGroups.has(e.key)?"Expand group":"Collapse group";const n=this.columns.find(e=>e.field===this.groupByField),l=n?.label||this.groupByField;let r;r=null==e.value||""===e.value?`${l} is undefined`:n&&"function"==typeof n.render?n.render(e.value,null):e.value,o.appendChild(a);const d=document.createElement("span");"string"==typeof r?d.innerHTML=r:d.textContent=r,o.appendChild(d);const c=document.createElement("span");return c.className="group-item-count",c.innerHTML=`(${e.items.length})`,c.style.opacity="0.8",c.style.fontSize="0.9em",c.style.fontWeight="normal",c.title=`${e.items.length} item${1===e.items.length?"":"s"} in this group`,o.appendChild(c),t.appendChild(o),a.addEventListener("click",s=>{s.stopPropagation(),s.preventDefault(),this.collapsedGroups.has(e.key)?(this.collapsedGroups.delete(e.key),t.classList.remove("collapsed")):(this.collapsedGroups.add(e.key),t.classList.add("collapsed")),this.render(),setTimeout(()=>{const t=this.bodyContainer.querySelector(`[data-group-key="${e.key}"]`);if(t){const e=this.getFocusableElementForRow(t);if(e){const t=this.getAllFocusableElements().indexOf(e);-1!==t&&this.focusElementAtIndex(t)}}},0)}),t.addEventListener("click",e=>{if(e.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const s=this.getFocusableElementForRow(t);if(s){if(this.getCurrentFocusedElement()===s)return;const e=this.getAllFocusableElements().indexOf(s);-1!==e&&this.focusElementAtIndex(e)}}),t.addEventListener("focus",e=>{this.updateFocusState(t)}),t}groupData(e){const t=new Map;return e.forEach(e=>{const s=e[this.groupByField];let i,o;Array.isArray(s)?(i=s.length>0?s.join(", "):"__null__",o=s.length>0?s.join(", "):null):(i=s??"__null__",o=s),t.has(i)||t.set(i,{key:i,value:o,items:[]}),t.get(i).items.push(e)}),Array.from(t.values()).sort((e,t)=>null==e.value?1:null==t.value?-1:String(e.value).localeCompare(String(t.value)))}sortData(e){return this.sortColumn?[...e].sort((e,t)=>{const s=e[this.sortColumn],i=t[this.sortColumn];if(null==s&&null==i)return 0;if(null==s)return"asc"===this.sortDirection?-1:1;if(null==i)return"asc"===this.sortDirection?1:-1;let o=0;return o="number"==typeof s&&"number"==typeof i?s-i:String(s).localeCompare(String(i)),"desc"===this.sortDirection?-o:o}):e}selectAll(){this.selectedRows.clear(),this.filteredData.forEach(e=>{const t=String(e[this.primaryKeyField]);this.selectedRows.add(t),e.selected=!0}),this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}updateInfoSection(){if(!this.infoSection)return;const e=this.virtualScrolling?Math.max(this.totalRecords,this.data.length):this.data.length,t=this.data.length,s=this.filteredData.length,i=this.getValidSelectedCount();this.infoSection.innerHTML="";const o=document.createElement("div");if(o.className="info-line-container",i>0){const e=document.createElement("div");e.className="info-line";const t=this.createFilterSelectedOnlyToggleButton();e.appendChild(t);const s=document.createElement("span");s.className="info-selection",s.textContent=`${i} selected`,e.appendChild(s),o.appendChild(e)}if(this.showAutoFetchButton&&this.virtualScrolling&&(this.hasMoreData||this.isAutoFetching)){const e=this.createAutoFetchButton();e.disabled=!1,o.appendChild(e)}if(this.showRefreshButton){const e=this.createRefreshButton();this.isLoading||this.isLoadingState?(e.classList.add("refreshing"),e.disabled=!0,e.title="Loading data..."):(e.classList.remove("refreshing"),e.disabled=!1,e.title="Refresh data"),o.appendChild(e)}o.children.length>0&&this.infoSection.appendChild(o);const a=document.createElement("div");a.className="info-line secondary";const n=document.createElement("span");n.className="info-stats";let l="";if(this.virtualScrolling)if(s<t)if(t<e){l=`${s} filtered (${Math.round(t/e*100)}% of ${e} total)`}else l=`${s} filtered (${e} total)`;else if(t<e){l=`${Math.round(t/e*100)}% of ${e} total`}else l=`${e} total`;else l=s<e?`${s} filtered (${e} total)`:`${e} total`;n.textContent=l,a.appendChild(n),this.infoSection.appendChild(a),this.createProgressBar(t,e,s)}createProgressBar(e,t,s){const i=document.createElement("div");i.className="progress-line";const o=this.virtualScrolling?this.totalRecords:this.data.length,a=this.virtualScrolling&&e<o;if(a||s<o){const t=document.createElement("div");t.className="loading-progress";const n=Math.ceil(.1*o),l=this.pageSize||50,r=Math.max(l,Math.min(n,100)),d=e<o?Math.min(o,e+r):e,c=s/o*100,h=e/o*100,u=d/o*100,p=s<e&&this.currentQuery&&""!==this.currentQuery.trim();if(p){if(s>0){const e=document.createElement("div");e.className="progress-segment filtered-segment",e.style.width=`${c}%`,e.style.opacity="1",t.appendChild(e)}if(e>s){const e=document.createElement("div");e.className="progress-segment loaded-segment",e.style.left=`${c}%`,e.style.width=h-c+"%",e.style.opacity="0.8",t.appendChild(e)}}else if(e>0){const e=document.createElement("div");e.className="progress-segment loaded-segment",e.style.width=`${h}%`,e.style.opacity="1",t.appendChild(e)}if(this.hasMoreData&&(this.isLoading||this.isAutoFetching&&!this.autoFetchPaused)&&e<o&&d>e){const e=document.createElement("div");e.className="progress-segment loading-segment",e.style.left=`${h}%`,e.style.width=u-h+"%",t.appendChild(e)}p&&a?t.setAttribute("data-state","filtered-loading"):p?t.setAttribute("data-state","filtered"):a&&t.setAttribute("data-state","sequential-loading"),i.appendChild(t),this.infoSection.appendChild(i)}}createRefreshButton(){const e=document.createElement("button");return e.className="refresh-button",e.type="button",e.title="Refresh data",e.setAttribute("aria-label","Refresh table data"),e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <path d="M23 4v6h-6"></path>\n <path d="M20.49 15a9 9 0 1 1-2.12-9.36L23 10"></path>\n </svg>\n ',e.addEventListener("click",async t=>{t.preventDefault(),t.stopPropagation(),e.classList.add("refreshing");try{await this.refresh()}catch(e){}finally{setTimeout(()=>{e.classList.remove("refreshing")},500)}}),e}createAutoFetchButton(){const e=document.createElement("button");e.className="auto-fetch-button",e.type="button",e.title="Auto-fetch all pages",e.setAttribute("aria-label","Automatically fetch all remaining pages");const t=t=>{this.isAutoFetching&&!t?(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <rect x="6" y="4" width="4" height="16"></rect>\n <rect x="14" y="4" width="4" height="16"></rect>\n </svg>\n ',e.title="Pause auto-fetch",e.classList.add("active"),e.classList.remove("paused")):(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <polygon points="5 3 19 12 5 21 5 3"></polygon>\n </svg>\n ',e.classList.remove("active"),t?(e.title="Resume auto-fetch (waiting for current page to complete)",e.classList.add("paused")):(e.title="Auto-fetch all pages",e.classList.remove("paused")))};return t(this.autoFetchPaused),e.addEventListener("click",async e=>{e.preventDefault(),e.stopPropagation(),this.isAutoFetching?(this.autoFetchPaused=!this.autoFetchPaused,t(this.autoFetchPaused),this.autoFetchPaused||this.continueAutoFetch()):this.startAutoFetch(t)}),this.autoFetchButton=e,this.updateAutoFetchButtonIcon=t,e}async startAutoFetch(e){if(this.virtualScrolling&&this.hasMoreData&&!this.isAutoFetching){this.isAutoFetching=!0,this.autoFetchPaused=!1,e(!1),console.log("🚀 Starting auto-fetch...");try{await this.continueAutoFetch()}catch(e){console.error("❌ Auto-fetch error:",e),this.stopAutoFetch()}}}async continueAutoFetch(){for(;this.hasMoreData&&this.isAutoFetching&&!this.autoFetchPaused&&(await this.loadNextPage(),this.hasMoreData&&this.isAutoFetching&&!this.autoFetchPaused)&&(await new Promise(e=>{this.autoFetchTimeout=setTimeout(e,this.autoFetchDelay)}),!this.autoFetchPaused););this.hasMoreData?this.autoFetchPaused&&(this.updateAutoFetchButtonIcon&&this.updateAutoFetchButtonIcon(!0),this.updateInfoSection()):this.stopAutoFetch()}stopAutoFetch(){this.isAutoFetching=!1,this.autoFetchPaused=!1,this.autoFetchTimeout&&(clearTimeout(this.autoFetchTimeout),this.autoFetchTimeout=null),this.updateAutoFetchButtonIcon&&(this.updateAutoFetchButtonIcon(!1),this.autoFetchButton?.classList.remove("active","paused")),this.updateInfoSection()}createFilterSelectedOnlyToggleButton(){const e=document.createElement("button");e.className="filter-selected-only-toggle-button",e.type="button";const t=()=>{this.showOnlySelected?(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"></path>\n <circle cx="12" cy="12" r="3"></circle>\n </svg>\n ',e.title="Show all rows",e.classList.add("active")):(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"></path>\n <circle cx="12" cy="12" r="3"></circle>\n </svg>\n ',e.title="Show only selected rows",e.classList.remove("active"))};return t(),e.addEventListener("click",e=>{e.preventDefault(),e.stopPropagation(),this.showOnlySelected=!this.showOnlySelected,t(),this.render(),console.log(this.showOnlySelected?"👁️ Showing only selected rows":"👁️ Showing all rows")}),e}updateInfoSectionWithAnticipatedProgress(){if(!this.infoSection||!this.virtualScrolling)return;const e=Math.max(this.totalRecords,this.data.length),t=this.data.length,s=this.filteredData.length,i=this.getValidSelectedCount(),o=Math.min(t+this.pageSize,e);this.infoSection.innerHTML="";const a=document.createElement("div");if(a.className="info-line-container",i>0){const e=document.createElement("div");e.className="info-line";const t=document.createElement("span");t.className="info-selection",t.textContent=`${i} selected`,e.appendChild(t),a.appendChild(e)}if(this.showAutoFetchButton&&this.virtualScrolling&&(this.hasMoreData||this.isAutoFetching)){const e=this.createAutoFetchButton();e.disabled=this.autoFetchPaused,a.appendChild(e)}if(this.showRefreshButton){const e=this.createRefreshButton();e.classList.add("refreshing"),e.disabled=!0,e.title="Loading data...",a.appendChild(e)}a.children.length>0&&this.infoSection.appendChild(a);const n=document.createElement("div");n.className="info-line secondary";const l=document.createElement("span");l.className="info-stats";let r="";if(s<t)if(o<e){r=`${s} filtered (${Math.round(o/e*100)}% of ${e} total)`}else r=`${s} filtered (${e} total)`;else if(o<e){r=`${Math.round(o/e*100)}% of ${e} total`}else r=`${e} total`;l.textContent=r,n.appendChild(l),this.infoSection.appendChild(n),this.createProgressBar(o,e,s)}applyQuery(e){if(this.currentQuery=e,this.queryEditor?.editor){this.queryEditor.editor.getValue()!==e&&this.queryEditor.editor.setValue(e)}if(e.trim())try{const t=this.queryEngine.filterObjects(e);this.filteredData=this.data.filter(e=>t.includes(e[this.primaryKeyField]))}catch(e){this.filteredData=[...this.data]}else this.filteredData=[...this.data];this.render()}sort(e,t){this.groupByField&&e===this.groupByField?this.sortColumn===e?"value"===this.sortMode&&"asc"===this.sortDirection?this.sortDirection="desc":"value"===this.sortMode&&"desc"===this.sortDirection?(this.sortMode="count",this.sortDirection="asc"):"count"===this.sortMode&&"asc"===this.sortDirection?this.sortDirection="desc":(this.sortColumn=null,this.sortDirection="asc",this.sortMode="value"):(this.sortColumn=e,this.sortDirection="asc",this.sortMode="value"):this.sortColumn===e?this.sortDirection="asc"===this.sortDirection?"desc":"asc":(this.sortColumn=e,this.sortDirection=t||"asc",this.sortMode="value"),this.render()}group(e){if(e){const t=this.columns.find(t=>t.field===e);if(!t)return void console.warn(`DivTable: Cannot group by field '${e}' - field not found in columns`);if(t.hidden)return void console.warn(`DivTable: Cannot group by field '${e}' - hidden columns cannot be used for grouping`);if(!1===t.groupable)return void console.warn(`DivTable: Cannot group by field '${e}' - column is marked as not groupable`)}if(this.groupByField=e||null,e){this.collapsedGroups.clear();this.groupData(this.filteredData).forEach(e=>{this.collapsedGroups.add(e.key)})}else this.collapsedGroups.clear();this.render()}clearGrouping(){this.group(null)}addRecord(e){if(!e||"object"!=typeof e)return console.warn("addRecord requires a valid record object"),!1;if(!e[this.primaryKeyField])return console.warn(`addRecord: Record must have a ${this.primaryKeyField} field`),!1;const t=String(e[this.primaryKeyField]),s=this.data.findIndex(e=>String(e[this.primaryKeyField])===t);return s>=0?(this.data[s]={...e},console.log(`addRecord: Updated existing record with ${this.primaryKeyField} '${t}'`)):(this.data.push(e),console.log(`addRecord: Added new record with ${this.primaryKeyField} '${t}'`)),this.isLoadingState=!1,this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.applyQuery(this.currentQuery),!0}removeRecord(e){if(null==e)return console.warn("removeRecord requires a valid ID"),!1;const t=String(e),s=this.data.findIndex(e=>String(e[this.primaryKeyField])===t);if(s>=0){const e=this.data[s];return this.data.splice(s,1),this.selectedRows.delete(t),this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.applyQuery(this.currentQuery),e}return console.warn(`removeRecord: Record with ${this.primaryKeyField} '${t}' not found`),!1}getSelectedRows(){return Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean)}getValidSelectedCount(){return this.getSelectedRows().length}toggleSelectedRowsFilter(e){return this.showOnlySelected=void 0!==e?e:!this.showOnlySelected,this.render(),console.log(this.showOnlySelected?"👁️ Showing only selected rows":"👁️ Showing all rows"),this.showOnlySelected}async refresh(){this.isAutoFetching&&this.stopAutoFetch();try{if(this.virtualScrolling&&"function"==typeof this.onNextPage){this.currentQuery,this.queryEditor?.editor&&this.queryEditor.editor.getValue();const e=new Set(this.selectedRows);this.isLoadingState=!0,this.data=[],this.filteredData=[],this.currentPage=0,this.isLoading=!0,this.hasMoreData=!0,this.queryEngine.setObjects([]),this.render();const t=0,s=await this.onNextPage(t,this.pageSize);if(this.isLoading=!1,s&&Array.isArray(s)&&s.length>0){this.replaceData(s),this.selectedRows.clear();for(const t of e){this.data.some(e=>String(e[this.primaryKeyField])===t)&&this.selectedRows.add(t)}this.render()}else this.isLoadingState=!1,this.render()}else"function"==typeof this.onRefresh?(this.showLoadingPlaceholder&&(this.isLoadingState=!0,this.render()),await Promise.resolve(this.onRefresh()),this.isLoadingState&&(this.isLoadingState=!1,this.render())):console.log("ℹ️ Refresh: No onRefresh callback provided for non-virtual scrolling table")}catch(e){throw console.error("❌ Refresh error:",e),this.isLoadingState=!1,this.render(),e}}updateQueryEditorIfNeeded(){if(!this.queryEditor||!this.queryEditor.editor)return;if(0===this.data.length)return;const e=this.queryEditor.editor.getFieldNames()||{},t=new Set(this.columns.filter(e=>e.field).map(e=>e.field)),s={};Object.keys(e).forEach(i=>{t.has(i)&&(s[i]=e[i])});const i={...s};this.data.length>0&&this.columns.forEach(e=>{const t=e.field;if(t&&s[t]){const o=s[t],a=e.type||o.type;if("string"===a&&void 0!==o.values){const e=[];this.data.forEach(s=>{const i=s[t];Array.isArray(i)?e.push(...i):e.push(i)});const s=[...new Set(e)],n=s.filter(e=>null!=e&&""!==e),l=s.some(e=>null==e||""===e),r=o.values.filter(e=>"NULL"!==e),d=[...new Set([...r,...n])];i[t]={type:a,values:l?[...d,"NULL"]:d}}else i[t]={type:a}}});if(this._shouldUpdateFieldNames(s,i))try{this.queryEditor.editor.updateFieldNames(i)||console.warn("⚠️ Failed to update query editor field values - dynamic update not available")}catch(e){console.warn("⚠️ Error updating query editor field values:",e)}}setupQueryEventHandlers(){setTimeout(()=>{const e=this.queryEditor.model?.getValue();""===e&&this.monaco.editor.setModelMarkers(this.queryEditor.model,this.queryEditor.model.getLanguageId(),[])},10),this.queryEditor.model&&this.queryEditor.model.onDidChangeContent(()=>{const e=this.queryEditor.model.getValue();this.handleQueryChange(e)}),this._setupQueryListeners()}verifyDataConsistency(){const e=[];for(const t of this.selectedRows){this.findRowData(t)||e.push(`Selected row ${t} not found in data`)}const t=Array.from(this.bodyContainer.querySelectorAll(".div-table-row[data-id]")).map(e=>e.dataset.id);for(const s of t){this.findRowData(s)||e.push(`Displayed row ${s} not found in data`)}return e.length>0&&console.warn("DivTable data consistency issues:",e),0===e.length}testGroupSelectionStates(){if(!this.groupByField)return void console.log("No grouping applied");const e=this.groupData(this.sortData(this.filteredData));console.log("Group selection states:"),e.forEach(e=>{const t=e.items.map(e=>String(e[this.primaryKeyField])),s=t.filter(e=>this.selectedRows.has(e));let i="none";s.length===t.length?i="all":s.length>0&&(i="partial"),console.log(`Group "${e.value}": ${s.length}/${t.length} selected (${i})`)})}handleVirtualScroll(){const e=this.bodyContainer.scrollTop,t=this.bodyContainer.scrollHeight,s=(e+this.bodyContainer.clientHeight)/t,i=this.filteredData.length;Math.floor(s*i)>=i-this.loadingThreshold&&this.hasMoreData&&!this.isLoading&&this.loadNextPage()}async loadNextPage(){if(!this.isLoading&&this.hasMoreData){this.isLoading=!0,this.showLoadingPlaceholders(),this.updateInfoSectionWithAnticipatedProgress();try{const e=this.currentPage+1,t=await this.onNextPage(e,this.pageSize);if(this.isLoading=!1,this.hideLoadingPlaceholders(),t&&Array.isArray(t)&&t.length>0){const s=this.appendData(t,!0);(s.added>0||s.updated>0)&&(this.currentPage=e),this.totalRecords&&this.totalRecords>0?this.hasMoreData=this.data.length<this.totalRecords:this.hasMoreData=t.length===this.pageSize,t.length<this.pageSize&&(this.hasMoreData=!1)}else this.hasMoreData=!1}catch(e){console.error("❌ Error loading next page:",e),this.isLoading=!1,this.hideLoadingPlaceholders(),this.showErrorIndicator()}finally{this.updateInfoSection()}}}showErrorIndicator(){let e=this.bodyContainer.querySelector(".error-indicator");if(!e){e=document.createElement("div"),e.className="error-indicator",e.innerHTML='\n <span>Error loading data. Please try again.</span>\n <button class="retry-button">Retry</button>\n ';e.querySelector(".retry-button").addEventListener("click",()=>{this.hideErrorIndicator(),this.loadNextPage()}),this.bodyContainer.appendChild(e)}e.style.display="flex"}hideErrorIndicator(){const e=this.bodyContainer.querySelector(".error-indicator");e&&(e.style.display="none")}showLoadingPlaceholders(){if(!this.showLoadingPlaceholder)return;this.hideLoadingPlaceholders();for(let e=0;e<3;e++){const e=this.createLoadingPlaceholderRow();this.bodyContainer.appendChild(e)}}hideLoadingPlaceholders(){this.bodyContainer.querySelectorAll(".div-table-row.loading-placeholder").forEach(e=>e.remove())}createLoadingPlaceholderRow(){const e=document.createElement("div");e.className="div-table-row loading-placeholder";const t=this.getOrderedColumns();let s="";if(this.showCheckboxes&&(s="40px "),t.forEach(e=>{if(this.groupByField&&e.field===this.groupByField)return void(s+="100px ");switch((e.responsive||{}).size){case"fixed-narrow":s+="80px ";break;case"fixed-medium":s+="120px ";break;case"flexible-small":default:s+="1fr ";break;case"flexible-medium":s+="2fr ";break;case"flexible-large":s+="3fr "}}),e.style.gridTemplateColumns=s.trim(),this.showCheckboxes){const t=document.createElement("div");t.className="div-table-cell checkbox-column loading-cell",e.appendChild(t)}return t.forEach(t=>{const s=document.createElement("div");s.className="div-table-cell loading-cell";const i=document.createElement("div");i.className="loading-shimmer-content";const o=60+30*Math.random();i.style.width=`${o}%`,s.appendChild(i),e.appendChild(s)}),e}clearRefreshButtonLoadingState(){if(this.showRefreshButton){const e=this.infoSection.querySelector(".refresh-button");e&&(e.classList.remove("refreshing"),e.disabled=!1,e.title="Refresh data")}}setTotalRecords(e){"number"!=typeof e||e<0?console.warn("DivTable: totalRecords must be a non-negative number"):(this.totalRecords=e,this.hasMoreData=this.data.length<e,this.updateInfoSection(),console.log(`DivTable: Updated totalRecords to ${e}, hasMoreData: ${this.hasMoreData}`))}setPageSize(e){if("number"!=typeof e||e<=0)return void console.warn("DivTable: pageSize must be a positive number");const t=this.pageSize;this.pageSize=e,this.loadingThreshold=Math.floor(.8*this.pageSize),this.visibleEndIndex=Math.min(this.visibleStartIndex+this.pageSize,this.data.length),this.updateInfoSection(),console.log(`DivTable: Updated pageSize from ${t} to ${e}, loadingThreshold: ${this.loadingThreshold}`)}setVirtualScrollingConfig({totalRecords:e,pageSize:t,loadingThreshold:s}){let i=!1;"number"==typeof e&&e>=0&&(this.totalRecords=e,this.hasMoreData=this.data.length<e,i=!0),"number"==typeof t&&t>0&&(this.pageSize=t,this.visibleEndIndex=Math.min(this.visibleStartIndex+this.pageSize,this.data.length),i=!0),"number"==typeof s&&s>0?(this.loadingThreshold=s,i=!0):"number"==typeof t&&(this.loadingThreshold=Math.floor(.8*this.pageSize),i=!0),i&&(this.updateInfoSection(),console.log(`DivTable: Updated virtual scrolling config - totalRecords: ${this.totalRecords}, pageSize: ${this.pageSize}, loadingThreshold: ${this.loadingThreshold}`))}setHasMoreData(e){this.hasMoreData=e}resetPagination(){this.currentPage=0,this.isLoading=!1,this.hasMoreData=!0,this.data=this.data.slice(0,this.pageSize),this.filteredData=[...this.data],this.hideErrorIndicator(),this.render()}appendData(e,t=!1){if(!e||!Array.isArray(e))return console.warn("appendData requires a valid array"),{added:0,updated:0,skipped:0,invalid:[]};const s=[];let i=0,o=0;for(const t of e){if(!t||"object"!=typeof t){s.push(t),console.warn("appendData: Skipping invalid record",t);continue}if(!t[this.primaryKeyField]){s.push(t),console.warn(`appendData: Skipping record without ${this.primaryKeyField}`,t);continue}const e=String(t[this.primaryKeyField]),a=this.data.findIndex(t=>String(t[this.primaryKeyField])===e);a>=0?(this.data[a]={...t},o++):(this.data.push(t),i++)}return(i>0||o>0)&&(this.isLoadingState=!1,this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.currentQuery.trim()?this.applyQuery(this.currentQuery):this.filteredData=[...this.data],t||this.updateInfoSection(),this.render()),{added:i,updated:o,skipped:s.length,invalid:s}}replaceData(e){if(!e||!Array.isArray(e))return console.warn("replaceData requires a valid array"),{success:!1,message:"Invalid data provided"};const t=[],s=new Set,i=[];for(const o of e){if(!o||"object"!=typeof o){console.warn("replaceData: Skipping invalid record",o);continue}if(!o[this.primaryKeyField]){console.warn(`replaceData: Skipping record without ${this.primaryKeyField}`,o);continue}const e=String(o[this.primaryKeyField]);s.has(e)?(t.push(e),console.warn(`replaceData: Skipping duplicate ${this.primaryKeyField} '${e}' within new data`)):(s.add(e),i.push(o))}return this.data=i,this.isLoadingState=!1,this.clearRefreshButtonLoadingState(),this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.currentQuery&&this.currentQuery.trim()?this.applyQuery(this.currentQuery):this.filteredData=[...this.data],this.selectedRows.clear(),this.virtualScrollingState={scrollTop:0,displayStartIndex:0,displayEndIndex:Math.min(this.pageSize,this.data.length),isLoading:!1},this.currentPage=0,this.startId=1,this.virtualScrolling&&this.totalRecords&&(this.hasMoreData=i.length<this.totalRecords),this.updateInfoSection(),this.render(),{success:!0,totalProvided:e.length,validRecords:i.length,skipped:e.length-i.length,duplicates:t}}resetToLoading(){this.isLoadingState=!0,this.data=[],this.filteredData=[],this.selectedRows.clear(),this.currentQuery="",this.queryEditor?.editor&&this.queryEditor.editor.setValue(""),this.queryEngine.setObjects([]),this.render()}setLoadingState(e){this.isLoadingState=Boolean(e),this.render()}hasAggregateColumns(){return this.columns.some(e=>e.aggregate)}getAggregateColumns(){return this.columns.filter(e=>e.aggregate)}calculateAggregate(e,t){if(!e.aggregate||!t||0===t.length)return null;const s=e.field,i=e.aggregate.toLowerCase(),o=t.map(e=>e[s]).filter(e=>null!=e&&!isNaN(parseFloat(e))).map(e=>parseFloat(e));if(0===o.length&&"count"!==i)return null;switch(i){case"sum":return o.reduce((e,t)=>e+t,0);case"avg":case"average":return o.length>0?o.reduce((e,t)=>e+t,0)/o.length:null;case"count":return t.length;case"min":return o.length>0?Math.min(...o):null;case"max":return o.length>0?Math.max(...o):null;default:return console.warn(`DivTable: Unknown aggregate type '${i}' for column '${s}'`),null}}getAggregationDataSet(e){return this.selectedRows.size>0?e.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}):e}formatAggregateValue(e,t){if(null==e)return"";if("function"==typeof t.aggregateRender)return t.aggregateRender(e);const s=t.aggregate.toLowerCase();return"count"===s?String(e):"number"==typeof e?"avg"===s||"average"===s?e.toLocaleString(void 0,{minimumFractionDigits:0,maximumFractionDigits:2}):e.toLocaleString():String(e)}createHeaderSummaryRow(e){const t=document.createElement("div");t.className="div-table-row summary-row header-summary";const s=this.getCompositeColumns(),i=this.getAggregationDataSet(e);let o="";if(this.showCheckboxes&&(o="40px "),s.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":o+="80px ";break;case"fixed-medium":o+="120px ";break;case"flexible-small":default:o+="1fr ";break;case"flexible-medium":o+="2fr ";break;case"flexible-large":o+="3fr "}}),t.style.gridTemplateColumns=o.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",t.appendChild(e)}return s.forEach(e=>{const s=document.createElement("div");if(s.className="div-table-cell summary-cell",e.compositeName)s.classList.add("composite-cell"),e.columns.forEach((e,t)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",e.aggregate){const t=this.calculateAggregate(e,i),s=this.formatAggregateValue(t,e);o.innerHTML=s,o.classList.add("aggregate-value")}s.appendChild(o)});else{const t=e.columns[0];if(t.aggregate){const e=this.calculateAggregate(t,i),o=this.formatAggregateValue(e,t);s.innerHTML=o,s.classList.add("aggregate-value")}}t.appendChild(s)}),t}createGroupSummaryRow(e){const t=document.createElement("div");t.className="div-table-row summary-row group-summary",t.dataset.groupKey=e.key;const s=this.getCompositeColumns();let i=e.items;this.selectedRows.size>0&&(i=e.items.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));let o="";if(this.showCheckboxes&&(o="40px "),s.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":o+="80px ";break;case"fixed-medium":o+="120px ";break;case"flexible-small":default:o+="1fr ";break;case"flexible-medium":o+="2fr ";break;case"flexible-large":o+="3fr "}}),t.style.gridTemplateColumns=o.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",t.appendChild(e)}return s.forEach(e=>{const s=document.createElement("div");if(s.className="div-table-cell summary-cell",e.compositeName)s.classList.add("composite-cell"),e.columns.forEach(e=>{const t=document.createElement("div");if(t.className="composite-sub-cell",e.aggregate){const s=this.calculateAggregate(e,i),o=this.formatAggregateValue(s,e);t.innerHTML=o,t.classList.add("aggregate-value")}s.appendChild(t)});else{const t=e.columns[0];if(t.aggregate){const e=this.calculateAggregate(t,i),o=this.formatAggregateValue(e,t);s.innerHTML=o,s.classList.add("aggregate-value")}}t.appendChild(s)}),t}createHeaderSummaryRowWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout(),i=this.getAggregationDataSet(e),o=document.createElement("div");o.className="div-table-row div-table-fixed-row summary-row header-summary";let a="";if(this.showCheckboxes&&(a="40px "),t.forEach(e=>{a+=this.getColumnGridSize(e)+" "}),o.style.gridTemplateColumns=a.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",o.appendChild(e)}t.forEach(e=>{const t=this.createSummaryCell(e,i);o.appendChild(t)});const n=document.createElement("div");n.className="div-table-row summary-row header-summary";let l="";return s.forEach(e=>{l+=this.getColumnGridSize(e)+" "}),n.style.gridTemplateColumns=l.trim(),s.forEach(e=>{const t=this.createSummaryCell(e,i);n.appendChild(t)}),{fixedSummary:o,scrollSummary:n}}createGroupSummaryRowWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout();let i=e.items;this.selectedRows.size>0&&(i=e.items.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));const o=document.createElement("div");o.className="div-table-row div-table-fixed-row summary-row group-summary",o.dataset.groupKey=e.key;let a="";if(this.showCheckboxes&&(a="40px "),t.forEach(e=>{a+=this.getColumnGridSize(e)+" "}),o.style.gridTemplateColumns=a.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",o.appendChild(e)}t.forEach(e=>{const t=this.createSummaryCell(e,i);o.appendChild(t)});const n=document.createElement("div");n.className="div-table-row summary-row group-summary",n.dataset.groupKey=e.key;let l="";return s.forEach(e=>{l+=this.getColumnGridSize(e)+" "}),n.style.gridTemplateColumns=l.trim(),s.forEach(e=>{const t=this.createSummaryCell(e,i);n.appendChild(t)}),{fixedSummary:o,scrollSummary:n}}createSummaryCell(e,t){const s=document.createElement("div");if(s.className="div-table-cell summary-cell",e.compositeName)s.classList.add("composite-cell"),e.columns.forEach(e=>{const i=document.createElement("div");if(i.className="composite-sub-cell",e.aggregate){const s=this.calculateAggregate(e,t),o=this.formatAggregateValue(s,e);i.innerHTML=o,i.classList.add("aggregate-value"),e.align&&(i.style.textAlign=e.align)}s.appendChild(i)});else{const i=e.columns[0];if(i.align&&(s.style.textAlign=i.align,s.style.justifyContent="right"===i.align?"flex-end":"center"===i.align?"center":"flex-start"),i.aggregate){const e=this.calculateAggregate(i,t),o=this.formatAggregateValue(e,i);s.innerHTML=o,s.classList.add("aggregate-value")}}return s}updateSummaryRows(){if(!this.hasAggregateColumns())return;if(!this.showHeaderSummary&&!this.showGroupSummary)return;let e=this.filteredData;this.showOnlySelected&&this.selectedRows.size>0&&(e=this.filteredData.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));const t=this.getAggregationDataSet(e);this.showHeaderSummary&&this.updateHeaderSummaryValues(t),this.showGroupSummary&&this.groupByField&&this.updateGroupSummaryValues(e)}updateHeaderSummaryValues(e){(this.fixedColumns>0?[this.fixedBodyContainer?.querySelector(".header-summary"),this.scrollBodyContainer?.querySelector(".header-summary")].filter(Boolean):[this.bodyContainer?.querySelector(".header-summary")].filter(Boolean)).forEach(t=>{const s=t.querySelectorAll(".aggregate-value"),i=this.getAggregateColumns();s.forEach((t,s)=>{if(i[s]){const o=i[s],a=this.calculateAggregate(o,e),n=this.formatAggregateValue(a,o);t.innerHTML=n}})})}updateGroupSummaryValues(e){this.groupData(e).forEach(e=>{let t=e.items;this.selectedRows.size>0&&(t=e.items.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));(this.fixedColumns>0?[this.fixedBodyContainer?.querySelector(`.group-summary[data-group-key="${e.key}"]`),this.scrollBodyContainer?.querySelector(`.group-summary[data-group-key="${e.key}"]`)].filter(Boolean):[this.bodyContainer?.querySelector(`.group-summary[data-group-key="${e.key}"]`)].filter(Boolean)).forEach(e=>{const s=e.querySelectorAll(".aggregate-value"),i=this.getAggregateColumns();s.forEach((e,s)=>{if(i[s]){const o=i[s],a=this.calculateAggregate(o,t),n=this.formatAggregateValue(a,o);e.innerHTML=n}})})})}}class s{constructor(e=[],t="id"){this.objects=e,this.primaryKeyField=t}setObjects(e){this.objects=e}filterObjects(e){if(!e.trim())return this.objects.map(e=>e[this.primaryKeyField]);if(!/[=!<>()]|(\bAND\b|\bOR\b|\bIN\b)/i.test(e))return this.searchObjects(e);const t=[];for(const s of this.objects)try{this.evaluateExpression(s,e)&&t.push(s[this.primaryKeyField])}catch(e){throw new Error(`Query error: ${e.message}`)}return t}searchObjects(e){const t=e.trim().toLowerCase().split(/\s+/).filter(Boolean);if(0===t.length)return this.objects.map(e=>e[this.primaryKeyField]);const s=[];for(const e of this.objects){const i=Object.values(e).map(e=>null==e?"":String(e).toLowerCase()).join(" ");t.every(e=>i.includes(e))&&s.push(e[this.primaryKeyField])}return s}evaluateExpression(e,t){if(!t.trim())return!0;for(t=t.replace(/\s+/g," ").trim();/\(([^()]+)\)/.test(t);)t=t.replace(/\(([^()]+)\)/g,(t,s)=>this.processGroup(e,s)?"true":"false");return this.processGroup(e,t)}processGroup(e,t){return t.split(/\s+OR\s+/).some(t=>t.split(/\s+AND\s+/).every(t=>{const s=t.trim().toLowerCase();if("false"===s)return!1;if("true"===s)return!0;try{const s=this.parseCondition(t);return this.applyCondition(e,s)}catch{throw new Error(`Invalid condition: ${t}`)}}))}parseCondition(e){const t=e.match(/(\w+)\s+IN\s+\[([^\]]+)\]/);if(t){const[,e,s]=t;return{field:e,operator:"IN",value:s.split(",").map(e=>{const t=e.trim().replace(/"/g,"");return"NULL"===t?null:t})}}const s=e.match(/(\w+)\s*(=|!=|>=|<=|>|<)\s*(.+)/i);if(s){const[,e,t,i]=s;let o=i.trim();return o.startsWith('"')&&o.endsWith('"')?o=o.slice(1,-1):"NULL"===o?o=null:"true"===o.toLowerCase()?o=!0:"false"===o.toLowerCase()?o=!1:isNaN(o)||""===o||(o=parseFloat(o)),{field:e,operator:t,value:o}}throw new Error(`Invalid condition: ${e}`)}applyCondition(e,{field:t,operator:s,value:i}){const o=t in e?e[t]:null,a=e=>null==e||""===e;switch(s){case"=":return null===i?a(o):!a(o)&&(Array.isArray(o)?o.includes(i):o==i);case"!=":return null===i?!a(o):!!a(o)||(Array.isArray(o)?!o.includes(i):o!=i);case">":return!a(o)&&(!Array.isArray(o)&&o>parseFloat(i));case"<":return!a(o)&&(!Array.isArray(o)&&o<parseFloat(i));case">=":return!a(o)&&(!Array.isArray(o)&&o>=parseFloat(i));case"<=":return!a(o)&&(!Array.isArray(o)&&o<=parseFloat(i));case"IN":return i.includes(null)?a(o)||i.includes(o):!a(o)&&(Array.isArray(o)?o.some(e=>i.includes(e)):i.includes(o));default:return!1}}}e.exports&&(e.exports={DivTable:t,QueryEngine:s})},853:()=>{}},t={};function s(i){var o=t[i];if(void 0!==o)return o.exports;var a=t[i]={exports:{}};return e[i](a,a.exports,s),a.exports}s(430);var i=s(853);return i=i.default})());
1
+ !function(e,t){"object"==typeof exports&&"object"==typeof module?module.exports=t():"function"==typeof define&&define.amd?define([],t):"object"==typeof exports?exports.DivTable=t():e.DivTable=t()}(this,()=>(()=>{var e={430:e=>{class t{constructor(e,t){this.monaco=e,this.options=t;const i=void 0!==t.data&&null!==t.data;this.data=i?t.data:[],this.columns=t.columns||[],this.columns.forEach(e=>{(e.subLabel||e.subField||e.subType||e.subRender)&&console.warn(`DivTable: Column '${e.field}' uses deprecated properties (subLabel, subField, subType, subRender). Please migrate to fieldCompositeName approach. See README for migration guide.`)}),this.showCheckboxes=!1!==t.showCheckboxes,this.multiSelect=!1!==t.multiSelect,this.onSelectionChange=t.onSelectionChange||(()=>{}),this.onRowFocus=t.onRowFocus||(()=>{}),this.showLoadingPlaceholder=!1!==t.showLoadingPlaceholder,this.isLoadingState=0===this.data.length&&this.showLoadingPlaceholder,this._shouldLoadFirstPage=!i&&"function"==typeof t.onNextPage,this.showRefreshButton=t.showRefreshButton||!1,this.onRefresh=t.onRefresh||(()=>{}),this.showAutoFetchButton=!1!==t.showAutoFetchButton,this.autoFetchDelay=t.autoFetchDelay||500,this.virtualScrolling=t.virtualScrolling||!1,this.pageSize=t.pageSize||100,this.totalRecords=t.totalRecords||(this.virtualScrolling?10*this.pageSize:this.data.length),this.onNextPage=t.onNextPage||(()=>{}),this.onPreviousPage=t.onPreviousPage||(()=>{}),this.loadingThreshold=t.loadingThreshold||Math.floor(.8*this.pageSize),this.scrollThreshold=t.scrollThreshold||.95,this.filteredData=[...this.data],this.sortColumn=null,this.sortDirection="asc",this.sortMode="value",this.groupByField=null,this.collapsedGroups=new Set,this.selectedRows=new Set,this.focusedRowId=null,this.currentQuery="",this._lastFocusCallback={rowId:null,groupKey:null},this.showOnlySelected=!1,this.currentPage=0,this.isLoading=!1,this.hasMoreData=!0,this.estimatedRowHeight=40,this.visibleStartIndex=0,this.visibleEndIndex=this.pageSize,this.isAutoFetching=!1,this.autoFetchPaused=!1,this.autoFetchTimeout=null,this.fixedColumns=t.fixedColumns||0,this.lazyCellRendering=!1!==t.lazyCellRendering,this.lazyRenderMargin=t.lazyRenderMargin||"200px",this.rowObserver=null,this.showHeaderSummary=t.showHeaderSummary||!1,this.showGroupSummary=t.showGroupSummary||!1,this.primaryKeyField=this.columns.find(e=>e.primaryKey)?.field||"id",this.queryEngine=new s(this.data,this.primaryKeyField),this.init(),t.group&&this.group(t.group),t.sort&&t.sort.field&&this.sort(t.sort.field,t.sort.direction)}init(){const e=this.options.tableWidgetElement;e?(this.showCheckboxes||e.classList.add("no-checkboxes"),this.multiSelect||e.classList.add("no-multiselect"),this.createTableStructure(e),this.setupQueryEditor(),this.render(),this.setupKeyboardNavigation(),this._shouldLoadFirstPage?setTimeout(()=>this.loadFirstPageAutomatically(),100):this.virtualScrolling&&this.data.length<this.totalRecords&&"function"==typeof this.onNextPage&&setTimeout(()=>this.loadNextPage(),100)):console.error("DivTable: tableWidgetElement is required")}async loadFirstPageAutomatically(){try{this.isLoading=!0,this.updateInfoSection();const e=await this.onNextPage(0,this.pageSize);this.isLoading=!1,e&&Array.isArray(e)&&e.length>0?this.replaceData(e):(this.isLoadingState=!1,this.hasMoreData=!1,this.render())}catch(e){console.error("❌ Error loading first page:",e),this.isLoading=!1,this.isLoadingState=!1,this.hasMoreData=!1,this.render()}}getOrderedColumns(){let e=this.columns.filter(e=>!e.hidden);if(!this.groupByField)return e;const t=[...e],s=t.findIndex(e=>e.field===this.groupByField);if(s>0){const[e]=t.splice(s,1);t.unshift(e)}return t}getCompositeColumns(){const e=this.getOrderedColumns(),t=new Map,s=[];return e.forEach(e=>{if(e.fieldCompositeName){if(!t.has(e.fieldCompositeName)){const i={compositeName:e.fieldCompositeName,columns:[]};t.set(e.fieldCompositeName,i),s.push(i)}t.get(e.fieldCompositeName).columns.push(e)}else s.push({compositeName:null,columns:[e]})}),s}getAllColumns(){return this.columns}createTableStructure(e){this.toolbar=e.querySelector(".div-table-toolbar"),this.toolbar||(this.toolbar=document.createElement("div"),this.toolbar.className="div-table-toolbar",e.appendChild(this.toolbar)),this.createToolbarElements(),this.tableContainer=document.createElement("div"),this.tableContainer.className="div-table-container",e.appendChild(this.tableContainer),this.fixedColumns>0?(this.tableContainer.classList.add("has-fixed-columns"),this.createFixedColumnsStructure()):(this.headerContainer=document.createElement("div"),this.headerContainer.className="div-table-header",this.tableContainer.appendChild(this.headerContainer),this.bodyContainer=document.createElement("div"),this.bodyContainer.className="div-table-body",this.tableContainer.appendChild(this.bodyContainer)),this.setupScrollShadow()}createFixedColumnsStructure(){this.columnsWrapper=document.createElement("div"),this.columnsWrapper.className="div-table-columns-wrapper",this.tableContainer.appendChild(this.columnsWrapper),this.fixedSection=document.createElement("div"),this.fixedSection.className="div-table-fixed-section",this.columnsWrapper.appendChild(this.fixedSection),this.fixedHeaderContainer=document.createElement("div"),this.fixedHeaderContainer.className="div-table-header div-table-fixed-header",this.fixedSection.appendChild(this.fixedHeaderContainer),this.fixedBodyContainer=document.createElement("div"),this.fixedBodyContainer.className="div-table-body div-table-fixed-body",this.fixedSection.appendChild(this.fixedBodyContainer),this.scrollSection=document.createElement("div"),this.scrollSection.className="div-table-scroll-section",this.columnsWrapper.appendChild(this.scrollSection),this.scrollHeaderContainer=document.createElement("div"),this.scrollHeaderContainer.className="div-table-header div-table-scroll-header",this.scrollSection.appendChild(this.scrollHeaderContainer),this.scrollBodyContainer=document.createElement("div"),this.scrollBodyContainer.className="div-table-body div-table-scroll-body",this.scrollSection.appendChild(this.scrollBodyContainer),this.headerContainer=this.scrollHeaderContainer,this.bodyContainer=this.scrollBodyContainer,this.setupFixedColumnsScrollSync()}setupFixedColumnsScrollSync(){let e=!1;this.scrollBodyContainer.addEventListener("scroll",()=>{e||(e=!0,this.fixedBodyContainer.scrollTop=this.scrollBodyContainer.scrollTop,this.scrollHeaderContainer.scrollLeft=this.scrollBodyContainer.scrollLeft,requestAnimationFrame(()=>{e=!1}))}),this.fixedBodyContainer.addEventListener("scroll",()=>{e||(e=!0,this.scrollBodyContainer.scrollTop=this.fixedBodyContainer.scrollTop,requestAnimationFrame(()=>{e=!1}))}),this.scrollHeaderContainer.addEventListener("scroll",()=>{e||(e=!0,this.scrollBodyContainer.scrollLeft=this.scrollHeaderContainer.scrollLeft,requestAnimationFrame(()=>{e=!1}))}),this.adjustFixedBodyForHorizontalScrollbar(),window.addEventListener("resize",()=>{this.adjustFixedBodyForHorizontalScrollbar()})}adjustFixedBodyForHorizontalScrollbar(){if(!this.fixedBodyContainer||!this.scrollBodyContainer)return;const e=this.scrollBodyContainer.offsetHeight-this.scrollBodyContainer.clientHeight;this.fixedBodyContainer.style.paddingBottom=e>0?`${e}px`:""}getEffectiveFixedColumnCount(){return this.fixedColumns}splitColumnsForFixedLayout(){const e=this.getCompositeColumns(),t=this.getEffectiveFixedColumnCount();return{fixedColumns:e.slice(0,t),scrollColumns:e.slice(t)}}createToolbarElements(){let e=this.toolbar.querySelector(".query-input-container");e||(e=document.createElement("div"),e.className="query-input-container",e.setAttribute("tabindex","0"),this.toolbar.appendChild(e));let t=this.toolbar.querySelector(".info-section");t||(t=document.createElement("div"),t.className="info-section",this.toolbar.appendChild(t)),this.infoSection=t}setupScrollShadow(){const e=this.fixedColumns>0?this.scrollBodyContainer:this.bodyContainer,t=this.fixedColumns>0?this.scrollHeaderContainer:this.headerContainer;e.addEventListener("scroll",()=>{e.scrollTop>0?(t.classList.add("scrolled"),this.fixedColumns>0&&this.fixedHeaderContainer&&this.fixedHeaderContainer.classList.add("scrolled")):(t.classList.remove("scrolled"),this.fixedColumns>0&&this.fixedHeaderContainer&&this.fixedHeaderContainer.classList.remove("scrolled")),this.virtualScrolling&&!this.isLoading&&this.handleVirtualScroll()})}setupQueryEditor(){const e=this.toolbar.querySelector(".query-input-container");if(!e)return;e.className="query-input-container query-inputfield";const t={},s=new Map;if(this.columns.forEach(e=>{e.field&&s.set(e.field,e)}),this.data.length>0){const e=this.data[0],i=new Set;Object.keys(e).forEach(o=>{if(i.has(o))return;const a=s.get(o);if(!a)return;if(a.hidden)return;let n,r;if(i.add(o),n=a.type?a.type:"boolean"==typeof e[o]?"boolean":"number"==typeof e[o]?"number":"string","string"===n){const e=[];this.data.forEach(t=>{const s=t[o];Array.isArray(s)?e.push(...s):e.push(s)});const t=[...new Set(e)],s=t.filter(e=>null!=e&&""!==e);r=t.some(e=>null==e||""===e)?[...s,"NULL"]:s}t[o]={type:n,values:r}}),this.columns.forEach(s=>{if(s.subField&&!s.hidden&&void 0!==e[s.subField]){const o=s.subField;if(i.has(o))return;let a,n;if(i.add(o),a=s.subType?s.subType:"boolean"==typeof e[o]?"boolean":"number"==typeof e[o]?"number":"string","string"===a){const e=[];this.data.forEach(t=>{const s=t[o];Array.isArray(s)?e.push(...s):e.push(s)});const t=[...new Set(e)],s=t.filter(e=>null!=e&&""!==e);n=t.some(e=>null==e||""===e)?[...s,"NULL"]:s}t[o]={type:a,values:n}}})}else this.columns.forEach(e=>{e.field&&!e.hidden&&(t[e.field]={type:e.type||"string",values:e.values||[]}),e.subField&&!e.hidden&&(t[e.subField]={type:e.subType||e.type||"string",values:e.values||[]})});"function"==typeof createQueryEditor&&(this.queryEditor=createQueryEditor(this.monaco,e,{fieldNames:t,initialValue:this.currentQuery,placeholder:this.generateDynamicPlaceholder(t)}),this.queryEditor.fieldNames=t,this.setupQueryEventHandlers())}handleQueryChange(e){void 0===e&&(e=this.queryEditor.model?.getValue()||"");const t=this.queryEditor.editor?.getModel();if(t){const s=this.monaco.editor.getModelMarkers({resource:t.uri}).some(e=>e.severity===this.monaco.MarkerSeverity.Error),i=this.toolbar.querySelector(".query-input-container");s?i.classList.add("error"):(i.classList.remove("error"),this.applyQuery(e))}else this.applyQuery(e)}_setupQueryListeners(){let e;this.queryEditor.model.onDidChangeContent(()=>{e&&clearTimeout(e),e=setTimeout(()=>this.handleQueryChange(),350)})}_shouldUpdateFieldNames(e,t){if(!e||0===Object.keys(e).length)return Object.keys(t).length>0;if(Object.keys(e).length!==Object.keys(t).length)return!0;for(const s in t){if(!e[s])return!0;if(e[s].type!==t[s].type)return!0;const i=e[s].values||[],o=t[s].values||[];if(i.length!==o.length)return!0;const a=[...i].sort(),n=[...o].sort();if(a.some((e,t)=>e!==n[t]))return!0}for(const s in e)if(!t[s])return!0;return!1}generateDynamicPlaceholder(e){if(!e||0===Object.keys(e).length)return"Filter data... (e.g., column > value)";const t=[],s=Object.keys(e);for(const i of s.slice(0,2)){const s=e[i];if("number"===s.type)t.push(`${i} > 100`);else if("boolean"===s.type)t.push(`${i} = true`);else if("string"===s.type)if(s.values&&s.values.length>0){const e=s.values.find(e=>"NULL"!==e)||s.values[0];e&&"NULL"!==e?t.push(`${i} = "${e}"`):t.push(`${i} LIKE "%text%"`)}else t.push(`${i} LIKE "%text%"`)}if(0===t.length)return"Filter data... (e.g., column = value)";const i="Filter data...";if(1===t.length)return`${i} (e.g., ${t[0]})`;return`${i} (e.g., ${t.slice(0,2).join(" AND ")})`}setupKeyboardNavigation(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer;e.addEventListener("keydown",e=>{this.handleKeyDown(e)});let t=!1;e.addEventListener("keydown",()=>{t=!0},{capture:!0}),e.addEventListener("mousedown",()=>{t=!1},{capture:!0}),e.addEventListener("focusin",s=>{!this.focusedRowId&&t&&s.target===e&&this.focusFirstRecord()})}getCurrentFocusedElement(){const e=document.activeElement;if(e&&"checkbox"===e.type){const t=e.closest(".div-table-row");if(t&&this.bodyContainer.contains(t))return{element:e,row:t,type:"checkbox"}}return e&&e.classList.contains("div-table-row")&&this.bodyContainer.contains(e)?{element:e,row:e,type:"row"}:null}getFocusableElementForRow(e){if(this.showCheckboxes){const t=e.querySelector('input[type="checkbox"]');if(t)return t}return e}handleKeyDown(e){const t=this.getAllFocusableElements();if(0===t.length)return;const s=this.getCurrentFocusedElement();if(!s)return;let i=t.indexOf(s.element);if(-1!==i)switch(e.key){case"ArrowDown":e.preventDefault(),this.focusElementAtIndex(Math.min(i+1,t.length-1));break;case"ArrowUp":e.preventDefault(),this.focusElementAtIndex(Math.max(i-1,0));break;case"ArrowRight":e.preventDefault(),this.handleRightArrow(s.row);break;case"ArrowLeft":e.preventDefault(),this.handleLeftArrow(s.row);break;case" ":case"Enter":e.preventDefault(),this.handleSelectionToggleForElement(s)}}getAllFocusableElements(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer,t=[],s=Array.from(e.querySelectorAll(".div-table-row"));for(const e of s)if(e.classList.contains("group-header"))if(this.showCheckboxes){const s=e.querySelector('input[type="checkbox"]');s&&"0"===s.getAttribute("tabindex")&&t.push(s)}else t.push(e);else if(e.dataset.id){const s=this.getRowGroupKey(e);if(!s||!this.collapsedGroups.has(s))if(this.showCheckboxes){const s=e.querySelector('input[type="checkbox"]');s&&"0"===s.getAttribute("tabindex")&&t.push(s)}else t.push(e)}return t}focusElementAtIndex(e){const t=this.getAllFocusableElements();if(e>=0&&e<t.length){const s=t[e];s.focus();const i=s.closest(".div-table-row");i&&this.updateFocusState(i)}}updateFocusState(e){if(this.fixedColumns>0){this.fixedBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),this.scrollBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),e.classList.add("focused");const t=e.dataset.id||e.dataset.groupKey;if(t){const s=e.dataset.id?`[data-id="${t}"]`:`[data-group-key="${t}"]`;if(e.closest(".div-table-fixed-body")){const e=this.scrollBodyContainer.querySelector(s);e&&e.classList.add("focused")}else if(e.closest(".div-table-scroll-body")){const e=this.fixedBodyContainer.querySelector(s);e&&e.classList.add("focused")}}}else{this.bodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),e.classList.add("focused")}if(e.classList.contains("group-header")){if(this.focusedRowId=null,this.focusedGroupKey=e.dataset.groupKey,this._lastFocusCallback.groupKey!==e.dataset.groupKey){this._lastFocusCallback={rowId:null,groupKey:e.dataset.groupKey};const t=this.groupData(this.filteredData).find(t=>t.key===e.dataset.groupKey);if(t){const e=this.columns.find(e=>e.field===this.groupByField),s={key:t.key,value:t.value,field:this.groupByField,label:e?.label||this.groupByField,itemCount:t.items.length};"function"==typeof this.onRowFocus&&this.onRowFocus(void 0,s)}}}else if(e.dataset.id&&(this.focusedRowId=e.dataset.id,this.focusedGroupKey=null,this._lastFocusCallback.rowId!==e.dataset.id)){this._lastFocusCallback={rowId:e.dataset.id,groupKey:null};const t=this.findRowData(e.dataset.id);"function"==typeof this.onRowFocus&&this.onRowFocus(t,void 0)}}handleSelectionToggleForElement(e){const t=e.row;t.classList.contains("group-header")?this.toggleGroupSelection(t):t.dataset.id&&this.toggleIndividualRowSelection(t)}handleRightArrow(e){if(e&&e.classList.contains("group-header")&&e.classList.contains("collapsed")){const t=e.dataset.groupKey;this.collapsedGroups.delete(t),e.classList.remove("collapsed");const s={key:t};this.render(),this.restoreGroupFocus(s)}}handleLeftArrow(e){if(e&&e.classList.contains("group-header")&&!e.classList.contains("collapsed")){const t=e.dataset.groupKey;this.collapsedGroups.add(t),e.classList.add("collapsed");const s={key:t};this.render(),this.restoreGroupFocus(s)}}restoreGroupFocus(e){const t=this.bodyContainer.querySelector(`[data-group-key="${e.key}"]`);if(t){if(this.showCheckboxes){const e=t.querySelector('input[type="checkbox"]');e&&e.focus()}else t.focus();this.updateFocusState(t)}}getVisibleRows(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer;return Array.from(e.querySelectorAll(".div-table-row[data-id]:not(.group-header):not(.group-collapsed)"))}getAllFocusableRows(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer,t=Array.from(e.querySelectorAll(".div-table-row")),s=[];for(const e of t)if(e.classList.contains("group-header"))s.push(e);else if(e.dataset.id){const t=this.getRowGroupKey(e);t&&this.collapsedGroups.has(t)||s.push(e)}return s}getRowGroupKey(e){let t=e.previousElementSibling;for(;t;){if(t.classList.contains("group-header"))return t.dataset.groupKey;t=t.previousElementSibling}return null}focusRow(e){const t=this.getAllFocusableElements();e>=0&&e<t.length&&this.focusElementAtIndex(e)}focusFirstRecord(){this.getAllFocusableRows().length>0&&this.focusRow(0)}setFocusedRow(e,t=!1){if(this.bodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>{e.classList.remove("focused")}),e){const s=this.bodyContainer.querySelector(`[data-id="${e}"]`);if(s){if(s.classList.add("focused"),s.scrollIntoView({behavior:"smooth",block:"nearest"}),!t){const e=s.querySelector('input[type="checkbox"]');e&&document.activeElement!==e&&e.focus()}if(this._lastFocusCallback.rowId!==e){this._lastFocusCallback={rowId:e,groupKey:null};const t=this.findRowData(e);this.onRowFocus(t)}}}this.focusedRowId=e}setFocusedGroup(e){this.bodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>{e.classList.remove("focused")}),this.focusedRowId=null;const t=this.bodyContainer.querySelector(`[data-group-key="${e.key}"]`);if(t){t.classList.add("focused"),t.scrollIntoView({behavior:"smooth",block:"nearest"});const s=this.columns.find(e=>e.field===this.groupByField),i={key:e.key,value:e.value,field:this.groupByField,label:s?.label||this.groupByField,itemCount:e.items.length};this.onRowFocus(void 0,i)}}findRowData(e){let t=this.filteredData.find(t=>String(t[this.primaryKeyField])===String(e));return t||(t=this.data.find(t=>String(t[this.primaryKeyField])===String(e))),t}handleSelectionToggle(e){const t=this.getAllFocusableRows();if(e<0||e>=t.length)return;const s=t[e];s.classList.contains("group-header")?this.toggleGroupSelection(s):s.dataset.id&&this.toggleIndividualRowSelection(s)}toggleGroupSelection(e){const t=e.dataset.groupKey,s=this.groupData(this.filteredData).find(e=>e.key===t);if(!s)return;const i=s.items.map(e=>String(e[this.primaryKeyField])),o=i.filter(e=>this.selectedRows.has(e)).length<i.length;s.items.forEach(e=>{const t=String(e[this.primaryKeyField]);o?(this.selectedRows.add(t),e.selected=!0):(this.selectedRows.delete(t),e.selected=!1)}),this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}toggleIndividualRowSelection(e){const t=e.dataset.id;if(!t)return void console.warn("DivTable: Row missing data-id attribute");const s=this.findRowData(t);if(!s)return void console.warn("DivTable: Could not find data for row ID:",t);this.selectedRows.has(t)?(this.selectedRows.delete(t),s.selected=!1,e.classList.remove("selected")):(this.multiSelect||this.clearSelection(),this.selectedRows.add(t),s.selected=!0,e.classList.add("selected")),this.updateSelectionStates(),this.updateInfoSection();const i=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(i)}toggleRowSelection(e){const t=this.getVisibleRows();if(e<0||e>=t.length)return;const s=t[e],i=s.dataset.id,o=this.findRowData(i);if(!o)return;this.selectedRows.has(i)?(this.selectedRows.delete(i),o.selected=!1,s.classList.remove("selected")):(this.multiSelect||this.clearSelection(),this.selectedRows.add(i),o.selected=!0,s.classList.add("selected")),this.updateCheckboxes(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}clearSelection(){this.selectedRows.clear(),this.filteredData.forEach(e=>e.selected=!1),this.updateSelectionStates(),this.updateInfoSection()}updateCheckboxes(){this.fixedColumns>0?this.fixedBodyContainer.querySelectorAll('.div-table-row[data-id] input[type="checkbox"]').forEach(e=>{const t=e.closest(".div-table-row").dataset.id;e.checked=this.selectedRows.has(t)}):this.bodyContainer.querySelectorAll('.div-table-row[data-id] input[type="checkbox"]').forEach(e=>{const t=e.closest(".div-table-row").dataset.id;e.checked=this.selectedRows.has(t)})}updateSelectionStates(){if(this.fixedColumns>0)return void this.updateSelectionStatesWithFixedColumns();this.bodyContainer.querySelectorAll(".div-table-row[data-id]").forEach(e=>{const t=e.dataset.id,s=e.querySelector('input[type="checkbox"]');this.selectedRows.has(t)?(e.classList.add("selected"),s&&(s.checked=!0)):(e.classList.remove("selected"),s&&(s.checked=!1))});const e=this.bodyContainer.querySelectorAll(".div-table-row.group-header");if(e.length>0){const t=this.groupData(this.sortData(this.filteredData));e.forEach(e=>{const s=e.querySelector('input[type="checkbox"]');if(!s)return;const i=e.dataset.groupKey,o=t.find(e=>e.key===i);if(!o)return;const a=o.items.map(e=>String(e[this.primaryKeyField])),n=a.filter(e=>this.selectedRows.has(e));0===n.length?(s.indeterminate=!1,s.checked=!1):n.length===a.length?(s.indeterminate=!1,s.checked=!0):(s.indeterminate=!0,s.checked=!1)})}this.updateHeaderCheckbox(),this.updateSummaryRows()}updateSelectionStatesWithFixedColumns(){this.fixedBodyContainer.querySelectorAll(".div-table-row[data-id]").forEach(e=>{const t=e.dataset.id,s=e.querySelector('input[type="checkbox"]');this.selectedRows.has(t)?(e.classList.add("selected"),s&&(s.checked=!0)):(e.classList.remove("selected"),s&&(s.checked=!1))}),this.scrollBodyContainer.querySelectorAll(".div-table-row[data-id]").forEach(e=>{const t=e.dataset.id;this.selectedRows.has(t)?e.classList.add("selected"):e.classList.remove("selected")});const e=this.fixedBodyContainer.querySelectorAll(".div-table-row.group-header");if(e.length>0){const t=this.groupData(this.sortData(this.filteredData));e.forEach(e=>{const s=e.querySelector('input[type="checkbox"]');if(!s)return;const i=e.dataset.groupKey,o=t.find(e=>e.key===i);if(!o)return;const a=o.items.map(e=>String(e[this.primaryKeyField])),n=a.filter(e=>this.selectedRows.has(e));0===n.length?(s.indeterminate=!1,s.checked=!1):n.length===a.length?(s.indeterminate=!1,s.checked=!0):(s.indeterminate=!0,s.checked=!1)})}this.updateHeaderCheckbox(),this.updateSummaryRows()}updateHeaderCheckbox(){let e;if(e=this.fixedColumns>0?this.fixedHeaderContainer.querySelector('input[type="checkbox"]'):this.headerContainer.querySelector('input[type="checkbox"]'),!e)return;const t=this.filteredData.length,s=this.filteredData.filter(e=>this.selectedRows.has(String(e[this.primaryKeyField]))).length;0===s?(e.checked=!1,e.indeterminate=!1):s===t?(e.checked=!0,e.indeterminate=!1):(e.checked=!1,e.indeterminate=!0)}updateTabIndexes(){const e=this.fixedColumns>0?this.fixedBodyContainer:this.bodyContainer,t=Array.from(e.querySelectorAll(".div-table-row"));for(const e of t)if(e.classList.contains("group-header")){if(this.showCheckboxes){const t=e.querySelector('input[type="checkbox"]');t&&t.setAttribute("tabindex","0")}}else if(e.dataset.id){const t=this.getRowGroupKey(e),s=!t||!this.collapsedGroups.has(t);if(this.showCheckboxes){const t=e.querySelector('input[type="checkbox"]');t&&t.setAttribute("tabindex",s?"0":"-1")}}}render(){this.renderHeader(),this.renderBody(),this.updateInfoSection(),this.updateSelectionStates(),this.updateTabIndexes(),"undefined"==typeof process&&setTimeout(()=>this.verifyDataConsistency(),0)}renderHeader(){if(this.fixedColumns>0)return void this.renderHeaderWithFixedColumns();this.headerContainer.innerHTML="";const e=this.getCompositeColumns();let t="";if(this.showCheckboxes&&(t="40px "),e.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":t+="80px ";break;case"fixed-medium":t+="120px ";break;case"flexible-small":default:t+="1fr ";break;case"flexible-medium":t+="2fr ";break;case"flexible-large":t+="3fr "}}),this.headerContainer.style.gridTemplateColumns=t.trim(),this.showCheckboxes){const e=document.createElement("div");if(e.className="div-table-header-cell checkbox-column",this.multiSelect){const t=document.createElement("input");t.type="checkbox",t.addEventListener("change",e=>{e.target.checked?this.selectAll():(this.clearSelection(),this.showOnlySelected&&(this.renderBody(),this.updateInfoSection()))}),e.appendChild(t)}this.headerContainer.appendChild(e)}e.forEach(e=>{const t=document.createElement("div");if(t.className="div-table-header-cell",e.compositeName)t.classList.add("composite-header"),this.renderCompositeHeaderCell(t,e);else{t.classList.add("sortable");const s=e.columns[0];this.renderSingleHeaderCell(t,s)}this.headerContainer.appendChild(t)}),this.updateScrollbarSpacer()}renderHeaderWithFixedColumns(){this.fixedHeaderContainer.innerHTML="",this.scrollHeaderContainer.innerHTML="";const{fixedColumns:e,scrollColumns:t}=this.splitColumnsForFixedLayout();let s="";this.showCheckboxes&&(s="40px "),e.forEach(e=>{s+=this.getColumnGridSize(e)+" "}),this.fixedHeaderContainer.style.gridTemplateColumns=s.trim();let i="";if(t.forEach(e=>{i+=this.getColumnGridSize(e)+" "}),this.scrollHeaderInner=document.createElement("div"),this.scrollHeaderInner.className="div-table-scroll-header-inner",this.scrollHeaderInner.style.gridTemplateColumns=i.trim(),this.scrollHeaderContainer.appendChild(this.scrollHeaderInner),this.showCheckboxes){const e=document.createElement("div");if(e.className="div-table-header-cell checkbox-column",this.multiSelect){const t=document.createElement("input");t.type="checkbox",t.addEventListener("change",e=>{e.target.checked?this.selectAll():(this.clearSelection(),this.showOnlySelected&&(this.renderBody(),this.updateInfoSection()))}),e.appendChild(t)}this.fixedHeaderContainer.appendChild(e)}e.forEach(e=>{const t=this.createHeaderCell(e);this.fixedHeaderContainer.appendChild(t)}),t.forEach(e=>{const t=this.createHeaderCell(e);this.scrollHeaderInner.appendChild(t)}),this.syncFixedColumnsHeaderHeights()}syncFixedColumnsHeaderHeights(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.fixedHeaderContainer||!this.scrollHeaderContainer)return;this.fixedHeaderContainer.style.height="",this.scrollHeaderContainer.style.height="";const e=this.fixedHeaderContainer.offsetHeight,t=this.scrollHeaderContainer.offsetHeight,s=Math.max(e,t);s>0&&(this.fixedHeaderContainer.style.height=`${s}px`,this.scrollHeaderContainer.style.height=`${s}px`)}syncFixedColumnsRowHeights(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.fixedBodyContainer||!this.scrollBodyContainer)return;const e=this.fixedBodyContainer.querySelectorAll(".div-table-row"),t=this.scrollBodyContainer.querySelectorAll(".div-table-row");e.length===t.length&&e.forEach((e,s)=>{const i=t[s];if(!i)return;e.style.height="",i.style.height="";const o=Math.max(e.offsetHeight,e.scrollHeight),a=Math.max(i.offsetHeight,i.scrollHeight);let n=0;e.querySelectorAll(".div-table-cell").forEach(e=>{n=Math.max(n,e.offsetHeight,e.scrollHeight)}),i.querySelectorAll(".div-table-cell").forEach(e=>{n=Math.max(n,e.offsetHeight,e.scrollHeight)});const r=Math.max(o,a,n);r>0&&(e.style.height=`${r}px`,i.style.height=`${r}px`)})}syncFixedColumnsColumnWidths(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.scrollHeaderInner||!this.scrollBodyContainer)return;const{scrollColumns:e}=this.splitColumnsForFixedLayout(),t=e.length;if(0===t)return;const s=Array.from(this.scrollHeaderInner.querySelectorAll(".div-table-header-cell")),i=Array.from(this.scrollBodyContainer.querySelectorAll(".div-table-row:not(.group-header)")),o=[];for(let e=0;e<t;e++){let t=0;s[e]&&(s[e].style.minWidth="",s[e].style.width="",t=Math.max(t,s[e].scrollWidth)),i.forEach(s=>{const i=s.querySelectorAll(".div-table-cell");i[e]&&(i[e].style.minWidth="",i[e].style.width="",t=Math.max(t,i[e].scrollWidth))}),o.push(t+4)}const a=o.map(e=>`${e}px`).join(" "),n=o.reduce((e,t)=>e+t,0);this.scrollHeaderInner.style.gridTemplateColumns=a;this.scrollBodyContainer.querySelectorAll(".div-table-row").forEach(e=>{e.classList.contains("group-header")?(e.style.gridTemplateColumns="1fr",e.style.minWidth=`${n}px`):e.classList.contains("summary-row")?(e.style.gridTemplateColumns=a,e.style.minWidth=`${n}px`):e.style.gridTemplateColumns=a}),this.updateFixedColumnsShadow()}updateFixedColumnsShadow(){if(!this.fixedColumns||this.fixedColumns<=0)return;if(!this.scrollBodyContainer||!this.fixedSection)return;this.scrollBodyContainer.scrollWidth>this.scrollBodyContainer.clientWidth?this.fixedSection.classList.add("has-scroll-shadow"):this.fixedSection.classList.remove("has-scroll-shadow")}getColumnGridSize(e){switch((e.columns[0].responsive||{}).size){case"fixed-narrow":return"80px";case"fixed-medium":return"120px";case"flexible-small":default:return"1fr";case"flexible-medium":return"2fr";case"flexible-large":return"3fr"}}createHeaderCell(e){const t=document.createElement("div");if(t.className="div-table-header-cell",e.compositeName)t.classList.add("composite-header"),this.renderCompositeHeaderCell(t,e);else{t.classList.add("sortable");const s=e.columns[0];this.renderSingleHeaderCell(t,s)}return t}updateScrollbarSpacer(){const e=this.headerContainer.querySelector(".scrollbar-spacer");e&&e.remove();if(this.bodyContainer.scrollHeight>this.bodyContainer.clientHeight){const e=this.bodyContainer.offsetWidth-this.bodyContainer.clientWidth,t=document.createElement("div");t.className="scrollbar-spacer",t.style.width=`${e}px`;const s=this.headerContainer.style.gridTemplateColumns;this.headerContainer.style.gridTemplateColumns=`${s} ${e}px`,this.headerContainer.appendChild(t)}}renderSingleHeaderCell(e,t){if(t.subLabel){e.classList.add("composite-header"),e.style.display="flex",e.style.flexDirection="column",e.style.gap="0",e.style.padding="8px 12px",e.style.alignItems="flex-start";const s=document.createElement("div");s.style.display="flex",s.style.alignItems="center",s.style.width="100%",s.style.marginBottom="4px";const i=document.createElement("span");i.className="composite-main-header",i.innerHTML=t.label||t.field,i.style.fontWeight="600",i.style.textAlign="left",i.style.flex="1",s.appendChild(i);const o=document.createElement("div");if(o.className="header-right-content",o.style.display="flex",o.style.alignItems="center",o.style.gap="4px",o.style.marginLeft="auto",!1!==t.groupable&&!t.hidden){const e=document.createElement("span");e.className="group-indicator",this.groupByField===t.field&&e.classList.add("grouped"),e.textContent=this.groupByField===t.field?"☴":"☷",e.style.cursor="pointer",e.style.fontSize="1em";const s=t.label||t.field;e.title=this.groupByField===t.field?`Grouped by ${s} (click to ungroup)`:`Click to group by ${s}`,e.addEventListener("click",e=>{e.stopPropagation(),this.groupByField===t.field?this.group(""):this.group(t.field)}),o.appendChild(e)}const a=document.createElement("span");a.className="sort-indicator",a.style.marginLeft="4px",this.sortColumn===t.field?(a.classList.add("active"),a.textContent="asc"===this.sortDirection?"↑":"↓"):a.textContent="⇅",o.appendChild(a),s.appendChild(o),e.appendChild(s);const n=document.createElement("div");n.className="composite-sub-header sortable",n.style.display="flex",n.style.alignItems="center",n.style.width="100%",n.style.cursor="pointer",n.style.borderRadius="4px",n.style.transition="background-color 0.2s ease";const r=document.createElement("span");if(r.innerHTML=t.subLabel,r.style.textAlign="left",r.style.flex="1",n.appendChild(r),t.subField){const e=document.createElement("span");e.className="sub-sort-indicator",e.style.marginLeft="4px",this.sortColumn===t.subField?(e.classList.add("active"),e.textContent="asc"===this.sortDirection?"↑":"↓"):e.textContent="⇅",n.appendChild(e),n.addEventListener("mouseenter",()=>{n.style.backgroundColor="var(--dt-bg-disabled)"}),n.addEventListener("mouseleave",()=>{n.style.backgroundColor="transparent"}),n.addEventListener("click",e=>{e.stopPropagation(),this.sort(t.subField)})}return e.appendChild(n),void s.addEventListener("click",e=>{e.target.classList.contains("group-indicator")||e.target.closest(".group-indicator")||this.sort(t.field)})}const s=document.createElement("div");if(s.className="header-left-content",this.groupByField===t.field){const e=this.groupData(this.filteredData),i=e.length,o=t.label||t.field,a=document.createElement("span");a.className="group-toggle-all";const n=e.every(e=>this.collapsedGroups.has(e.key));n&&a.classList.add("collapsed"),a.textContent="❯",a.title=n?"Expand all groups":"Collapse all groups",a.addEventListener("click",t=>{t.stopPropagation(),t.preventDefault(),n?this.collapsedGroups.clear():e.forEach(e=>{this.collapsedGroups.add(e.key)}),this.render()}),s.appendChild(a);const r=document.createElement("span");r.innerHTML=o,s.appendChild(r);const l=document.createElement("span");l.className="group-count",l.innerHTML=`&nbsp;(${i})`,l.style.opacity="0.8",l.style.fontSize="0.9em",l.style.fontWeight="normal",l.title=`${i} distinct value${1===i?"":"s"} in ${o}`,s.appendChild(l)}else{const e=document.createElement("span");e.innerHTML=t.label||t.field,s.appendChild(e)}e.appendChild(s);const i=document.createElement("div");if(i.className="header-right-content",!1!==t.groupable&&!t.hidden){const e=document.createElement("span");e.className="group-indicator",this.groupByField===t.field&&e.classList.add("grouped"),e.textContent=this.groupByField===t.field?"☴":"☷",e.style.cursor="pointer",e.style.fontSize="1em";const s=t.label||t.field;e.title=this.groupByField===t.field?`Grouped by ${s} (click to ungroup)`:`Click to group by ${s}`,e.addEventListener("click",e=>{e.stopPropagation(),this.groupByField===t.field?this.group(""):this.group(t.field)}),i.appendChild(e)}const o=document.createElement("span");if(o.className="sort-indicator",o.style.fontSize="12px",o.style.marginLeft="4px",this.sortColumn===t.field){o.classList.add("active");const s=this.groupByField&&t.field===this.groupByField;s&&"count"===this.sortMode?o.textContent="asc"===this.sortDirection?"↑1":"↓9":s&&"value"===this.sortMode?o.textContent="asc"===this.sortDirection?"↑A":"↓Z":o.textContent="asc"===this.sortDirection?"↑":"↓",e.classList.add("sorted",this.sortDirection)}else o.textContent="⇅";i.appendChild(o),e.appendChild(i),e.addEventListener("click",e=>{e.target.classList.contains("group-indicator")||e.target.classList.contains("group-toggle-all")||e.target.closest(".group-toggle-all")||e.target.closest(".group-indicator")||this.sort(t.field)})}renderCompositeHeaderCell(e,t){e.style.display="flex",e.style.flexDirection="column",e.style.gap="4px",e.style.padding="8px 12px";t.columns.find(e=>this.groupByField===e.field);t.columns.forEach((t,s)=>{const i=document.createElement("div");i.className="composite-sub-header sortable",i.style.display="flex",i.style.alignItems="center",i.style.gap="8px";const o=document.createElement("div");if(o.style.display="flex",o.style.alignItems="center",o.style.gap="8px",o.style.flex="1",this.groupByField===t.field){const e=this.groupData(this.filteredData),s=e.length,i=t.label||t.field,a=document.createElement("span");a.className="group-toggle-all";const n=e.every(e=>this.collapsedGroups.has(e.key));n&&a.classList.add("collapsed"),a.textContent="❯",a.title=n?"Expand all groups":"Collapse all groups",a.addEventListener("click",t=>{t.stopPropagation(),t.preventDefault(),n?this.collapsedGroups.clear():e.forEach(e=>{this.collapsedGroups.add(e.key)}),this.render()}),o.appendChild(a);const r=document.createElement("span");r.innerHTML=i,o.appendChild(r);const l=document.createElement("span");l.className="group-count",l.innerHTML=`&nbsp;(${s})`,l.style.opacity="0.8",l.style.fontSize="0.9em",l.style.fontWeight="normal",l.title=`${s} distinct value${1===s?"":"s"} in ${i}`,o.appendChild(l)}else{const e=document.createElement("span");e.innerHTML=t.label||t.field,o.appendChild(e)}i.appendChild(o);const a=document.createElement("div");if(a.style.display="flex",a.style.alignItems="center",a.style.gap="4px",!1!==t.groupable&&!t.hidden){const e=document.createElement("span");e.className="group-indicator",this.groupByField===t.field&&e.classList.add("grouped"),e.textContent=this.groupByField===t.field?"☴":"☷",e.style.cursor="pointer",e.style.fontSize="1em";const s=t.label||t.field;e.title=this.groupByField===t.field?`Grouped by ${s} (click to ungroup)`:`Click to group by ${s}`,e.addEventListener("click",e=>{e.stopPropagation(),this.groupByField===t.field?this.group(""):this.group(t.field)}),a.appendChild(e)}const n=document.createElement("span");if(n.className="sort-indicator",n.style.marginLeft="4px",this.sortColumn===t.field){n.classList.add("active");const e=this.groupByField&&t.field===this.groupByField;e&&"count"===this.sortMode?n.textContent="asc"===this.sortDirection?"↑1":"↓9":e&&"value"===this.sortMode?n.textContent="asc"===this.sortDirection?"↑A":"↓Z":n.textContent="asc"===this.sortDirection?"↑":"↓",i.classList.add("sorted",this.sortDirection)}else n.textContent="⇅";a.appendChild(n),i.appendChild(a),i.addEventListener("click",e=>{e.target.classList.contains("group-indicator")||e.target.classList.contains("group-toggle-all")||e.target.closest(".group-indicator")||e.target.closest(".group-toggle-all")||this.sort(t.field)}),e.appendChild(i)})}renderBody(){if(this.rowObserver&&this.rowObserver.disconnect(),this.fixedColumns>0)return void this.renderBodyWithFixedColumns();if(this.bodyContainer.innerHTML="",this.isLoadingState)return void this.showLoadingPlaceholders();let e=this.filteredData;if(this.showOnlySelected&&0===this.selectedRows.size&&(this.showOnlySelected=!1,console.log("👁️ No rows selected - automatically showing all rows")),this.showOnlySelected&&this.selectedRows.size>0&&(e=this.filteredData.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)})),0===e.length){const e=document.createElement("div");return e.className="div-table-empty",e.textContent=this.showOnlySelected&&this.selectedRows.size>0?"No selected rows match current filters":"No data to display",void this.bodyContainer.appendChild(e)}if(this.groupByField?this.renderGroupedRows(e):this.renderRegularRows(e),this.showHeaderSummary&&this.hasAggregateColumns()){const t=this.createHeaderSummaryRow(e);this.bodyContainer.insertBefore(t,this.bodyContainer.firstChild)}this.lazyCellRendering&&this.setupLazyRenderingObserver()}renderBodyWithFixedColumns(){const e=this.scrollBodyContainer?.scrollLeft||0;if(this.fixedBodyContainer.innerHTML="",this.scrollBodyContainer.innerHTML="",this.isLoadingState)return void this.showLoadingPlaceholders();let t=this.filteredData;if(this.showOnlySelected&&0===this.selectedRows.size&&(this.showOnlySelected=!1),this.showOnlySelected&&this.selectedRows.size>0&&(t=this.filteredData.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)})),0===t.length){const e=document.createElement("div");return e.className="div-table-empty",e.textContent=this.showOnlySelected&&this.selectedRows.size>0?"No selected rows match current filters":"No data to display",void this.fixedBodyContainer.appendChild(e)}if(this.groupByField?this.renderGroupedRowsWithFixedColumns(t):this.renderRegularRowsWithFixedColumns(t),this.showHeaderSummary&&this.hasAggregateColumns()){const{fixedSummary:e,scrollSummary:s}=this.createHeaderSummaryRowWithFixedColumns(t);this.fixedBodyContainer.insertBefore(e,this.fixedBodyContainer.firstChild),this.scrollBodyContainer.insertBefore(s,this.scrollBodyContainer.firstChild)}this.syncFixedColumnsColumnWidths(),this.syncFixedColumnsRowHeights(),this.lazyCellRendering&&this.setupLazyRenderingObserver(),e>0&&requestAnimationFrame(()=>{this.scrollBodyContainer.scrollLeft=e}),requestAnimationFrame(()=>{this.adjustFixedBodyForHorizontalScrollbar()})}renderRegularRowsWithFixedColumns(e=this.filteredData){this.sortData(e).forEach(e=>{const{fixedRow:t,scrollRow:s}=this.createRowWithFixedColumns(e);this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s)})}renderGroupedRowsWithFixedColumns(e=this.filteredData){let t=this.groupData(e);this.sortColumn===this.groupByField&&(t=t.sort((e,t)=>{if("count"===this.sortMode){const s=e.items.length-t.items.length;return"desc"===this.sortDirection?-s:s}{if(null==e.value&&null==t.value)return 0;if(null==e.value)return"asc"===this.sortDirection?-1:1;if(null==t.value)return"asc"===this.sortDirection?1:-1;let s=0;return s="number"==typeof e.value&&"number"==typeof t.value?e.value-t.value:String(e.value).localeCompare(String(t.value)),"desc"===this.sortDirection?-s:s}})),t.forEach(e=>{this.sortColumn!==this.groupByField&&(e.items=this.sortData(e.items));const{fixedGroupHeader:t,scrollGroupHeader:s}=this.createGroupHeaderWithFixedColumns(e);if(this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s),this.collapsedGroups.has(e.key)||e.items.forEach(e=>{const{fixedRow:t,scrollRow:s}=this.createRowWithFixedColumns(e);this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s)}),this.showGroupSummary&&this.hasAggregateColumns()){const{fixedSummary:t,scrollSummary:s}=this.createGroupSummaryRowWithFixedColumns(e);this.fixedBodyContainer.appendChild(t),this.scrollBodyContainer.appendChild(s)}})}setupLazyRenderingObserver(){if(this.rowObserver&&this.rowObserver.disconnect(),"undefined"==typeof IntersectionObserver)return console.warn("DivTable: IntersectionObserver not supported, falling back to eager rendering"),void this.populateAllUnpopulatedRows();const e=this.fixedColumns>0?this.scrollBodyContainer:this.bodyContainer;this.rowObserver=new IntersectionObserver(e=>{e.forEach(e=>{if(e.isIntersecting){const t=e.target;if("true"!==t.dataset.populated){const e=t.dataset.id,s=this.findRowData(e);if(s)if(this.fixedColumns>0){let i,o;t.classList.contains("div-table-fixed-row")?(i=t,o=this.scrollBodyContainer.querySelector(`.div-table-row[data-id="${e}"]`)):(o=t,i=this.fixedBodyContainer.querySelector(`.div-table-row[data-id="${e}"]`)),i&&o&&this.populateRowCellsWithFixedColumns(i,o,s)}else this.populateRowCells(t,s)}this.rowObserver.unobserve(t)}})},{root:e,rootMargin:this.lazyRenderMargin,threshold:0});if((this.fixedColumns>0?this.scrollBodyContainer.querySelectorAll('.div-table-row[data-populated="false"]'):this.bodyContainer.querySelectorAll('.div-table-row[data-populated="false"]')).forEach(e=>{this.rowObserver.observe(e)}),this.fixedColumns>0&&this.fixedBodyContainer){this.fixedBodyContainer.querySelectorAll('.div-table-row[data-populated="false"]').forEach(e=>{this.rowObserver.observe(e)})}}populateAllUnpopulatedRows(){(this.fixedColumns>0?this.scrollBodyContainer:this.bodyContainer).querySelectorAll('.div-table-row[data-populated="false"]').forEach(e=>{const t=e.dataset.id,s=this.findRowData(t);s&&this.populateRowCells(e,s)})}renderRegularRows(e=this.filteredData){this.sortData(e).forEach(e=>{const t=this.createRow(e);this.bodyContainer.appendChild(t)})}renderGroupedRows(e=this.filteredData){let t=this.groupData(e);this.sortColumn===this.groupByField&&(t=t.sort((e,t)=>{if("count"===this.sortMode){const s=e.items.length-t.items.length;return"desc"===this.sortDirection?-s:s}{if(null==e.value&&null==t.value)return 0;if(null==e.value)return"asc"===this.sortDirection?-1:1;if(null==t.value)return"asc"===this.sortDirection?1:-1;let s=0;return s="number"==typeof e.value&&"number"==typeof t.value?e.value-t.value:String(e.value).localeCompare(String(t.value)),"desc"===this.sortDirection?-s:s}})),t.forEach(e=>{this.sortColumn!==this.groupByField&&(e.items=this.sortData(e.items));const t=this.createGroupHeader(e);if(this.bodyContainer.appendChild(t),this.collapsedGroups.has(e.key)||e.items.forEach(e=>{const t=this.createRow(e);this.bodyContainer.appendChild(t)}),this.showGroupSummary&&this.hasAggregateColumns()){const t=this.createGroupSummaryRow(e);this.bodyContainer.appendChild(t)}})}populateRowCells(e,t){if("true"===e.dataset.populated)return;const s=this.getCompositeColumns(),i=String(t[this.primaryKeyField]);if(this.showCheckboxes){const t=document.createElement("div");t.className="div-table-cell checkbox-column";const s=document.createElement("input");s.type="checkbox",s.checked=this.selectedRows.has(i),s.addEventListener("change",t=>{t.stopPropagation();const o=this.findRowData(i);if(!o)return void console.warn("DivTable: Could not find data for row ID:",i);if(s.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(i),o.selected=!0,e.classList.add("selected");else if(this.selectedRows.delete(i),o.selected=!1,e.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const a=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(a)}),s.addEventListener("focus",t=>{this.updateFocusState(e)}),t.appendChild(s),t.addEventListener("click",e=>{e.target!==s&&(e.stopPropagation(),s.click())}),e.appendChild(t)}s.forEach(s=>{const i=document.createElement("div");if(i.className="div-table-cell",s.compositeName)i.classList.add("composite-cell"),s.columns.forEach((e,s)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",this.groupByField&&e.field===this.groupByField)o.classList.add("grouped-column"),o.textContent="";else if(e.subField){o.classList.add("composite-column"),o.style.display="flex",o.style.flexDirection="column",o.style.gap="2px";const s=document.createElement("div");s.className="composite-main","function"==typeof e.render?s.innerHTML=e.render(t[e.field],t):s.innerHTML=t[e.field]??"";const i=document.createElement("div");i.className="composite-sub","function"==typeof e.subRender?i.innerHTML=e.subRender(t[e.subField],t):i.innerHTML=t[e.subField]??"",o.appendChild(s),o.appendChild(i)}else"function"==typeof e.render?o.innerHTML=e.render(t[e.field],t):o.innerHTML=t[e.field]??"";i.appendChild(o)});else{const e=s.columns[0];if(this.groupByField&&e.field===this.groupByField)i.classList.add("grouped-column"),i.textContent="";else if(e.subField){i.classList.add("composite-column");const s=document.createElement("div");s.className="composite-main","function"==typeof e.render?s.innerHTML=e.render(t[e.field],t):s.innerHTML=t[e.field]??"";const o=document.createElement("div");o.className="composite-sub","function"==typeof e.subRender?o.innerHTML=e.subRender(t[e.subField],t):o.innerHTML=t[e.subField]??"",i.appendChild(s),i.appendChild(o)}else"function"==typeof e.render?i.innerHTML=e.render(t[e.field],t):i.innerHTML=t[e.field]??""}e.appendChild(i)}),e.dataset.populated="true",this.updateTabIndexes()}populateRowCellsWithFixedColumns(e,t,s){if("true"===e.dataset.populated)return;const{fixedColumns:i,scrollColumns:o}=this.splitColumnsForFixedLayout(),a=String(s[this.primaryKeyField]);if(this.showCheckboxes){const s=document.createElement("div");s.className="div-table-cell checkbox-column";const i=document.createElement("input");i.type="checkbox",i.checked=this.selectedRows.has(a),i.addEventListener("change",s=>{s.stopPropagation();const o=this.findRowData(a);if(!o)return void console.warn("DivTable: Could not find data for row ID:",a);if(i.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(a),o.selected=!0,e.classList.add("selected"),t.classList.add("selected");else if(this.selectedRows.delete(a),o.selected=!1,e.classList.remove("selected"),t.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const n=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(n)}),i.addEventListener("focus",s=>{this.updateFocusStateForFixedRows(e,t)}),s.appendChild(i),s.addEventListener("click",e=>{e.target!==i&&(e.stopPropagation(),i.click())}),e.appendChild(s)}i.forEach(t=>{const i=this.createCellForComposite(t,s);e.appendChild(i)}),o.forEach(e=>{const i=this.createCellForComposite(e,s);t.appendChild(i)}),e.dataset.populated="true",t.dataset.populated="true",requestAnimationFrame(()=>{requestAnimationFrame(()=>{e.style.height="",t.style.height="";const s=Math.max(e.offsetHeight,e.scrollHeight),i=Math.max(t.offsetHeight,t.scrollHeight);let o=0;e.querySelectorAll(".div-table-cell").forEach(e=>{o=Math.max(o,e.offsetHeight,e.scrollHeight)}),t.querySelectorAll(".div-table-cell").forEach(e=>{o=Math.max(o,e.offsetHeight,e.scrollHeight)});const a=Math.max(s,i,o);a>0&&(e.style.height=`${a}px`,t.style.height=`${a}px`)})}),this.updateTabIndexes()}createRow(e){const t=document.createElement("div");t.className="div-table-row",t.dataset.id=e[this.primaryKeyField];const s=this.getCompositeColumns();let i="";this.showCheckboxes&&(i="40px "),s.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":i+="80px ";break;case"fixed-medium":i+="120px ";break;case"flexible-small":default:i+="1fr ";break;case"flexible-medium":i+="2fr ";break;case"flexible-large":i+="3fr "}}),t.style.gridTemplateColumns=i.trim();const o=String(e[this.primaryKeyField]);if(this.selectedRows.has(o)&&t.classList.add("selected"),this.focusedRowId===o&&t.classList.add("focused"),this.lazyCellRendering)return t.style.minHeight=this.estimatedRowHeight+"px",t.dataset.populated="false",t.addEventListener("click",s=>{if("true"!==t.dataset.populated&&this.populateRowCells(t,e),s.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const i=this.getFocusableElementForRow(t);if(i){if(this.getCurrentFocusedElement()===i)return;const e=this.getAllFocusableElements().indexOf(i);-1!==e&&this.focusElementAtIndex(e)}}),t.addEventListener("focus",s=>{"true"!==t.dataset.populated&&this.populateRowCells(t,e),this.updateFocusState(t)}),t;if(this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column";const s=document.createElement("input");s.type="checkbox",s.checked=this.selectedRows.has(o),s.addEventListener("change",e=>{e.stopPropagation();const i=this.findRowData(o);if(!i)return void console.warn("DivTable: Could not find data for row ID:",o);if(s.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(o),i.selected=!0,t.classList.add("selected");else if(this.selectedRows.delete(o),i.selected=!1,t.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const a=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(a)}),s.addEventListener("focus",e=>{this.updateFocusState(t)}),s.addEventListener("blur",e=>{}),e.appendChild(s),e.addEventListener("click",e=>{e.target!==s&&(e.stopPropagation(),s.click())}),t.appendChild(e)}return s.forEach(s=>{const i=document.createElement("div");if(i.className="div-table-cell",s.compositeName)i.classList.add("composite-cell"),s.columns.forEach((t,s)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",this.groupByField&&t.field===this.groupByField)o.classList.add("grouped-column"),o.textContent="";else if(t.subField){o.classList.add("composite-column"),o.style.display="flex",o.style.flexDirection="column",o.style.gap="2px";const s=document.createElement("div");s.className="composite-main","function"==typeof t.render?s.innerHTML=t.render(e[t.field],e):s.innerHTML=e[t.field]??"";const i=document.createElement("div");i.className="composite-sub","function"==typeof t.subRender?i.innerHTML=t.subRender(e[t.subField],e):i.innerHTML=e[t.subField]??"",o.appendChild(s),o.appendChild(i)}else"function"==typeof t.render?o.innerHTML=t.render(e[t.field],e):o.innerHTML=e[t.field]??"";i.appendChild(o)});else{const t=s.columns[0];if(this.groupByField&&t.field===this.groupByField)i.classList.add("grouped-column"),i.textContent="";else if(t.subField){i.classList.add("composite-column");const s=document.createElement("div");s.className="composite-main","function"==typeof t.render?s.innerHTML=t.render(e[t.field],e):s.innerHTML=e[t.field]??"";const o=document.createElement("div");o.className="composite-sub","function"==typeof t.subRender?o.innerHTML=t.subRender(e[t.subField],e):o.innerHTML=e[t.subField]??"",i.appendChild(s),i.appendChild(o)}else"function"==typeof t.render?i.innerHTML=t.render(e[t.field],e):i.innerHTML=e[t.field]??""}t.appendChild(i)}),t.addEventListener("click",e=>{if(e.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const s=this.getFocusableElementForRow(t);if(s){if(this.getCurrentFocusedElement()===s)return;const e=this.getAllFocusableElements().indexOf(s);-1!==e&&this.focusElementAtIndex(e)}}),t.addEventListener("focus",e=>{this.updateFocusState(t)}),t}createRowWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout(),i=String(e[this.primaryKeyField]),o=document.createElement("div");o.className="div-table-row div-table-fixed-row",o.dataset.id=i;let a="";this.showCheckboxes&&(a="40px "),t.forEach(e=>{a+=this.getColumnGridSize(e)+" "}),o.style.gridTemplateColumns=a.trim();const n=document.createElement("div");n.className="div-table-row div-table-scroll-row",n.dataset.id=i;let r="";if(s.forEach(e=>{r+=this.getColumnGridSize(e)+" "}),n.style.gridTemplateColumns=r.trim(),this.selectedRows.has(i)&&(o.classList.add("selected"),n.classList.add("selected")),this.focusedRowId===i&&(o.classList.add("focused"),n.classList.add("focused")),this.lazyCellRendering){o.style.minHeight=this.estimatedRowHeight+"px",n.style.minHeight=this.estimatedRowHeight+"px",o.dataset.populated="false",n.dataset.populated="false";const t=(t,s)=>{if("true"!==o.dataset.populated&&this.populateRowCellsWithFixedColumns(o,n,e),t.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const i=this.getFocusableElementForRow(o);if(i){const e=this.getAllFocusableElements().indexOf(i);-1!==e&&this.focusElementAtIndex(e)}};return o.addEventListener("click",e=>t(e,o)),n.addEventListener("click",e=>t(e,n)),o.addEventListener("focus",t=>{"true"!==o.dataset.populated&&this.populateRowCellsWithFixedColumns(o,n,e),this.updateFocusStateForFixedRows(o,n)}),o.addEventListener("mouseenter",()=>n.classList.add("hover")),o.addEventListener("mouseleave",()=>n.classList.remove("hover")),n.addEventListener("mouseenter",()=>o.classList.add("hover")),n.addEventListener("mouseleave",()=>o.classList.remove("hover")),{fixedRow:o,scrollRow:n}}if(this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column";const t=document.createElement("input");t.type="checkbox",t.checked=this.selectedRows.has(i),t.addEventListener("change",e=>{e.stopPropagation();const s=this.findRowData(i);if(!s)return void console.warn("DivTable: Could not find data for row ID:",i);if(t.checked)this.multiSelect||this.clearSelection(),this.selectedRows.add(i),s.selected=!0,o.classList.add("selected"),n.classList.add("selected");else if(this.selectedRows.delete(i),s.selected=!1,o.classList.remove("selected"),n.classList.remove("selected"),this.showOnlySelected){this.renderBody(),this.updateInfoSection();const e=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);return void("function"==typeof this.onSelectionChange&&this.onSelectionChange(e))}this.updateSelectionStates(),this.updateInfoSection();const a=Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean);"function"==typeof this.onSelectionChange&&this.onSelectionChange(a)}),t.addEventListener("focus",e=>{this.updateFocusStateForFixedRows(o,n)}),e.appendChild(t),e.addEventListener("click",e=>{e.target!==t&&(e.stopPropagation(),t.click())}),o.appendChild(e)}t.forEach(t=>{const s=this.createCellForComposite(t,e);o.appendChild(s)}),s.forEach(t=>{const s=this.createCellForComposite(t,e);n.appendChild(s)});const l=(e,t)=>{if(e.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const s=this.getFocusableElementForRow(o);if(s){const e=this.getAllFocusableElements().indexOf(s);-1!==e&&this.focusElementAtIndex(e)}};return o.addEventListener("click",e=>l(e)),n.addEventListener("click",e=>l(e)),o.addEventListener("mouseenter",()=>{n.classList.add("hover")}),o.addEventListener("mouseleave",()=>{n.classList.remove("hover")}),n.addEventListener("mouseenter",()=>{o.classList.add("hover")}),n.addEventListener("mouseleave",()=>{o.classList.remove("hover")}),{fixedRow:o,scrollRow:n}}updateFocusStateForFixedRows(e,t){this.fixedBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),this.scrollBodyContainer.querySelectorAll(".div-table-row.focused").forEach(e=>e.classList.remove("focused")),e.classList.add("focused"),t.classList.add("focused");const s=e.dataset.id;if(s&&(this.focusedRowId=s,this._lastFocusCallback.rowId!==s)){this._lastFocusCallback={rowId:s,groupKey:null};const e=this.findRowData(s);this.onRowFocus(e)}}createCellForComposite(e,t){const s=document.createElement("div");if(s.className="div-table-cell",!e.compositeName&&e.columns[0]?.align&&(s.style.textAlign=e.columns[0].align,s.style.justifyContent="right"===e.columns[0].align?"flex-end":"center"===e.columns[0].align?"center":"flex-start"),e.compositeName)s.classList.add("composite-cell"),e.columns.forEach((e,i)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",this.groupByField&&e.field===this.groupByField)o.classList.add("grouped-column"),o.textContent="";else if(e.subField){o.classList.add("composite-column"),o.style.display="flex",o.style.flexDirection="column",o.style.gap="2px";const s=document.createElement("div");s.className="composite-main","function"==typeof e.render?s.innerHTML=e.render(t[e.field],t):s.innerHTML=t[e.field]??"";const i=document.createElement("div");i.className="composite-sub","function"==typeof e.subRender?i.innerHTML=e.subRender(t[e.subField],t):i.innerHTML=t[e.subField]??"",o.appendChild(s),o.appendChild(i)}else"function"==typeof e.render?o.innerHTML=e.render(t[e.field],t):o.innerHTML=t[e.field]??"";s.appendChild(o)});else{const i=e.columns[0];if(this.groupByField&&i.field===this.groupByField)s.classList.add("grouped-column"),s.textContent="";else if(i.subField){s.classList.add("composite-column");const e=document.createElement("div");e.className="composite-main","function"==typeof i.render?e.innerHTML=i.render(t[i.field],t):e.innerHTML=t[i.field]??"";const o=document.createElement("div");o.className="composite-sub","function"==typeof i.subRender?o.innerHTML=i.subRender(t[i.subField],t):o.innerHTML=t[i.subField]??"",s.appendChild(e),s.appendChild(o)}else"function"==typeof i.render?s.innerHTML=i.render(t[i.field],t):s.innerHTML=t[i.field]??""}return s}createGroupHeaderWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout(),i=document.createElement("div");i.className="div-table-row group-header div-table-fixed-row",i.dataset.groupKey=e.key;let o="";this.showCheckboxes&&(o="40px "),t.forEach(e=>{o+=this.getColumnGridSize(e)+" "}),i.style.gridTemplateColumns=o.trim();const a=document.createElement("div");a.className="div-table-row group-header div-table-scroll-row",a.dataset.groupKey=e.key;let n="";if(s.forEach(e=>{n+=this.getColumnGridSize(e)+" "}),a.style.gridTemplateColumns=n.trim(),this.collapsedGroups.has(e.key)&&(i.classList.add("collapsed"),a.classList.add("collapsed")),this.showCheckboxes){const t=document.createElement("div");t.className="div-table-cell checkbox-column";const s=document.createElement("input");s.type="checkbox";const o=e.items.map(e=>String(e[this.primaryKeyField])),n=o.filter(e=>this.selectedRows.has(e));0===n.length?(s.checked=!1,s.indeterminate=!1):n.length===o.length?(s.checked=!0,s.indeterminate=!1):(s.checked=!1,s.indeterminate=!0),s.addEventListener("change",t=>{t.stopPropagation();const s=0===o.filter(e=>this.selectedRows.has(e)).length;if(e.items.forEach(e=>{const t=String(e[this.primaryKeyField]);s?(this.selectedRows.add(t),e.selected=!0):(this.selectedRows.delete(t),e.selected=!1)}),this.showOnlySelected)return this.renderBody(),this.updateInfoSection(),void("function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean)));this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}),s.addEventListener("focus",e=>{this.updateFocusStateForFixedRows(i,a)}),t.appendChild(s),i.appendChild(t)}const r=document.createElement("div");r.className="div-table-cell",r.style.gridColumn=this.showCheckboxes?"2 / -1":"1 / -1",r.style.display="flex",r.style.alignItems="center",r.style.gap="8px";const l=document.createElement("span");l.className="group-toggle",this.collapsedGroups.has(e.key)&&l.classList.add("collapsed"),l.textContent="❯",l.title=this.collapsedGroups.has(e.key)?"Expand group":"Collapse group";const d=this.columns.find(e=>e.field===this.groupByField),c=d?.label||this.groupByField;let h;h=null==e.value||""===e.value?`${c} is undefined`:d&&"function"==typeof d.render?d.render(e.value,null):e.value,r.appendChild(l);const u=document.createElement("span");"string"==typeof h?u.innerHTML=h:u.textContent=h,r.appendChild(u);const p=document.createElement("span");p.className="group-item-count",p.innerHTML=`(${e.items.length})`,p.style.opacity="0.8",p.style.fontSize="0.9em",p.style.fontWeight="normal",p.title=`${e.items.length} item${1===e.items.length?"":"s"} in this group`,r.appendChild(p),i.appendChild(r);const m=document.createElement("div");m.className="div-table-cell",m.style.gridColumn="1 / -1",a.appendChild(m);return l.addEventListener("click",t=>{t.stopPropagation(),t.preventDefault(),this.collapsedGroups.has(e.key)?(this.collapsedGroups.delete(e.key),i.classList.remove("collapsed"),a.classList.remove("collapsed")):(this.collapsedGroups.add(e.key),i.classList.add("collapsed"),a.classList.add("collapsed")),this.render()}),i.addEventListener("mouseenter",()=>{a.classList.add("hover")}),i.addEventListener("mouseleave",()=>{a.classList.remove("hover")}),a.addEventListener("mouseenter",()=>{i.classList.add("hover")}),a.addEventListener("mouseleave",()=>{i.classList.remove("hover")}),{fixedGroupHeader:i,scrollGroupHeader:a}}createGroupHeader(e){const t=document.createElement("div");t.className="div-table-row group-header",t.dataset.groupKey=e.key;const s=this.getOrderedColumns();let i="";if(this.showCheckboxes&&(i="40px "),s.forEach(e=>{switch((e.responsive||{}).size){case"fixed-narrow":i+="80px ";break;case"fixed-medium":i+="120px ";break;case"flexible-small":default:i+="1fr ";break;case"flexible-medium":i+="2fr ";break;case"flexible-large":i+="3fr "}}),t.style.gridTemplateColumns=i.trim(),this.collapsedGroups.has(e.key)&&t.classList.add("collapsed"),this.showCheckboxes){const s=document.createElement("div");s.className="div-table-cell checkbox-column";const i=document.createElement("input");i.type="checkbox";const o=e.items.map(e=>String(e[this.primaryKeyField])),a=o.filter(e=>this.selectedRows.has(e));0===a.length?(i.checked=!1,i.indeterminate=!1):a.length===o.length?(i.checked=!0,i.indeterminate=!1):(i.checked=!1,i.indeterminate=!0),i.addEventListener("change",t=>{t.stopPropagation();const s=0===e.items.map(e=>String(e[this.primaryKeyField])).filter(e=>this.selectedRows.has(e)).length;if(e.items.forEach(e=>{const t=String(e[this.primaryKeyField]);s?(this.selectedRows.add(t),e.selected=!0):(this.selectedRows.delete(t),e.selected=!1)}),this.showOnlySelected)return this.renderBody(),this.updateInfoSection(),void("function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean)));this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}),i.addEventListener("focus",e=>{this.updateFocusState(t)}),s.appendChild(i),t.appendChild(s)}const o=document.createElement("div");o.className="div-table-cell",o.style.gridColumn=this.showCheckboxes?"2 / -1":"1 / -1",o.style.display="flex",o.style.alignItems="center",o.style.gap="8px";const a=document.createElement("span");a.className="group-toggle",this.collapsedGroups.has(e.key)&&a.classList.add("collapsed"),a.textContent="❯",a.title=this.collapsedGroups.has(e.key)?"Expand group":"Collapse group";const n=this.columns.find(e=>e.field===this.groupByField),r=n?.label||this.groupByField;let l;l=null==e.value||""===e.value?`${r} is undefined`:n&&"function"==typeof n.render?n.render(e.value,null):e.value,o.appendChild(a);const d=document.createElement("span");"string"==typeof l?d.innerHTML=l:d.textContent=l,o.appendChild(d);const c=document.createElement("span");return c.className="group-item-count",c.innerHTML=`(${e.items.length})`,c.style.opacity="0.8",c.style.fontSize="0.9em",c.style.fontWeight="normal",c.title=`${e.items.length} item${1===e.items.length?"":"s"} in this group`,o.appendChild(c),t.appendChild(o),a.addEventListener("click",s=>{s.stopPropagation(),s.preventDefault(),this.collapsedGroups.has(e.key)?(this.collapsedGroups.delete(e.key),t.classList.remove("collapsed")):(this.collapsedGroups.add(e.key),t.classList.add("collapsed")),this.render(),setTimeout(()=>{const t=this.bodyContainer.querySelector(`[data-group-key="${e.key}"]`);if(t){const e=this.getFocusableElementForRow(t);if(e){const t=this.getAllFocusableElements().indexOf(e);-1!==t&&this.focusElementAtIndex(t)}}},0)}),t.addEventListener("click",e=>{if(e.target.closest(".checkbox-column"))return;if(window.getSelection().toString().length>0)return;const s=this.getFocusableElementForRow(t);if(s){if(this.getCurrentFocusedElement()===s)return;const e=this.getAllFocusableElements().indexOf(s);-1!==e&&this.focusElementAtIndex(e)}}),t.addEventListener("focus",e=>{this.updateFocusState(t)}),t}groupData(e){const t=new Map;return e.forEach(e=>{const s=e[this.groupByField];let i,o;Array.isArray(s)?(i=s.length>0?s.join(", "):"__null__",o=s.length>0?s.join(", "):null):(i=s??"__null__",o=s),t.has(i)||t.set(i,{key:i,value:o,items:[]}),t.get(i).items.push(e)}),Array.from(t.values()).sort((e,t)=>null==e.value?1:null==t.value?-1:String(e.value).localeCompare(String(t.value)))}sortData(e){return this.sortColumn?[...e].sort((e,t)=>{const s=e[this.sortColumn],i=t[this.sortColumn];if(null==s&&null==i)return 0;if(null==s)return"asc"===this.sortDirection?-1:1;if(null==i)return"asc"===this.sortDirection?1:-1;let o=0;return o="number"==typeof s&&"number"==typeof i?s-i:String(s).localeCompare(String(i)),"desc"===this.sortDirection?-o:o}):e}selectAll(){this.selectedRows.clear(),this.filteredData.forEach(e=>{const t=String(e[this.primaryKeyField]);this.selectedRows.add(t),e.selected=!0}),this.updateSelectionStates(),this.updateInfoSection(),"function"==typeof this.onSelectionChange&&this.onSelectionChange(Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean))}updateInfoSection(){if(!this.infoSection)return;const e=this.virtualScrolling?Math.max(this.totalRecords,this.data.length):this.data.length,t=this.data.length,s=this.filteredData.length,i=this.getValidSelectedCount();this.infoSection.innerHTML="";const o=document.createElement("div");if(o.className="info-line-container",i>0){const e=document.createElement("div");e.className="info-line";const t=this.createFilterSelectedOnlyToggleButton();e.appendChild(t);const s=document.createElement("span");s.className="info-selection",s.textContent=`${i} selected`,e.appendChild(s),o.appendChild(e)}if(this.showAutoFetchButton&&this.virtualScrolling&&(this.hasMoreData||this.isAutoFetching)){const e=this.createAutoFetchButton();e.disabled=!1,o.appendChild(e)}if(this.showRefreshButton){const e=this.createRefreshButton();this.isLoading||this.isLoadingState?(e.classList.add("refreshing"),e.disabled=!0,e.title="Loading data..."):(e.classList.remove("refreshing"),e.disabled=!1,e.title="Refresh data"),o.appendChild(e)}o.children.length>0&&this.infoSection.appendChild(o);const a=document.createElement("div");a.className="info-line secondary";const n=document.createElement("span");n.className="info-stats";let r="";if(this.virtualScrolling)if(s<t)if(t<e){r=`${s} filtered (${Math.round(t/e*100)}% of ${e} total)`}else r=`${s} filtered (${e} total)`;else if(t<e){r=`${Math.round(t/e*100)}% of ${e} total`}else r=`${e} total`;else r=s<e?`${s} filtered (${e} total)`:`${e} total`;n.textContent=r,a.appendChild(n),this.infoSection.appendChild(a),this.createProgressBar(t,e,s)}createProgressBar(e,t,s){const i=document.createElement("div");i.className="progress-line";const o=this.virtualScrolling?this.totalRecords:this.data.length,a=this.virtualScrolling&&e<o;if(a||s<o){const t=document.createElement("div");t.className="loading-progress";const n=Math.ceil(.1*o),r=this.pageSize||50,l=Math.max(r,Math.min(n,100)),d=e<o?Math.min(o,e+l):e,c=s/o*100,h=e/o*100,u=d/o*100,p=s<e&&this.currentQuery&&""!==this.currentQuery.trim();if(p){if(s>0){const e=document.createElement("div");e.className="progress-segment filtered-segment",e.style.width=`${c}%`,e.style.opacity="1",t.appendChild(e)}if(e>s){const e=document.createElement("div");e.className="progress-segment loaded-segment",e.style.left=`${c}%`,e.style.width=h-c+"%",e.style.opacity="0.8",t.appendChild(e)}}else if(e>0){const e=document.createElement("div");e.className="progress-segment loaded-segment",e.style.width=`${h}%`,e.style.opacity="1",t.appendChild(e)}if(this.hasMoreData&&(this.isLoading||this.isAutoFetching&&!this.autoFetchPaused)&&e<o&&d>e){const e=document.createElement("div");e.className="progress-segment loading-segment",e.style.left=`${h}%`,e.style.width=u-h+"%",t.appendChild(e)}p&&a?t.setAttribute("data-state","filtered-loading"):p?t.setAttribute("data-state","filtered"):a&&t.setAttribute("data-state","sequential-loading"),i.appendChild(t),this.infoSection.appendChild(i)}}createRefreshButton(){const e=document.createElement("button");return e.className="refresh-button",e.type="button",e.title="Refresh data",e.setAttribute("aria-label","Refresh table data"),e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <path d="M23 4v6h-6"></path>\n <path d="M20.49 15a9 9 0 1 1-2.12-9.36L23 10"></path>\n </svg>\n ',e.addEventListener("click",async t=>{t.preventDefault(),t.stopPropagation(),e.classList.add("refreshing");try{await this.refresh()}catch(e){}finally{setTimeout(()=>{e.classList.remove("refreshing")},500)}}),e}createAutoFetchButton(){const e=document.createElement("button");e.className="auto-fetch-button",e.type="button",e.title="Auto-fetch all pages",e.setAttribute("aria-label","Automatically fetch all remaining pages");const t=t=>{this.isAutoFetching&&!t?(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <rect x="6" y="4" width="4" height="16"></rect>\n <rect x="14" y="4" width="4" height="16"></rect>\n </svg>\n ',e.title="Pause auto-fetch",e.classList.add("active"),e.classList.remove("paused")):(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <polygon points="5 3 19 12 5 21 5 3"></polygon>\n </svg>\n ',e.classList.remove("active"),t?(e.title="Resume auto-fetch (waiting for current page to complete)",e.classList.add("paused")):(e.title="Auto-fetch all pages",e.classList.remove("paused")))};return t(this.autoFetchPaused),e.addEventListener("click",async e=>{e.preventDefault(),e.stopPropagation(),this.isAutoFetching?(this.autoFetchPaused=!this.autoFetchPaused,t(this.autoFetchPaused),this.autoFetchPaused||this.continueAutoFetch()):this.startAutoFetch(t)}),this.autoFetchButton=e,this.updateAutoFetchButtonIcon=t,e}async startAutoFetch(e){if(this.virtualScrolling&&this.hasMoreData&&!this.isAutoFetching){this.isAutoFetching=!0,this.autoFetchPaused=!1,e(!1),console.log("🚀 Starting auto-fetch...");try{await this.continueAutoFetch()}catch(e){console.error("❌ Auto-fetch error:",e),this.stopAutoFetch()}}}async continueAutoFetch(){for(;this.hasMoreData&&this.isAutoFetching&&!this.autoFetchPaused&&(await this.loadNextPage(),this.hasMoreData&&this.isAutoFetching&&!this.autoFetchPaused)&&(await new Promise(e=>{this.autoFetchTimeout=setTimeout(e,this.autoFetchDelay)}),!this.autoFetchPaused););this.hasMoreData?this.autoFetchPaused&&(this.updateAutoFetchButtonIcon&&this.updateAutoFetchButtonIcon(!0),this.updateInfoSection()):this.stopAutoFetch()}stopAutoFetch(){this.isAutoFetching=!1,this.autoFetchPaused=!1,this.autoFetchTimeout&&(clearTimeout(this.autoFetchTimeout),this.autoFetchTimeout=null),this.updateAutoFetchButtonIcon&&(this.updateAutoFetchButtonIcon(!1),this.autoFetchButton?.classList.remove("active","paused")),this.updateInfoSection()}createFilterSelectedOnlyToggleButton(){const e=document.createElement("button");e.className="filter-selected-only-toggle-button",e.type="button";const t=()=>{this.showOnlySelected?(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"></path>\n <circle cx="12" cy="12" r="3"></circle>\n </svg>\n ',e.title="Show all rows",e.classList.add("active")):(e.innerHTML='\n <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">\n <path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"></path>\n <circle cx="12" cy="12" r="3"></circle>\n </svg>\n ',e.title="Show only selected rows",e.classList.remove("active"))};return t(),e.addEventListener("click",e=>{e.preventDefault(),e.stopPropagation(),this.showOnlySelected=!this.showOnlySelected,t(),this.render(),console.log(this.showOnlySelected?"👁️ Showing only selected rows":"👁️ Showing all rows")}),e}updateInfoSectionWithAnticipatedProgress(){if(!this.infoSection||!this.virtualScrolling)return;const e=Math.max(this.totalRecords,this.data.length),t=this.data.length,s=this.filteredData.length,i=this.getValidSelectedCount(),o=Math.min(t+this.pageSize,e);this.infoSection.innerHTML="";const a=document.createElement("div");if(a.className="info-line-container",i>0){const e=document.createElement("div");e.className="info-line";const t=document.createElement("span");t.className="info-selection",t.textContent=`${i} selected`,e.appendChild(t),a.appendChild(e)}if(this.showAutoFetchButton&&this.virtualScrolling&&(this.hasMoreData||this.isAutoFetching)){const e=this.createAutoFetchButton();e.disabled=this.autoFetchPaused,a.appendChild(e)}if(this.showRefreshButton){const e=this.createRefreshButton();e.classList.add("refreshing"),e.disabled=!0,e.title="Loading data...",a.appendChild(e)}a.children.length>0&&this.infoSection.appendChild(a);const n=document.createElement("div");n.className="info-line secondary";const r=document.createElement("span");r.className="info-stats";let l="";if(s<t)if(o<e){l=`${s} filtered (${Math.round(o/e*100)}% of ${e} total)`}else l=`${s} filtered (${e} total)`;else if(o<e){l=`${Math.round(o/e*100)}% of ${e} total`}else l=`${e} total`;r.textContent=l,n.appendChild(r),this.infoSection.appendChild(n),this.createProgressBar(o,e,s)}applyQuery(e){if(this.currentQuery=e,this.queryEditor?.editor){this.queryEditor.editor.getValue()!==e&&this.queryEditor.editor.setValue(e)}if(e.trim())try{const t=this.queryEngine.filterObjects(e);this.filteredData=this.data.filter(e=>t.includes(e[this.primaryKeyField]))}catch(e){this.filteredData=[...this.data]}else this.filteredData=[...this.data];this.render()}sort(e,t){this.groupByField&&e===this.groupByField?this.sortColumn===e?"value"===this.sortMode&&"asc"===this.sortDirection?this.sortDirection="desc":"value"===this.sortMode&&"desc"===this.sortDirection?(this.sortMode="count",this.sortDirection="asc"):"count"===this.sortMode&&"asc"===this.sortDirection?this.sortDirection="desc":(this.sortColumn=null,this.sortDirection="asc",this.sortMode="value"):(this.sortColumn=e,this.sortDirection="asc",this.sortMode="value"):this.sortColumn===e?this.sortDirection="asc"===this.sortDirection?"desc":"asc":(this.sortColumn=e,this.sortDirection=t||"asc",this.sortMode="value"),this.render()}group(e){if(e){const t=this.columns.find(t=>t.field===e);if(!t)return void console.warn(`DivTable: Cannot group by field '${e}' - field not found in columns`);if(t.hidden)return void console.warn(`DivTable: Cannot group by field '${e}' - hidden columns cannot be used for grouping`);if(!1===t.groupable)return void console.warn(`DivTable: Cannot group by field '${e}' - column is marked as not groupable`)}if(this.groupByField=e||null,e){this.collapsedGroups.clear();this.groupData(this.filteredData).forEach(e=>{this.collapsedGroups.add(e.key)})}else this.collapsedGroups.clear();this.render()}clearGrouping(){this.group(null)}addRecord(e){if(!e||"object"!=typeof e)return console.warn("addRecord requires a valid record object"),!1;if(!e[this.primaryKeyField])return console.warn(`addRecord: Record must have a ${this.primaryKeyField} field`),!1;const t=String(e[this.primaryKeyField]),s=this.data.findIndex(e=>String(e[this.primaryKeyField])===t);return s>=0?(this.data[s]={...e},console.log(`addRecord: Updated existing record with ${this.primaryKeyField} '${t}'`)):(this.data.push(e),console.log(`addRecord: Added new record with ${this.primaryKeyField} '${t}'`)),this.isLoadingState=!1,this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.applyQuery(this.currentQuery),!0}removeRecord(e){if(null==e)return console.warn("removeRecord requires a valid ID"),!1;const t=String(e),s=this.data.findIndex(e=>String(e[this.primaryKeyField])===t);if(s>=0){const e=this.data[s];return this.data.splice(s,1),this.selectedRows.delete(t),this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.applyQuery(this.currentQuery),e}return console.warn(`removeRecord: Record with ${this.primaryKeyField} '${t}' not found`),!1}getSelectedRows(){return Array.from(this.selectedRows).map(e=>this.findRowData(e)).filter(Boolean)}getValidSelectedCount(){return this.getSelectedRows().length}toggleSelectedRowsFilter(e){return this.showOnlySelected=void 0!==e?e:!this.showOnlySelected,this.render(),console.log(this.showOnlySelected?"👁️ Showing only selected rows":"👁️ Showing all rows"),this.showOnlySelected}async refresh(){this.isAutoFetching&&this.stopAutoFetch();try{if(this.virtualScrolling&&"function"==typeof this.onNextPage){this.currentQuery,this.queryEditor?.editor&&this.queryEditor.editor.getValue();const e=new Set(this.selectedRows);this.isLoadingState=!0,this.data=[],this.filteredData=[],this.currentPage=0,this.isLoading=!0,this.hasMoreData=!0,this.queryEngine.setObjects([]),this.render();const t=0,s=await this.onNextPage(t,this.pageSize);if(this.isLoading=!1,s&&Array.isArray(s)&&s.length>0){this.replaceData(s),this.selectedRows.clear();for(const t of e){this.data.some(e=>String(e[this.primaryKeyField])===t)&&this.selectedRows.add(t)}this.render()}else this.isLoadingState=!1,this.render()}else"function"==typeof this.onRefresh?(this.showLoadingPlaceholder&&(this.isLoadingState=!0,this.render()),await Promise.resolve(this.onRefresh()),this.isLoadingState&&(this.isLoadingState=!1,this.render())):console.log("ℹ️ Refresh: No onRefresh callback provided for non-virtual scrolling table")}catch(e){throw console.error("❌ Refresh error:",e),this.isLoadingState=!1,this.render(),e}}updateQueryEditorIfNeeded(){if(!this.queryEditor||!this.queryEditor.editor)return;if(0===this.data.length)return;const e=this.queryEditor.editor.getFieldNames()||{},t=new Set(this.columns.filter(e=>e.field).map(e=>e.field)),s={};Object.keys(e).forEach(i=>{t.has(i)&&(s[i]=e[i])});const i={...s};this.data.length>0&&this.columns.forEach(e=>{const t=e.field;if(t&&s[t]){const o=s[t],a=e.type||o.type;if("string"===a&&void 0!==o.values){const e=[];this.data.forEach(s=>{const i=s[t];Array.isArray(i)?e.push(...i):e.push(i)});const s=[...new Set(e)],n=s.filter(e=>null!=e&&""!==e),r=s.some(e=>null==e||""===e),l=o.values.filter(e=>"NULL"!==e),d=[...new Set([...l,...n])];i[t]={type:a,values:r?[...d,"NULL"]:d}}else i[t]={type:a}}});if(this._shouldUpdateFieldNames(s,i))try{this.queryEditor.editor.updateFieldNames(i)||console.warn("⚠️ Failed to update query editor field values - dynamic update not available")}catch(e){console.warn("⚠️ Error updating query editor field values:",e)}}setupQueryEventHandlers(){setTimeout(()=>{const e=this.queryEditor.model?.getValue();""===e&&this.monaco.editor.setModelMarkers(this.queryEditor.model,this.queryEditor.model.getLanguageId(),[])},10),this.queryEditor.model&&this.queryEditor.model.onDidChangeContent(()=>{const e=this.queryEditor.model.getValue();this.handleQueryChange(e)}),this._setupQueryListeners()}verifyDataConsistency(){const e=[];for(const t of this.selectedRows){this.findRowData(t)||e.push(`Selected row ${t} not found in data`)}const t=Array.from(this.bodyContainer.querySelectorAll(".div-table-row[data-id]")).map(e=>e.dataset.id);for(const s of t){this.findRowData(s)||e.push(`Displayed row ${s} not found in data`)}return e.length>0&&console.warn("DivTable data consistency issues:",e),0===e.length}testGroupSelectionStates(){if(!this.groupByField)return void console.log("No grouping applied");const e=this.groupData(this.sortData(this.filteredData));console.log("Group selection states:"),e.forEach(e=>{const t=e.items.map(e=>String(e[this.primaryKeyField])),s=t.filter(e=>this.selectedRows.has(e));let i="none";s.length===t.length?i="all":s.length>0&&(i="partial"),console.log(`Group "${e.value}": ${s.length}/${t.length} selected (${i})`)})}handleVirtualScroll(){const e=this.bodyContainer.scrollTop,t=this.bodyContainer.scrollHeight,s=(e+this.bodyContainer.clientHeight)/t,i=this.filteredData.length;Math.floor(s*i)>=i-this.loadingThreshold&&this.hasMoreData&&!this.isLoading&&this.loadNextPage()}async loadNextPage(){if(!this.isLoading&&this.hasMoreData){this.isLoading=!0,this.showLoadingPlaceholders(),this.updateInfoSectionWithAnticipatedProgress();try{const e=this.currentPage+1,t=await this.onNextPage(e,this.pageSize);if(this.isLoading=!1,this.hideLoadingPlaceholders(),t&&Array.isArray(t)&&t.length>0){const s=this.appendData(t,!0);(s.added>0||s.updated>0)&&(this.currentPage=e),this.totalRecords&&this.totalRecords>0?this.hasMoreData=this.data.length<this.totalRecords:this.hasMoreData=t.length===this.pageSize,t.length<this.pageSize&&(this.hasMoreData=!1)}else this.hasMoreData=!1}catch(e){console.error("❌ Error loading next page:",e),this.isLoading=!1,this.hideLoadingPlaceholders(),this.showErrorIndicator()}finally{this.updateInfoSection()}}}showErrorIndicator(){let e=this.bodyContainer.querySelector(".error-indicator");if(!e){e=document.createElement("div"),e.className="error-indicator",e.innerHTML='\n <span>Error loading data. Please try again.</span>\n <button class="retry-button">Retry</button>\n ';e.querySelector(".retry-button").addEventListener("click",()=>{this.hideErrorIndicator(),this.loadNextPage()}),this.bodyContainer.appendChild(e)}e.style.display="flex"}hideErrorIndicator(){const e=this.bodyContainer.querySelector(".error-indicator");e&&(e.style.display="none")}showLoadingPlaceholders(){if(!this.showLoadingPlaceholder)return;this.hideLoadingPlaceholders();for(let e=0;e<3;e++){const e=this.createLoadingPlaceholderRow();this.bodyContainer.appendChild(e)}}hideLoadingPlaceholders(){this.bodyContainer.querySelectorAll(".div-table-row.loading-placeholder").forEach(e=>e.remove())}createLoadingPlaceholderRow(){const e=document.createElement("div");e.className="div-table-row loading-placeholder";const t=this.getOrderedColumns();let s="";if(this.showCheckboxes&&(s="40px "),t.forEach(e=>{if(this.groupByField&&e.field===this.groupByField)return void(s+="100px ");switch((e.responsive||{}).size){case"fixed-narrow":s+="80px ";break;case"fixed-medium":s+="120px ";break;case"flexible-small":default:s+="1fr ";break;case"flexible-medium":s+="2fr ";break;case"flexible-large":s+="3fr "}}),e.style.gridTemplateColumns=s.trim(),this.showCheckboxes){const t=document.createElement("div");t.className="div-table-cell checkbox-column loading-cell",e.appendChild(t)}return t.forEach(t=>{const s=document.createElement("div");s.className="div-table-cell loading-cell";const i=document.createElement("div");i.className="loading-shimmer-content";const o=60+30*Math.random();i.style.width=`${o}%`,s.appendChild(i),e.appendChild(s)}),e}clearRefreshButtonLoadingState(){if(this.showRefreshButton){const e=this.infoSection.querySelector(".refresh-button");e&&(e.classList.remove("refreshing"),e.disabled=!1,e.title="Refresh data")}}setTotalRecords(e){"number"!=typeof e||e<0?console.warn("DivTable: totalRecords must be a non-negative number"):(this.totalRecords=e,this.hasMoreData=this.data.length<e,this.updateInfoSection(),console.log(`DivTable: Updated totalRecords to ${e}, hasMoreData: ${this.hasMoreData}`))}setPageSize(e){if("number"!=typeof e||e<=0)return void console.warn("DivTable: pageSize must be a positive number");const t=this.pageSize;this.pageSize=e,this.loadingThreshold=Math.floor(.8*this.pageSize),this.visibleEndIndex=Math.min(this.visibleStartIndex+this.pageSize,this.data.length),this.updateInfoSection(),console.log(`DivTable: Updated pageSize from ${t} to ${e}, loadingThreshold: ${this.loadingThreshold}`)}setVirtualScrollingConfig({totalRecords:e,pageSize:t,loadingThreshold:s}){let i=!1;"number"==typeof e&&e>=0&&(this.totalRecords=e,this.hasMoreData=this.data.length<e,i=!0),"number"==typeof t&&t>0&&(this.pageSize=t,this.visibleEndIndex=Math.min(this.visibleStartIndex+this.pageSize,this.data.length),i=!0),"number"==typeof s&&s>0?(this.loadingThreshold=s,i=!0):"number"==typeof t&&(this.loadingThreshold=Math.floor(.8*this.pageSize),i=!0),i&&(this.updateInfoSection(),console.log(`DivTable: Updated virtual scrolling config - totalRecords: ${this.totalRecords}, pageSize: ${this.pageSize}, loadingThreshold: ${this.loadingThreshold}`))}setHasMoreData(e){this.hasMoreData=e}resetPagination(){this.currentPage=0,this.isLoading=!1,this.hasMoreData=!0,this.data=this.data.slice(0,this.pageSize),this.filteredData=[...this.data],this.hideErrorIndicator(),this.render()}appendData(e,t=!1){if(!e||!Array.isArray(e))return console.warn("appendData requires a valid array"),{added:0,updated:0,skipped:0,invalid:[]};const s=[];let i=0,o=0;for(const t of e){if(!t||"object"!=typeof t){s.push(t),console.warn("appendData: Skipping invalid record",t);continue}if(!t[this.primaryKeyField]){s.push(t),console.warn(`appendData: Skipping record without ${this.primaryKeyField}`,t);continue}const e=String(t[this.primaryKeyField]),a=this.data.findIndex(t=>String(t[this.primaryKeyField])===e);a>=0?(this.data[a]={...t},o++):(this.data.push(t),i++)}return(i>0||o>0)&&(this.isLoadingState=!1,this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.currentQuery.trim()?this.applyQuery(this.currentQuery):this.filteredData=[...this.data],t||this.updateInfoSection(),this.render()),{added:i,updated:o,skipped:s.length,invalid:s}}replaceData(e){if(!e||!Array.isArray(e))return console.warn("replaceData requires a valid array"),{success:!1,message:"Invalid data provided"};const t=[],s=new Set,i=[];for(const o of e){if(!o||"object"!=typeof o){console.warn("replaceData: Skipping invalid record",o);continue}if(!o[this.primaryKeyField]){console.warn(`replaceData: Skipping record without ${this.primaryKeyField}`,o);continue}const e=String(o[this.primaryKeyField]);s.has(e)?(t.push(e),console.warn(`replaceData: Skipping duplicate ${this.primaryKeyField} '${e}' within new data`)):(s.add(e),i.push(o))}return this.data=i,this.isLoadingState=!1,this.clearRefreshButtonLoadingState(),this.queryEngine.setObjects(this.data),this.updateQueryEditorIfNeeded(),this.currentQuery&&this.currentQuery.trim()?this.applyQuery(this.currentQuery):this.filteredData=[...this.data],this.selectedRows.clear(),this.virtualScrollingState={scrollTop:0,displayStartIndex:0,displayEndIndex:Math.min(this.pageSize,this.data.length),isLoading:!1},this.currentPage=0,this.startId=1,this.virtualScrolling&&this.totalRecords&&(this.hasMoreData=i.length<this.totalRecords),this.updateInfoSection(),this.render(),{success:!0,totalProvided:e.length,validRecords:i.length,skipped:e.length-i.length,duplicates:t}}resetToLoading(){this.isLoadingState=!0,this.data=[],this.filteredData=[],this.selectedRows.clear(),this.currentQuery="",this.queryEditor?.editor&&this.queryEditor.editor.setValue(""),this.queryEngine.setObjects([]),this.render()}setLoadingState(e){this.isLoadingState=Boolean(e),this.render()}hasAggregateColumns(){return this.columns.some(e=>e.aggregate)}getAggregateColumns(){return this.columns.filter(e=>e.aggregate)}calculateAggregate(e,t){if(!e.aggregate||!t||0===t.length)return null;const s=e.field,i=e.aggregate.toLowerCase(),o=t.map(e=>e[s]).filter(e=>null!=e&&!isNaN(parseFloat(e))).map(e=>parseFloat(e));if(0===o.length&&"count"!==i)return null;switch(i){case"sum":return o.reduce((e,t)=>e+t,0);case"avg":case"average":return o.length>0?o.reduce((e,t)=>e+t,0)/o.length:null;case"count":return t.length;case"min":return o.length>0?Math.min(...o):null;case"max":return o.length>0?Math.max(...o):null;default:return console.warn(`DivTable: Unknown aggregate type '${i}' for column '${s}'`),null}}getAggregationDataSet(e){return this.selectedRows.size>0?e.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}):e}formatAggregateValue(e,t){if(null==e)return"";if("function"==typeof t.aggregateRender)return t.aggregateRender(e);const s=t.aggregate.toLowerCase();return"count"===s?String(e):"number"==typeof e?"avg"===s||"average"===s?e.toLocaleString(void 0,{minimumFractionDigits:0,maximumFractionDigits:2}):e.toLocaleString():String(e)}createHeaderSummaryRow(e){const t=document.createElement("div");t.className="div-table-row summary-row header-summary";const s=this.getCompositeColumns(),i=this.getAggregationDataSet(e);let o="";if(this.showCheckboxes&&(o="40px "),s.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":o+="80px ";break;case"fixed-medium":o+="120px ";break;case"flexible-small":default:o+="1fr ";break;case"flexible-medium":o+="2fr ";break;case"flexible-large":o+="3fr "}}),t.style.gridTemplateColumns=o.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",t.appendChild(e)}return s.forEach(e=>{const s=document.createElement("div");if(s.className="div-table-cell summary-cell",e.compositeName)s.classList.add("composite-cell"),e.columns.forEach((e,t)=>{const o=document.createElement("div");if(o.className="composite-sub-cell",e.aggregate){const t=this.calculateAggregate(e,i),s=this.formatAggregateValue(t,e);o.innerHTML=s,o.classList.add("aggregate-value")}s.appendChild(o)});else{const t=e.columns[0];if(t.aggregate){const e=this.calculateAggregate(t,i),o=this.formatAggregateValue(e,t);s.innerHTML=o,s.classList.add("aggregate-value")}}t.appendChild(s)}),t}createGroupSummaryRow(e){const t=document.createElement("div");t.className="div-table-row summary-row group-summary",t.dataset.groupKey=e.key;const s=this.getCompositeColumns();let i=e.items;this.selectedRows.size>0&&(i=e.items.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));let o="";if(this.showCheckboxes&&(o="40px "),s.forEach(e=>{switch((e.columns[0].responsive||{}).size){case"fixed-narrow":o+="80px ";break;case"fixed-medium":o+="120px ";break;case"flexible-small":default:o+="1fr ";break;case"flexible-medium":o+="2fr ";break;case"flexible-large":o+="3fr "}}),t.style.gridTemplateColumns=o.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",t.appendChild(e)}return s.forEach(e=>{const s=document.createElement("div");if(s.className="div-table-cell summary-cell",e.compositeName)s.classList.add("composite-cell"),e.columns.forEach(e=>{const t=document.createElement("div");if(t.className="composite-sub-cell",e.aggregate){const s=this.calculateAggregate(e,i),o=this.formatAggregateValue(s,e);t.innerHTML=o,t.classList.add("aggregate-value")}s.appendChild(t)});else{const t=e.columns[0];if(t.aggregate){const e=this.calculateAggregate(t,i),o=this.formatAggregateValue(e,t);s.innerHTML=o,s.classList.add("aggregate-value")}}t.appendChild(s)}),t}createHeaderSummaryRowWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout(),i=this.getAggregationDataSet(e),o=document.createElement("div");o.className="div-table-row div-table-fixed-row summary-row header-summary";let a="";if(this.showCheckboxes&&(a="40px "),t.forEach(e=>{a+=this.getColumnGridSize(e)+" "}),o.style.gridTemplateColumns=a.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",o.appendChild(e)}t.forEach(e=>{const t=this.createSummaryCell(e,i);o.appendChild(t)});const n=document.createElement("div");n.className="div-table-row summary-row header-summary";let r="";return s.forEach(e=>{r+=this.getColumnGridSize(e)+" "}),n.style.gridTemplateColumns=r.trim(),s.forEach(e=>{const t=this.createSummaryCell(e,i);n.appendChild(t)}),{fixedSummary:o,scrollSummary:n}}createGroupSummaryRowWithFixedColumns(e){const{fixedColumns:t,scrollColumns:s}=this.splitColumnsForFixedLayout();let i=e.items;this.selectedRows.size>0&&(i=e.items.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));const o=document.createElement("div");o.className="div-table-row div-table-fixed-row summary-row group-summary",o.dataset.groupKey=e.key;let a="";if(this.showCheckboxes&&(a="40px "),t.forEach(e=>{a+=this.getColumnGridSize(e)+" "}),o.style.gridTemplateColumns=a.trim(),this.showCheckboxes){const e=document.createElement("div");e.className="div-table-cell checkbox-column summary-cell",o.appendChild(e)}t.forEach(e=>{const t=this.createSummaryCell(e,i);o.appendChild(t)});const n=document.createElement("div");n.className="div-table-row summary-row group-summary",n.dataset.groupKey=e.key;let r="";return s.forEach(e=>{r+=this.getColumnGridSize(e)+" "}),n.style.gridTemplateColumns=r.trim(),s.forEach(e=>{const t=this.createSummaryCell(e,i);n.appendChild(t)}),{fixedSummary:o,scrollSummary:n}}createSummaryCell(e,t){const s=document.createElement("div");if(s.className="div-table-cell summary-cell",e.compositeName)s.classList.add("composite-cell"),e.columns.forEach(e=>{const i=document.createElement("div");if(i.className="composite-sub-cell",e.aggregate){const s=this.calculateAggregate(e,t),o=this.formatAggregateValue(s,e);i.innerHTML=o,i.classList.add("aggregate-value"),e.align&&(i.style.textAlign=e.align)}s.appendChild(i)});else{const i=e.columns[0];if(i.align&&(s.style.textAlign=i.align,s.style.justifyContent="right"===i.align?"flex-end":"center"===i.align?"center":"flex-start"),i.aggregate){const e=this.calculateAggregate(i,t),o=this.formatAggregateValue(e,i);s.innerHTML=o,s.classList.add("aggregate-value")}}return s}updateSummaryRows(){if(!this.hasAggregateColumns())return;if(!this.showHeaderSummary&&!this.showGroupSummary)return;let e=this.filteredData;this.showOnlySelected&&this.selectedRows.size>0&&(e=this.filteredData.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));const t=this.getAggregationDataSet(e);this.showHeaderSummary&&this.updateHeaderSummaryValues(t),this.showGroupSummary&&this.groupByField&&this.updateGroupSummaryValues(e)}updateHeaderSummaryValues(e){(this.fixedColumns>0?[this.fixedBodyContainer?.querySelector(".header-summary"),this.scrollBodyContainer?.querySelector(".header-summary")].filter(Boolean):[this.bodyContainer?.querySelector(".header-summary")].filter(Boolean)).forEach(t=>{const s=t.querySelectorAll(".aggregate-value"),i=this.getAggregateColumns();s.forEach((t,s)=>{if(i[s]){const o=i[s],a=this.calculateAggregate(o,e),n=this.formatAggregateValue(a,o);t.innerHTML=n}})})}updateGroupSummaryValues(e){this.groupData(e).forEach(e=>{let t=e.items;this.selectedRows.size>0&&(t=e.items.filter(e=>{const t=String(e[this.primaryKeyField]);return this.selectedRows.has(t)}));(this.fixedColumns>0?[this.fixedBodyContainer?.querySelector(`.group-summary[data-group-key="${e.key}"]`),this.scrollBodyContainer?.querySelector(`.group-summary[data-group-key="${e.key}"]`)].filter(Boolean):[this.bodyContainer?.querySelector(`.group-summary[data-group-key="${e.key}"]`)].filter(Boolean)).forEach(e=>{const s=e.querySelectorAll(".aggregate-value"),i=this.getAggregateColumns();s.forEach((e,s)=>{if(i[s]){const o=i[s],a=this.calculateAggregate(o,t),n=this.formatAggregateValue(a,o);e.innerHTML=n}})})})}}class s{constructor(e=[],t="id"){this.objects=e,this.primaryKeyField=t}setObjects(e){this.objects=e}filterObjects(e){if(!e.trim())return this.objects.map(e=>e[this.primaryKeyField]);if(!/[=!<>()]|(\bAND\b|\bOR\b|\bIN\b)/i.test(e))return this.searchObjects(e);const t=[];for(const s of this.objects)try{this.evaluateExpression(s,e)&&t.push(s[this.primaryKeyField])}catch(e){throw new Error(`Query error: ${e.message}`)}return t}searchObjects(e){const t=e.trim().toLowerCase().split(/\s+/).filter(Boolean);if(0===t.length)return this.objects.map(e=>e[this.primaryKeyField]);const s=[];for(const e of this.objects){const i=Object.values(e).map(e=>null==e?"":String(e).toLowerCase()).join(" ");t.every(e=>i.includes(e))&&s.push(e[this.primaryKeyField])}return s}evaluateExpression(e,t){if(!t.trim())return!0;for(t=t.replace(/\s+/g," ").trim();/\(([^()]+)\)/.test(t);)t=t.replace(/\(([^()]+)\)/g,(t,s)=>this.processGroup(e,s)?"true":"false");return this.processGroup(e,t)}processGroup(e,t){return t.split(/\s+OR\s+/).some(t=>t.split(/\s+AND\s+/).every(t=>{const s=t.trim().toLowerCase();if("false"===s)return!1;if("true"===s)return!0;try{const s=this.parseCondition(t);return this.applyCondition(e,s)}catch{throw new Error(`Invalid condition: ${t}`)}}))}parseCondition(e){const t=e.match(/(\w+)\s+IN\s+\[([^\]]+)\]/);if(t){const[,e,s]=t;return{field:e,operator:"IN",value:s.split(",").map(e=>{const t=e.trim().replace(/"/g,"");return"NULL"===t?null:t})}}const s=e.match(/(\w+)\s*(=|!=|>=|<=|>|<)\s*(.+)/i);if(s){const[,e,t,i]=s;let o=i.trim();return o.startsWith('"')&&o.endsWith('"')?o=o.slice(1,-1):"NULL"===o?o=null:"true"===o.toLowerCase()?o=!0:"false"===o.toLowerCase()?o=!1:isNaN(o)||""===o||(o=parseFloat(o)),{field:e,operator:t,value:o}}throw new Error(`Invalid condition: ${e}`)}applyCondition(e,{field:t,operator:s,value:i}){const o=t in e?e[t]:null,a=e=>null==e||""===e;switch(s){case"=":return null===i?a(o):!a(o)&&(Array.isArray(o)?o.includes(i):o==i);case"!=":return null===i?!a(o):!!a(o)||(Array.isArray(o)?!o.includes(i):o!=i);case">":return!a(o)&&(!Array.isArray(o)&&o>parseFloat(i));case"<":return!a(o)&&(!Array.isArray(o)&&o<parseFloat(i));case">=":return!a(o)&&(!Array.isArray(o)&&o>=parseFloat(i));case"<=":return!a(o)&&(!Array.isArray(o)&&o<=parseFloat(i));case"IN":return i.includes(null)?a(o)||i.includes(o):!a(o)&&(Array.isArray(o)?o.some(e=>i.includes(e)):i.includes(o));default:return!1}}}e.exports&&(e.exports={DivTable:t,QueryEngine:s})},853:(e,t,s)=>{"use strict";s.r(t)}},t={};function s(i){var o=t[i];if(void 0!==o)return o.exports;var a=t[i]={exports:{}};return e[i](a,a.exports,s),a.exports}return s.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},s(430),s(853)})());
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vii7/div-table-widget",
3
- "version": "1.1.1",
3
+ "version": "1.2.0",
4
4
  "description": "A modern table widget built with CSS Grid and Flexbox, featuring Monaco Editor integration for advanced query capabilities",
5
5
  "main": "dist/divtable.min.js",
6
6
  "module": "src/div-table.js",
@@ -27,7 +27,9 @@
27
27
  "virtual-scrolling",
28
28
  "pagination",
29
29
  "sorting",
30
- "grouping"
30
+ "grouping",
31
+ "theming",
32
+ "dark-mode"
31
33
  ],
32
34
  "author": "VIIgit",
33
35
  "license": "Apache-2.0",
@@ -0,0 +1,104 @@
1
+ /**
2
+ * DivTable Widget - Dark Theme
3
+ * Include this file after div-table.css to enable dark mode.
4
+ * Activate by adding class="theme-dark" to a parent element (e.g., <body>).
5
+ *
6
+ * Usage:
7
+ * <link rel="stylesheet" href="div-table.css">
8
+ * <link rel="stylesheet" href="div-table-theme-dark.css">
9
+ * <body class="theme-dark">...</body>
10
+ *
11
+ * Or toggle dynamically:
12
+ * document.body.classList.toggle('theme-dark');
13
+ */
14
+
15
+ /* Dark theme variables - activated via .theme-dark or .dark class */
16
+ .theme-dark,
17
+ .dark {
18
+ /* === Primary/Accent Colors === */
19
+ --dt-primary: hsl(38, 100%, 50%);
20
+ --dt-primary-hover: hsl(38, 100%, 40%);
21
+ --dt-primary-light: hsla(38, 100%, 50%, 0.12);
22
+ --dt-primary-lighter: hsla(38, 100%, 50%, 0.07);
23
+ --dt-focus-ring: hsla(38, 100%, 50%, 0.18);
24
+
25
+ /* === Background Colors === */
26
+ --dt-bg-base: hsl(0, 0%, 9%);
27
+ --dt-bg-light: hsl(0, 0%, 14%);
28
+ --dt-bg-hover: hsl(0, 0%, 18%);
29
+ --dt-bg-selected: hsla(38, 100%, 50%, 0.12);
30
+ --dt-bg-header: hsl(0, 0%, 12%);
31
+ --dt-bg-summary: hsl(0, 0%, 12%);
32
+ --dt-bg-disabled: hsl(0, 0%, 20%);
33
+
34
+ /* === Border Colors === */
35
+ --dt-border-light: hsl(0, 0%, 22%);
36
+ --dt-border-medium: hsl(0, 0%, 20%);
37
+ --dt-border-dark: hsl(0, 0%, 18%);
38
+ --dt-border-row: hsl(0, 0%, 22%);
39
+ --dt-border-focus: hsl(38, 100%, 50%);
40
+ --dt-border-hover: hsl(38, 100%, 50%);
41
+
42
+ /* === Text Colors === */
43
+ --dt-text-primary: hsl(0, 0%, 98%);
44
+ --dt-text-secondary: hsl(0, 0%, 90%);
45
+ --dt-text-muted: hsl(0, 0%, 60%);
46
+ --dt-text-light: hsl(0, 0%, 90%);
47
+ --dt-text-disabled: hsl(0, 0%, 55%);
48
+ --dt-text-inverse: hsl(0, 0%, 9%);
49
+
50
+ /* === Shadow === */
51
+ --dt-shadow: rgba(0, 0, 0, 0.4);
52
+ --dt-shadow-medium: rgba(0, 0, 0, 0.5);
53
+ --dt-shadow-heavy: rgba(0, 0, 0, 0.6);
54
+
55
+ /* === Error State === */
56
+ --dt-error: hsl(0, 84%, 60%);
57
+ --dt-error-light: hsla(0, 84%, 60%, 0.6);
58
+ --dt-error-hover: hsl(0, 62%, 30%);
59
+ --dt-error-active: hsl(0, 62%, 20%);
60
+ --dt-error-bg: hsl(0, 30%, 14%);
61
+ --dt-error-border: hsl(0, 84%, 70%);
62
+ --dt-error-text: hsl(0, 84%, 65%);
63
+ --dt-error-border-hover: hsla(0, 84%, 60%, 0.6);
64
+ --dt-error-focus-ring: hsla(0, 84%, 60%, 0.25);
65
+
66
+ /* === Success State === */
67
+ --dt-success: hsl(143, 72%, 50%);
68
+ --dt-success-bg: hsl(143, 25%, 15%);
69
+ --dt-success-bg-hover: hsl(143, 25%, 22%);
70
+
71
+ /* === Warning State === */
72
+ --dt-warning: hsl(43, 100%, 50%);
73
+ --dt-warning-bg: hsl(43, 25%, 15%);
74
+ --dt-warning-bg-hover: hsl(43, 25%, 22%);
75
+
76
+ /* === Info State === */
77
+ --dt-info: hsl(198, 89%, 60%);
78
+ --dt-info-bg: hsl(198, 25%, 15%);
79
+ --dt-info-bg-hover: hsl(198, 25%, 22%);
80
+
81
+ /* === Button Colors === */
82
+ --dt-button-bg: hsl(0, 0%, 14%);
83
+ --dt-button-bg-hover: hsl(0, 0%, 18%);
84
+ --dt-button-text: hsl(0, 0%, 98%);
85
+
86
+ /* === Scrollbar Colors === */
87
+ --dt-scrollbar-track: hsl(0, 0%, 14%);
88
+ --dt-scrollbar-thumb: hsl(0, 0%, 22%);
89
+ --dt-scrollbar-thumb-hover: hsl(0, 0%, 28%);
90
+
91
+ /* === Spinner Colors === */
92
+ --dt-spinner-track: hsl(0, 0%, 20%);
93
+ --dt-spinner-active: hsl(0, 0%, 90%);
94
+
95
+ /* === Skeleton Loading === */
96
+ --dt-skeleton-base: hsl(0, 0%, 14%);
97
+ --dt-skeleton-shine: hsl(0, 0%, 20%);
98
+
99
+ /* === Group Row === */
100
+ --dt-group-bg: hsla(0, 0%, 14%, 0.5);
101
+
102
+ /* === Summary Row === */
103
+ --dt-summary-border: hsl(0, 0%, 18%);
104
+ }
package/src/div-table.css CHANGED
@@ -99,6 +99,7 @@
99
99
  /* Table widget container */
100
100
  .div-table-widget {
101
101
  width: 100%;
102
+ height: 100%;
102
103
  box-sizing: border-box;
103
104
  background: var(--dt-bg-base);
104
105
  border-radius: 8px;
@@ -572,6 +573,7 @@
572
573
 
573
574
  /* Row styling - CSS Grid based */
574
575
  .div-table-row {
576
+ color: var(--dt-text-primary);
575
577
  display: grid;
576
578
  min-height: 40px;
577
579
  align-items: stretch;
@@ -954,6 +956,11 @@ input[type="checkbox"]:indeterminate::after {
954
956
  margin-bottom: 4px;
955
957
  }
956
958
 
959
+ /* Legacy composite header styling (for subLabel pattern) */
960
+ .composite-main-header {
961
+ color: var(--dt-text-primary);
962
+ }
963
+
957
964
  .composite-sub-header:hover {
958
965
  background-color: var(--dt-bg-disabled);
959
966
  }
package/src/div-table.js CHANGED
@@ -1712,12 +1712,21 @@ class DivTable {
1712
1712
  fixedRow.style.height = '';
1713
1713
  scrollRow.style.height = '';
1714
1714
 
1715
- // Get natural heights
1716
- const fixedHeight = fixedRow.offsetHeight;
1717
- const scrollHeight = scrollRow.offsetHeight;
1715
+ // Get natural heights including any cell content overflow
1716
+ const fixedHeight = Math.max(fixedRow.offsetHeight, fixedRow.scrollHeight);
1717
+ const scrollHeight = Math.max(scrollRow.offsetHeight, scrollRow.scrollHeight);
1718
+
1719
+ // Also check individual cell heights
1720
+ let maxCellHeight = 0;
1721
+ fixedRow.querySelectorAll('.div-table-cell').forEach(cell => {
1722
+ maxCellHeight = Math.max(maxCellHeight, cell.offsetHeight, cell.scrollHeight);
1723
+ });
1724
+ scrollRow.querySelectorAll('.div-table-cell').forEach(cell => {
1725
+ maxCellHeight = Math.max(maxCellHeight, cell.offsetHeight, cell.scrollHeight);
1726
+ });
1718
1727
 
1719
1728
  // Set both to the maximum height
1720
- const maxHeight = Math.max(fixedHeight, scrollHeight);
1729
+ const maxHeight = Math.max(fixedHeight, scrollHeight, maxCellHeight);
1721
1730
  if (maxHeight > 0) {
1722
1731
  fixedRow.style.height = `${maxHeight}px`;
1723
1732
  scrollRow.style.height = `${maxHeight}px`;
@@ -1893,7 +1902,6 @@ class DivTable {
1893
1902
  mainLabel.className = 'composite-main-header';
1894
1903
  mainLabel.innerHTML = col.label || col.field;
1895
1904
  mainLabel.style.fontWeight = '600';
1896
- mainLabel.style.color = '#374151';
1897
1905
  mainLabel.style.textAlign = 'left';
1898
1906
  mainLabel.style.flex = '1';
1899
1907
  mainLabelContainer.appendChild(mainLabel);
@@ -1960,7 +1968,6 @@ class DivTable {
1960
1968
 
1961
1969
  const subLabel = document.createElement('span');
1962
1970
  subLabel.innerHTML = col.subLabel;
1963
- subLabel.style.color = '#6b7280';
1964
1971
  subLabel.style.textAlign = 'left';
1965
1972
  subLabel.style.flex = '1';
1966
1973
  subLabelContainer.appendChild(subLabel);
@@ -1980,9 +1987,9 @@ class DivTable {
1980
1987
 
1981
1988
  subLabelContainer.appendChild(subSortIndicator);
1982
1989
 
1983
- // Add hover effect
1990
+ // Add hover effect - use CSS variable for theming support
1984
1991
  subLabelContainer.addEventListener('mouseenter', () => {
1985
- subLabelContainer.style.backgroundColor = '#f3f4f6';
1992
+ subLabelContainer.style.backgroundColor = 'var(--dt-bg-disabled)';
1986
1993
  });
1987
1994
  subLabelContainer.addEventListener('mouseleave', () => {
1988
1995
  subLabelContainer.style.backgroundColor = 'transparent';
@@ -2765,9 +2772,6 @@ class DivTable {
2765
2772
 
2766
2773
  if (composite.compositeName) {
2767
2774
  cell.classList.add('composite-cell');
2768
- cell.style.display = 'flex';
2769
- cell.style.flexDirection = 'column';
2770
- cell.style.gap = '4px';
2771
2775
 
2772
2776
  composite.columns.forEach((col, index) => {
2773
2777
  const subCell = document.createElement('div');
@@ -2856,22 +2860,6 @@ class DivTable {
2856
2860
  // Mark as populated
2857
2861
  row.dataset.populated = 'true';
2858
2862
 
2859
- // Measure actual height and set it explicitly to prevent bouncing on re-renders
2860
- // Use requestAnimationFrame to ensure DOM has updated
2861
- requestAnimationFrame(() => {
2862
- const actualHeight = row.offsetHeight;
2863
- if (actualHeight > 0) {
2864
- // Set explicit height to prevent layout recalculation bouncing
2865
- row.style.minHeight = `${actualHeight}px`;
2866
- row.style.height = `${actualHeight}px`;
2867
-
2868
- // Update estimate for future unpopulated rows
2869
- if (actualHeight > this.estimatedRowHeight) {
2870
- this.estimatedRowHeight = actualHeight;
2871
- }
2872
- }
2873
- });
2874
-
2875
2863
  // Update tab indexes after population
2876
2864
  this.updateTabIndexes();
2877
2865
  }
@@ -2981,32 +2969,28 @@ class DivTable {
2981
2969
  // Use double requestAnimationFrame to ensure layout is fully complete
2982
2970
  requestAnimationFrame(() => {
2983
2971
  requestAnimationFrame(() => {
2984
- // Get natural heights after cell content is fully rendered
2985
- // Temporarily remove any height constraints to get true natural height
2986
- const prevFixedHeight = fixedRow.style.height;
2987
- const prevScrollHeight = scrollRow.style.height;
2988
- const prevFixedMinHeight = fixedRow.style.minHeight;
2989
- const prevScrollMinHeight = scrollRow.style.minHeight;
2990
-
2972
+ // Reset any fixed heights to get natural content height
2991
2973
  fixedRow.style.height = '';
2992
2974
  scrollRow.style.height = '';
2993
- fixedRow.style.minHeight = '40px';
2994
- scrollRow.style.minHeight = '40px';
2995
2975
 
2996
- // Force layout recalculation
2997
- const fixedHeight = fixedRow.offsetHeight;
2998
- const scrollHeight = scrollRow.offsetHeight;
2976
+ // Get the maximum height from both rows, including any cell content
2977
+ // Use scrollHeight to capture content that might overflow
2978
+ const fixedHeight = Math.max(fixedRow.offsetHeight, fixedRow.scrollHeight);
2979
+ const scrollHeight = Math.max(scrollRow.offsetHeight, scrollRow.scrollHeight);
2999
2980
 
3000
- // Set both to the maximum height to keep rows in sync
3001
- const maxHeight = Math.max(fixedHeight, scrollHeight, 40); // Ensure minimum 44px
3002
- fixedRow.style.minHeight = `${maxHeight}px`;
3003
- fixedRow.style.height = `${maxHeight}px`;
3004
- scrollRow.style.minHeight = `${maxHeight}px`;
3005
- scrollRow.style.height = `${maxHeight}px`;
2981
+ // Also check individual cell heights
2982
+ let maxCellHeight = 0;
2983
+ fixedRow.querySelectorAll('.div-table-cell').forEach(cell => {
2984
+ maxCellHeight = Math.max(maxCellHeight, cell.offsetHeight, cell.scrollHeight);
2985
+ });
2986
+ scrollRow.querySelectorAll('.div-table-cell').forEach(cell => {
2987
+ maxCellHeight = Math.max(maxCellHeight, cell.offsetHeight, cell.scrollHeight);
2988
+ });
3006
2989
 
3007
- // Update estimate for future unpopulated rows
3008
- if (maxHeight > this.estimatedRowHeight) {
3009
- this.estimatedRowHeight = maxHeight;
2990
+ const maxHeight = Math.max(fixedHeight, scrollHeight, maxCellHeight);
2991
+ if (maxHeight > 0) {
2992
+ fixedRow.style.height = `${maxHeight}px`;
2993
+ scrollRow.style.height = `${maxHeight}px`;
3010
2994
  }
3011
2995
  });
3012
2996
  });
@@ -3206,9 +3190,6 @@ class DivTable {
3206
3190
  if (composite.compositeName) {
3207
3191
  // Composite cell with multiple columns stacked vertically
3208
3192
  cell.classList.add('composite-cell');
3209
- cell.style.display = 'flex';
3210
- cell.style.flexDirection = 'column';
3211
- cell.style.gap = '4px';
3212
3193
 
3213
3194
  composite.columns.forEach((col, index) => {
3214
3195
  const subCell = document.createElement('div');
@@ -3586,9 +3567,6 @@ class DivTable {
3586
3567
  if (composite.compositeName) {
3587
3568
  // Composite cell with multiple columns stacked vertically
3588
3569
  cell.classList.add('composite-cell');
3589
- cell.style.display = 'flex';
3590
- cell.style.flexDirection = 'column';
3591
- cell.style.gap = '4px';
3592
3570
 
3593
3571
  composite.columns.forEach((col, index) => {
3594
3572
  const subCell = document.createElement('div');