@spectrum-web-components/picker 0.36.0 → 0.37.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/test/index.js CHANGED
@@ -1,5 +1,6 @@
1
1
  "use strict";
2
2
  import {
3
+ aTimeout,
3
4
  elementUpdated,
4
5
  expect,
5
6
  fixture,
@@ -15,7 +16,6 @@ import {
15
16
  arrowLeftEvent,
16
17
  arrowRightEvent,
17
18
  arrowUpEvent,
18
- escapeEvent,
19
19
  testForLitDevWarnings,
20
20
  tEvent
21
21
  } from "../../../test/testing-helpers.js";
@@ -32,21 +32,24 @@ import {
32
32
  } from "../stories/picker.stories.js";
33
33
  import { sendMouse } from "../../../test/plugins/browser.js";
34
34
  import { ignoreResizeObserverLoopError } from "../../../test/testing-helpers.js";
35
- import {
36
- isFirefox,
37
- isWebKit
38
- } from "@spectrum-web-components/shared/src/platform.js";
35
+ import { isFirefox } from "@spectrum-web-components/shared/src/platform.js";
36
+ import "@spectrum-web-components/picker/sp-picker.js";
37
+ import "@spectrum-web-components/field-label/sp-field-label.js";
38
+ import "@spectrum-web-components/menu/sp-menu.js";
39
+ import "@spectrum-web-components/menu/sp-menu-group.js";
40
+ import "@spectrum-web-components/menu/sp-menu-item.js";
41
+ import "@spectrum-web-components/theme/src/themes.js";
39
42
  ignoreResizeObserverLoopError(before, after);
40
- const isMenuActiveElement = function() {
43
+ const isMenuActiveElement = function(el) {
41
44
  var _a;
42
- return ((_a = document.activeElement) == null ? void 0 : _a.localName) === "sp-menu";
45
+ return ((_a = el.shadowRoot.activeElement) == null ? void 0 : _a.localName) === "sp-menu";
43
46
  };
44
47
  export function runPickerTests() {
45
48
  let el;
46
49
  const pickerFixture = async () => {
47
50
  const test = await fixture(
48
51
  html`
49
- <div>
52
+ <sp-theme scale="medium" color="light">
50
53
  <sp-field-label for="picker">
51
54
  Where do you live?
52
55
  </sp-field-label>
@@ -60,11 +63,10 @@ export function runPickerTests() {
60
63
  </sp-menu-item>
61
64
  <sp-menu-item>Feather...</sp-menu-item>
62
65
  <sp-menu-item>Select and Mask...</sp-menu-item>
63
- <sp-menu-divider></sp-menu-divider>
64
66
  <sp-menu-item>Save Selection</sp-menu-item>
65
67
  <sp-menu-item disabled>Make Work Path</sp-menu-item>
66
68
  </sp-picker>
67
- </div>
69
+ </sp-theme>
68
70
  `
69
71
  );
70
72
  return test.querySelector("sp-picker");
@@ -91,6 +93,8 @@ export function runPickerTests() {
91
93
  ).to.not.be.null;
92
94
  el2.value = "option-2";
93
95
  await elementUpdated(el2);
96
+ await nextFrame();
97
+ await nextFrame();
94
98
  snapshot = await a11ySnapshot({});
95
99
  expect(
96
100
  findAccessibilityNode(
@@ -121,6 +125,8 @@ export function runPickerTests() {
121
125
  ).to.not.be.null;
122
126
  el2.value = "option-2";
123
127
  await elementUpdated(el2);
128
+ await nextFrame();
129
+ await nextFrame();
124
130
  snapshot = await a11ySnapshot({});
125
131
  expect(
126
132
  findAccessibilityNode(
@@ -151,6 +157,8 @@ export function runPickerTests() {
151
157
  ).to.not.be.null;
152
158
  el2.value = "option-2";
153
159
  await elementUpdated(el2);
160
+ await nextFrame();
161
+ await nextFrame();
154
162
  snapshot = await a11ySnapshot({});
155
163
  if (isFirefox()) {
156
164
  expect(
@@ -175,13 +183,8 @@ export function runPickerTests() {
175
183
  beforeEach(async () => {
176
184
  el = await pickerFixture();
177
185
  await elementUpdated(el);
178
- });
179
- afterEach(async () => {
180
- if (el.open) {
181
- const closed = oneEvent(el, "sp-closed");
182
- el.open = false;
183
- await closed;
184
- }
186
+ await nextFrame();
187
+ await nextFrame();
185
188
  });
186
189
  it("loads accessibly", async () => {
187
190
  await expect(el).to.be.accessible();
@@ -194,7 +197,7 @@ export function runPickerTests() {
194
197
  el.open = true;
195
198
  await opened;
196
199
  expect(el.open).to.be.true;
197
- const accessibleCloseButton = document.querySelector(
200
+ const accessibleCloseButton = el.shadowRoot.querySelector(
198
201
  ".visually-hidden button"
199
202
  );
200
203
  expect(accessibleCloseButton).to.have.attribute(
@@ -210,10 +213,13 @@ export function runPickerTests() {
210
213
  expect(document.activeElement).to.eq(el);
211
214
  });
212
215
  it("accepts new selected item content", async () => {
216
+ await nextFrame();
217
+ await nextFrame();
213
218
  const option2 = el.querySelector('[value="option-2"');
214
219
  el.value = "option-2";
215
220
  await elementUpdated(option2);
216
221
  await elementUpdated(el);
222
+ await aTimeout(150);
217
223
  expect(el.value).to.equal("option-2");
218
224
  expect((el.button.textContent || "").trim()).to.include(
219
225
  "Select Inverse"
@@ -234,9 +240,11 @@ export function runPickerTests() {
234
240
  expect((el.button.textContent || "").trim()).to.include(newLabel2);
235
241
  });
236
242
  it("accepts new selected item content when open", async () => {
243
+ await nextFrame();
237
244
  const option2 = el.querySelector('[value="option-2"');
238
245
  el.value = "option-2";
239
246
  await elementUpdated(el);
247
+ await aTimeout(150);
240
248
  expect(el.value).to.equal("option-2");
241
249
  expect((el.button.textContent || "").trim()).to.include(
242
250
  "Select Inverse"
@@ -257,21 +265,27 @@ export function runPickerTests() {
257
265
  );
258
266
  });
259
267
  it("unsets value when children removed", async () => {
268
+ await nextFrame();
260
269
  el.value = "option-2";
261
270
  await elementUpdated(el);
271
+ await aTimeout(150);
262
272
  expect(el.value).to.equal("option-2");
263
273
  expect((el.button.textContent || "").trim()).to.include(
264
274
  "Select Inverse"
265
275
  );
266
276
  const items = el.querySelectorAll("sp-menu-item");
267
- const removals = [];
268
277
  items.forEach((item) => {
269
- const removal = oneEvent(el, "sp-menu-item-removed");
270
278
  item.remove();
271
- removals.push(removal);
272
279
  });
273
- await Promise.all(removals);
274
280
  await elementUpdated(el);
281
+ await nextFrame();
282
+ await aTimeout(150);
283
+ expect(
284
+ el.optionsMenu.childItems.length
285
+ ).to.equal(0);
286
+ if ("showPopover" in document.createElement("div")) {
287
+ return;
288
+ }
275
289
  expect(el.value).to.equal("");
276
290
  expect((el.button.textContent || "").trim()).to.not.include(
277
291
  "Select Inverse"
@@ -298,7 +312,7 @@ export function runPickerTests() {
298
312
  item.value = "option-new";
299
313
  item.textContent = "New Option";
300
314
  el.append(item);
301
- await elementUpdated(item);
315
+ await nextFrame();
302
316
  await elementUpdated(el);
303
317
  let opened = oneEvent(el, "sp-opened");
304
318
  el.open = true;
@@ -316,6 +330,7 @@ export function runPickerTests() {
316
330
  expect(el.value, "second time").to.equal("option-new");
317
331
  });
318
332
  it('manages its "name" value in the accessibility tree', async () => {
333
+ await nextFrame();
319
334
  let snapshot = await a11ySnapshot({});
320
335
  expect(
321
336
  findAccessibilityNode(
@@ -326,6 +341,8 @@ export function runPickerTests() {
326
341
  ).to.not.be.null;
327
342
  el.value = "option-2";
328
343
  await elementUpdated(el);
344
+ await nextFrame();
345
+ await nextFrame();
329
346
  snapshot = await a11ySnapshot({});
330
347
  expect(
331
348
  findAccessibilityNode(
@@ -342,12 +359,16 @@ export function runPickerTests() {
342
359
  el.open = true;
343
360
  await opened;
344
361
  expect(
345
- el.optionsMenu.getAttribute("aria-activedescendant")
362
+ el.optionsMenu.getAttribute(
363
+ "aria-activedescendant"
364
+ )
346
365
  ).to.equal(firstItem == null ? void 0 : firstItem.id);
347
366
  await sendKeys({ press: "ArrowDown" });
348
367
  await elementUpdated(el);
349
368
  expect(
350
- el.optionsMenu.getAttribute("aria-activedescendant")
369
+ el.optionsMenu.getAttribute(
370
+ "aria-activedescendant"
371
+ )
351
372
  ).to.equal(secondItem == null ? void 0 : secondItem.id);
352
373
  });
353
374
  it("renders invalid accessibly", async () => {
@@ -362,6 +383,7 @@ export function runPickerTests() {
362
383
  await expect(el).to.be.accessible();
363
384
  });
364
385
  it("opens with visible focus on a menu item on `DownArrow`", async () => {
386
+ var _a, _b;
365
387
  const firstItem = el.querySelector("sp-menu-item");
366
388
  await elementUpdated(el);
367
389
  expect(firstItem.focused, "should not visually focused").to.be.false;
@@ -380,12 +402,24 @@ export function runPickerTests() {
380
402
  });
381
403
  await closed;
382
404
  expect(el.open).to.be.false;
383
- await waitUntil(() => !firstItem.focused, "not visually focused");
405
+ expect(
406
+ document.activeElement === el,
407
+ `focused ${(_a = document.activeElement) == null ? void 0 : _a.localName} instead of back on Picker`
408
+ ).to.be.true;
409
+ expect(
410
+ el.shadowRoot.activeElement === el.button,
411
+ `focused ${(_b = el.shadowRoot.activeElement) == null ? void 0 : _b.localName} instead of back on button`
412
+ ).to.be.true;
413
+ await waitUntil(
414
+ () => !firstItem.focused,
415
+ "finally, not visually focused"
416
+ );
384
417
  });
385
- it("opens without visible focus on a menu item on click", async () => {
418
+ it("opens, on click, without visible focus on a menu item", async () => {
419
+ await nextFrame();
420
+ await nextFrame();
386
421
  const firstItem = el.querySelector("sp-menu-item");
387
- await elementUpdated(el);
388
- const boundingRect = el.getBoundingClientRect();
422
+ const boundingRect = el.button.getBoundingClientRect();
389
423
  expect(firstItem.focused, "not visually focused").to.be.false;
390
424
  const opened = oneEvent(el, "sp-opened");
391
425
  sendMouse({
@@ -400,10 +434,69 @@ export function runPickerTests() {
400
434
  ]
401
435
  });
402
436
  await opened;
403
- await elementUpdated(el);
404
437
  expect(el.open).to.be.true;
405
438
  expect(firstItem.focused, "still not visually focused").to.be.false;
406
439
  });
440
+ it("opens/closes multiple times", async () => {
441
+ expect(el.open).to.be.false;
442
+ const boundingRect = el.button.getBoundingClientRect();
443
+ let opened = oneEvent(el, "sp-opened");
444
+ sendMouse({
445
+ steps: [
446
+ {
447
+ type: "click",
448
+ position: [
449
+ boundingRect.x + boundingRect.width / 2,
450
+ boundingRect.y + boundingRect.height / 2
451
+ ]
452
+ }
453
+ ]
454
+ });
455
+ await opened;
456
+ expect(el.open).to.be.true;
457
+ let closed = oneEvent(el, "sp-closed");
458
+ sendMouse({
459
+ steps: [
460
+ {
461
+ type: "click",
462
+ position: [
463
+ boundingRect.x + boundingRect.width / 2,
464
+ boundingRect.y + boundingRect.height / 2
465
+ ]
466
+ }
467
+ ]
468
+ });
469
+ await closed;
470
+ expect(el.open).to.be.false;
471
+ opened = oneEvent(el, "sp-opened");
472
+ sendMouse({
473
+ steps: [
474
+ {
475
+ type: "click",
476
+ position: [
477
+ boundingRect.x + boundingRect.width / 2,
478
+ boundingRect.y + boundingRect.height / 2
479
+ ]
480
+ }
481
+ ]
482
+ });
483
+ await opened;
484
+ expect(el.open).to.be.true;
485
+ closed = oneEvent(el, "sp-closed");
486
+ sendMouse({
487
+ steps: [
488
+ {
489
+ type: "click",
490
+ position: [
491
+ boundingRect.x + boundingRect.width / 2,
492
+ boundingRect.y + boundingRect.height / 2
493
+ ]
494
+ }
495
+ ]
496
+ });
497
+ await closed;
498
+ expect(el.open).to.be.false;
499
+ });
407
500
  it("closes when becoming disabled", async () => {
408
501
  expect(el.open).to.be.false;
409
502
  el.click();
@@ -419,11 +512,15 @@ export function runPickerTests() {
419
512
  document.body.append(other);
420
513
  await elementUpdated(el);
421
514
  expect(el.open).to.be.false;
515
+ const opened = oneEvent(el, "sp-opened");
422
516
  el.click();
517
+ await opened;
423
518
  await elementUpdated(el);
424
519
  expect(el.open).to.be.true;
520
+ const closed = oneEvent(el, "sp-closed");
425
521
  other.click();
426
- await waitUntil(() => !el.open, "closed");
522
+ closed;
523
+ await elementUpdated(el);
427
524
  other.remove();
428
525
  });
429
526
  it("selects", async () => {
@@ -435,7 +532,6 @@ export function runPickerTests() {
435
532
  const opened = oneEvent(el, "sp-opened");
436
533
  button.click();
437
534
  await opened;
438
- await elementUpdated(el);
439
535
  expect(el.open).to.be.true;
440
536
  expect((_a = el.selectedItem) == null ? void 0 : _a.itemText).to.be.undefined;
441
537
  expect(el.value).to.equal("");
@@ -455,31 +551,27 @@ export function runPickerTests() {
455
551
  "sp-menu-item:nth-of-type(2)"
456
552
  );
457
553
  const button = el.button;
458
- const opened = oneEvent(el, "sp-opened");
554
+ let opened = oneEvent(el, "sp-opened");
459
555
  button.click();
460
556
  await opened;
461
- await nextFrame();
462
557
  expect(el.open).to.be.true;
463
558
  expect((_a = el.selectedItem) == null ? void 0 : _a.itemText).to.be.undefined;
464
559
  expect(el.value).to.equal("");
465
- const closed = oneEvent(el, "sp-closed");
560
+ let closed = oneEvent(el, "sp-closed");
466
561
  secondItem.click();
467
562
  await closed;
468
- await nextFrame();
469
563
  expect(el.open).to.be.false;
470
564
  expect((_b = el.selectedItem) == null ? void 0 : _b.itemText).to.equal("Select Inverse");
471
565
  expect(el.value).to.equal("option-2");
472
- const opened2 = oneEvent(el, "sp-opened");
566
+ opened = oneEvent(el, "sp-opened");
473
567
  button.click();
474
- await opened2;
475
- await nextFrame();
568
+ await opened;
476
569
  expect(el.open).to.be.true;
477
570
  expect((_c = el.selectedItem) == null ? void 0 : _c.itemText).to.equal("Select Inverse");
478
571
  expect(el.value).to.equal("option-2");
479
- const closed2 = oneEvent(el, "sp-closed");
572
+ closed = oneEvent(el, "sp-closed");
480
573
  firstItem.click();
481
- await closed2;
482
- await nextFrame();
574
+ await closed;
483
575
  expect(el.open).to.be.false;
484
576
  expect((_d = el.selectedItem) == null ? void 0 : _d.itemText).to.equal("Deselect");
485
577
  expect(el.value).to.equal("Deselect");
@@ -487,7 +579,6 @@ export function runPickerTests() {
487
579
  it("dispatches bubbling and composed events", async () => {
488
580
  const changeSpy = spy();
489
581
  const parent = el.parentElement;
490
- parent.attachShadow({ mode: "open" });
491
582
  parent.shadowRoot.append(el);
492
583
  const secondItem = el.querySelector(
493
584
  "sp-menu-item:nth-of-type(2)"
@@ -497,11 +588,9 @@ export function runPickerTests() {
497
588
  const opened = oneEvent(el, "sp-opened");
498
589
  el.open = true;
499
590
  await opened;
500
- await elementUpdated(el);
501
591
  const closed = oneEvent(el, "sp-closed");
502
592
  secondItem.click();
503
593
  await closed;
504
- await elementUpdated(el);
505
594
  expect(el.value).to.equal(secondItem.value);
506
595
  expect(changeSpy.calledOnce).to.be.true;
507
596
  });
@@ -512,10 +601,9 @@ export function runPickerTests() {
512
601
  "sp-menu-item:nth-of-type(2)"
513
602
  );
514
603
  const button = el.button;
515
- let opened = oneEvent(el, "sp-opened");
604
+ const opened = oneEvent(el, "sp-opened");
516
605
  button.click();
517
606
  await opened;
518
- await elementUpdated(el);
519
607
  expect(el.open).to.be.true;
520
608
  expect((_a = el.selectedItem) == null ? void 0 : _a.itemText).to.be.undefined;
521
609
  expect(el.value).to.equal("");
@@ -524,14 +612,12 @@ export function runPickerTests() {
524
612
  event.preventDefault();
525
613
  preventChangeSpy();
526
614
  });
527
- const closed = oneEvent(el, "sp-closed");
528
- opened = oneEvent(el, "sp-opened");
529
615
  secondItem.click();
530
- await closed;
531
- await opened;
532
- await elementUpdated(el);
616
+ await nextFrame();
617
+ await nextFrame();
533
618
  expect(preventChangeSpy.calledOnce).to.be.true;
534
619
  expect(secondItem.selected, "selection prevented").to.be.false;
620
+ expect(el.open).to.be.true;
535
621
  });
536
622
  it("can throw focus after `change`", async () => {
537
623
  var _a;
@@ -574,20 +660,17 @@ export function runPickerTests() {
574
660
  button.dispatchEvent(tEvent());
575
661
  await elementUpdated(el);
576
662
  expect(el.open, "still closed").to.be.false;
663
+ const opened = oneEvent(el, "sp-opened");
577
664
  button.dispatchEvent(arrowUpEvent());
578
665
  await elementUpdated(el);
579
666
  expect(el.open, "open by ArrowUp").to.be.true;
580
- await waitUntil(
581
- () => document.querySelector("active-overlay") !== null,
582
- "an active-overlay has been inserted on the page"
583
- );
584
- button.dispatchEvent(escapeEvent());
585
- await elementUpdated(el);
586
- await waitUntil(() => el.open === false, "closed by Escape");
587
- await waitUntil(
588
- () => document.querySelector("active-overlay") === null,
589
- "an active-overlay has been inserted on the page"
590
- );
667
+ await opened;
668
+ const closed = oneEvent(el, "sp-closed");
669
+ sendKeys({
670
+ press: "Escape"
671
+ });
672
+ await closed;
673
+ expect(el.open).to.be.false;
591
674
  });
592
675
  it("opens on ArrowDown", async () => {
593
676
  var _a, _b;
@@ -601,19 +684,18 @@ export function runPickerTests() {
601
684
  const opened = oneEvent(el, "sp-opened");
602
685
  button.dispatchEvent(arrowDownEvent());
603
686
  await opened;
604
- await elementUpdated(el);
605
687
  expect(el.open, "open by ArrowDown").to.be.true;
606
688
  expect((_a = el.selectedItem) == null ? void 0 : _a.itemText).to.be.undefined;
607
689
  expect(el.value).to.equal("");
608
690
  const closed = oneEvent(el, "sp-closed");
609
691
  firstItem.click();
610
692
  await closed;
611
- await elementUpdated(el);
612
693
  expect(el.open).to.be.false;
613
694
  expect((_b = el.selectedItem) == null ? void 0 : _b.itemText).to.equal("Deselect");
614
695
  expect(el.value).to.equal("Deselect");
615
696
  });
616
697
  it("quick selects on ArrowLeft/Right", async () => {
698
+ await nextFrame();
617
699
  const selectionSpy = spy();
618
700
  el.addEventListener("change", (event) => {
619
701
  const { value } = event.target;
@@ -641,6 +723,7 @@ export function runPickerTests() {
641
723
  expect(selectionSpy.calledWith("Make Work Path")).to.be.false;
642
724
  });
643
725
  it("quick selects first item on ArrowRight when no value", async () => {
726
+ await nextFrame();
644
727
  const selectionSpy = spy();
645
728
  el.addEventListener("change", (event) => {
646
729
  const { value } = event.target;
@@ -656,8 +739,12 @@ export function runPickerTests() {
656
739
  it("loads", async () => {
657
740
  expect(el).to.not.be.undefined;
658
741
  });
659
- it("refocuses on list when open", async () => {
742
+ it("closes when focusing away from the menu", async () => {
660
743
  const firstItem = el.querySelector("sp-menu-item");
744
+ const thirdItem = el.querySelector(
745
+ "sp-menu-item:nth-of-type(3)"
746
+ );
747
+ const button = el.button;
661
748
  const input = document.createElement("input");
662
749
  el.insertAdjacentElement("afterend", input);
663
750
  el.focus();
@@ -665,44 +752,74 @@ export function runPickerTests() {
665
752
  expect(document.activeElement === input).to.be.true;
666
753
  await sendKeys({ press: "Shift+Tab" });
667
754
  expect(document.activeElement === el).to.be.true;
668
- await sendKeys({ press: "Enter" });
669
755
  const opened = oneEvent(el, "sp-opened");
670
- el.open = true;
756
+ sendKeys({ press: "Enter" });
671
757
  await opened;
672
758
  await elementUpdated(el);
673
759
  await waitUntil(
674
760
  () => firstItem.focused,
675
761
  "The first items should have become focused visually."
676
762
  );
677
- el.blur();
678
- await elementUpdated(el);
679
- expect(el.open).to.be.true;
763
+ await sendKeys({ press: "ArrowDown" });
764
+ await sendKeys({ press: "ArrowDown" });
765
+ expect(thirdItem.focused).to.be.true;
766
+ const closed = oneEvent(el, "sp-closed");
767
+ button.focus();
768
+ await closed;
769
+ expect(isMenuActiveElement(el)).to.be.false;
770
+ expect(el.open).to.be.false;
771
+ });
772
+ it("does not listen to streaming `Enter` keydown", async () => {
773
+ const openSpy = spy();
774
+ const closedSpy = spy();
775
+ el.addEventListener("sp-opened", () => openSpy());
776
+ el.addEventListener("sp-closed", () => closedSpy());
777
+ const firstItem = el.querySelector("sp-menu-item");
778
+ const thirdItem = el.querySelector(
779
+ "sp-menu-item:nth-of-type(3)"
780
+ );
781
+ const input = document.createElement("input");
782
+ el.insertAdjacentElement("afterend", input);
680
783
  el.focus();
681
- await elementUpdated(el);
784
+ await sendKeys({ press: "Tab" });
785
+ expect(document.activeElement === input).to.be.true;
786
+ await sendKeys({ press: "Shift+Tab" });
787
+ expect(document.activeElement === el).to.be.true;
788
+ const opened = oneEvent(el, "sp-opened");
789
+ sendKeys({ down: "Enter" });
790
+ await opened;
791
+ await aTimeout(300);
792
+ expect(openSpy.callCount).to.equal(1);
793
+ await sendKeys({ up: "Enter" });
682
794
  await waitUntil(
683
- () => isMenuActiveElement(),
684
- "first item refocused"
795
+ () => firstItem.focused,
796
+ "The first items should have become focused visually."
685
797
  );
686
- expect(el.open).to.be.true;
687
- expect(isMenuActiveElement()).to.be.true;
688
798
  await sendKeys({ press: "ArrowDown" });
689
- await sendKeys({ press: "ArrowUp" });
690
- expect(firstItem.focused).to.be.true;
799
+ await sendKeys({ press: "ArrowDown" });
800
+ expect(thirdItem.focused).to.be.true;
801
+ const closed = oneEvent(el, "sp-closed");
802
+ sendKeys({ down: "Enter" });
803
+ await closed;
804
+ await aTimeout(300);
805
+ expect(el.value).to.equal(thirdItem.value);
806
+ expect(openSpy.callCount).to.equal(1);
807
+ expect(closedSpy.callCount).to.equal(1);
808
+ await sendKeys({ up: "Enter" });
691
809
  });
692
- it("does not allow tabing to close", async () => {
810
+ it("allows tabing to close", async () => {
811
+ const input = document.createElement("input");
812
+ el.insertAdjacentElement("afterend", input);
813
+ const opened = oneEvent(el, "sp-opened");
693
814
  el.open = true;
694
- await elementUpdated(el);
815
+ await opened;
816
+ await nextFrame();
695
817
  expect(el.open).to.be.true;
696
818
  el.focus();
697
- await elementUpdated(el);
698
- await waitUntil(
699
- () => isMenuActiveElement(),
700
- "first item refocused"
701
- );
702
- expect(el.open).to.be.true;
703
- expect(isMenuActiveElement()).to.be.true;
704
- await sendKeys({ press: "Tab" });
705
- expect(el.open, "stays open").to.be.true;
819
+ const closed = oneEvent(el, "sp-closed");
820
+ sendKeys({ press: "Tab" });
821
+ await closed;
822
+ expect(el.open, "closes").to.be.false;
706
823
  });
707
824
  describe("tab order", () => {
708
825
  let input1;
@@ -757,51 +874,7 @@ export function runPickerTests() {
757
874
  input1
758
875
  );
759
876
  });
760
- it('traps tab in the menu as a `type="modal"` overlay forward', async () => {
761
- el.focus();
762
- await nextFrame();
763
- expect(document.activeElement, "focuses el").to.equal(el);
764
- const opened = oneEvent(el, "sp-opened");
765
- sendKeys({ press: "ArrowDown" });
766
- await opened;
767
- expect(el.open, "opened").to.be.true;
768
- await waitUntil(
769
- () => isMenuActiveElement(),
770
- "first item focused"
771
- );
772
- const activeElement = document.activeElement;
773
- if (!isWebKit()) {
774
- const blured = oneEvent(activeElement, "blur");
775
- sendKeys({ press: "Tab" });
776
- await blured;
777
- expect(el.open, "picker still open").to.be.true;
778
- expect(document.activeElement === input1).to.be.false;
779
- expect(document.activeElement === input2).to.be.false;
780
- }
781
- });
782
- it('traps tab in the menu as a `type="modal"` overlay backwards', async () => {
783
- el.focus();
784
- await nextFrame();
785
- expect(document.activeElement, "focuses el").to.equal(el);
786
- const opened = oneEvent(el, "sp-opened");
787
- await sendKeys({ press: "ArrowDown" });
788
- await opened;
789
- expect(el.open, "opened").to.be.true;
790
- await waitUntil(
791
- () => isMenuActiveElement(),
792
- "first item focused"
793
- );
794
- const activeElement = document.activeElement;
795
- if (!isWebKit()) {
796
- const blured = oneEvent(activeElement, "blur");
797
- sendKeys({ press: "Shift+Tab" });
798
- await blured;
799
- expect(el.open, "picker still open").to.be.true;
800
- expect(document.activeElement === input1).to.be.false;
801
- expect(document.activeElement === input2).to.be.false;
802
- }
803
- });
804
- it("can close and immediate tab to the next tab stop", async () => {
877
+ it("can close and immediately tab to the next tab stop", async () => {
805
878
  el.focus();
806
879
  await nextFrame();
807
880
  expect(document.activeElement, "focuses el").to.equal(el);
@@ -810,7 +883,7 @@ export function runPickerTests() {
810
883
  await opened;
811
884
  expect(el.open, "opened").to.be.true;
812
885
  await waitUntil(
813
- () => isMenuActiveElement(),
886
+ () => isMenuActiveElement(el),
814
887
  "first item focused"
815
888
  );
816
889
  const closed = oneEvent(el, "sp-closed");
@@ -827,13 +900,13 @@ export function runPickerTests() {
827
900
  it("can close and immediate shift+tab to the previous tab stop", async () => {
828
901
  el.focus();
829
902
  await nextFrame();
830
- expect(document.activeElement, "focuses el").to.equal(el);
903
+ expect(document.activeElement === el, "focuses el").to.be.true;
831
904
  const opened = oneEvent(el, "sp-opened");
832
905
  await sendKeys({ press: "ArrowUp" });
833
906
  await opened;
834
907
  expect(el.open, "opened").to.be.true;
835
908
  await waitUntil(
836
- () => isMenuActiveElement(),
909
+ () => isMenuActiveElement(el),
837
910
  "first item focused"
838
911
  );
839
912
  const closed = oneEvent(el, "sp-closed");
@@ -842,7 +915,7 @@ export function runPickerTests() {
842
915
  expect(el.open).to.be.false;
843
916
  expect(document.activeElement === el).to.be.true;
844
917
  const focused = oneEvent(input1, "focus");
845
- await sendKeys({ press: "Shift+Tab" });
918
+ sendKeys({ press: "Shift+Tab" });
846
919
  await focused;
847
920
  expect(el.open).to.be.false;
848
921
  expect(document.activeElement === input1).to.be.true;
@@ -857,8 +930,9 @@ export function runPickerTests() {
857
930
  expect(el.open).to.be.false;
858
931
  });
859
932
  it("scrolls selected into view on open", async () => {
860
- await el.generatePopover();
861
- el.popoverEl.style.height = "40px";
933
+ const styles = document.createElement("style");
934
+ styles.innerText = "sp-popover { height: 40px; }";
935
+ el.shadowRoot.append(styles);
862
936
  const firstItem = el.querySelector(
863
937
  "sp-menu-item:first-child"
864
938
  );
@@ -868,11 +942,15 @@ export function runPickerTests() {
868
942
  lastItem.disabled = false;
869
943
  el.value = lastItem.value;
870
944
  await elementUpdated(el);
945
+ const opened = oneEvent(el, "sp-opened");
871
946
  el.open = true;
872
- await elementUpdated(el);
873
- await waitUntil(() => isMenuActiveElement(), "first item focused");
947
+ await opened;
948
+ await waitUntil(
949
+ () => isMenuActiveElement(el),
950
+ "first item focused"
951
+ );
874
952
  const getParentOffset = (el2) => {
875
- const parentScroll = el2.parentElement.scrollTop;
953
+ const parentScroll = el2.assignedSlot.parentElement.scrollTop;
876
954
  const parentOffset = el2.offsetTop - parentScroll;
877
955
  return parentOffset;
878
956
  };
@@ -881,7 +959,9 @@ export function runPickerTests() {
881
959
  lastItem.dispatchEvent(
882
960
  new FocusEvent("focusin", { bubbles: true })
883
961
  );
884
- lastItem.dispatchEvent(arrowDownEvent());
962
+ await sendKeys({
963
+ press: "ArrowDown"
964
+ });
885
965
  await elementUpdated(el);
886
966
  await nextFrame();
887
967
  expect(getParentOffset(lastItem)).to.be.greaterThan(40);
@@ -905,7 +985,6 @@ export function runPickerTests() {
905
985
  <sp-menu-item value="1">
906
986
  I'm already using them
907
987
  </sp-menu-item>
908
- <sp-menu-divider></sp-menu-divider>
909
988
  <sp-menu-item value="2">Soon</sp-menu-item>
910
989
  <sp-menu-item value="3">
911
990
  As part of my next project
@@ -919,6 +998,8 @@ export function runPickerTests() {
919
998
  beforeEach(async () => {
920
999
  el = await groupedFixture();
921
1000
  await elementUpdated(el);
1001
+ await nextFrame();
1002
+ await nextFrame();
922
1003
  });
923
1004
  it("selects the item with a matching value in a group", async () => {
924
1005
  const item = el.querySelector("#should-be-selected");
@@ -944,7 +1025,6 @@ export function runPickerTests() {
944
1025
  </sp-menu-item>
945
1026
  <sp-menu-item>Feather...</sp-menu-item>
946
1027
  <sp-menu-item>Select and Mask...</sp-menu-item>
947
- <sp-menu-divider></sp-menu-divider>
948
1028
  <sp-menu-item>Save Selection</sp-menu-item>
949
1029
  <sp-menu-item disabled>Make Work Path</sp-menu-item>
950
1030
  </sp-picker>
@@ -956,6 +1036,7 @@ export function runPickerTests() {
956
1036
  beforeEach(async () => {
957
1037
  el = await pickerFixture2();
958
1038
  await elementUpdated(el);
1039
+ await nextFrame();
959
1040
  });
960
1041
  afterEach(async () => {
961
1042
  if (el.open) {
@@ -987,7 +1068,6 @@ export function runPickerTests() {
987
1068
  </sp-menu-item>
988
1069
  <sp-menu-item>Feather...</sp-menu-item>
989
1070
  <sp-menu-item>Select and Mask...</sp-menu-item>
990
- <sp-menu-divider></sp-menu-divider>
991
1071
  <sp-menu-item>Save Selection</sp-menu-item>
992
1072
  <sp-menu-item disabled>
993
1073
  Make Work Path
@@ -1041,6 +1121,7 @@ export function runPickerTests() {
1041
1121
  beforeEach(async () => {
1042
1122
  el = await pickerFixture2();
1043
1123
  await elementUpdated(el);
1124
+ await nextFrame();
1044
1125
  });
1045
1126
  afterEach(async () => {
1046
1127
  if (el.open) {
@@ -1057,7 +1138,6 @@ export function runPickerTests() {
1057
1138
  const opened = oneEvent(el, "sp-opened");
1058
1139
  el.button.click();
1059
1140
  await opened;
1060
- await elementUpdated(el);
1061
1141
  expect(el.open).to.be.true;
1062
1142
  expect((_a = el.selectedItem) == null ? void 0 : _a.itemText).to.be.undefined;
1063
1143
  expect(el.value).to.equal("");
@@ -1077,6 +1157,7 @@ export function runPickerTests() {
1077
1157
  `);
1078
1158
  const el2 = test.querySelector("sp-picker");
1079
1159
  await elementUpdated(el2);
1160
+ await nextFrame();
1080
1161
  let snapshot = await a11ySnapshot({});
1081
1162
  expect(
1082
1163
  findAccessibilityNode(
@@ -1087,6 +1168,9 @@ export function runPickerTests() {
1087
1168
  ).to.not.be.null;
1088
1169
  el2.value = "2";
1089
1170
  await elementUpdated(el2);
1171
+ await nextFrame();
1172
+ await nextFrame();
1173
+ expect(el2.value).to.equal("2");
1090
1174
  snapshot = await a11ySnapshot({});
1091
1175
  expect(
1092
1176
  findAccessibilityNode(
@@ -1099,6 +1183,8 @@ export function runPickerTests() {
1099
1183
  it("toggles between pickers", async () => {
1100
1184
  const el2 = await pickerFixture();
1101
1185
  const el1 = await pickerFixture();
1186
+ el1.parentElement.style.float = "left";
1187
+ el2.parentElement.style.float = "left";
1102
1188
  el1.id = "away";
1103
1189
  el2.id = "other";
1104
1190
  await Promise.all([elementUpdated(el1), elementUpdated(el2)]);
@@ -1119,8 +1205,8 @@ export function runPickerTests() {
1119
1205
  closed = oneEvent(el2, "sp-closed");
1120
1206
  el1.click();
1121
1207
  await Promise.all([open, closed]);
1122
- expect(el1.open).to.be.true;
1123
1208
  expect(el2.open).to.be.false;
1209
+ expect(el1.open).to.be.true;
1124
1210
  closed = oneEvent(el1, "sp-closed");
1125
1211
  sendKeys({
1126
1212
  press: "Escape"
@@ -1129,7 +1215,7 @@ export function runPickerTests() {
1129
1215
  expect(el1.open).to.be.false;
1130
1216
  });
1131
1217
  it("displays selected item text by default", async () => {
1132
- var _a, _b, _c, _d;
1218
+ var _a, _b, _c, _d, _e;
1133
1219
  const el2 = await fixture(
1134
1220
  html`
1135
1221
  <sp-picker
@@ -1140,12 +1226,12 @@ export function runPickerTests() {
1140
1226
  <sp-menu-item value="inverse">Select Inverse</sp-menu-item>
1141
1227
  <sp-menu-item>Feather...</sp-menu-item>
1142
1228
  <sp-menu-item>Select and Mask...</sp-menu-item>
1143
- <sp-menu-divider></sp-menu-divider>
1144
1229
  <sp-menu-item>Save Selection</sp-menu-item>
1145
1230
  <sp-menu-item disabled>Make Work Path</sp-menu-item>
1146
1231
  </sp-picker>
1147
1232
  `
1148
1233
  );
1234
+ await nextFrame();
1149
1235
  await elementUpdated(el2);
1150
1236
  await waitUntil(
1151
1237
  () => {
@@ -1171,16 +1257,21 @@ export function runPickerTests() {
1171
1257
  const opened = oneEvent(el2, "sp-opened");
1172
1258
  sendKeys({ press: "Enter" });
1173
1259
  await opened;
1174
- await elementUpdated(el2.optionsMenu);
1175
1260
  expect(
1176
- el2.optionsMenu === document.activeElement,
1261
+ el2 === document.activeElement,
1177
1262
  `activeElement is ${(_d = document.activeElement) == null ? void 0 : _d.localName}`
1178
1263
  ).to.be.true;
1264
+ expect(
1265
+ el2.optionsMenu === el2.shadowRoot.activeElement,
1266
+ `activeElement is ${(_e = el2.shadowRoot.activeElement) == null ? void 0 : _e.localName}`
1267
+ ).to.be.true;
1179
1268
  expect(firstItem.focused, 'firstItem NOT "focused"').to.be.false;
1180
1269
  expect(secondItem.focused, 'secondItem "focused"').to.be.true;
1181
- expect(el2.optionsMenu.getAttribute("aria-activedescendant")).to.equal(
1182
- secondItem.id
1183
- );
1270
+ expect(
1271
+ el2.optionsMenu.getAttribute(
1272
+ "aria-activedescendant"
1273
+ )
1274
+ ).to.equal(secondItem.id);
1184
1275
  });
1185
1276
  it("resets value when item not available", async () => {
1186
1277
  var _a;
@@ -1194,7 +1285,6 @@ export function runPickerTests() {
1194
1285
  <sp-menu-item value="inverse">Select Inverse</sp-menu-item>
1195
1286
  <sp-menu-item>Feather...</sp-menu-item>
1196
1287
  <sp-menu-item>Select and Mask...</sp-menu-item>
1197
- <sp-menu-divider></sp-menu-divider>
1198
1288
  <sp-menu-item>Save Selection</sp-menu-item>
1199
1289
  <sp-menu-item disabled>Make Work Path</sp-menu-item>
1200
1290
  </sp-picker>
@@ -1262,15 +1352,11 @@ export function runPickerTests() {
1262
1352
  await elementUpdated(el2);
1263
1353
  expect(openedSpy.calledOnce).to.be.true;
1264
1354
  expect(closedSpy.calledOnce).to.be.false;
1265
- const openedEvent = openedSpy.args[0][0];
1266
- expect(openedEvent.detail.interaction).to.equal("modal");
1267
1355
  const closed = oneEvent(el2, "sp-closed");
1268
1356
  el2.open = false;
1269
1357
  await closed;
1270
1358
  await elementUpdated(el2);
1271
1359
  expect(closedSpy.calledOnce).to.be.true;
1272
- const closedEvent = closedSpy.args[0][0];
1273
- expect(closedEvent.detail.interaction).to.equal("modal");
1274
1360
  });
1275
1361
  }
1276
1362
  //# sourceMappingURL=index.js.map