@toolbox-web/grid 2.0.0-rc.2 → 2.0.0-rc.4

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.
Files changed (68) hide show
  1. package/all.js +2 -2
  2. package/all.js.map +1 -1
  3. package/index.js +1 -1
  4. package/index.js.map +1 -1
  5. package/lib/core/internal/diagnostics.d.ts +9 -1
  6. package/lib/features/registry.js.map +1 -1
  7. package/lib/plugins/clipboard/index.js.map +1 -1
  8. package/lib/plugins/column-virtualization/index.js.map +1 -1
  9. package/lib/plugins/context-menu/index.js.map +1 -1
  10. package/lib/plugins/editing/index.js.map +1 -1
  11. package/lib/plugins/export/index.js.map +1 -1
  12. package/lib/plugins/filtering/FilteringPlugin.d.ts +3 -1
  13. package/lib/plugins/filtering/index.js +1 -1
  14. package/lib/plugins/filtering/index.js.map +1 -1
  15. package/lib/plugins/grouping-columns/index.js.map +1 -1
  16. package/lib/plugins/grouping-rows/GroupingRowsPlugin.d.ts +14 -22
  17. package/lib/plugins/grouping-rows/index.js +2 -2
  18. package/lib/plugins/grouping-rows/index.js.map +1 -1
  19. package/lib/plugins/grouping-rows/types.d.ts +7 -35
  20. package/lib/plugins/master-detail/MasterDetailPlugin.d.ts +30 -0
  21. package/lib/plugins/master-detail/index.js +1 -1
  22. package/lib/plugins/master-detail/index.js.map +1 -1
  23. package/lib/plugins/multi-sort/index.js.map +1 -1
  24. package/lib/plugins/pinned-columns/index.js.map +1 -1
  25. package/lib/plugins/pinned-rows/index.js.map +1 -1
  26. package/lib/plugins/pivot/index.js.map +1 -1
  27. package/lib/plugins/print/index.js.map +1 -1
  28. package/lib/plugins/reorder-columns/index.js.map +1 -1
  29. package/lib/plugins/reorder-rows/index.js.map +1 -1
  30. package/lib/plugins/responsive/index.js.map +1 -1
  31. package/lib/plugins/selection/index.js +1 -1
  32. package/lib/plugins/selection/index.js.map +1 -1
  33. package/lib/plugins/server-side/ServerSidePlugin.d.ts +48 -14
  34. package/lib/plugins/server-side/datasource-types.d.ts +189 -0
  35. package/lib/plugins/server-side/datasource.d.ts +5 -5
  36. package/lib/plugins/server-side/index.d.ts +1 -1
  37. package/lib/plugins/server-side/index.js +1 -1
  38. package/lib/plugins/server-side/index.js.map +1 -1
  39. package/lib/plugins/server-side/types.d.ts +8 -82
  40. package/lib/plugins/tooltip/index.js +1 -1
  41. package/lib/plugins/tooltip/index.js.map +1 -1
  42. package/lib/plugins/tree/TreePlugin.d.ts +10 -4
  43. package/lib/plugins/tree/index.js +1 -1
  44. package/lib/plugins/tree/index.js.map +1 -1
  45. package/lib/plugins/tree/tree-datasource.d.ts +13 -0
  46. package/lib/plugins/tree/types.d.ts +13 -0
  47. package/lib/plugins/undo-redo/index.js.map +1 -1
  48. package/lib/plugins/visibility/index.js.map +1 -1
  49. package/package.json +1 -1
  50. package/public.d.ts +3 -0
  51. package/umd/grid.all.umd.js +1 -1
  52. package/umd/grid.all.umd.js.map +1 -1
  53. package/umd/grid.umd.js +1 -1
  54. package/umd/grid.umd.js.map +1 -1
  55. package/umd/plugins/filtering.umd.js +1 -1
  56. package/umd/plugins/filtering.umd.js.map +1 -1
  57. package/umd/plugins/grouping-rows.umd.js +1 -1
  58. package/umd/plugins/grouping-rows.umd.js.map +1 -1
  59. package/umd/plugins/master-detail.umd.js +1 -1
  60. package/umd/plugins/master-detail.umd.js.map +1 -1
  61. package/umd/plugins/selection.umd.js +1 -1
  62. package/umd/plugins/selection.umd.js.map +1 -1
  63. package/umd/plugins/server-side.umd.js +1 -1
  64. package/umd/plugins/server-side.umd.js.map +1 -1
  65. package/umd/plugins/tooltip.umd.js +1 -1
  66. package/umd/plugins/tooltip.umd.js.map +1 -1
  67. package/umd/plugins/tree.umd.js +1 -1
  68. package/umd/plugins/tree.umd.js.map +1 -1
@@ -42,14 +42,14 @@ export interface GroupDefinition {
42
42
  /** Server-computed aggregate values keyed by field name. */
43
43
  aggregates?: Record<string, unknown>;
44
44
  }
45
- /** Detail payload for `group-expand` event. */
45
+ /** Detail payload for `group-expand` event (pre-defined group mode). */
46
46
  export interface GroupExpandDetail {
47
47
  /** The key of the group being expanded. */
48
48
  groupKey: string;
49
49
  /** The full path of group keys from root to this group. */
50
50
  groupPath: string[];
51
51
  }
