tree-element 0.3.2 → 0.4.1
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 +23 -20
- package/lib/classNames.js +4 -4
- package/lib/classNames.js.map +1 -1
- package/lib/dataLoader.d.ts +0 -1
- package/lib/dataLoader.d.ts.map +1 -1
- package/lib/dataLoader.js +10 -7
- package/lib/dataLoader.js.map +1 -1
- package/lib/dragAndDropHandler/generateHitAreas.d.ts.map +1 -1
- package/lib/dragAndDropHandler/generateHitAreas.js +3 -2
- package/lib/dragAndDropHandler/generateHitAreas.js.map +1 -1
- package/lib/dragAndDropHandler/index.d.ts +2 -4
- package/lib/dragAndDropHandler/index.d.ts.map +1 -1
- package/lib/dragAndDropHandler/index.js +2 -9
- package/lib/dragAndDropHandler/index.js.map +1 -1
- package/lib/elementsRenderer.d.ts +11 -4
- package/lib/elementsRenderer.d.ts.map +1 -1
- package/lib/elementsRenderer.js +104 -43
- package/lib/elementsRenderer.js.map +1 -1
- package/lib/events.d.ts +13 -7
- package/lib/events.d.ts.map +1 -1
- package/lib/folderOpenState.d.ts +8 -0
- package/lib/folderOpenState.d.ts.map +1 -0
- package/lib/folderOpenState.js +22 -0
- package/lib/folderOpenState.js.map +1 -0
- package/lib/index.d.ts +27 -20
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +166 -65
- package/lib/index.js.map +1 -1
- package/lib/keyHandler.d.ts +16 -3
- package/lib/keyHandler.d.ts.map +1 -1
- package/lib/keyHandler.js +79 -32
- package/lib/keyHandler.js.map +1 -1
- package/lib/methodTypes.d.ts +3 -0
- package/lib/methodTypes.d.ts.map +1 -1
- package/lib/mouseHandler.d.ts.map +1 -1
- package/lib/mouseHandler.js +12 -12
- package/lib/mouseHandler.js.map +1 -1
- package/lib/node.d.ts +12 -10
- package/lib/node.d.ts.map +1 -1
- package/lib/node.js +12 -10
- package/lib/node.js.map +1 -1
- package/lib/nodeElement/folderElement.d.ts +7 -5
- package/lib/nodeElement/folderElement.d.ts.map +1 -1
- package/lib/nodeElement/folderElement.js +35 -55
- package/lib/nodeElement/folderElement.js.map +1 -1
- package/lib/nodeElement/index.d.ts +3 -2
- package/lib/nodeElement/index.d.ts.map +1 -1
- package/lib/nodeElement/index.js +15 -12
- package/lib/nodeElement/index.js.map +1 -1
- package/lib/options.d.ts +29 -14
- package/lib/options.d.ts.map +1 -1
- package/lib/options.js +12 -0
- package/lib/options.js.map +1 -0
- package/lib/saveStateHandler.d.ts.map +1 -1
- package/lib/saveStateHandler.js +6 -6
- package/lib/saveStateHandler.js.map +1 -1
- package/lib/selectNodeHandler.d.ts +3 -0
- package/lib/selectNodeHandler.d.ts.map +1 -1
- package/lib/selectNodeHandler.js +66 -22
- package/lib/selectNodeHandler.js.map +1 -1
- package/lib/setDefaultOptions.d.ts.map +1 -1
- package/lib/setDefaultOptions.js +1 -0
- package/lib/setDefaultOptions.js.map +1 -1
- package/lib/version.d.ts +1 -1
- package/lib/version.js +1 -1
- package/lib/version.js.map +1 -1
- package/package.json +38 -32
- package/src/classNames.ts +4 -4
- package/src/dataLoader.ts +9 -10
- package/src/dragAndDropHandler/generateHitAreas.ts +3 -2
- package/src/dragAndDropHandler/index.ts +3 -17
- package/src/elementsRenderer.ts +124 -55
- package/src/events.ts +13 -7
- package/src/folderOpenState.ts +38 -0
- package/src/index.ts +191 -82
- package/src/keyHandler.ts +104 -34
- package/src/methodTypes.ts +6 -0
- package/src/mouseHandler.ts +15 -13
- package/src/node.ts +12 -10
- package/src/nodeElement/folderElement.ts +47 -72
- package/src/nodeElement/index.ts +20 -17
- package/src/options.ts +46 -14
- package/src/saveStateHandler.ts +5 -8
- package/src/selectNodeHandler.ts +69 -25
- package/src/setDefaultOptions.ts +1 -0
- package/src/version.ts +1 -1
- package/tree_element.css +48 -5
- package/tree_element.debug.js +540 -278
- package/tree_element.debug.js.map +1 -1
- package/tree_element.js +2 -2
- package/tree_element.js.map +1 -1
package/lib/elementsRenderer.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { setFolderLiOpenState, setTogglerOpenState } from './folderOpenState.js';
|
|
2
2
|
|
|
3
3
|
/* Renders the tree to html.
|
|
4
4
|
*
|
|
@@ -23,6 +23,7 @@ class ElementsRenderer {
|
|
|
23
23
|
_getTree: getTree,
|
|
24
24
|
_htmlElement: htmlElement,
|
|
25
25
|
_isNodeSelected: isNodeSelected,
|
|
26
|
+
_multiSelect: multiSelect,
|
|
26
27
|
_onCreateLi: onCreateLi,
|
|
27
28
|
_openedIcon: openedIcon = "+",
|
|
28
29
|
_rtl: rtl,
|
|
@@ -39,18 +40,22 @@ class ElementsRenderer {
|
|
|
39
40
|
this._getTree = getTree;
|
|
40
41
|
this._htmlElement = htmlElement;
|
|
41
42
|
this._isNodeSelected = isNodeSelected;
|
|
43
|
+
this._multiSelect = multiSelect;
|
|
42
44
|
this._onCreateLi = onCreateLi;
|
|
43
45
|
this._rtl = rtl;
|
|
44
46
|
this._setNodeElement = setNodeElement;
|
|
45
47
|
this._showEmptyFolder = showEmptyFolder;
|
|
46
48
|
this._tabIndex = tabIndex;
|
|
47
|
-
this.
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
this.
|
|
53
|
-
this.
|
|
49
|
+
this._icons = {
|
|
50
|
+
closed: this._createButtonElement(closedIcon),
|
|
51
|
+
opened: this._createButtonElement(openedIcon)
|
|
52
|
+
};
|
|
53
|
+
let templates = this._createTemplates();
|
|
54
|
+
this._closedFolderTemplate = templates.closedFolderTemplate;
|
|
55
|
+
this._groupUlTemplate = templates.groupUlTemplate;
|
|
56
|
+
this._nodeTemplate = templates.nodeTemplate;
|
|
57
|
+
this._openedFolderTemplate = templates.openedFolderTemplate;
|
|
58
|
+
this._rootUlTemplate = templates.rootUlTemplate;
|
|
54
59
|
}
|
|
55
60
|
_render(fromNode) {
|
|
56
61
|
if (fromNode?.parent) {
|
|
@@ -64,7 +69,7 @@ class ElementsRenderer {
|
|
|
64
69
|
* null when the folder is not rendered or has no children.
|
|
65
70
|
*/
|
|
66
71
|
_renderChildren(node) {
|
|
67
|
-
return
|
|
72
|
+
return node.element && node.hasChildren() ? this._createDomElements(node.element, node.children, false, node.getLevel() + 1) : null;
|
|
68
73
|
}
|
|
69
74
|
_renderFromNode(node) {
|
|
70
75
|
if (!node.element) {
|
|
@@ -84,6 +89,43 @@ class ElementsRenderer {
|
|
|
84
89
|
this._createDomElements(this._htmlElement, tree.children, true, 1);
|
|
85
90
|
}
|
|
86
91
|
}
|
|
92
|
+
|
|
93
|
+
/* Change dragAndDrop after construction. The rendered lists and the
|
|
94
|
+
* templates for new lists get or lose the dnd class.
|
|
95
|
+
*/
|
|
96
|
+
_setDragAndDrop(dragAndDrop) {
|
|
97
|
+
this._dragAndDrop = dragAndDrop;
|
|
98
|
+
this._updateTemplates();
|
|
99
|
+
for (let ul of this._htmlElement.querySelectorAll(`ul.${this._classNames.common}`)) {
|
|
100
|
+
ul.classList.toggle(this._classNames.dnd, dragAndDrop);
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
/* Change multiSelect after construction. Only the templates are updated;
|
|
105
|
+
* the tree must be rendered again.
|
|
106
|
+
*/
|
|
107
|
+
_setMultiSelect(multiSelect) {
|
|
108
|
+
this._multiSelect = multiSelect;
|
|
109
|
+
this._updateTemplates();
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
/* Change tabIndex after construction. The rendered nodes and the
|
|
113
|
+
* templates for new nodes get the new tabindex. The tab stop is updated by
|
|
114
|
+
* TreeElement.updateTabStop.
|
|
115
|
+
*/
|
|
116
|
+
_setTabIndex(tabIndex) {
|
|
117
|
+
this._tabIndex = tabIndex;
|
|
118
|
+
this._updateTemplates();
|
|
119
|
+
for (let li of this._htmlElement.querySelectorAll("li[role=treeitem]")) {
|
|
120
|
+
if (tabIndex === undefined) {
|
|
121
|
+
li.removeAttribute("tabindex");
|
|
122
|
+
} else if (!this._multiSelect && li.getAttribute("aria-selected") === "true") {
|
|
123
|
+
li.setAttribute("tabindex", String(tabIndex));
|
|
124
|
+
} else {
|
|
125
|
+
li.setAttribute("tabindex", "-1");
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
}
|
|
87
129
|
_attachNodeData(node, li) {
|
|
88
130
|
node.element = li;
|
|
89
131
|
this._setNodeElement(li, node);
|
|
@@ -125,10 +167,10 @@ class ElementsRenderer {
|
|
|
125
167
|
// li > div > [toggler], title span, [toggler]
|
|
126
168
|
let div = li.firstChild;
|
|
127
169
|
let titleSpan = div.childNodes[this._buttonLeft ? 1 : 0];
|
|
128
|
-
this.
|
|
170
|
+
this._fillNode(li, titleSpan, node.name, isSelected, level);
|
|
129
171
|
if (node.is_loading) {
|
|
130
172
|
li.classList.add(this._classNames.loading);
|
|
131
|
-
|
|
173
|
+
li.setAttribute("aria-busy", "true");
|
|
132
174
|
}
|
|
133
175
|
return li;
|
|
134
176
|
}
|
|
@@ -139,30 +181,22 @@ class ElementsRenderer {
|
|
|
139
181
|
* state, so there is a template for each.
|
|
140
182
|
*/
|
|
141
183
|
_createFolderTemplate(isOpen) {
|
|
142
|
-
let
|
|
143
|
-
|
|
144
|
-
liClasses.push(this._classNames.closed);
|
|
145
|
-
}
|
|
146
|
-
let li = this._createLiTemplate(liClasses.join(" "));
|
|
184
|
+
let li = this._createLiTemplate(`${this._classNames.common} ${this._classNames.folder}`);
|
|
185
|
+
setFolderLiOpenState(li, isOpen, this._classNames);
|
|
147
186
|
let div = li.firstChild;
|
|
148
187
|
|
|
149
188
|
// The toggler is hidden from screen readers: the icon is decoration, and
|
|
150
189
|
// aria-expanded on the treeitem has the open state.
|
|
151
190
|
let toggler = document.createElement("span");
|
|
152
|
-
toggler.className = this._getButtonClasses(
|
|
191
|
+
toggler.className = this._getButtonClasses();
|
|
153
192
|
toggler.setAttribute("aria-hidden", "true");
|
|
154
|
-
|
|
155
|
-
if (iconElement) {
|
|
156
|
-
toggler.append(iconElement.cloneNode(true));
|
|
157
|
-
}
|
|
193
|
+
setTogglerOpenState(toggler, isOpen, this._classNames, this._icons);
|
|
158
194
|
if (this._buttonLeft) {
|
|
159
195
|
div.append(toggler);
|
|
160
196
|
}
|
|
161
197
|
|
|
162
198
|
// title span
|
|
163
|
-
|
|
164
|
-
titleSpan.setAttribute("aria-expanded", getBoolString(isOpen));
|
|
165
|
-
div.append(titleSpan);
|
|
199
|
+
div.append(this._createTitleSpanTemplate(true));
|
|
166
200
|
if (!this._buttonLeft) {
|
|
167
201
|
div.append(toggler);
|
|
168
202
|
}
|
|
@@ -186,11 +220,22 @@ class ElementsRenderer {
|
|
|
186
220
|
|
|
187
221
|
/*
|
|
188
222
|
Create the outer part of a <li> template: li > div
|
|
223
|
+
The li is the treeitem, so the ul of its children is inside the treeitem.
|
|
189
224
|
*/
|
|
190
225
|
_createLiTemplate(liClasses) {
|
|
191
226
|
let li = document.createElement("li");
|
|
192
227
|
li.className = liClasses;
|
|
193
|
-
li.setAttribute("role", "
|
|
228
|
+
li.setAttribute("role", "treeitem");
|
|
229
|
+
|
|
230
|
+
// Only a multiselect tree marks the nodes that are not selected
|
|
231
|
+
if (this._multiSelect) {
|
|
232
|
+
li.setAttribute("aria-selected", "false");
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
// Every node is focusable, but only the tab stop is in the tab order
|
|
236
|
+
if (this._tabIndex !== undefined) {
|
|
237
|
+
li.setAttribute("tabindex", "-1");
|
|
238
|
+
}
|
|
194
239
|
let div = document.createElement("div");
|
|
195
240
|
div.className = `${this._classNames.element} ${this._classNames.common}`;
|
|
196
241
|
div.setAttribute("role", "none");
|
|
@@ -206,7 +251,7 @@ class ElementsRenderer {
|
|
|
206
251
|
// li > div > title span
|
|
207
252
|
let div = li.firstChild;
|
|
208
253
|
let titleSpan = div.firstChild;
|
|
209
|
-
this.
|
|
254
|
+
this._fillNode(li, titleSpan, node.name, isSelected, level);
|
|
210
255
|
return li;
|
|
211
256
|
}
|
|
212
257
|
|
|
@@ -219,6 +264,15 @@ class ElementsRenderer {
|
|
|
219
264
|
div.append(this._createTitleSpanTemplate(false));
|
|
220
265
|
return li;
|
|
221
266
|
}
|
|
267
|
+
_createTemplates() {
|
|
268
|
+
return {
|
|
269
|
+
closedFolderTemplate: this._createFolderTemplate(false),
|
|
270
|
+
groupUlTemplate: this._createUlTemplate(false),
|
|
271
|
+
nodeTemplate: this._createNodeTemplate(),
|
|
272
|
+
openedFolderTemplate: this._createFolderTemplate(true),
|
|
273
|
+
rootUlTemplate: this._createUlTemplate(true)
|
|
274
|
+
};
|
|
275
|
+
}
|
|
222
276
|
_createTitleSpanTemplate(isFolder) {
|
|
223
277
|
let titleSpan = document.createElement("span");
|
|
224
278
|
let classes = `${this._classNames.title} ${this._classNames.common}`;
|
|
@@ -227,13 +281,6 @@ class ElementsRenderer {
|
|
|
227
281
|
}
|
|
228
282
|
classes += ` ${this._buttonLeft ? this._classNames.titleButtonLeft : this._classNames.titleButtonRight}`;
|
|
229
283
|
titleSpan.className = classes;
|
|
230
|
-
titleSpan.setAttribute("role", "treeitem");
|
|
231
|
-
titleSpan.setAttribute("aria-selected", "false");
|
|
232
|
-
|
|
233
|
-
// Every node is focusable, but only the tab stop is in the tab order
|
|
234
|
-
if (this._tabIndex !== undefined) {
|
|
235
|
-
titleSpan.setAttribute("tabindex", "-1");
|
|
236
|
-
}
|
|
237
284
|
return titleSpan;
|
|
238
285
|
}
|
|
239
286
|
_createUlTemplate(isRootNode) {
|
|
@@ -262,20 +309,25 @@ class ElementsRenderer {
|
|
|
262
309
|
if (this._ariaLabelledBy !== undefined) {
|
|
263
310
|
ul.setAttribute("aria-labelledby", this._ariaLabelledBy);
|
|
264
311
|
}
|
|
312
|
+
if (this._multiSelect) {
|
|
313
|
+
ul.setAttribute("aria-multiselectable", "true");
|
|
314
|
+
}
|
|
265
315
|
}
|
|
266
316
|
return ul;
|
|
267
317
|
}
|
|
268
318
|
|
|
269
319
|
/*
|
|
270
|
-
Set the parts of a cloned title span that differ per node
|
|
320
|
+
Set the parts of a cloned li and title span that differ per node
|
|
271
321
|
*/
|
|
272
|
-
|
|
273
|
-
|
|
322
|
+
_fillNode(li, titleSpan, nodeName, isSelected, level) {
|
|
323
|
+
li.setAttribute("aria-level", String(level));
|
|
274
324
|
if (isSelected) {
|
|
275
|
-
|
|
325
|
+
li.setAttribute("aria-selected", "true");
|
|
276
326
|
let tabIndex = this._tabIndex;
|
|
277
|
-
|
|
278
|
-
|
|
327
|
+
|
|
328
|
+
// With multiSelect the tab stop is the active node, see updateTabStop
|
|
329
|
+
if (tabIndex !== undefined && !this._multiSelect) {
|
|
330
|
+
li.setAttribute("tabindex", String(tabIndex));
|
|
279
331
|
}
|
|
280
332
|
}
|
|
281
333
|
if (this._autoEscape) {
|
|
@@ -284,12 +336,13 @@ class ElementsRenderer {
|
|
|
284
336
|
// eslint-disable-next-line no-unsanitized/property -- the user opted out of escaping with autoEscape: false
|
|
285
337
|
titleSpan.innerHTML = nodeName;
|
|
286
338
|
}
|
|
339
|
+
|
|
340
|
+
// The treeitem is named by its title, without the html when autoEscape
|
|
341
|
+
// is false. Otherwise the name would contain everything in the row.
|
|
342
|
+
li.setAttribute("aria-label", titleSpan.textContent);
|
|
287
343
|
}
|
|
288
|
-
_getButtonClasses(
|
|
344
|
+
_getButtonClasses() {
|
|
289
345
|
let classes = [this._classNames.toggler, this._classNames.common];
|
|
290
|
-
if (!isOpen) {
|
|
291
|
-
classes.push(this._classNames.closed);
|
|
292
|
-
}
|
|
293
346
|
if (this._buttonLeft) {
|
|
294
347
|
classes.push(this._classNames.togglerLeft);
|
|
295
348
|
} else {
|
|
@@ -304,6 +357,14 @@ class ElementsRenderer {
|
|
|
304
357
|
_mustRenderChildren(node) {
|
|
305
358
|
return node.hasChildren() && node.is_open === true;
|
|
306
359
|
}
|
|
360
|
+
_updateTemplates() {
|
|
361
|
+
let templates = this._createTemplates();
|
|
362
|
+
this._closedFolderTemplate = templates.closedFolderTemplate;
|
|
363
|
+
this._groupUlTemplate = templates.groupUlTemplate;
|
|
364
|
+
this._nodeTemplate = templates.nodeTemplate;
|
|
365
|
+
this._openedFolderTemplate = templates.openedFolderTemplate;
|
|
366
|
+
this._rootUlTemplate = templates.rootUlTemplate;
|
|
367
|
+
}
|
|
307
368
|
}
|
|
308
369
|
|
|
309
370
|
export { ElementsRenderer as default };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"elementsRenderer.js","sources":["../src/elementsRenderer.ts"],"sourcesContent":["import type { ClassNames } from \"./classNames\";\nimport type { GetTree, IsNodeSelected } from \"./methodTypes\";\nimport type { Node } from \"./node\";\nimport type { IconElement, OnCreateLi } from \"./options\";\n\nimport { getBoolString } from \"./util\";\n\ninterface ElementsRendererParams {\n ariaLabel?: string;\n ariaLabelledBy?: string;\n autoEscape: boolean;\n buttonLeft: boolean;\n classNames: ClassNames;\n closedIcon?: IconElement;\n dragAndDrop: boolean;\n getTree: GetTree;\n htmlElement: HTMLElement;\n isNodeSelected: IsNodeSelected;\n onCreateLi?: OnCreateLi;\n openedIcon?: IconElement;\n rtl?: boolean;\n setNodeElement: (element: HTMLElement, node: Node) => void;\n showEmptyFolder: boolean;\n tabIndex?: number;\n}\n\n/* Renders the tree to html.\n *\n * The children of a closed folder are not rendered. They are rendered when\n * the folder is opened, see renderChildren.\n *\n * The elements are created by cloning templates. A template is a fully\n * built <li> or <ul> with everything that is the same for every node\n * (structure, roles, static classes, the toggler icon). Per node only the\n * parts that differ are set: the title, the aria attributes and the\n * selected and loading classes.\n */\nexport default class ElementsRenderer {\n public closedIconElement?: globalThis.Node;\n public openedIconElement?: globalThis.Node;\n private ariaLabel?: string;\n private ariaLabelledBy?: string;\n private autoEscape: boolean;\n private buttonLeft: boolean;\n private classNames: ClassNames;\n private closedFolderTemplate: HTMLLIElement;\n private dragAndDrop: boolean;\n private getTree: GetTree;\n private groupUlTemplate: HTMLUListElement;\n private htmlElement: HTMLElement;\n private isNodeSelected: IsNodeSelected;\n private nodeTemplate: HTMLLIElement;\n private onCreateLi?: OnCreateLi;\n private openedFolderTemplate: HTMLLIElement;\n private rootUlTemplate: HTMLUListElement;\n private rtl?: boolean;\n private setNodeElement: (element: HTMLElement, node: Node) => void;\n private showEmptyFolder: boolean;\n private tabIndex?: number;\n\n constructor({\n ariaLabel,\n ariaLabelledBy,\n autoEscape,\n buttonLeft,\n classNames,\n closedIcon = \"-\",\n dragAndDrop,\n getTree,\n htmlElement,\n isNodeSelected,\n onCreateLi,\n openedIcon = \"+\",\n rtl,\n setNodeElement,\n showEmptyFolder,\n tabIndex,\n }: ElementsRendererParams) {\n this.ariaLabel = ariaLabel;\n this.ariaLabelledBy = ariaLabelledBy;\n this.autoEscape = autoEscape;\n this.buttonLeft = buttonLeft;\n this.classNames = classNames;\n this.dragAndDrop = dragAndDrop;\n this.getTree = getTree;\n this.htmlElement = htmlElement;\n this.isNodeSelected = isNodeSelected;\n this.onCreateLi = onCreateLi;\n this.rtl = rtl;\n this.setNodeElement = setNodeElement;\n this.showEmptyFolder = showEmptyFolder;\n this.tabIndex = tabIndex;\n this.openedIconElement = this.createButtonElement(openedIcon);\n this.closedIconElement = this.createButtonElement(closedIcon);\n\n this.rootUlTemplate = this.createUlTemplate(true);\n this.groupUlTemplate = this.createUlTemplate(false);\n this.nodeTemplate = this.createNodeTemplate();\n this.openedFolderTemplate = this.createFolderTemplate(true);\n this.closedFolderTemplate = this.createFolderTemplate(false);\n }\n\n public render(fromNode: Node | null): void {\n if (fromNode?.parent) {\n this.renderFromNode(fromNode);\n } else {\n this.renderFromRoot();\n }\n }\n\n /* Render the children of a rendered folder. Returns the new <ul>, or\n * null when the folder is not rendered or has no children.\n */\n public renderChildren(node: Node): HTMLUListElement | null {\n return !node.element || !node.hasChildren()\n ? null\n : this.createDomElements(\n node.element,\n node.children,\n false,\n node.getLevel() + 1,\n );\n }\n\n public renderFromNode(node: Node): void {\n if (!node.element) {\n return;\n }\n\n const currentLi = node.element;\n const newLi = this.createLi(node, node.getLevel());\n currentLi.replaceWith(newLi);\n\n if (this.mustRenderChildren(node)) {\n this.createDomElements(newLi, node.children, false, node.getLevel() + 1);\n }\n }\n\n public renderFromRoot(): void {\n this.htmlElement.textContent = \"\";\n\n const tree = this.getTree();\n\n if (tree) {\n this.createDomElements(this.htmlElement, tree.children, true, 1);\n }\n }\n\n private attachNodeData(node: Node, li: HTMLElement): void {\n node.element = li;\n this.setNodeElement(li, node);\n }\n\n /* Returns the template of a toggler icon; it is cloned for every folder.\n * A string is parsed as html and becomes a fragment, so it can hold\n * entities, text and elements.\n */\n private createButtonElement(value: IconElement): globalThis.Node | undefined {\n if (typeof value === \"string\") {\n const template = document.createElement(\"template\");\n // eslint-disable-next-line no-unsanitized/property -- icon options are documented to accept html\n template.innerHTML = value;\n\n return template.content;\n }\n return value.nodeType ? value : undefined;\n }\n\n private createDomElements(\n element: Element,\n children: Node[],\n isRootNode: boolean,\n level: number,\n ): HTMLUListElement {\n const template = isRootNode ? this.rootUlTemplate : this.groupUlTemplate;\n const ul = template.cloneNode() as HTMLUListElement;\n element.append(ul);\n\n for (const child of children) {\n const li = this.createLi(child, level);\n ul.append(li);\n\n if (this.mustRenderChildren(child)) {\n this.createDomElements(li, child.children, false, level + 1);\n }\n }\n\n return ul;\n }\n\n private createFolderLi(\n node: Node,\n level: number,\n isSelected: boolean,\n ): HTMLLIElement {\n const template = node.is_open\n ? this.openedFolderTemplate\n : this.closedFolderTemplate;\n const li = template.cloneNode(true) as HTMLLIElement;\n\n if (isSelected) {\n li.classList.add(this.classNames.selected);\n }\n\n // li > div > [toggler], title span, [toggler]\n const div = li.firstChild as HTMLDivElement;\n const titleSpan = div.childNodes[\n this.buttonLeft ? 1 : 0\n ] as HTMLSpanElement;\n\n this.fillTitleSpan(titleSpan, node.name, isSelected, level);\n\n if (node.is_loading) {\n li.classList.add(this.classNames.loading);\n titleSpan.setAttribute(\"aria-busy\", \"true\");\n }\n\n return li;\n }\n\n /* Template for a folder <li>:\n * li > div > [toggler], title span, [toggler]\n * The toggler icon and the aria-expanded attribute depend on the open\n * state, so there is a template for each.\n */\n private createFolderTemplate(isOpen: boolean): HTMLLIElement {\n const liClasses = [this.classNames.common, this.classNames.folder];\n\n if (!isOpen) {\n liClasses.push(this.classNames.closed);\n }\n\n const li = this.createLiTemplate(liClasses.join(\" \"));\n const div = li.firstChild as HTMLDivElement;\n\n // The toggler is hidden from screen readers: the icon is decoration, and\n // aria-expanded on the treeitem has the open state.\n const toggler = document.createElement(\"span\");\n toggler.className = this.getButtonClasses(isOpen);\n toggler.setAttribute(\"aria-hidden\", \"true\");\n\n const iconElement = isOpen\n ? this.openedIconElement\n : this.closedIconElement;\n\n if (iconElement) {\n toggler.append(iconElement.cloneNode(true));\n }\n\n if (this.buttonLeft) {\n div.append(toggler);\n }\n\n // title span\n const titleSpan = this.createTitleSpanTemplate(true);\n titleSpan.setAttribute(\"aria-expanded\", getBoolString(isOpen));\n div.append(titleSpan);\n\n if (!this.buttonLeft) {\n div.append(toggler);\n }\n\n return li;\n }\n\n /* Create the <li> element\n * Attach it to node.element.\n * Call onCreateLi\n */\n private createLi(node: Node, level: number): HTMLLIElement {\n const isSelected = this.isNodeSelected(node);\n\n const mustShowFolder =\n node.isFolder() || (node.isEmptyFolder && this.showEmptyFolder);\n\n const li = mustShowFolder\n ? this.createFolderLi(node, level, isSelected)\n : this.createNodeLi(node, level, isSelected);\n\n this.attachNodeData(node, li);\n\n if (this.onCreateLi) {\n this.onCreateLi(node, li, isSelected);\n }\n\n return li;\n }\n\n /*\n Create the outer part of a <li> template: li > div\n */\n private createLiTemplate(liClasses: string): HTMLLIElement {\n const li = document.createElement(\"li\");\n li.className = liClasses;\n li.setAttribute(\"role\", \"none\");\n\n const div = document.createElement(\"div\");\n div.className = `${this.classNames.element} ${this.classNames.common}`;\n div.setAttribute(\"role\", \"none\");\n\n li.append(div);\n\n return li;\n }\n\n private createNodeLi(\n node: Node,\n level: number,\n isSelected: boolean,\n ): HTMLLIElement {\n const li = this.nodeTemplate.cloneNode(true) as HTMLLIElement;\n\n if (isSelected) {\n li.classList.add(this.classNames.selected);\n }\n\n // li > div > title span\n const div = li.firstChild as HTMLDivElement;\n const titleSpan = div.firstChild as HTMLSpanElement;\n\n this.fillTitleSpan(titleSpan, node.name, isSelected, level);\n\n return li;\n }\n\n /*\n Template for a <li> without children: li > div > title span\n */\n private createNodeTemplate(): HTMLLIElement {\n const li = this.createLiTemplate(this.classNames.common);\n const div = li.firstChild as HTMLDivElement;\n\n div.append(this.createTitleSpanTemplate(false));\n\n return li;\n }\n\n private createTitleSpanTemplate(isFolder: boolean): HTMLSpanElement {\n const titleSpan = document.createElement(\"span\");\n\n let classes = `${this.classNames.title} ${this.classNames.common}`;\n\n if (isFolder) {\n classes += ` ${this.classNames.titleFolder}`;\n }\n\n classes += ` ${this.buttonLeft ? this.classNames.titleButtonLeft : this.classNames.titleButtonRight}`;\n\n titleSpan.className = classes;\n titleSpan.setAttribute(\"role\", \"treeitem\");\n titleSpan.setAttribute(\"aria-selected\", \"false\");\n\n // Every node is focusable, but only the tab stop is in the tab order\n if (this.tabIndex !== undefined) {\n titleSpan.setAttribute(\"tabindex\", \"-1\");\n }\n\n return titleSpan;\n }\n\n private createUlTemplate(isRootNode: boolean): HTMLUListElement {\n let classString;\n let role;\n\n if (isRootNode) {\n classString = this.classNames.tree;\n role = \"tree\";\n\n if (this.rtl) {\n classString += ` ${this.classNames.rtl}`;\n }\n } else {\n classString = \"\";\n role = \"group\";\n }\n\n if (this.dragAndDrop) {\n classString += ` ${this.classNames.dnd}`;\n }\n\n const ul = document.createElement(\"ul\");\n ul.className = `${this.classNames.common} ${classString}`;\n\n ul.setAttribute(\"role\", role);\n\n if (isRootNode) {\n if (this.ariaLabel !== undefined) {\n ul.setAttribute(\"aria-label\", this.ariaLabel);\n }\n\n if (this.ariaLabelledBy !== undefined) {\n ul.setAttribute(\"aria-labelledby\", this.ariaLabelledBy);\n }\n }\n\n return ul;\n }\n\n /*\n Set the parts of a cloned title span that differ per node\n */\n private fillTitleSpan(\n titleSpan: HTMLSpanElement,\n nodeName: string,\n isSelected: boolean,\n level: number,\n ): void {\n titleSpan.setAttribute(\"aria-level\", String(level));\n\n if (isSelected) {\n titleSpan.setAttribute(\"aria-selected\", \"true\");\n\n const tabIndex = this.tabIndex;\n\n if (tabIndex !== undefined) {\n titleSpan.setAttribute(\"tabindex\", String(tabIndex));\n }\n }\n\n if (this.autoEscape) {\n titleSpan.textContent = nodeName;\n } else {\n // eslint-disable-next-line no-unsanitized/property -- the user opted out of escaping with autoEscape: false\n titleSpan.innerHTML = nodeName;\n }\n }\n\n private getButtonClasses(isOpen: boolean): string {\n const classes = [this.classNames.toggler, this.classNames.common];\n\n if (!isOpen) {\n classes.push(this.classNames.closed);\n }\n\n if (this.buttonLeft) {\n classes.push(this.classNames.togglerLeft);\n } else {\n classes.push(this.classNames.togglerRight);\n }\n\n return classes.join(\" \");\n }\n\n /*\n The children of a closed folder are rendered when it is opened\n */\n private mustRenderChildren(node: Node): boolean {\n return node.hasChildren() && node.is_open === true;\n }\n}\n"],"names":["ariaLabel","ariaLabelledBy","autoEscape","buttonLeft","classNames","dragAndDrop","getTree","htmlElement","isNodeSelected","onCreateLi","rtl","setNodeElement","showEmptyFolder","tabIndex","openedIconElement","createButtonElement","closedIconElement","rootUlTemplate","createUlTemplate","groupUlTemplate","nodeTemplate","createNodeTemplate","openedFolderTemplate","createFolderTemplate","closedFolderTemplate","render","renderFromNode","renderFromRoot","renderChildren","createDomElements","createLi","mustRenderChildren","attachNodeData","createFolderLi","fillTitleSpan","createLiTemplate","getButtonClasses","createTitleSpanTemplate","createNodeLi"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"elementsRenderer.js","sources":["../src/elementsRenderer.ts"],"sourcesContent":["import type { ClassNames } from \"./classNames\";\nimport type { FolderIcons } from \"./folderOpenState\";\nimport type { GetTree, IsNodeSelected } from \"./methodTypes\";\nimport type { Node } from \"./node\";\nimport type { IconElement, OnCreateLi } from \"./options\";\n\nimport { setFolderLiOpenState, setTogglerOpenState } from \"./folderOpenState\";\n\ninterface ElementsRendererParams {\n ariaLabel?: string;\n ariaLabelledBy?: string;\n autoEscape: boolean;\n buttonLeft: boolean;\n classNames: ClassNames;\n closedIcon?: IconElement;\n dragAndDrop: boolean;\n getTree: GetTree;\n htmlElement: HTMLElement;\n isNodeSelected: IsNodeSelected;\n multiSelect: boolean;\n onCreateLi?: OnCreateLi;\n openedIcon?: IconElement;\n rtl?: boolean;\n setNodeElement: (element: HTMLElement, node: Node) => void;\n showEmptyFolder: boolean;\n tabIndex?: number;\n}\n\n/* Renders the tree to html.\n *\n * The children of a closed folder are not rendered. They are rendered when\n * the folder is opened, see renderChildren.\n *\n * The elements are created by cloning templates. A template is a fully\n * built <li> or <ul> with everything that is the same for every node\n * (structure, roles, static classes, the toggler icon). Per node only the\n * parts that differ are set: the title, the aria attributes and the\n * selected and loading classes.\n */\nexport default class ElementsRenderer {\n public icons: FolderIcons;\n private ariaLabel?: string;\n private ariaLabelledBy?: string;\n private autoEscape: boolean;\n private buttonLeft: boolean;\n private classNames: ClassNames;\n private closedFolderTemplate: HTMLLIElement;\n private dragAndDrop: boolean;\n private getTree: GetTree;\n private groupUlTemplate: HTMLUListElement;\n private htmlElement: HTMLElement;\n private isNodeSelected: IsNodeSelected;\n private multiSelect: boolean;\n private nodeTemplate: HTMLLIElement;\n private onCreateLi?: OnCreateLi;\n private openedFolderTemplate: HTMLLIElement;\n private rootUlTemplate: HTMLUListElement;\n private rtl?: boolean;\n private setNodeElement: (element: HTMLElement, node: Node) => void;\n private showEmptyFolder: boolean;\n private tabIndex?: number;\n\n constructor({\n ariaLabel,\n ariaLabelledBy,\n autoEscape,\n buttonLeft,\n classNames,\n closedIcon = \"-\",\n dragAndDrop,\n getTree,\n htmlElement,\n isNodeSelected,\n multiSelect,\n onCreateLi,\n openedIcon = \"+\",\n rtl,\n setNodeElement,\n showEmptyFolder,\n tabIndex,\n }: ElementsRendererParams) {\n this.ariaLabel = ariaLabel;\n this.ariaLabelledBy = ariaLabelledBy;\n this.autoEscape = autoEscape;\n this.buttonLeft = buttonLeft;\n this.classNames = classNames;\n this.dragAndDrop = dragAndDrop;\n this.getTree = getTree;\n this.htmlElement = htmlElement;\n this.isNodeSelected = isNodeSelected;\n this.multiSelect = multiSelect;\n this.onCreateLi = onCreateLi;\n this.rtl = rtl;\n this.setNodeElement = setNodeElement;\n this.showEmptyFolder = showEmptyFolder;\n this.tabIndex = tabIndex;\n this.icons = {\n closed: this.createButtonElement(closedIcon),\n opened: this.createButtonElement(openedIcon),\n };\n\n const templates = this.createTemplates();\n this.closedFolderTemplate = templates.closedFolderTemplate;\n this.groupUlTemplate = templates.groupUlTemplate;\n this.nodeTemplate = templates.nodeTemplate;\n this.openedFolderTemplate = templates.openedFolderTemplate;\n this.rootUlTemplate = templates.rootUlTemplate;\n }\n\n public render(fromNode: Node | null): void {\n if (fromNode?.parent) {\n this.renderFromNode(fromNode);\n } else {\n this.renderFromRoot();\n }\n }\n\n /* Render the children of a rendered folder. Returns the new <ul>, or\n * null when the folder is not rendered or has no children.\n */\n public renderChildren(node: Node): HTMLUListElement | null {\n return node.element && node.hasChildren()\n ? this.createDomElements(\n node.element,\n node.children,\n false,\n node.getLevel() + 1,\n )\n : null;\n }\n\n public renderFromNode(node: Node): void {\n if (!node.element) {\n return;\n }\n\n const currentLi = node.element;\n const newLi = this.createLi(node, node.getLevel());\n currentLi.replaceWith(newLi);\n\n if (this.mustRenderChildren(node)) {\n this.createDomElements(newLi, node.children, false, node.getLevel() + 1);\n }\n }\n\n public renderFromRoot(): void {\n this.htmlElement.textContent = \"\";\n\n const tree = this.getTree();\n\n if (tree) {\n this.createDomElements(this.htmlElement, tree.children, true, 1);\n }\n }\n\n /* Change dragAndDrop after construction. The rendered lists and the\n * templates for new lists get or lose the dnd class.\n */\n public setDragAndDrop(dragAndDrop: boolean): void {\n this.dragAndDrop = dragAndDrop;\n this.updateTemplates();\n\n for (const ul of this.htmlElement.querySelectorAll(\n `ul.${this.classNames.common}`,\n )) {\n ul.classList.toggle(this.classNames.dnd, dragAndDrop);\n }\n }\n\n /* Change multiSelect after construction. Only the templates are updated;\n * the tree must be rendered again.\n */\n public setMultiSelect(multiSelect: boolean): void {\n this.multiSelect = multiSelect;\n this.updateTemplates();\n }\n\n /* Change tabIndex after construction. The rendered nodes and the\n * templates for new nodes get the new tabindex. The tab stop is updated by\n * TreeElement.updateTabStop.\n */\n public setTabIndex(tabIndex: number | undefined): void {\n this.tabIndex = tabIndex;\n this.updateTemplates();\n\n for (const li of this.htmlElement.querySelectorAll(\"li[role=treeitem]\")) {\n if (tabIndex === undefined) {\n li.removeAttribute(\"tabindex\");\n } else if (\n !this.multiSelect &&\n li.getAttribute(\"aria-selected\") === \"true\"\n ) {\n li.setAttribute(\"tabindex\", String(tabIndex));\n } else {\n li.setAttribute(\"tabindex\", \"-1\");\n }\n }\n }\n\n private attachNodeData(node: Node, li: HTMLElement): void {\n node.element = li;\n this.setNodeElement(li, node);\n }\n\n /* Returns the template of a toggler icon; it is cloned for every folder.\n * A string is parsed as html and becomes a fragment, so it can hold\n * entities, text and elements.\n */\n private createButtonElement(value: IconElement): globalThis.Node | undefined {\n if (typeof value === \"string\") {\n const template = document.createElement(\"template\");\n // eslint-disable-next-line no-unsanitized/property -- icon options are documented to accept html\n template.innerHTML = value;\n\n return template.content;\n }\n return value.nodeType ? value : undefined;\n }\n\n private createDomElements(\n element: Element,\n children: Node[],\n isRootNode: boolean,\n level: number,\n ): HTMLUListElement {\n const template = isRootNode ? this.rootUlTemplate : this.groupUlTemplate;\n const ul = template.cloneNode() as HTMLUListElement;\n element.append(ul);\n\n for (const child of children) {\n const li = this.createLi(child, level);\n ul.append(li);\n\n if (this.mustRenderChildren(child)) {\n this.createDomElements(li, child.children, false, level + 1);\n }\n }\n\n return ul;\n }\n\n private createFolderLi(\n node: Node,\n level: number,\n isSelected: boolean,\n ): HTMLLIElement {\n const template = node.is_open\n ? this.openedFolderTemplate\n : this.closedFolderTemplate;\n const li = template.cloneNode(true) as HTMLLIElement;\n\n if (isSelected) {\n li.classList.add(this.classNames.selected);\n }\n\n // li > div > [toggler], title span, [toggler]\n const div = li.firstChild as HTMLDivElement;\n const titleSpan = div.childNodes[\n this.buttonLeft ? 1 : 0\n ] as HTMLSpanElement;\n\n this.fillNode(li, titleSpan, node.name, isSelected, level);\n\n if (node.is_loading) {\n li.classList.add(this.classNames.loading);\n li.setAttribute(\"aria-busy\", \"true\");\n }\n\n return li;\n }\n\n /* Template for a folder <li>:\n * li > div > [toggler], title span, [toggler]\n * The toggler icon and the aria-expanded attribute depend on the open\n * state, so there is a template for each.\n */\n private createFolderTemplate(isOpen: boolean): HTMLLIElement {\n const li = this.createLiTemplate(\n `${this.classNames.common} ${this.classNames.folder}`,\n );\n setFolderLiOpenState(li, isOpen, this.classNames);\n\n const div = li.firstChild as HTMLDivElement;\n\n // The toggler is hidden from screen readers: the icon is decoration, and\n // aria-expanded on the treeitem has the open state.\n const toggler = document.createElement(\"span\");\n toggler.className = this.getButtonClasses();\n toggler.setAttribute(\"aria-hidden\", \"true\");\n setTogglerOpenState(toggler, isOpen, this.classNames, this.icons);\n\n if (this.buttonLeft) {\n div.append(toggler);\n }\n\n // title span\n div.append(this.createTitleSpanTemplate(true));\n\n if (!this.buttonLeft) {\n div.append(toggler);\n }\n\n return li;\n }\n\n /* Create the <li> element\n * Attach it to node.element.\n * Call onCreateLi\n */\n private createLi(node: Node, level: number): HTMLLIElement {\n const isSelected = this.isNodeSelected(node);\n\n const mustShowFolder =\n node.isFolder() || (node.isEmptyFolder && this.showEmptyFolder);\n\n const li = mustShowFolder\n ? this.createFolderLi(node, level, isSelected)\n : this.createNodeLi(node, level, isSelected);\n\n this.attachNodeData(node, li);\n\n if (this.onCreateLi) {\n this.onCreateLi(node, li, isSelected);\n }\n\n return li;\n }\n\n /*\n Create the outer part of a <li> template: li > div\n The li is the treeitem, so the ul of its children is inside the treeitem.\n */\n private createLiTemplate(liClasses: string): HTMLLIElement {\n const li = document.createElement(\"li\");\n li.className = liClasses;\n li.setAttribute(\"role\", \"treeitem\");\n\n // Only a multiselect tree marks the nodes that are not selected\n if (this.multiSelect) {\n li.setAttribute(\"aria-selected\", \"false\");\n }\n\n // Every node is focusable, but only the tab stop is in the tab order\n if (this.tabIndex !== undefined) {\n li.setAttribute(\"tabindex\", \"-1\");\n }\n\n const div = document.createElement(\"div\");\n div.className = `${this.classNames.element} ${this.classNames.common}`;\n div.setAttribute(\"role\", \"none\");\n\n li.append(div);\n\n return li;\n }\n\n private createNodeLi(\n node: Node,\n level: number,\n isSelected: boolean,\n ): HTMLLIElement {\n const li = this.nodeTemplate.cloneNode(true) as HTMLLIElement;\n\n if (isSelected) {\n li.classList.add(this.classNames.selected);\n }\n\n // li > div > title span\n const div = li.firstChild as HTMLDivElement;\n const titleSpan = div.firstChild as HTMLSpanElement;\n\n this.fillNode(li, titleSpan, node.name, isSelected, level);\n\n return li;\n }\n\n /*\n Template for a <li> without children: li > div > title span\n */\n private createNodeTemplate(): HTMLLIElement {\n const li = this.createLiTemplate(this.classNames.common);\n const div = li.firstChild as HTMLDivElement;\n\n div.append(this.createTitleSpanTemplate(false));\n\n return li;\n }\n\n private createTemplates() {\n return {\n closedFolderTemplate: this.createFolderTemplate(false),\n groupUlTemplate: this.createUlTemplate(false),\n nodeTemplate: this.createNodeTemplate(),\n openedFolderTemplate: this.createFolderTemplate(true),\n rootUlTemplate: this.createUlTemplate(true),\n };\n }\n\n private createTitleSpanTemplate(isFolder: boolean): HTMLSpanElement {\n const titleSpan = document.createElement(\"span\");\n\n let classes = `${this.classNames.title} ${this.classNames.common}`;\n\n if (isFolder) {\n classes += ` ${this.classNames.titleFolder}`;\n }\n\n classes += ` ${this.buttonLeft ? this.classNames.titleButtonLeft : this.classNames.titleButtonRight}`;\n\n titleSpan.className = classes;\n\n return titleSpan;\n }\n\n private createUlTemplate(isRootNode: boolean): HTMLUListElement {\n let classString;\n let role;\n\n if (isRootNode) {\n classString = this.classNames.tree;\n role = \"tree\";\n\n if (this.rtl) {\n classString += ` ${this.classNames.rtl}`;\n }\n } else {\n classString = \"\";\n role = \"group\";\n }\n\n if (this.dragAndDrop) {\n classString += ` ${this.classNames.dnd}`;\n }\n\n const ul = document.createElement(\"ul\");\n ul.className = `${this.classNames.common} ${classString}`;\n\n ul.setAttribute(\"role\", role);\n\n if (isRootNode) {\n if (this.ariaLabel !== undefined) {\n ul.setAttribute(\"aria-label\", this.ariaLabel);\n }\n\n if (this.ariaLabelledBy !== undefined) {\n ul.setAttribute(\"aria-labelledby\", this.ariaLabelledBy);\n }\n\n if (this.multiSelect) {\n ul.setAttribute(\"aria-multiselectable\", \"true\");\n }\n }\n\n return ul;\n }\n\n /*\n Set the parts of a cloned li and title span that differ per node\n */\n private fillNode(\n li: HTMLLIElement,\n titleSpan: HTMLSpanElement,\n nodeName: string,\n isSelected: boolean,\n level: number,\n ): void {\n li.setAttribute(\"aria-level\", String(level));\n\n if (isSelected) {\n li.setAttribute(\"aria-selected\", \"true\");\n\n const tabIndex = this.tabIndex;\n\n // With multiSelect the tab stop is the active node, see updateTabStop\n if (tabIndex !== undefined && !this.multiSelect) {\n li.setAttribute(\"tabindex\", String(tabIndex));\n }\n }\n\n if (this.autoEscape) {\n titleSpan.textContent = nodeName;\n } else {\n // eslint-disable-next-line no-unsanitized/property -- the user opted out of escaping with autoEscape: false\n titleSpan.innerHTML = nodeName;\n }\n\n // The treeitem is named by its title, without the html when autoEscape\n // is false. Otherwise the name would contain everything in the row.\n li.setAttribute(\"aria-label\", titleSpan.textContent);\n }\n\n private getButtonClasses(): string {\n const classes = [this.classNames.toggler, this.classNames.common];\n\n if (this.buttonLeft) {\n classes.push(this.classNames.togglerLeft);\n } else {\n classes.push(this.classNames.togglerRight);\n }\n\n return classes.join(\" \");\n }\n\n /*\n The children of a closed folder are rendered when it is opened\n */\n private mustRenderChildren(node: Node): boolean {\n return node.hasChildren() && node.is_open === true;\n }\n\n private updateTemplates(): void {\n const templates = this.createTemplates();\n this.closedFolderTemplate = templates.closedFolderTemplate;\n this.groupUlTemplate = templates.groupUlTemplate;\n this.nodeTemplate = templates.nodeTemplate;\n this.openedFolderTemplate = templates.openedFolderTemplate;\n this.rootUlTemplate = templates.rootUlTemplate;\n }\n}\n"],"names":["ariaLabel","ariaLabelledBy","autoEscape","buttonLeft","classNames","dragAndDrop","getTree","htmlElement","isNodeSelected","multiSelect","onCreateLi","rtl","setNodeElement","showEmptyFolder","tabIndex","icons","createButtonElement","createTemplates","closedFolderTemplate","groupUlTemplate","nodeTemplate","openedFolderTemplate","rootUlTemplate","render","renderFromNode","renderFromRoot","renderChildren","createDomElements","createLi","mustRenderChildren","setDragAndDrop","updateTemplates","setMultiSelect","setTabIndex","attachNodeData","createFolderLi","fillNode","createFolderTemplate","createLiTemplate","getButtonClasses","createTitleSpanTemplate","createNodeLi","createNodeTemplate","createUlTemplate"],"mappings":"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"}
|
package/lib/events.d.ts
CHANGED
|
@@ -13,7 +13,7 @@ export interface TreeEvents {
|
|
|
13
13
|
/**
|
|
14
14
|
* Dispatched once, after the tree is rendered for the first time. With
|
|
15
15
|
* `dataUrl` this is after the data has arrived, so it is the moment the
|
|
16
|
-
*
|
|
16
|
+
* API is safe to use:
|
|
17
17
|
*
|
|
18
18
|
* ```js
|
|
19
19
|
* element.addEventListener("tree.init", () => {
|
|
@@ -73,7 +73,7 @@ export interface TreeEvents {
|
|
|
73
73
|
originalEvent: MouseEvent;
|
|
74
74
|
};
|
|
75
75
|
/**
|
|
76
|
-
* Dispatched
|
|
76
|
+
* Dispatched when a node is right-clicked, unless `useContextMenu` is
|
|
77
77
|
* `false`. The browser's own menu is suppressed.
|
|
78
78
|
*
|
|
79
79
|
* @group Mouse
|
|
@@ -84,7 +84,7 @@ export interface TreeEvents {
|
|
|
84
84
|
};
|
|
85
85
|
/**
|
|
86
86
|
* Dispatched when `Enter` is pressed on the selected node, or on the
|
|
87
|
-
* focused node when no node is selected. Use it for what
|
|
87
|
+
* focused node when no node is selected. Use it for what clicking a
|
|
88
88
|
* link would do, like opening the edit page of the node:
|
|
89
89
|
*
|
|
90
90
|
* ```js
|
|
@@ -130,7 +130,9 @@ export interface TreeEvents {
|
|
|
130
130
|
*/
|
|
131
131
|
"tree.select": {
|
|
132
132
|
/**
|
|
133
|
-
The node that was selected before, if any.
|
|
133
|
+
The node that was selected before, if any. When several nodes were
|
|
134
|
+
selected, this is the first, and the others get a `tree.deselect`,
|
|
135
|
+
dispatched before this event.
|
|
134
136
|
*/
|
|
135
137
|
deselectedNode: Node | null;
|
|
136
138
|
/**
|
|
@@ -143,13 +145,17 @@ export interface TreeEvents {
|
|
|
143
145
|
* is clicked again or passed to `selectNode` again with
|
|
144
146
|
* `mustToggle: true`. No `tree.select` is dispatched for it.
|
|
145
147
|
*
|
|
148
|
+
* When several nodes are selected and a click or `selectNode` selects just
|
|
149
|
+
* one node, it is dispatched for each node that loses the selection, except
|
|
150
|
+
* the one in the `deselectedNode` of `tree.select`.
|
|
151
|
+
*
|
|
146
152
|
* ```js
|
|
147
153
|
* element.addEventListener("tree.deselect", (e) => {
|
|
148
154
|
* console.log("deselected", e.detail.node.name);
|
|
149
155
|
* });
|
|
150
156
|
* ```
|
|
151
157
|
*
|
|
152
|
-
* Selecting another node does not dispatch it
|
|
158
|
+
* Selecting another node does not dispatch it—that is a `tree.select`
|
|
153
159
|
* with the previous node in `deselectedNode`. It is also not dispatched
|
|
154
160
|
* by `selectNode` without `mustToggle: true`, `selectNode(null)`,
|
|
155
161
|
* `removeFromSelection`, `removeNode`, `loadData` and restoring a saved
|
|
@@ -186,7 +192,7 @@ export interface TreeEvents {
|
|
|
186
192
|
};
|
|
187
193
|
/**
|
|
188
194
|
* Dispatched when data is set on the tree, both from the `data` option
|
|
189
|
-
* and from a
|
|
195
|
+
* and from a URL.
|
|
190
196
|
*
|
|
191
197
|
* @group Loading data
|
|
192
198
|
*/
|
|
@@ -211,7 +217,7 @@ export interface TreeEvents {
|
|
|
211
217
|
};
|
|
212
218
|
/**
|
|
213
219
|
* Dispatched when a request finishes. It is dispatched when the request
|
|
214
|
-
* fails too
|
|
220
|
+
* fails too, and a [`tree.load_failed`](#tree-load-failed) follows it.
|
|
215
221
|
*
|
|
216
222
|
* @group Loading data
|
|
217
223
|
*/
|
package/lib/events.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"events.d.ts","sourceRoot":"","sources":["../src/events.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,QAAQ,CAAC;AAEvD,MAAM,WAAW,QAAQ;IACvB,MAAM,EAAE,MAAM,IAAI,CAAC;IACnB,SAAS,EAAE,IAAI,CAAC;IAChB,aAAa,EAAE,KAAK,CAAC;IACrB,QAAQ,EAAE,QAAQ,CAAC;IACnB,cAAc,EAAE,IAAI,GAAG,IAAI,CAAC;IAC5B,UAAU,EAAE,IAAI,CAAC;CAClB;AAGD,MAAM,MAAM,SAAS,CAAC,IAAI,SAAS,aAAa,GAAG,aAAa,IAAI,WAAW,CAC7E,UAAU,CAAC,IAAI,CAAC,CACjB,CAAC;AAEF,MAAM,MAAM,aAAa,GAAG,MAAM,UAAU,CAAC;AAO7C,MAAM,WAAW,UAAU;IACzB;;;;;;;;;;;;;;;;;;;;;;;;;;;;OA4BG;IACH,WAAW,EAAE,SAAS,CAAC;IACvB;;;;OAIG;IACH,cAAc,EAAE,SAAS,CAAC;IAC1B;;;;;;;;;;;;OAYG;IACH,YAAY,EAAE;QACZ,IAAI,EAAE,IAAI,CAAC;QACX,aAAa,EAAE,UAAU,CAAC;KAC3B,CAAC;IACF;;;;OAIG;IACH,eAAe,EAAE;QACf,IAAI,EAAE,IAAI,CAAC;QACX,aAAa,EAAE,UAAU,CAAC;KAC3B,CAAC;IACF;;;;;OAKG;IACH,kBAAkB,EAAE;QAClB,IAAI,EAAE,IAAI,CAAC;QACX,aAAa,EAAE,UAAU,CAAC;KAC3B,CAAC;IACF;;;;;;;;;;;;OAYG;IACH,eAAe,EAAE;QACf,IAAI,EAAE,IAAI,CAAC;QACX,aAAa,EAAE,aAAa,CAAC;KAC9B,CAAC;IACF;;;;OAIG;IACH,WAAW,EAAE;QACX,IAAI,EAAE,IAAI,CAAC;KACZ,CAAC;IACF;;;;OAIG;IACH,YAAY,EAAE;QACZ,IAAI,EAAE,IAAI,CAAC;KACZ,CAAC;IACF;;;;;;;;;;;;OAYG;IACH,aAAa,EAAE;QACb
|
|
1
|
+
{"version":3,"file":"events.d.ts","sourceRoot":"","sources":["../src/events.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import type { ClassNames } from "./classNames.js";
|
|
2
|
+
export interface FolderIcons {
|
|
3
|
+
closed?: globalThis.Node;
|
|
4
|
+
opened?: globalThis.Node;
|
|
5
|
+
}
|
|
6
|
+
export declare const setTogglerOpenState: (toggler: HTMLElement, isOpen: boolean, classNames: ClassNames, icons: FolderIcons) => void;
|
|
7
|
+
export declare const setFolderLiOpenState: (li: HTMLElement, isOpen: boolean, classNames: ClassNames) => void;
|
|
8
|
+
//# sourceMappingURL=folderOpenState.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"folderOpenState.d.ts","sourceRoot":"","sources":["../src/folderOpenState.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAI/C,MAAM,WAAW,WAAW;IAC1B,MAAM,CAAC,EAAE,UAAU,CAAC,IAAI,CAAC;IACzB,MAAM,CAAC,EAAE,UAAU,CAAC,IAAI,CAAC;CAC1B;AAOD,eAAO,MAAM,mBAAmB,GAC9B,SAAS,WAAW,EACpB,QAAQ,OAAO,EACf,YAAY,UAAU,EACtB,OAAO,WAAW,KACjB,IASF,CAAC;AAEF,eAAO,MAAM,oBAAoB,GAC/B,IAAI,WAAW,EACf,QAAQ,OAAO,EACf,YAAY,UAAU,KACrB,IAGF,CAAC"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { getBoolString } from './util.js';
|
|
2
|
+
|
|
3
|
+
/* The open state of a folder is shown on the toggler and on the <li>.
|
|
4
|
+
* These are used both when a folder is rendered and when it is opened or
|
|
5
|
+
* closed, so a rendered folder looks the same as a toggled one.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
let setTogglerOpenState = (toggler, isOpen, classNames, icons) => {
|
|
9
|
+
toggler.classList.toggle(classNames.closed, !isOpen);
|
|
10
|
+
toggler.replaceChildren();
|
|
11
|
+
let iconElement = isOpen ? icons.opened : icons.closed;
|
|
12
|
+
if (iconElement) {
|
|
13
|
+
toggler.append(iconElement.cloneNode(true));
|
|
14
|
+
}
|
|
15
|
+
};
|
|
16
|
+
let setFolderLiOpenState = (li, isOpen, classNames) => {
|
|
17
|
+
li.classList.toggle(classNames.closed, !isOpen);
|
|
18
|
+
li.setAttribute("aria-expanded", getBoolString(isOpen));
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
export { setFolderLiOpenState, setTogglerOpenState };
|
|
22
|
+
//# sourceMappingURL=folderOpenState.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"folderOpenState.js","sources":["../src/folderOpenState.ts"],"sourcesContent":["import type { ClassNames } from \"./classNames\";\n\nimport { getBoolString } from \"./util\";\n\nexport interface FolderIcons {\n closed?: globalThis.Node;\n opened?: globalThis.Node;\n}\n\n/* The open state of a folder is shown on the toggler and on the <li>.\n * These are used both when a folder is rendered and when it is opened or\n * closed, so a rendered folder looks the same as a toggled one.\n */\n\nexport const setTogglerOpenState = (\n toggler: HTMLElement,\n isOpen: boolean,\n classNames: ClassNames,\n icons: FolderIcons,\n): void => {\n toggler.classList.toggle(classNames.closed, !isOpen);\n toggler.replaceChildren();\n\n const iconElement = isOpen ? icons.opened : icons.closed;\n\n if (iconElement) {\n toggler.append(iconElement.cloneNode(true));\n }\n};\n\nexport const setFolderLiOpenState = (\n li: HTMLElement,\n isOpen: boolean,\n classNames: ClassNames,\n): void => {\n li.classList.toggle(classNames.closed, !isOpen);\n li.setAttribute(\"aria-expanded\", getBoolString(isOpen));\n};\n"],"names":[],"mappings":";;AASA;AACA;AACA;AACA;;AAEO,IAAM,mBAAmB,GAAG,CACjC,OAAoB,EACpB,MAAe,EACf,UAAsB,EACtB,KAAkB,KACT;EACT,OAAO,CAAC,SAAS,CAAC,MAAM,CAAC,UAAU,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC;EACpD,OAAO,CAAC,eAAe,EAAE;EAEzB,IAAM,WAAW,GAAG,MAAM,GAAG,KAAK,CAAC,MAAM,GAAG,KAAK,CAAC,MAAM;AAExD,EAAA,IAAI,WAAW,EAAE;IACf,OAAO,CAAC,MAAM,CAAC,WAAW,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;AAC7C,EAAA;AACF;AAEO,IAAM,oBAAoB,GAAG,CAClC,EAAe,EACf,MAAe,EACf,UAAsB,KACb;EACT,EAAE,CAAC,SAAS,CAAC,MAAM,CAAC,UAAU,CAAC,MAAM,EAAE,CAAC,MAAM,CAAC;EAC/C,EAAE,CAAC,YAAY,CAAC,eAAe,EAAE,aAAa,CAAC,MAAM,CAAC,CAAC;AACzD;;"}
|