jqtree 1.7.5 → 1.8.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.
Files changed (119) hide show
  1. package/.eslintrc +13 -3
  2. package/.github/workflows/ci.yml +6 -6
  3. package/.github/workflows/codeql-analysis.yml +4 -4
  4. package/.github/workflows/size.yml +3 -3
  5. package/.github/workflows/static.yml +1 -1
  6. package/bower.json +1 -1
  7. package/config/babel.config.json +1 -1
  8. package/config/jest.config.js +4 -0
  9. package/config/jest.polyfills.js +14 -0
  10. package/config/production +2 -0
  11. package/devserver/devserver_scroll.js +8 -0
  12. package/devserver/test_index.html +9 -0
  13. package/devserver/test_scroll.html +28 -0
  14. package/devserver/test_scroll_container.html +39 -0
  15. package/docs/.ruby-version +1 -1
  16. package/docs/_config.yml +1 -1
  17. package/docs/_entries/general/changelog.md +11 -0
  18. package/docs/_entries/multiple_selection/get-selected-nodes.md +1 -1
  19. package/docs/_entries/node/getnextnode.md +3 -6
  20. package/docs/_entries/node/getnextsibling.md +1 -1
  21. package/docs/_entries/node/getnextvisiblenode.md +8 -5
  22. package/docs/_entries/node/getpreviousnode.md +12 -0
  23. package/docs/_entries/node/getprevioussibling.md +1 -1
  24. package/docs/_entries/node/getpreviousvisiblenode.md +6 -5
  25. package/package.json +35 -29
  26. package/src/dataLoader.ts +57 -34
  27. package/src/dragAndDropHandler/dragElement.ts +54 -0
  28. package/src/dragAndDropHandler/generateHitAreas.ts +176 -0
  29. package/src/dragAndDropHandler/index.ts +454 -0
  30. package/src/dragAndDropHandler/iterateVisibleNodes.ts +91 -0
  31. package/src/dragAndDropHandler/types.ts +13 -0
  32. package/src/elementsRenderer.ts +75 -40
  33. package/src/jqtreeMethodTypes.ts +40 -0
  34. package/src/jqtreeOptions.ts +43 -25
  35. package/src/keyHandler.ts +59 -30
  36. package/src/mouseHandler.ts +385 -0
  37. package/src/mouseUtils.ts +23 -0
  38. package/src/node.ts +1 -29
  39. package/src/nodeElement/borderDropHint.ts +32 -0
  40. package/src/nodeElement/folderElement.ts +133 -0
  41. package/src/nodeElement/ghostDropHint.ts +69 -0
  42. package/src/nodeElement/index.ts +102 -0
  43. package/src/playwright/coverage.ts +4 -7
  44. package/src/playwright/playwright.test.ts +150 -53
  45. package/src/playwright/testUtils.ts +28 -5
  46. package/src/position.ts +28 -0
  47. package/src/saveStateHandler.ts +75 -26
  48. package/src/scrollHandler/containerScrollParent.ts +13 -23
  49. package/src/scrollHandler/createScrollParent.ts +22 -22
  50. package/src/scrollHandler/documentScrollParent.ts +16 -13
  51. package/src/scrollHandler.ts +13 -15
  52. package/src/selectNodeHandler.ts +10 -16
  53. package/src/test/jqTree/events.test.ts +97 -30
  54. package/src/test/jqTree/keyboard.test.ts +18 -23
  55. package/src/test/jqTree/loadOnDemand.test.ts +22 -15
  56. package/src/test/jqTree/methods.test.ts +40 -14
  57. package/src/test/jqTree/mouse.test.ts +82 -0
  58. package/src/test/jqTree/options.test.ts +24 -12
  59. package/src/test/node.test.ts +3 -2
  60. package/src/test/{nodeUtil.test.ts → position.test.ts} +1 -1
  61. package/src/tree.jquery.ts +314 -208
  62. package/src/util.ts +12 -0
  63. package/src/version.ts +1 -1
  64. package/tree.jquery.debug.js +2594 -3419
  65. package/tree.jquery.debug.js.map +1 -1
  66. package/tree.jquery.js +3 -3
  67. package/tree.jquery.js.map +1 -1
  68. package/tsconfig.json +5 -3
  69. package/docs/_entries/functions/get-selected-nodes.md +0 -10
  70. package/lib/dataLoader.js +0 -123
  71. package/lib/dragAndDropHandler.js +0 -588
  72. package/lib/elementsRenderer.js +0 -267
  73. package/lib/jqtreeOptions.js +0 -1
  74. package/lib/keyHandler.js +0 -111
  75. package/lib/mouse.widget.js +0 -255
  76. package/lib/node.js +0 -708
  77. package/lib/nodeElement.js +0 -274
  78. package/lib/nodeUtils.js +0 -10
  79. package/lib/playwright/coverage.js +0 -99
  80. package/lib/playwright/playwright.test.js +0 -606
  81. package/lib/playwright/testUtils.js +0 -210
  82. package/lib/saveStateHandler.js +0 -277
  83. package/lib/scrollHandler/containerScrollParent.js +0 -160
  84. package/lib/scrollHandler/createScrollParent.js +0 -57
  85. package/lib/scrollHandler/documentScrollParent.js +0 -169
  86. package/lib/scrollHandler/scrollParent.js +0 -58
  87. package/lib/scrollHandler/types.js +0 -1
  88. package/lib/scrollHandler.js +0 -71
  89. package/lib/selectNodeHandler.js +0 -128
  90. package/lib/simple.widget.js +0 -158
  91. package/lib/test/global.d.js +0 -3
  92. package/lib/test/jqTree/accessibility.test.js +0 -37
  93. package/lib/test/jqTree/create.test.js +0 -48
  94. package/lib/test/jqTree/events.test.js +0 -210
  95. package/lib/test/jqTree/keyboard.test.js +0 -225
  96. package/lib/test/jqTree/loadOnDemand.test.js +0 -218
  97. package/lib/test/jqTree/methods.test.js +0 -1348
  98. package/lib/test/jqTree/options.test.js +0 -548
  99. package/lib/test/jqTree/scrollHandler/containerScrollParent.test.js +0 -94
  100. package/lib/test/node.test.js +0 -1202
  101. package/lib/test/nodeUtil.test.js +0 -27
  102. package/lib/test/nodeUtils.test.js +0 -20
  103. package/lib/test/support/exampleData.js +0 -35
  104. package/lib/test/support/jqTreeMatchers.js +0 -70
  105. package/lib/test/support/matchers.d.js +0 -1
  106. package/lib/test/support/setupTests.js +0 -7
  107. package/lib/test/support/testUtil.js +0 -29
  108. package/lib/test/support/treeStructure.js +0 -38
  109. package/lib/test/util.test.js +0 -26
  110. package/lib/tree.jquery.d.js +0 -1
  111. package/lib/tree.jquery.js +0 -1105
  112. package/lib/types.js +0 -1
  113. package/lib/typings.d.js +0 -2
  114. package/lib/util.js +0 -15
  115. package/lib/version.js +0 -8
  116. package/src/dragAndDropHandler.ts +0 -713
  117. package/src/mouse.widget.ts +0 -266
  118. package/src/nodeElement.ts +0 -272
  119. package/src/types.ts +0 -19