52
- /** Detail payload for `group-collapse` event. */
52
+ /** Detail payload for `group-collapse` event (pre-defined group mode). */
53
53
  export interface GroupCollapseDetail {
54
54
  /** The key of the group being collapsed. */
55
55
  groupKey: string;
@@ -79,12 +79,8 @@ export interface GroupingRowsConfig {
79
79
  * When provided, the plugin renders these groups as collapsible headers
80
80
  * instead of analyzing row data with `groupOn`.
81
81
  *
82
- * Accepts:
83
- * - A static `GroupDefinition[]` array
84
- * - An async callback `() => Promise<GroupDefinition[]>` that fetches groups on attach
85
- *
86
- * When combined with {@link GroupingRowsConfig.rows | rows}, the plugin handles
87
- * the full lifecycle automatically — loading indicator, data fetch, and render.
82
+ * When combined with `ServerSidePlugin`, group definitions are delivered
83
+ * automatically via `datasource:data` events and this config is not needed.
88
84
  *
89
85
  * @example Static groups
90
86
  * ```typescript
@@ -95,34 +91,8 @@ export interface GroupingRowsConfig {
95
91
  * ],
96
92
  * });
97
93
  * ```
98
- *
99
- * @example Async groups with lazy-loaded rows
100
- * ```typescript
101
- * new GroupingRowsPlugin({
102
- * groups: () => fetch('/api/groups').then(r => r.json()),
103
- * rows: (group) => fetch(`/api/groups/${group.key}/rows`).then(r => r.json()),
104
- * });
105
- * ```
106
- */
107
- groups?: GroupDefinition[] | (() => Promise<GroupDefinition[]>);
108
- /**
109
- * Callback to lazily load rows for an expanded group.
110
- *
111
- * When a user expands a group, the plugin calls this callback with the
112
- * group definition. The plugin manages the loading indicator automatically.
113
- *
114
- * If not provided, use the imperative {@link GroupingRowsPlugin.setGroupRows | setGroupRows()}
115
- * API and listen for `group-expand` events instead.
116
- *
117
- * @example
118
- * ```typescript
119
- * new GroupingRowsPlugin({
120
- * groups: () => fetch('/api/groups').then(r => r.json()),
121
- * rows: (group) => fetch(`/api/groups/${group.key}/rows`).then(r => r.json()),
122
- * });
123
- * ```
124
94
  */
125
- rows?: (group: GroupDefinition) => Promise<unknown[]>;
95
+ groups?: GroupDefinition[];
126
96
  /**
127
97
  * Default expanded state for group rows.
128
98
  * - `true`: Expand all groups initially
@@ -273,6 +243,8 @@ export interface GroupToggleDetail {
273
243
  value: any;
274
244
  /** Depth level */
275
245
  depth: number;
246
+ /** All currently expanded keys after the operation */
247
+ expandedKeys?: string[];
276
248
  }
277
249
  declare module '../../core/types' {
278
250
  interface DataGridEventMap {
@@ -71,6 +71,15 @@ export declare class MasterDetailPlugin extends BaseGridPlugin<MasterDetailConfi
71
71
  readonly name = "masterDetail";
72
72
  /** @internal */
73
73
  readonly styles: string;
74
+ /**
75
+ * Optional dependency on ServerSide for async detail data.
76
+ * When loaded, MasterDetail can fetch detail data via `datasource:fetch-children`.
77
+ */
78
+ static readonly dependencies: {
79
+ name: string;
80
+ required: boolean;
81
+ reason: string;
82
+ }[];
74
83
  /** @internal */
75
84
  protected get defaultConfig(): Partial<MasterDetailConfig>;
76
85
  /**
@@ -125,6 +134,10 @@ export declare class MasterDetailPlugin extends BaseGridPlugin<MasterDetailConfi
125
134
  /** Rows that were just expanded by user action and should animate.
126
135
  * Prevents re-animation when rows scroll back into the virtual window. */
127
136
  private rowsToAnimate;
137
+ /** Rows currently waiting for datasource:children response. */
138
+ private loadingDetails;
139
+ /** Child rows received via datasource:children, keyed by parent row reference. */
140
+ private detailDataMap;
128
141
  /** Default height for detail rows when not configured */
129
142
  private static readonly DEFAULT_DETAIL_HEIGHT;
130
143
  /**
@@ -212,6 +225,23 @@ export declare class MasterDetailPlugin extends BaseGridPlugin<MasterDetailConfi
212
225
  * @returns The detail HTMLElement or undefined
213
226
  */
214
227
  getDetailElement(rowIndex: number): HTMLElement | undefined;
228
+ /**
229
+ * Get async detail data fetched via `ServerSidePlugin` for a specific row.
230
+ *
231
+ * Returns the child rows received from `datasource:children` after a
232
+ * `datasource:fetch-children` query was fired on expand. Returns `undefined`
233
+ * when ServerSide is not loaded or data has not arrived yet.
234
+ *
235
+ * @param rowIndex - Index of the row
236
+ * @returns Array of child rows or undefined
237
+ */
238
+ getDetailData(rowIndex: number): unknown[] | undefined;
239
+ /**
240
+ * Check if detail data is currently being loaded for a row.
241
+ * @param rowIndex - Index of the row
242
+ * @returns Whether the detail is loading
243
+ */
244
+ isDetailLoading(rowIndex: number): boolean;
215
245
  /**
216
246
  * Re-parse light DOM to refresh the detail renderer.
217
247
  * Call this after framework templates are registered (e.g., Angular ngAfterContentInit).
@@ -1,2 +1,2 @@
1
- const e=/{{\s*([^}]+)\s*}}/g,t="__DG_EMPTY__",i=/^[\w$. '?+\-*/%:()!<>=,&|]+$/,n=["__otorp__","__retteGenifed__","__retteSenifed__","rotcurtsnoc","wodniw","sihTlabolg","labolg","ssecorp","noitcnuF","tropmi","lave","tcelfeR","yxorP","rorrE","stnemugra","tnemucod","noitacol","eikooc","egarotSlacol","egarotSnoisses","BDdexedni","hctef","tseuqeRpttHLMX","tekcoSbeW","rekroW","rekroWderahS","rekroWecivreS","renepo","tnerap","pot","semarf","fles"].map(e=>e.split("").reverse().join("")),r=new RegExp(`__(proto|defineGetter|defineSetter)|${n.slice(3).join("|")}|this\\b`),s=/* @__PURE__ */new Set(["script","iframe","object","embed","form","input","button","textarea","select","link","meta","base","style","template","slot","portal","frame","frameset","applet","noscript","noembed","plaintext","xmp","listing"]),o=/^on\w+$/i,a=/* @__PURE__ */new Set(["href","src","action","formaction","data","srcdoc","xlink:href","poster","srcset"]),l=/^\s*(javascript|vbscript|data|blob):/i;function d(e){if(!e||"string"!=typeof e)return"";if(-1===e.indexOf("<"))return e;const t=document.createElement("template");return t.innerHTML=e,function(e){const t=[],i=e.querySelectorAll("*");for(const n of i){const e=n.tagName.toLowerCase();if(s.has(e)){t.push(n);continue}if("svg"===e||"http://www.w3.org/2000/svg"===n.namespaceURI){if(Array.from(n.attributes).some(e=>o.test(e.name)||"href"===e.name||"xlink:href"===e.name)){t.push(n);continue}}const i=[];for(const t of n.attributes){const e=t.name.toLowerCase();o.test(e)?i.push(t.name):(a.has(e)&&l.test(t.value)||"style"===e&&/expression\s*\(|javascript:|behavior\s*:/i.test(t.value))&&i.push(t.name)}i.forEach(e=>n.removeAttribute(e))}t.forEach(e=>e.remove())}(t.content),t.innerHTML}function c(e,t){const i=function(e){const t=[];let i=0;for(;i<e.length;){const n=e[i];if(" "!==n){if(n>="0"&&n<="9"||"."===n&&i+1<e.length&&e[i+1]>="0"&&e[i+1]<="9"){const n=i;for(;i<e.length&&(e[i]>="0"&&e[i]<="9"||"."===e[i]);)i++;t.push({type:"num",v:Number(e.slice(n,i))});continue}if("'"===n){let n="";for(i++;i<e.length&&"'"!==e[i];)n+=e[i++];if(i>=e.length)return null;i++,t.push({type:"str",v:n});continue}if(n>="a"&&n<="z"||n>="A"&&n<="Z"||"_"===n||"$"===n){const n=i;for(;i<e.length&&/[\w$.]/.test(e[i]);)i++;t.push({type:"id",v:e.slice(n,i)});continue}if(i+2<e.length){const n=e.slice(i,i+3);if("==="===n||"!=="===n){t.push({type:"op",v:n}),i+=3;continue}}if(i+1<e.length){const n=e.slice(i,i+2);if("=="===n||"!="===n||"<="===n||">="===n||"&&"===n||"||"===n){t.push({type:"op",v:n}),i+=2;continue}}if(!"+-*/%<>!?:(),".includes(n))return null;t.push({type:"op",v:n}),i++}else i++}return t}(e);if(!i)return;const n=i;let r=0;function s(){return n[r]}function o(){return n[r++]}function a(e,t){const i=s();return!!i&&(i.type===e&&(void 0===t||i.v===t))}function l(){const e=function(){let e=d();for(;a("op","||");)o(),e=e||d();return e}();if(a("op","?")){o();const t=l();if(!a("op",":"))return;o();const i=l();return e?t:i}return e}function d(){let e=c();for(;a("op","&&");)o(),e=e&&c();return e}function c(){let e=u();for(;;){const t=s();if(!t||"op"!==t.type)break;if("==="===t.v)o(),e=e===u();else if("!=="===t.v)o(),e=e!==u();else if("=="===t.v)o(),e=e==u();else{if("!="!==t.v)break;o(),e=e!=u()}}return e}function u(){let e=h();for(;;){const t=s();if(!t||"op"!==t.type)break;if("<"===t.v)o(),e=e<h();else if(">"===t.v)o(),e=e>h();else if("<="===t.v)o(),e=e<=h();else{if(">="!==t.v)break;o(),e=e>=h()}}return e}function h(){let e=f();for(;;){const t=s();if(!t||"op"!==t.type)break;if("+"===t.v)o(),e+=f();else{if("-"!==t.v)break;o(),e-=f()}}return e}function f(){let e=g();for(;;){const t=s();if(!t||"op"!==t.type)break;if("*"===t.v)o(),e*=g();else if("/"===t.v)o(),e/=g();else{if("%"!==t.v)break;o(),e%=g()}}return e}function g(){return a("op","!")?(o(),!g()):p()}function p(){const e=s();if(e){if("num"===e.type)return o(),e.v;if("str"===e.type)return o(),e.v;if("id"===e.type)return o(),function(e){if("value"===e)return t.value;if(e.startsWith("row.")){const i=e.slice(4);return t.row?t.row[i]:void 0}return"row"===e?t.row:void 0}(e.v);if("op"===e.type&&"("===e.v){o();const e=l();return a("op",")")&&o(),e}return"op"===e.type&&"-"===e.v?(o(),-p()):void 0}}const m=l();return r<n.length?void 0:m}function u(n,s){if(!n||-1===n.indexOf("{{"))return n;const o=[],a=n.replace(e,(e,n)=>{const a=function(e,n){if(e=(e||"").trim(),!e)return t;if(h.test(e))return t;if("value"===e)return null==n.value?t:String(n.value);if(e.startsWith("row.")&&!/[()?]/.test(e)&&!e.includes(":")){const i=e.slice(4),r=n.row?n.row[i]:void 0;return null==r?t:String(r)}if(e.length>80)return t;if(!i.test(e)||r.test(e))return t;const s=e.match(/\./g);if(s&&s.length>1)return t;try{const i=c(e,n),r=null==i?"":String(i);return h.test(r)?t:r||t}catch{return t}}(n,s);return o.push({expr:n.trim(),result:a}),a}),l=(d=a)?d.replace(new RegExp(t,"g"),"").replace(/Reflect\.[^<>{}\s]+|\bProxy\b|ownKeys\([^)]*\)/g,""):d;var d;const u=o.length&&o.every(e=>""===e.result||e.result===t);return h.test(n)||u?"":l}const h=/Reflect|Proxy|ownKeys/;function f(e,t){return`[tbw-grid${e?`#${e}`:""}${t?`:${t}`:""}]`}function g(e,t,i,n){return`${f(i,n)} ${e}: ${t}\n\n → More info: ${function(e){return`https://toolboxjs.com/grid/errors#${e.toLowerCase()}`}(e)}`}const p='<svg viewBox="0 0 16 16" width="12" height="12"><path fill="currentColor" d="M6 10.5a.5.5 0 0 1 .5-.5h3a.5.5 0 0 1 0 1h-3a.5.5 0 0 1-.5-.5zm-2-3a.5.5 0 0 1 .5-.5h7a.5.5 0 0 1 0 1h-7a.5.5 0 0 1-.5-.5zm-2-3a.5.5 0 0 1 .5-.5h11a.5.5 0 0 1 0 1h-11a.5.5 0 0 1-.5-.5z"/></svg>',m={expand:"▶",collapse:"▼",sortAsc:"▲",sortDesc:"▼",sortNone:"⇅",submenuArrow:"▶",dragHandle:"⋮⋮",toolPanel:"☰",filter:p,filterActive:p,print:"🖨️"};class w{static dependencies;static manifest;aliases;version="undefined"!=typeof __GRID_VERSION__?__GRID_VERSION__:"dev";styles;cellRenderers;headerRenderers;cellEditors;grid;config;userConfig;#e;get defaultConfig(){return{}}constructor(e={}){this.userConfig=e}attach(e){this.#e?.abort(),this.#e=new AbortController,this.grid=e,this.config={...this.defaultConfig,...this.userConfig}}detach(){this.#e?.abort(),this.#e=void 0}getPlugin(e){return this.grid?.getPlugin(e)}emit(e,t){this.grid?.dispatchEvent?.(new CustomEvent(e,{detail:t,bubbles:!0}))}emitCancelable(e,t){const i=new CustomEvent(e,{detail:t,bubbles:!0,cancelable:!0});return this.grid?.dispatchEvent?.(i),i.defaultPrevented}on(e,t){this.grid?._pluginManager?.subscribe(this,e,t)}off(e){this.grid?._pluginManager?.unsubscribe(this,e)}emitPluginEvent(e,t){this.grid?._pluginManager?.emitPluginEvent(e,t)}broadcast(e,t){this.emitPluginEvent(e,t),this.emit(e,t)}requestRender(){this.grid?.requestRender?.()}requestColumnsRender(){this.grid?.requestColumnsRender?.()}requestRenderWithFocus(){this.grid?.requestRenderWithFocus?.()}requestAfterRender(){this.grid?.requestAfterRender?.()}requestVirtualRefresh(){this.grid?.requestVirtualRefresh?.()}get rows(){return this.grid?.rows??[]}get sourceRows(){return this.grid?.sourceRows??[]}get columns(){return this.grid?.columns??[]}get visibleColumns(){return this.grid?._visibleColumns??[]}get gridElement(){return this.grid?._hostElement}get disconnectSignal(){return this.#e?.signal??this.grid?.disconnectSignal}get gridIcons(){const e=this.grid?.gridConfig?.icons??{};return{...m,...e}}get isAnimationEnabled(){const e=this.grid?.effectiveConfig?.animation?.mode??"reduced-motion";if(!1===e||"off"===e)return!1;if(!0===e||"on"===e)return!0;const t=this.gridElement;if(t){return"0"!==getComputedStyle(t).getPropertyValue("--tbw-animation-enabled").trim()}return!0}get animationDuration(){const e=this.gridElement;if(e){const t=getComputedStyle(e).getPropertyValue("--tbw-animation-duration").trim(),i=parseInt(t,10);if(!isNaN(i))return i}return 200}setIcon(e,t,i){e.dataset.icon=t.replace(/([A-Z])/g,"-$1").toLowerCase(),"collapse"===t?e.dataset.expanded="":"expand"===t&&delete e.dataset.expanded;const n=this.#t(t,i);void 0!==n?"string"==typeof n?e.innerHTML=d(n):n instanceof HTMLElement&&(e.innerHTML="",e.appendChild(n.cloneNode(!0))):e.innerHTML=""}#t(e,t){return void 0!==t?t:this.grid?.gridConfig?.icons?.[e]}updateSortIndicator(e,t){e.querySelector('[part~="sort-indicator"], .sort-indicator')?.remove();const i=document.createElement("span");i.setAttribute("part","sort-indicator"),i.className="sort-indicator",t?(e.setAttribute("aria-sort","asc"===t?"ascending":"descending"),e.setAttribute("data-sort",t),this.setIcon(i,"asc"===t?"sortAsc":"sortDesc")):(e.setAttribute("aria-sort","none"),e.removeAttribute("data-sort"),this.setIcon(i,"sortNone"));const n=e.querySelector(".tbw-filter-btn")??e.querySelector(".resize-handle");return n?e.insertBefore(i,n):e.appendChild(i),i}warn(e,t){void 0!==t?console.warn(g(e,t,this.gridElement.id,this.name)):console.warn(`${f(this.gridElement.id,this.name)} ${e}`)}throwDiagnostic(e,t){throw new Error(g(e,t,this.gridElement.id,this.name))}}const b="__tbw_expander";function v(e){return e.field===b}function x(e,t){return e.has(t)?e.delete(t):e.add(t),e}function R(e,t,i,n){const r=document.createElement("div");r.className="master-detail-row",r.setAttribute("data-detail-for",String(t)),r.setAttribute("role","row");const s=document.createElement("div");s.className="master-detail-cell",s.setAttribute("role","cell"),s.style.gridColumn=`1 / ${n+1}`;const o=i(e,t);return"string"==typeof o?s.innerHTML=o:o instanceof HTMLElement&&s.appendChild(o),r.appendChild(s),r}class y extends w{name="masterDetail";styles="@layer tbw-plugins{tbw-grid .cell[data-field=__tbw_expander]{border-right:none!important;padding:0;display:flex;align-items:center;justify-content:center}tbw-grid .header-row .cell[data-field=__tbw_expander]{display:none}tbw-grid .master-detail-expander{display:flex;align-items:center;justify-content:center;width:100%;height:100%}tbw-grid .master-detail-toggle{cursor:pointer;opacity:.7;-webkit-user-select:none;user-select:none;display:inline-flex;align-items:center;justify-content:center}tbw-grid .master-detail-toggle:hover{opacity:1}tbw-grid .master-detail-row{grid-column:1 / -1;display:grid;background:var(--tbw-master-detail-bg, var(--tbw-color-row-alt));border-bottom:1px solid var(--tbw-master-detail-border, var(--tbw-color-border));overflow:hidden}tbw-grid .master-detail-cell{padding:var(--tbw-detail-padding, var(--tbw-spacing-xl, 1rem));overflow:auto}tbw-grid .master-detail-row.tbw-expanding{animation:tbw-detail-expand var(--tbw-animation-duration, .2s) var(--tbw-animation-easing, ease-out) forwards}tbw-grid .master-detail-row.tbw-collapsing{animation:tbw-detail-collapse var(--tbw-animation-duration, .2s) var(--tbw-animation-easing, ease-out) forwards}@keyframes tbw-detail-expand{0%{opacity:0;max-height:0;padding-top:0;padding-bottom:0}to{opacity:1;max-height:var(--tbw-detail-max-height, 31.25rem);padding-top:var(--tbw-detail-padding, var(--tbw-spacing-xl, 1rem));padding-bottom:var(--tbw-detail-padding, var(--tbw-spacing-xl, 1rem))}}@keyframes tbw-detail-collapse{0%{opacity:1;max-height:var(--tbw-detail-max-height, 31.25rem)}to{opacity:0;max-height:0}}}";get#i(){return this.grid}get defaultConfig(){return{detailHeight:"auto",expandOnRowClick:!1,collapseOnClickOutside:!1,animation:"slide"}}attach(e){super.attach(e),this.parseLightDomDetail()}parseLightDomDetail(){const e=this.gridElement;if(!e)return;const t=e.querySelector("tbw-grid-detail");if(!t)return;const i=this.#i.__frameworkAdapter;if(i?.parseDetailElement){const e=i.parseDetailElement(t);if(e)return void(this.config={...this.config,detailRenderer:e})}const n=t.getAttribute("animation"),r=t.getAttribute("show-expand-column"),s=t.getAttribute("expand-on-row-click"),o=t.getAttribute("collapse-on-click-outside"),a=t.getAttribute("height"),l={};null!==n&&(l.animation="false"!==n&&n),null!==r&&(l.showExpandColumn="false"!==r),null!==s&&(l.expandOnRowClick="true"===s),null!==o&&(l.collapseOnClickOutside="true"===o),null!==a&&(l.detailHeight="auto"===a?"auto":parseInt(a,10));const c=t.innerHTML.trim();c&&!this.config.detailRenderer&&(l.detailRenderer=(e,t)=>d(u(c,{value:e,row:e}))),Object.keys(l).length>0&&(this.config={...this.config,...l})}get animationStyle(){return!!this.isAnimationEnabled&&(this.config.animation??"slide")}animateExpand(e,t,i){if(!this.isAnimationEnabled||!1===this.animationStyle)return!1;e.classList.add("tbw-expanding");let n=!1;const r=()=>{n||(n=!0,e.classList.remove("tbw-expanding"),void 0!==t&&void 0!==i&&this.#n(e,t,i))};return e.addEventListener("animationend",r,{once:!0}),setTimeout(r,this.animationDuration+50),!0}animateCollapse(e,t){if(!this.isAnimationEnabled||!1===this.animationStyle)return void t();e.classList.add("tbw-collapsing");const i=()=>{e.classList.remove("tbw-collapsing"),t()};e.addEventListener("animationend",i,{once:!0}),setTimeout(i,this.animationDuration+50)}#n(e,t,i){if(!e.isConnected)return;const n=e.offsetHeight;if(n>0){const e=this.measuredDetailHeights.get(t);this.measuredDetailHeights.set(t,n),e!==n&&this.grid.invalidateRowHeight(i)}}expandedRows=/* @__PURE__ */new Set;detailElements=/* @__PURE__ */new Map;measuredDetailHeights=/* @__PURE__ */new Map;rowsToAnimate=/* @__PURE__ */new Set;static DEFAULT_DETAIL_HEIGHT=150;getDetailHeight(e){const t=this.detailElements.get(e);if(t){if(!(t.classList.contains("tbw-expanding")||t.classList.contains("tbw-collapsing"))){const i=t.offsetHeight;if(i>0)return this.measuredDetailHeights.set(e,i),i}}const i=this.measuredDetailHeights.get(e);return i&&i>0?i:"number"==typeof this.config?.detailHeight?this.config.detailHeight:y.DEFAULT_DETAIL_HEIGHT}toggleAndEmit(e,t){if(e?.__isGroupRow)return;this.expandedRows=x(this.expandedRows,e);const i=this.expandedRows.has(e);i&&this.rowsToAnimate.add(e),this.emit("detail-expand",{rowIndex:t,row:e,expanded:i}),this.requestRender()}detach(){this.expandedRows.clear(),this.detailElements.clear(),this.measuredDetailHeights.clear(),this.rowsToAnimate.clear()}processColumns(e){if(!(!0===this.config.showExpandColumn||!1!==this.config.showExpandColumn&&!!this.config.detailRenderer))return[...e];const t=[...e],i=function(e){return e.find(v)}(t);if(i)return t;const n=(r=this.name,{field:b,header:"",width:32,resizable:!1,sortable:!1,filterable:!1,meta:{lockPosition:!0,suppressMovable:!0,expanderColumn:!0,expanderPlugin:r,utility:!0}});var r;return n.viewRenderer=e=>{const{row:t}=e,i=this.expandedRows.has(t),n=document.createElement("span");n.className="master-detail-expander expander-cell";const r=document.createElement("span");return r.className="master-detail-toggle"+(i?" expanded":""),this.setIcon(r,i?"collapse":"expand"),r.setAttribute("role","button"),r.setAttribute("tabindex","0"),r.setAttribute("aria-expanded",String(i)),r.setAttribute("aria-label",i?"Collapse details":"Expand details"),n.appendChild(r),n},[n,...t]}onRowClick(e){if(this.config.expandOnRowClick&&this.config.detailRenderer)return this.toggleAndEmit(e.row,e.rowIndex),!1}onCellClick(e){const t=e.originalEvent?.target;if(t?.classList.contains("master-detail-toggle"))return this.toggleAndEmit(e.row,e.rowIndex),!0;this.expandedRows.size>0&&queueMicrotask(()=>this.#r())}onKeyDown(e){if(" "!==e.key)return;const t=this.grid._focusCol,i=this.grid._focusRow,n=this.visibleColumns[t];if(!n||!v(n))return;const r=this.rows[i];return r?(e.preventDefault(),this.toggleAndEmit(r,i),this.requestRenderWithFocus(),!0):void 0}afterRender(){this.#s(),this.#r()}#s(){const e=this.gridElement?.querySelector('.header-row .cell[data-field="__tbw_expander"]');if(!e)return;const t=parseInt(e.getAttribute("data-col")||"0",10),i=e.nextElementSibling;i&&(i.style.gridColumn=`${t+1} / ${t+3}`)}onScrollRender(){this.config.detailRenderer&&0!==this.expandedRows.size&&this.#r()}#r(){if(!this.config.detailRenderer)return;const e=this.gridElement?.querySelector(".rows");if(!e)return;const t=this.grid,i=t._rowPool,n=t._virtualization?.start??0,r=t._virtualization?.end??0,s=this.columns.length,o=n,a=r,l=/* @__PURE__ */new Map;if(i){const t=Math.min(i.length,a-o);for(let n=0;n<t;n++){const t=i[n];t.parentNode===e&&l.set(o+n,t)}}else{const t=e.querySelectorAll(".data-grid-row");for(const e of t){const t=e.querySelector(".cell[data-row]"),i=t?parseInt(t.getAttribute("data-row")??"-1",10):-1;i>=0&&l.set(i,e)}}for(const[d,c]of this.detailElements){const e=this.rows.indexOf(d),t=this.expandedRows.has(d),i=e>=0&&l.has(e);if(!t||!i){const e=this.#i.__frameworkAdapter;if(e?.unmount){const t=c.querySelector(".master-detail-cell"),i=t?.firstElementChild;i&&e.unmount(i)}c.parentNode&&c.remove(),this.detailElements.delete(d)}}for(const[d,c]of l){const e=this.rows[d];if(!e||!this.expandedRows.has(e))continue;const t=this.detailElements.get(e);if(t){t.previousElementSibling!==c&&c.after(t);continue}const i=R(e,d,this.config.detailRenderer,s);"number"==typeof this.config.detailHeight&&(i.style.height=`${this.config.detailHeight}px`),c.after(i),this.detailElements.set(e,i);const n=this.rowsToAnimate.has(e);n&&this.rowsToAnimate.delete(e);n&&this.animateExpand(i,e,d)||requestAnimationFrame(()=>{this.#n(i,e,d)})}}getRowHeight(e,t){if(!this.expandedRows.has(e))return;return(this.grid.defaultRowHeight??28)+this.getDetailHeight(e)}adjustVirtualStart(e,t,i){if(0===this.expandedRows.size)return e;const n=this.grid?._virtualization?.positionCache;let r=e;if(n&&n.length>0)for(const s of this.expandedRows){const i=this.rows.indexOf(s);if(i<0||i>=e)continue;n[i].offset+n[i].height>t&&i<r&&(r=i)}else{const n=[];for(const e of this.expandedRows){const t=this.rows.indexOf(e);t>=0&&n.push({index:t,row:e})}n.sort((e,t)=>e.index-t.index);let s=0;for(const{index:o,row:a}of n){const n=o*i+s,l=this.getDetailHeight(a);s+=l,o>=e||n+i+l>t&&o<r&&(r=o)}}return r}expand(e){const t=this.rows[e];t&&!t.__isGroupRow&&(this.rowsToAnimate.add(t),this.expandedRows=function(e,t){return e.add(t),e}(this.expandedRows,t),this.requestRender())}collapse(e){const t=this.rows[e];t&&(this.expandedRows=function(e,t){return e.delete(t),e}(this.expandedRows,t),this.requestRender())}toggle(e){const t=this.rows[e];t&&!t.__isGroupRow&&(this.expandedRows=x(this.expandedRows,t),this.expandedRows.has(t)&&this.rowsToAnimate.add(t),this.requestRender())}isExpanded(e){const t=this.rows[e];return!!t&&function(e,t){return e.has(t)}(this.expandedRows,t)}expandAll(){for(const e of this.rows)e?.__isGroupRow||(this.rowsToAnimate.add(e),this.expandedRows.add(e));this.requestRender()}collapseAll(){this.expandedRows.clear(),this.requestRender()}getExpandedRows(){const e=[];for(const t of this.expandedRows){const i=this.rows.indexOf(t);i>=0&&e.push(i)}return e}getDetailElement(e){const t=this.rows[e];return t?this.detailElements.get(t):void 0}refreshDetailRenderer(){const e=this.config.detailRenderer;if(this.config={...this.config,detailRenderer:void 0},this.parseLightDomDetail(),!this.config.detailRenderer&&e&&(this.config={...this.config,detailRenderer:e}),this.config.detailRenderer){const e=this.#i;"function"==typeof e.refreshColumns?e.refreshColumns():this.requestRender()}}}export{y as MasterDetailPlugin};
1
+ const e=/{{\s*([^}]+)\s*}}/g,t="__DG_EMPTY__",i=/^[\w$. '?+\-*/%:()!<>=,&|]+$/,n=["__otorp__","__retteGenifed__","__retteSenifed__","rotcurtsnoc","wodniw","sihTlabolg","labolg","ssecorp","noitcnuF","tropmi","lave","tcelfeR","yxorP","rorrE","stnemugra","tnemucod","noitacol","eikooc","egarotSlacol","egarotSnoisses","BDdexedni","hctef","tseuqeRpttHLMX","tekcoSbeW","rekroW","rekroWderahS","rekroWecivreS","renepo","tnerap","pot","semarf","fles"].map(e=>e.split("").reverse().join("")),r=new RegExp(`__(proto|defineGetter|defineSetter)|${n.slice(3).join("|")}|this\\b`),s=/* @__PURE__ */new Set(["script","iframe","object","embed","form","input","button","textarea","select","link","meta","base","style","template","slot","portal","frame","frameset","applet","noscript","noembed","plaintext","xmp","listing"]),o=/^on\w+$/i,a=/* @__PURE__ */new Set(["href","src","action","formaction","data","srcdoc","xlink:href","poster","srcset"]),l=/^\s*(javascript|vbscript|data|blob):/i;function d(e){if(!e||"string"!=typeof e)return"";if(-1===e.indexOf("<"))return e;const t=document.createElement("template");return t.innerHTML=e,function(e){const t=[],i=e.querySelectorAll("*");for(const n of i){const e=n.tagName.toLowerCase();if(s.has(e)){t.push(n);continue}if("svg"===e||"http://www.w3.org/2000/svg"===n.namespaceURI){if(Array.from(n.attributes).some(e=>o.test(e.name)||"href"===e.name||"xlink:href"===e.name)){t.push(n);continue}}const i=[];for(const t of n.attributes){const e=t.name.toLowerCase();o.test(e)?i.push(t.name):(a.has(e)&&l.test(t.value)||"style"===e&&/expression\s*\(|javascript:|behavior\s*:/i.test(t.value))&&i.push(t.name)}i.forEach(e=>n.removeAttribute(e))}t.forEach(e=>e.remove())}(t.content),t.innerHTML}function c(e,t){const i=function(e){const t=[];let i=0;for(;i<e.length;){const n=e[i];if(" "!==n){if(n>="0"&&n<="9"||"."===n&&i+1<e.length&&e[i+1]>="0"&&e[i+1]<="9"){const n=i;for(;i<e.length&&(e[i]>="0"&&e[i]<="9"||"."===e[i]);)i++;t.push({type:"num",v:Number(e.slice(n,i))});continue}if("'"===n){let n="";for(i++;i<e.length&&"'"!==e[i];)n+=e[i++];if(i>=e.length)return null;i++,t.push({type:"str",v:n});continue}if(n>="a"&&n<="z"||n>="A"&&n<="Z"||"_"===n||"$"===n){const n=i;for(;i<e.length&&/[\w$.]/.test(e[i]);)i++;t.push({type:"id",v:e.slice(n,i)});continue}if(i+2<e.length){const n=e.slice(i,i+3);if("==="===n||"!=="===n){t.push({type:"op",v:n}),i+=3;continue}}if(i+1<e.length){const n=e.slice(i,i+2);if("=="===n||"!="===n||"<="===n||">="===n||"&&"===n||"||"===n){t.push({type:"op",v:n}),i+=2;continue}}if(!"+-*/%<>!?:(),".includes(n))return null;t.push({type:"op",v:n}),i++}else i++}return t}(e);if(!i)return;const n=i;let r=0;function s(){return n[r]}function o(){return n[r++]}function a(e,t){const i=s();return!!i&&(i.type===e&&(void 0===t||i.v===t))}function l(){const e=function(){let e=d();for(;a("op","||");)o(),e=e||d();return e}();if(a("op","?")){o();const t=l();if(!a("op",":"))return;o();const i=l();return e?t:i}return e}function d(){let e=c();for(;a("op","&&");)o(),e=e&&c();return e}function c(){let e=u();for(;;){const t=s();if(!t||"op"!==t.type)break;if("==="===t.v)o(),e=e===u();else if("!=="===t.v)o(),e=e!==u();else if("=="===t.v)o(),e=e==u();else{if("!="!==t.v)break;o(),e=e!=u()}}return e}function u(){let e=h();for(;;){const t=s();if(!t||"op"!==t.type)break;if("<"===t.v)o(),e=e<h();else if(">"===t.v)o(),e=e>h();else if("<="===t.v)o(),e=e<=h();else{if(">="!==t.v)break;o(),e=e>=h()}}return e}function h(){let e=g();for(;;){const t=s();if(!t||"op"!==t.type)break;if("+"===t.v)o(),e+=g();else{if("-"!==t.v)break;o(),e-=g()}}return e}function g(){let e=f();for(;;){const t=s();if(!t||"op"!==t.type)break;if("*"===t.v)o(),e*=f();else if("/"===t.v)o(),e/=f();else{if("%"!==t.v)break;o(),e%=f()}}return e}function f(){return a("op","!")?(o(),!f()):p()}function p(){const e=s();if(e){if("num"===e.type)return o(),e.v;if("str"===e.type)return o(),e.v;if("id"===e.type)return o(),function(e){if("value"===e)return t.value;if(e.startsWith("row.")){const i=e.slice(4);return t.row?t.row[i]:void 0}return"row"===e?t.row:void 0}(e.v);if("op"===e.type&&"("===e.v){o();const e=l();return a("op",")")&&o(),e}return"op"===e.type&&"-"===e.v?(o(),-p()):void 0}}const m=l();return r<n.length?void 0:m}function u(n,s){if(!n||-1===n.indexOf("{{"))return n;const o=[],a=n.replace(e,(e,n)=>{const a=function(e,n){if(e=(e||"").trim(),!e)return t;if(h.test(e))return t;if("value"===e)return null==n.value?t:String(n.value);if(e.startsWith("row.")&&!/[()?]/.test(e)&&!e.includes(":")){const i=e.slice(4),r=n.row?n.row[i]:void 0;return null==r?t:String(r)}if(e.length>80)return t;if(!i.test(e)||r.test(e))return t;const s=e.match(/\./g);if(s&&s.length>1)return t;try{const i=c(e,n),r=null==i?"":String(i);return h.test(r)?t:r||t}catch{return t}}(n,s);return o.push({expr:n.trim(),result:a}),a}),l=(d=a)?d.replace(new RegExp(t,"g"),"").replace(/Reflect\.[^<>{}\s]+|\bProxy\b|ownKeys\([^)]*\)/g,""):d;var d;const u=o.length&&o.every(e=>""===e.result||e.result===t);return h.test(n)||u?"":l}const h=/Reflect|Proxy|ownKeys/;function g(e,t){return`[tbw-grid${e?`#${e}`:""}${t?`:${t}`:""}]`}function f(e,t,i,n){return`${g(i,n)} ${e}: ${t}\n\n → More info: ${function(e){return`https://toolboxjs.com/grid/errors#${e.toLowerCase()}`}(e)}`}const p='<svg viewBox="0 0 16 16" width="12" height="12"><path fill="currentColor" d="M6 10.5a.5.5 0 0 1 .5-.5h3a.5.5 0 0 1 0 1h-3a.5.5 0 0 1-.5-.5zm-2-3a.5.5 0 0 1 .5-.5h7a.5.5 0 0 1 0 1h-7a.5.5 0 0 1-.5-.5zm-2-3a.5.5 0 0 1 .5-.5h11a.5.5 0 0 1 0 1h-11a.5.5 0 0 1-.5-.5z"/></svg>',m={expand:"▶",collapse:"▼",sortAsc:"▲",sortDesc:"▼",sortNone:"⇅",submenuArrow:"▶",dragHandle:"⋮⋮",toolPanel:"☰",filter:p,filterActive:p,print:"🖨️"};class w{static dependencies;static manifest;aliases;version="undefined"!=typeof __GRID_VERSION__?__GRID_VERSION__:"dev";styles;cellRenderers;headerRenderers;cellEditors;grid;config;userConfig;#e;get defaultConfig(){return{}}constructor(e={}){this.userConfig=e}attach(e){this.#e?.abort(),this.#e=new AbortController,this.grid=e,this.config={...this.defaultConfig,...this.userConfig}}detach(){this.#e?.abort(),this.#e=void 0}getPlugin(e){return this.grid?.getPlugin(e)}emit(e,t){this.grid?.dispatchEvent?.(new CustomEvent(e,{detail:t,bubbles:!0}))}emitCancelable(e,t){const i=new CustomEvent(e,{detail:t,bubbles:!0,cancelable:!0});return this.grid?.dispatchEvent?.(i),i.defaultPrevented}on(e,t){this.grid?._pluginManager?.subscribe(this,e,t)}off(e){this.grid?._pluginManager?.unsubscribe(this,e)}emitPluginEvent(e,t){this.grid?._pluginManager?.emitPluginEvent(e,t)}broadcast(e,t){this.emitPluginEvent(e,t),this.emit(e,t)}requestRender(){this.grid?.requestRender?.()}requestColumnsRender(){this.grid?.requestColumnsRender?.()}requestRenderWithFocus(){this.grid?.requestRenderWithFocus?.()}requestAfterRender(){this.grid?.requestAfterRender?.()}requestVirtualRefresh(){this.grid?.requestVirtualRefresh?.()}get rows(){return this.grid?.rows??[]}get sourceRows(){return this.grid?.sourceRows??[]}get columns(){return this.grid?.columns??[]}get visibleColumns(){return this.grid?._visibleColumns??[]}get gridElement(){return this.grid?._hostElement}get disconnectSignal(){return this.#e?.signal??this.grid?.disconnectSignal}get gridIcons(){const e=this.grid?.gridConfig?.icons??{};return{...m,...e}}get isAnimationEnabled(){const e=this.grid?.effectiveConfig?.animation?.mode??"reduced-motion";if(!1===e||"off"===e)return!1;if(!0===e||"on"===e)return!0;const t=this.gridElement;if(t){return"0"!==getComputedStyle(t).getPropertyValue("--tbw-animation-enabled").trim()}return!0}get animationDuration(){const e=this.gridElement;if(e){const t=getComputedStyle(e).getPropertyValue("--tbw-animation-duration").trim(),i=parseInt(t,10);if(!isNaN(i))return i}return 200}setIcon(e,t,i){e.dataset.icon=t.replace(/([A-Z])/g,"-$1").toLowerCase(),"collapse"===t?e.dataset.expanded="":"expand"===t&&delete e.dataset.expanded;const n=this.#t(t,i);void 0!==n?"string"==typeof n?e.innerHTML=d(n):n instanceof HTMLElement&&(e.innerHTML="",e.appendChild(n.cloneNode(!0))):e.innerHTML=""}#t(e,t){return void 0!==t?t:this.grid?.gridConfig?.icons?.[e]}updateSortIndicator(e,t){e.querySelector('[part~="sort-indicator"], .sort-indicator')?.remove();const i=document.createElement("span");i.setAttribute("part","sort-indicator"),i.className="sort-indicator",t?(e.setAttribute("aria-sort","asc"===t?"ascending":"descending"),e.setAttribute("data-sort",t),this.setIcon(i,"asc"===t?"sortAsc":"sortDesc")):(e.setAttribute("aria-sort","none"),e.removeAttribute("data-sort"),this.setIcon(i,"sortNone"));const n=e.querySelector(".tbw-filter-btn")??e.querySelector(".resize-handle");return n?e.insertBefore(i,n):e.appendChild(i),i}warn(e,t){void 0!==t?console.warn(f(e,t,this.gridElement.id,this.name)):console.warn(`${g(this.gridElement.id,this.name)} ${e}`)}throwDiagnostic(e,t){throw new Error(f(e,t,this.gridElement.id,this.name))}}const b="__tbw_expander";function v(e){return e.field===b}function x(e,t){return e.has(t)?e.delete(t):e.add(t),e}function R(e,t,i,n){const r=document.createElement("div");r.className="master-detail-row",r.setAttribute("data-detail-for",String(t)),r.setAttribute("role","row");const s=document.createElement("div");s.className="master-detail-cell",s.setAttribute("role","cell"),s.style.gridColumn=`1 / ${n+1}`;const o=i(e,t);return"string"==typeof o?s.innerHTML=o:o instanceof HTMLElement&&s.appendChild(o),r.appendChild(s),r}class y extends w{name="masterDetail";styles="@layer tbw-plugins{tbw-grid .cell[data-field=__tbw_expander]{border-right:none!important;padding:0;display:flex;align-items:center;justify-content:center}tbw-grid .header-row .cell[data-field=__tbw_expander]{display:none}tbw-grid .master-detail-expander{display:flex;align-items:center;justify-content:center;width:100%;height:100%}tbw-grid .master-detail-toggle{cursor:pointer;opacity:.7;-webkit-user-select:none;user-select:none;display:inline-flex;align-items:center;justify-content:center}tbw-grid .master-detail-toggle:hover{opacity:1}tbw-grid .master-detail-row{grid-column:1 / -1;display:grid;background:var(--tbw-master-detail-bg, var(--tbw-color-row-alt));border-bottom:1px solid var(--tbw-master-detail-border, var(--tbw-color-border));overflow:hidden}tbw-grid .master-detail-cell{padding:var(--tbw-detail-padding, var(--tbw-spacing-xl, 1rem));overflow:auto}tbw-grid .master-detail-row.tbw-expanding{animation:tbw-detail-expand var(--tbw-animation-duration, .2s) var(--tbw-animation-easing, ease-out) forwards}tbw-grid .master-detail-row.tbw-collapsing{animation:tbw-detail-collapse var(--tbw-animation-duration, .2s) var(--tbw-animation-easing, ease-out) forwards}@keyframes tbw-detail-expand{0%{opacity:0;max-height:0;padding-top:0;padding-bottom:0}to{opacity:1;max-height:var(--tbw-detail-max-height, 31.25rem);padding-top:var(--tbw-detail-padding, var(--tbw-spacing-xl, 1rem));padding-bottom:var(--tbw-detail-padding, var(--tbw-spacing-xl, 1rem))}}@keyframes tbw-detail-collapse{0%{opacity:1;max-height:var(--tbw-detail-max-height, 31.25rem)}to{opacity:0;max-height:0}}}";static dependencies=[{name:"serverSide",required:!1,reason:"Fetches detail data via datasource:fetch-children on expand"}];get#i(){return this.grid}get defaultConfig(){return{detailHeight:"auto",expandOnRowClick:!1,collapseOnClickOutside:!1,animation:"slide"}}attach(e){super.attach(e),this.parseLightDomDetail(),this.on("datasource:children",e=>{const t=e;if("master-detail"!==t.context?.source)return;t.claimed=!0;const i=t.context.row;if(i&&this.expandedRows.has(i)){this.detailDataMap.set(i,t.rows),this.loadingDetails.delete(i);const e=this.detailElements.get(i);e&&(e.remove(),this.detailElements.delete(i),this.measuredDetailHeights.delete(i)),this.requestRender()}})}parseLightDomDetail(){const e=this.gridElement;if(!e)return;const t=e.querySelector("tbw-grid-detail");if(!t)return;const i=this.#i.__frameworkAdapter;if(i?.parseDetailElement){const e=i.parseDetailElement(t);if(e)return void(this.config={...this.config,detailRenderer:e})}const n=t.getAttribute("animation"),r=t.getAttribute("show-expand-column"),s=t.getAttribute("expand-on-row-click"),o=t.getAttribute("collapse-on-click-outside"),a=t.getAttribute("height"),l={};null!==n&&(l.animation="false"!==n&&n),null!==r&&(l.showExpandColumn="false"!==r),null!==s&&(l.expandOnRowClick="true"===s),null!==o&&(l.collapseOnClickOutside="true"===o),null!==a&&(l.detailHeight="auto"===a?"auto":parseInt(a,10));const c=t.innerHTML.trim();c&&!this.config.detailRenderer&&(l.detailRenderer=(e,t)=>d(u(c,{value:e,row:e}))),Object.keys(l).length>0&&(this.config={...this.config,...l})}get animationStyle(){return!!this.isAnimationEnabled&&(this.config.animation??"slide")}animateExpand(e,t,i){if(!this.isAnimationEnabled||!1===this.animationStyle)return!1;e.classList.add("tbw-expanding");let n=!1;const r=()=>{n||(n=!0,e.classList.remove("tbw-expanding"),void 0!==t&&void 0!==i&&this.#n(e,t,i))};return e.addEventListener("animationend",r,{once:!0}),setTimeout(r,this.animationDuration+50),!0}animateCollapse(e,t){if(!this.isAnimationEnabled||!1===this.animationStyle)return void t();e.classList.add("tbw-collapsing");const i=()=>{e.classList.remove("tbw-collapsing"),t()};e.addEventListener("animationend",i,{once:!0}),setTimeout(i,this.animationDuration+50)}#n(e,t,i){if(!e.isConnected)return;const n=e.offsetHeight;if(n>0){const e=this.measuredDetailHeights.get(t);this.measuredDetailHeights.set(t,n),e!==n&&this.grid.invalidateRowHeight(i)}}expandedRows=/* @__PURE__ */new Set;detailElements=/* @__PURE__ */new Map;measuredDetailHeights=/* @__PURE__ */new Map;rowsToAnimate=/* @__PURE__ */new Set;loadingDetails=/* @__PURE__ */new Set;detailDataMap=/* @__PURE__ */new Map;static DEFAULT_DETAIL_HEIGHT=150;getDetailHeight(e){const t=this.detailElements.get(e);if(t){if(!(t.classList.contains("tbw-expanding")||t.classList.contains("tbw-collapsing"))){const i=t.offsetHeight;if(i>0)return this.measuredDetailHeights.set(e,i),i}}const i=this.measuredDetailHeights.get(e);return i&&i>0?i:"number"==typeof this.config?.detailHeight?this.config.detailHeight:y.DEFAULT_DETAIL_HEIGHT}toggleAndEmit(e,t){if(e?.__isGroupRow)return;this.expandedRows=x(this.expandedRows,e);const i=this.expandedRows.has(e);if(i){if(this.rowsToAnimate.add(e),!this.detailDataMap.has(e)){const i=this.grid?.query?.("datasource:is-active",null);i&&(this.loadingDetails.add(e),this.grid.query("datasource:fetch-children",{context:{source:"master-detail",row:e,rowIndex:t}}))}}else this.loadingDetails.delete(e);this.emit("detail-expand",{rowIndex:t,row:e,expanded:i}),this.requestRender()}detach(){this.expandedRows.clear(),this.detailElements.clear(),this.measuredDetailHeights.clear(),this.rowsToAnimate.clear(),this.loadingDetails.clear(),this.detailDataMap.clear()}processColumns(e){if(!(!0===this.config.showExpandColumn||!1!==this.config.showExpandColumn&&!!this.config.detailRenderer))return[...e];const t=[...e],i=function(e){return e.find(v)}(t);if(i)return t;const n=(r=this.name,{field:b,header:"",width:32,resizable:!1,sortable:!1,filterable:!1,meta:{lockPosition:!0,suppressMovable:!0,expanderColumn:!0,expanderPlugin:r,utility:!0}});var r;return n.viewRenderer=e=>{const{row:t}=e,i=this.expandedRows.has(t),n=document.createElement("span");n.className="master-detail-expander expander-cell";const r=document.createElement("span");return r.className="master-detail-toggle"+(i?" expanded":""),this.setIcon(r,i?"collapse":"expand"),r.setAttribute("role","button"),r.setAttribute("tabindex","0"),r.setAttribute("aria-expanded",String(i)),r.setAttribute("aria-label",i?"Collapse details":"Expand details"),n.appendChild(r),n},[n,...t]}onRowClick(e){if(this.config.expandOnRowClick&&this.config.detailRenderer)return this.toggleAndEmit(e.row,e.rowIndex),!1}onCellClick(e){const t=e.originalEvent?.target;if(t?.classList.contains("master-detail-toggle"))return this.toggleAndEmit(e.row,e.rowIndex),!0;this.expandedRows.size>0&&queueMicrotask(()=>this.#r())}onKeyDown(e){if(" "!==e.key)return;const t=this.grid._focusCol,i=this.grid._focusRow,n=this.visibleColumns[t];if(!n||!v(n))return;const r=this.rows[i];return r?(e.preventDefault(),this.toggleAndEmit(r,i),this.requestRenderWithFocus(),!0):void 0}afterRender(){this.#s(),this.#r()}#s(){const e=this.gridElement?.querySelector('.header-row .cell[data-field="__tbw_expander"]');if(!e)return;const t=parseInt(e.getAttribute("data-col")||"0",10),i=e.nextElementSibling;i&&(i.style.gridColumn=`${t+1} / ${t+3}`)}onScrollRender(){this.config.detailRenderer&&0!==this.expandedRows.size&&this.#r()}#r(){if(!this.config.detailRenderer)return;const e=this.gridElement?.querySelector(".rows");if(!e)return;const t=this.grid,i=t._rowPool,n=t._virtualization?.start??0,r=t._virtualization?.end??0,s=this.columns.length,o=n,a=r,l=/* @__PURE__ */new Map;if(i){const t=Math.min(i.length,a-o);for(let n=0;n<t;n++){const t=i[n];t.parentNode===e&&l.set(o+n,t)}}else{const t=e.querySelectorAll(".data-grid-row");for(const e of t){const t=e.querySelector(".cell[data-row]"),i=t?parseInt(t.getAttribute("data-row")??"-1",10):-1;i>=0&&l.set(i,e)}}for(const[d,c]of this.detailElements){const e=this.rows.indexOf(d),t=this.expandedRows.has(d),i=e>=0&&l.has(e);if(!t||!i){const e=this.#i.__frameworkAdapter;if(e?.unmount){const t=c.querySelector(".master-detail-cell"),i=t?.firstElementChild;i&&e.unmount(i)}c.parentNode&&c.remove(),this.detailElements.delete(d)}}for(const[d,c]of l){const e=this.rows[d];if(!e||!this.expandedRows.has(e))continue;const t=this.detailElements.get(e);if(t){t.previousElementSibling!==c&&c.after(t);continue}const i=R(e,d,this.config.detailRenderer,s);"number"==typeof this.config.detailHeight&&(i.style.height=`${this.config.detailHeight}px`),c.after(i),this.detailElements.set(e,i);const n=this.rowsToAnimate.has(e);n&&this.rowsToAnimate.delete(e);n&&this.animateExpand(i,e,d)||requestAnimationFrame(()=>{this.#n(i,e,d)})}}getRowHeight(e,t){if(!this.expandedRows.has(e))return;return(this.grid.defaultRowHeight??28)+this.getDetailHeight(e)}adjustVirtualStart(e,t,i){if(0===this.expandedRows.size)return e;const n=this.grid?._virtualization?.positionCache;let r=e;if(n&&n.length>0)for(const s of this.expandedRows){const i=this.rows.indexOf(s);if(i<0||i>=e)continue;n[i].offset+n[i].height>t&&i<r&&(r=i)}else{const n=[];for(const e of this.expandedRows){const t=this.rows.indexOf(e);t>=0&&n.push({index:t,row:e})}n.sort((e,t)=>e.index-t.index);let s=0;for(const{index:o,row:a}of n){const n=o*i+s,l=this.getDetailHeight(a);s+=l,o>=e||n+i+l>t&&o<r&&(r=o)}}return r}expand(e){const t=this.rows[e];t&&!t.__isGroupRow&&(this.rowsToAnimate.add(t),this.expandedRows=function(e,t){return e.add(t),e}(this.expandedRows,t),this.requestRender())}collapse(e){const t=this.rows[e];t&&(this.expandedRows=function(e,t){return e.delete(t),e}(this.expandedRows,t),this.requestRender())}toggle(e){const t=this.rows[e];t&&!t.__isGroupRow&&(this.expandedRows=x(this.expandedRows,t),this.expandedRows.has(t)&&this.rowsToAnimate.add(t),this.requestRender())}isExpanded(e){const t=this.rows[e];return!!t&&function(e,t){return e.has(t)}(this.expandedRows,t)}expandAll(){for(const e of this.rows)e?.__isGroupRow||(this.rowsToAnimate.add(e),this.expandedRows.add(e));this.requestRender()}collapseAll(){this.expandedRows.clear(),this.requestRender()}getExpandedRows(){const e=[];for(const t of this.expandedRows){const i=this.rows.indexOf(t);i>=0&&e.push(i)}return e}getDetailElement(e){const t=this.rows[e];return t?this.detailElements.get(t):void 0}getDetailData(e){const t=this.rows[e];return t?this.detailDataMap.get(t):void 0}isDetailLoading(e){const t=this.rows[e];return!!t&&this.loadingDetails.has(t)}refreshDetailRenderer(){const e=this.config.detailRenderer;if(this.config={...this.config,detailRenderer:void 0},this.parseLightDomDetail(),!this.config.detailRenderer&&e&&(this.config={...this.config,detailRenderer:e}),this.config.detailRenderer){const e=this.#i;"function"==typeof e.refreshColumns?e.refreshColumns():this.requestRender()}}}export{y as MasterDetailPlugin};
2
2
  //# sourceMappingURL=index.js.map