@@ -0,0 +1,102 @@
1
+ import { Node } from "../node";
2
+ import { Position } from "../position";
3
+ import { DropHint } from "../dragAndDropHandler/types";
4
+ import BorderDropHint from "./borderDropHint";
5
+ import GhostDropHint from "./ghostDropHint";
6
+ import { GetScrollLeft } from "../jqtreeMethodTypes";
7
+
8
+ export interface NodeElementParams {
9
+ getScrollLeft: GetScrollLeft;
10
+ node: Node;
11
+ tabIndex?: number;
12
+ $treeElement: JQuery<HTMLElement>;
13
+ }
14
+
15
+ class NodeElement {
16
+ public node: Node;
17
+ public element: HTMLElement;
18
+ private getScrollLeft: GetScrollLeft;
19
+ private tabIndex?: number;
20
+ private $treeElement: JQuery<HTMLElement>;
21
+
22
+ constructor({
23
+ getScrollLeft,
24
+ node,
25
+ tabIndex,
26
+ $treeElement,
27
+ }: NodeElementParams) {
28
+ this.getScrollLeft = getScrollLeft;
29
+ this.tabIndex = tabIndex;
30
+ this.$treeElement = $treeElement;
31
+
32
+ this.init(node);
33
+ }
34
+
35
+ public init(node: Node): void {
36
+ this.node = node;
37
+
38
+ if (!node.element) {
39
+ const element = this.$treeElement.get(0);
40
+
41
+ if (element) {
42
+ node.element = element;
43
+ }
44
+ }
45
+
46
+ if (node.element) {
47
+ this.element = node.element;
48
+ }
49
+ }
50
+
51
+ public addDropHint(position: number): DropHint {
52
+ if (this.mustShowBorderDropHint(position)) {
53
+ return new BorderDropHint(this.element, this.getScrollLeft());
54
+ } else {
55
+ return new GhostDropHint(this.node, this.element, position);
56
+ }
57
+ }
58
+
59
+ public select(mustSetFocus: boolean): void {
60
+ this.element.classList.add("jqtree-selected");
61
+
62
+ const titleSpan = this.getTitleSpan();
63
+ const tabIndex = this.tabIndex;
64
+
65
+ // Check for null or undefined
66
+ if (tabIndex != null) {
67
+ titleSpan.setAttribute("tabindex", tabIndex.toString());
68
+ }
69
+
70
+ titleSpan.setAttribute("aria-selected", "true");
71
+
72
+ if (mustSetFocus) {
73
+ titleSpan.focus();
74
+ }
75
+ }
76
+
77
+ public deselect(): void {
78
+ this.element.classList.remove("jqtree-selected");
79
+
80
+ const titleSpan = this.getTitleSpan();
81
+ titleSpan.removeAttribute("tabindex");
82
+ titleSpan.setAttribute("aria-selected", "false");
83
+
84
+ titleSpan.blur();
85
+ }
86
+
87
+ protected getUl(): HTMLUListElement {
88
+ return this.element.querySelector(":scope > ul") as HTMLUListElement;
89
+ }
90
+
91
+ protected getTitleSpan(): HTMLSpanElement {
92
+ return this.element.querySelector(
93
+ ":scope > .jqtree-element > span.jqtree-title",
94
+ ) as HTMLSpanElement;
95
+ }
96
+
97
+ protected mustShowBorderDropHint(position: Position): boolean {
98
+ return position === Position.Inside;
99
+ }
100
+ }
101
+
102
+ export default NodeElement;
@@ -13,17 +13,14 @@ export const initCoverage = async (context: BrowserContext) => {
13
13
  await context.exposeFunction(
14
14
  "collectIstanbulCoverage",
15
15
  (coverageJSON: string) => {
16
- if (!coverageJSON) {
17
- console.log("No coverage");
18
- } else {
16
+ if (coverageJSON) {
19
17
  const filename = path.join(
20
18
  istanbulCLIOutput,
21
- `playwright_coverage_${generateUUID()}.json`
19
+ `playwright_coverage_${generateUUID()}.json`,
22
20
  );
23
- console.log(`Writing coverage to ${filename}`);
24
21
  fs.writeFileSync(filename, coverageJSON);
25
22
  }
26
- }
23
+ },
27
24
  );
28
25
  };
29
26
 
@@ -34,7 +31,7 @@ export const saveCoverage = async (context: BrowserContext) => {
34
31
  const anyWindow = window as any;
35
32
  // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment, @typescript-eslint/no-unsafe-member-access
36
33
  const coverageData = anyWindow.__coverage__;
37
- // eslint-disable-next-line @typescript-eslint/no-unsafe-call, @typescript-eslint/no-unsafe-member-access
34
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-call, @typescript-eslint/no-unsafe-member-access, playwright/no-unsafe-references
38
35
  anyWindow.collectIstanbulCoverage(JSON.stringify(coverageData));
39
36
  });
40
37
  }
@@ -1,10 +1,14 @@
1
1
  import { test, expect, Page } from "@playwright/test";
2
2
  import {
3
+ boundingBox,
3
4
  dragAndDrop,
4
5
  findNodeElement,
6
+ getNodeRect,
7
+ getSelectedNodeName,
5
8
  getTreeStructure,
6
9
  moveMouseToNode,
7
10
  selectNode,
11
+ sleep,
8
12
  } from "./testUtils";
9
13
  import { initCoverage, saveCoverage } from "./coverage";
10
14
 
@@ -17,10 +21,6 @@ const initPage = async (page: Page, baseURL: string | undefined) => {
17
21
  await page.waitForLoadState("domcontentloaded");
18
22
 
19
23
  page.on("console", (msg) => console.log(`console: ${msg.text()}`));
20
-
21
- await page.evaluate(`
22
- console.log(window.__coverage__ ? 'Coverage enabled' : 'Coverage not enabled');
23
- `);
24
24
  };
25
25
 
26
26
  interface InitTreeOptions {
@@ -74,6 +74,8 @@ test.describe("without dragAndDrop", () => {
74
74
  const saurischia = await findNodeElement(page, "Saurischia");
75
75
  await selectNode(saurischia);
76
76
 
77
+ expect(await getSelectedNodeName(page)).toBe("Saurischia");
78
+
77
79
  const screenshot = await page.screenshot();
78
80
  expect(screenshot).toMatchSnapshot();
79
81
  });
@@ -116,10 +118,54 @@ test.describe("with dragAndDrop", () => {
116
118
  const screenshot = await page.screenshot();
117
119
  expect(screenshot).toMatchSnapshot();
118
120
  });
121
+
122
+ test("moves a node with touch events", async ({ page }) => {
123
+ const client = await page.context().newCDPSession(page);
124
+
125
+ const box1 = await getNodeRect(page, "Herrerasaurians");
126
+
127
+ await client.send("Input.dispatchTouchEvent", {
128
+ type: "touchStart",
129
+ touchPoints: [{ x: box1.x + 10, y: box1.y + box1.height / 2 }],
130
+ });
131
+
132
+ await sleep(page, 200);
133
+
134
+ const box2 = await getNodeRect(page, "Ornithischians");
135
+ await client.send("Input.dispatchTouchEvent", {
136
+ type: "touchEnd",
137
+ touchPoints: [{ x: box2.x + 10, y: box2.y + box2.height / 2 }],
138
+ });
139
+
140
+ const structure = await getTreeStructure(page);
141
+
142
+ expect(structure).toEqual([
143
+ expect.objectContaining({
144
+ name: "Saurischia",
145
+ children: [
146
+ expect.objectContaining({ name: "Theropods" }),
147
+ expect.objectContaining({ name: "Sauropodomorphs" }),
148
+ ],
149
+ }),
150
+ expect.objectContaining({
151
+ name: "Ornithischians",
152
+ children: [
153
+ expect.objectContaining({ name: "Herrerasaurians" }),
154
+ expect.objectContaining({ name: "Heterodontosaurids" }),
155
+ expect.objectContaining({ name: "Thyreophorans" }),
156
+ expect.objectContaining({ name: "Ornithopods" }),
157
+ expect.objectContaining({
158
+ name: "Pachycephalosaurians",
159
+ }),
160
+ expect.objectContaining({ name: "Ceratopsians" }),
161
+ ],
162
+ }),
163
+ ]);
164
+ });
119
165
  });
120
166
 
121
167
  test.describe("autoscroll when the window is scrollable", () => {
122
- test("it scrolls vertically when the users drags an element to the bottom ", async ({
168
+ test("it scrolls vertically when the users drags an element to the bottom", async ({
123
169
  baseURL,
124
170
  page,
125
171
  }) => {
@@ -136,12 +182,10 @@ test.describe("autoscroll when the window is scrollable", () => {
136
182
  await moveMouseToNode(page, "Saurischia");
137
183
  await page.mouse.down();
138
184
 
139
- // eslint-disable-next-line playwright/no-wait-for-timeout
140
- await page.waitForTimeout(200);
185
+ await sleep(page, 200);
141
186
 
142
187
  await page.mouse.move(20, 190);
143
- // eslint-disable-next-line playwright/no-wait-for-timeout
144
- await page.waitForTimeout(50);
188
+ await sleep(page, 50);
145
189
 
146
190
  expect(
147
191
  await page
@@ -166,13 +210,10 @@ test.describe("autoscroll when the window is scrollable", () => {
166
210
 
167
211
  await moveMouseToNode(page, "Saurischia");
168
212
  await page.mouse.down();
169
-
170
- // eslint-disable-next-line playwright/no-wait-for-timeout
171
- await page.waitForTimeout(200);
213
+ await sleep(page, 200);
172
214
 
173
215
  await page.mouse.move(55, 10);
174
- // eslint-disable-next-line playwright/no-wait-for-timeout
175
- await page.waitForTimeout(50);
216
+ await sleep(page, 50);
176
217
 
177
218
  expect(
178
219
  await page
@@ -206,7 +247,7 @@ test.describe("autoscroll when the window is scrollable", () => {
206
247
  });
207
248
  });
208
249
 
209
- test.describe("autoscroll when the container is scrollable", () => {
250
+ test.describe("autoscroll when the container is scrollable vertically", () => {
210
251
  test.beforeEach(async ({ page, baseURL }) => {
211
252
  await initPage(page, baseURL);
212
253
 
@@ -220,7 +261,6 @@ test.describe("autoscroll when the container is scrollable", () => {
220
261
  const container = document.createElement("div");
221
262
  container.id = "container";
222
263
  container.style.height = "200px";
223
- container.style.width = "60px";
224
264
  container.style.overflowY = "scroll";
225
265
 
226
266
  document.body.replaceChild(container, treeElement);
@@ -233,72 +273,129 @@ test.describe("autoscroll when the container is scrollable", () => {
233
273
  test("it scrolls vertically when the users drags an element to the bottom", async ({
234
274
  page,
235
275
  }) => {
276
+ const container = page.locator("#container");
277
+
236
278
  expect(
237
- await page
238
- .locator("#container")
239
- .evaluate((element) => element.scrollTop),
279
+ await container.evaluate((element) => element.scrollTop),
240
280
  ).toEqual(0);
241
281
 
242
282
  await moveMouseToNode(page, "Saurischia");
243
283
  await page.mouse.down();
244
-
245
- // eslint-disable-next-line playwright/no-wait-for-timeout
246
- await page.waitForTimeout(200);
284
+ await sleep(page, 200);
247
285
 
248
286
  await page.mouse.move(20, 245);
249
- // eslint-disable-next-line playwright/no-wait-for-timeout
250
- await page.waitForTimeout(50);
287
+ await sleep(page, 50);
251
288
 
252
289
  expect(
253
- await page
254
- .locator("#container")
255
- .evaluate((element) => element.scrollTop),
290
+ await container.evaluate((element) => element.scrollTop),
291
+ ).toBeGreaterThan(0);
292
+ });
293
+
294
+ test("scrollToNode scrolls to a node", async ({ page }) => {
295
+ const container = page.locator("#container");
296
+
297
+ expect(
298
+ await container.evaluate((element) => element.scrollTop),
299
+ ).toEqual(0);
300
+
301
+ await page.evaluate(`
302
+ const $tree = jQuery("#tree1");
303
+ const node = $tree.tree("getNodeByName", "Sauropodomorphs");
304
+ $tree.tree("scrollToNode",node);
305
+ `);
306
+
307
+ expect(
308
+ await container.evaluate((element) => element.scrollTop),
256
309
  ).toBeGreaterThan(0);
257
310
  });
311
+ });
312
+
313
+ test.describe("autoscroll when the container is scrollable horizontally", () => {
314
+ test.beforeEach(async ({ page, baseURL }) => {
315
+ await initPage(page, baseURL);
316
+
317
+ // Add a container and make it the parent of the tree element
318
+ await page.evaluate(`
319
+ document.body.style.marginLeft = "40px";
320
+ document.body.style.marginTop = "40px";
321
+
322
+ const treeElement = document.querySelector("#tree1");
323
+
324
+ const container = document.createElement("div");
325
+ container.id = "container";
326
+ container.style.width = "400px";
327
+ container.style.overflowX = "scroll";
328
+ container.classList.add('wide-tree');
329
+
330
+ document.body.replaceChild(container, treeElement);
331
+ container.appendChild(treeElement);
332
+ `);
333
+
334
+ await initTree(page, { autoOpen: 3, dragAndDrop: true });
335
+ });
258
336
 
259
337
  test("it scrolls horizontally when the users drags an element to the right", async ({
260
338
  page,
261
339
  }) => {
340
+ const container = page.locator("#container");
341
+
262
342
  expect(
263
- await page
264
- .locator("#container")
265
- .evaluate((element) => element.scrollLeft),
343
+ await container.evaluate((element) => element.scrollLeft),
266
344
  ).toEqual(0);
267
345
 
268
346
  await moveMouseToNode(page, "Saurischia");
269
347
  await page.mouse.down();
348
+ await sleep(page, 200);
270
349
 
271
- // eslint-disable-next-line playwright/no-wait-for-timeout
272
- await page.waitForTimeout(200);
350
+ const containerBox = await boundingBox(container);
273
351
 
274
- await page.mouse.move(100, 50);
275
- // eslint-disable-next-line playwright/no-wait-for-timeout
276
- await page.waitForTimeout(50);
352
+ await page.mouse.move(
353
+ containerBox.x + containerBox.width,
354
+ containerBox.y + 10,
355
+ );
356
+ await sleep(page, 100);
277
357
 
278
358
  expect(
279
- await page
280
- .locator("#container")
281
- .evaluate((element) => element.scrollLeft),
359
+ await container.evaluate((element) => element.scrollLeft),
282
360
  ).toBeGreaterThan(0);
283
361
  });
284
362
 
285
- test("scrollToNode scrolls to a node", async ({ page }) => {
286
- expect(
287
- await page
288
- .locator("#container")
289
- .evaluate((element) => element.scrollTop),
290
- ).toEqual(0);
363
+ test("it moves a node after scrolling horizontally", async ({ page }) => {
364
+ await moveMouseToNode(page, "Coelophysoids");
365
+ await page.mouse.down();
366
+ await sleep(page, 200);
291
367
 
292
- await page.evaluate(`
368
+ const container = page.locator("#container");
369
+ const containerBox = await boundingBox(container);
370
+
371
+ await page.mouse.move(
372
+ containerBox.x + containerBox.width,
373
+ containerBox.y + 10,
374
+ );
375
+
376
+ await page.waitForFunction(() => {
377
+ const container = document.querySelector("#container");
378
+
379
+ if (!container) {
380
+ return false;
381
+ }
382
+
383
+ return (
384
+ container.scrollLeft >=
385
+ container.scrollWidth - container.clientWidth
386
+ );
387
+ });
388
+
389
+ await moveMouseToNode(page, "Tyrannosauroids");
390
+ await page.mouse.down();
391
+ await sleep(page, 200);
392
+
393
+ const childrenJson = await page.evaluate<string>(`
293
394
  const $tree = jQuery("#tree1");
294
- const node = $tree.tree("getNodeByName", "Sauropodomorphs");
295
- $tree.tree("scrollToNode",node);
395
+ const node = $tree.tree("getNodeByName", "Tyrannosauroids");
396
+ const children = node.children.map(child => child.name)
397
+ JSON.stringify(children);
296
398
  `);
297
-
298
- expect(
299
- await page
300
- .locator("#container")
301
- .evaluate((element) => element.scrollTop),
302
- ).toBeGreaterThan(0);
399
+ expect(JSON.parse(childrenJson)).toEqual(["Coelophysoids"]);
303
400
  });
304
401
  });
@@ -1,4 +1,4 @@
1
- import { Page, ElementHandle } from "@playwright/test";
1
+ import { ElementHandle, Locator, Page } from "@playwright/test";
2
2
 
3
3
  interface BoundingBox {
4
4
  x: number;
@@ -7,7 +7,10 @@ interface BoundingBox {
7
7
  height: number;
8
8
  }
9
9
 
10
- const locateTitle = (page: Page, title: string) =>
10
+ export const sleep = async (page: Page, timeout: number) =>
11
+ await page.waitForTimeout(timeout); // eslint-disable-line playwright/no-wait-for-timeout
12
+
13
+ export const locateTitle = (page: Page, title: string) =>
11
14
  page.locator(".jqtree-title", {
12
15
  hasText: title,
13
16
  });
@@ -42,6 +45,16 @@ export const selectNode = async (nodeElement: ElementHandle) => {
42
45
  await titleHandle.click();
43
46
  };
44
47
 
48
+ export const boundingBox = async (locator: Locator) => {
49
+ const result = await locator.boundingBox();
50
+
51
+ if (!result) {
52
+ throw new Error("Empty boundingBox");
53
+ }
54
+
55
+ return result;
56
+ };
57
+
45
58
  const getRect = async (
46
59
  elementHandle: ElementHandle<HTMLElement>,
47
60
  ): Promise<BoundingBox> => {
@@ -97,7 +110,10 @@ export const getTreeStructure = async (page: Page) => {
97
110
  return JSON.parse(structure) as JQTreeMatchers.TreeStructure;
98
111
  };
99
112
 
100
- const getNodeRect = async (page: Page, title: string): Promise<BoundingBox> => {
113
+ export const getNodeRect = async (
114
+ page: Page,
115
+ title: string,
116
+ ): Promise<BoundingBox> => {
101
117
  const titleElement = await locateTitle(page, title).elementHandle();
102
118
 
103
119
  if (!titleElement) {
@@ -122,9 +138,16 @@ export const dragAndDrop = async (
122
138
  await moveMouseToNode(page, fromTitle);
123
139
  await page.mouse.down();
124
140
 
125
- // eslint-disable-next-line playwright/no-wait-for-timeout
126
- await page.waitForTimeout(200);
141
+ await sleep(page, 200);
127
142
 
128
143
  await moveMouseToNode(page, toTitle);
129
144
  await page.mouse.up();
130
145
  };
146
+
147
+ export const getSelectedNodeName = async (page: Page) => {
148
+ return await page.evaluate(`
149
+ const $tree = jQuery("#tree1");
150
+ const node = $tree.tree('getSelectedNode');
151
+ node?.name;
152
+ `);
153
+ };
@@ -0,0 +1,28 @@
1
+ export enum Position {
2
+ Before = 1,
3
+ After,
4
+ Inside,
5
+ None,
6
+ }
7
+
8
+ const positionNames: Record<string, Position> = {
9
+ before: Position.Before,
10
+ after: Position.After,
11
+ inside: Position.Inside,
12
+ none: Position.None,
13
+ };
14
+
15
+ export const getPositionName = (position: Position): string => {
16
+ for (const name in positionNames) {
17
+ if (Object.prototype.hasOwnProperty.call(positionNames, name)) {
18
+ if (positionNames[name] === position) {
19
+ return name;
20
+ }
21
+ }
22
+ }
23
+
24
+ return "";
25
+ };
26
+
27
+ export const getPosition = (name: string): Position | undefined =>
28
+ positionNames[name];