@crowdstrike/glide-core 0.5.2 → 0.6.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 (100) hide show
  1. package/README.md +11 -1
  2. package/dist/accordion.styles.js +1 -0
  3. package/dist/button-group.button.js +1 -1
  4. package/dist/button-group.button.styles.js +2 -1
  5. package/dist/button.d.ts +3 -2
  6. package/dist/button.js +1 -1
  7. package/dist/button.styles.js +1 -1
  8. package/dist/button.test.basics.js +6 -0
  9. package/dist/checkbox.js +1 -1
  10. package/dist/checkbox.styles.js +4 -1
  11. package/dist/drawer.js +1 -1
  12. package/dist/drawer.styles.js +1 -5
  13. package/dist/drawer.test.floating-components.d.ts +1 -0
  14. package/dist/drawer.test.floating-components.js +51 -0
  15. package/dist/dropdown.js +1 -1
  16. package/dist/dropdown.option.js +1 -1
  17. package/dist/dropdown.option.test.interactions.multiple.js +1 -6
  18. package/dist/dropdown.styles.js +1 -0
  19. package/dist/dropdown.test.focus.js +11 -1
  20. package/dist/dropdown.test.interactions.filterable.js +64 -0
  21. package/dist/icon-button.d.ts +3 -2
  22. package/dist/icon-button.js +1 -1
  23. package/dist/icon-button.styles.js +9 -9
  24. package/dist/icon-button.test.basics.js +13 -6
  25. package/dist/input.js +1 -1
  26. package/dist/input.styles.js +1 -0
  27. package/dist/label.js +1 -1
  28. package/dist/label.styles.js +11 -13
  29. package/dist/library/localize.d.ts +17 -0
  30. package/dist/library/localize.js +1 -0
  31. package/dist/library/set-containing-block.d.ts +15 -0
  32. package/dist/library/set-containing-block.js +1 -0
  33. package/dist/menu.button.js +1 -1
  34. package/dist/menu.d.ts +5 -4
  35. package/dist/menu.js +1 -1
  36. package/dist/menu.link.js +1 -1
  37. package/dist/menu.options.d.ts +22 -0
  38. package/dist/menu.options.js +1 -0
  39. package/dist/menu.options.styles.d.ts +2 -0
  40. package/dist/menu.options.styles.js +33 -0
  41. package/dist/menu.options.test.basics.d.ts +2 -0
  42. package/dist/menu.options.test.basics.js +43 -0
  43. package/dist/menu.stories.d.ts +1 -0
  44. package/dist/menu.styles.js +3 -27
  45. package/dist/menu.test.basics.d.ts +1 -0
  46. package/dist/menu.test.basics.js +67 -45
  47. package/dist/menu.test.focus.js +34 -16
  48. package/dist/menu.test.interactions.d.ts +1 -0
  49. package/dist/menu.test.interactions.js +315 -173
  50. package/dist/modal.js +1 -1
  51. package/dist/modal.styles.js +1 -4
  52. package/dist/modal.tertiary-icon.d.ts +1 -0
  53. package/dist/modal.tertiary-icon.js +1 -1
  54. package/dist/modal.test.floating-components.d.ts +1 -0
  55. package/dist/modal.test.floating-components.js +62 -0
  56. package/dist/radio-group.js +1 -1
  57. package/dist/radio-group.styles.js +18 -22
  58. package/dist/radio.styles.js +11 -28
  59. package/dist/split-button.d.ts +3 -0
  60. package/dist/split-button.js +1 -1
  61. package/dist/split-button.styles.js +0 -1
  62. package/dist/split-button.test.basics.js +16 -1
  63. package/dist/split-container.d.ts +1 -0
  64. package/dist/split-container.js +1 -1
  65. package/dist/split-container.styles.js +2 -0
  66. package/dist/split-container.test.basics.js +11 -16
  67. package/dist/styles/focus-outline.js +1 -1
  68. package/dist/styles/variables.css +1 -1
  69. package/dist/tab.js +1 -1
  70. package/dist/tab.styles.js +79 -54
  71. package/dist/tag.js +1 -1
  72. package/dist/tag.styles.js +1 -0
  73. package/dist/tag.test.basics.js +1 -1
  74. package/dist/tag.test.translations.d.ts +1 -0
  75. package/dist/tag.test.translations.js +25 -0
  76. package/dist/textarea.styles.js +2 -1
  77. package/dist/toasts.js +1 -1
  78. package/dist/toasts.toast.js +1 -1
  79. package/dist/toggle.js +1 -1
  80. package/dist/toggle.test.basics.js +4 -0
  81. package/dist/toggle.test.states.js +8 -0
  82. package/dist/tooltip.d.ts +2 -0
  83. package/dist/tooltip.js +1 -1
  84. package/dist/tooltip.styles.js +2 -0
  85. package/dist/translations/en.d.ts +3 -0
  86. package/dist/translations/en.js +1 -0
  87. package/dist/translations/fr.d.ts +3 -0
  88. package/dist/translations/fr.js +1 -0
  89. package/dist/translations/ja.d.ts +3 -0
  90. package/dist/translations/ja.js +1 -0
  91. package/dist/tree.d.ts +1 -0
  92. package/dist/tree.item.d.ts +3 -1
  93. package/dist/tree.item.js +1 -1
  94. package/dist/tree.item.menu.d.ts +2 -0
  95. package/dist/tree.item.menu.js +1 -1
  96. package/dist/tree.item.menu.test.basics.js +6 -7
  97. package/dist/tree.item.styles.js +22 -7
  98. package/dist/tree.js +1 -1
  99. package/dist/tree.stories.d.ts +1 -0
  100. package/package.json +19 -13
@@ -1,4 +1,5 @@
1
1
  import './menu.link.js';
2
+ import './menu.options.js';
2
3
  import { elementUpdated, expect, fixture, html } from '@open-wc/testing';
3
4
  import { sendKeys } from '@web/test-runner-commands';
4
5
  import GlideCoreMenu from './menu.js';
@@ -6,138 +7,179 @@ GlideCoreMenu.shadowRootOptions.mode = 'open';
6
7
  it('opens when clicked', async () => {
7
8
  const component = await fixture(html `<glide-core-menu>
8
9
  <button slot="target">Target</button>
9
- <glide-core-menu-link label="Link"></glide-core-menu-link>
10
+
11
+ <glide-core-menu-options>
12
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
13
+ </glide-core-menu-options>
10
14
  </glide-core-menu>`);
11
15
  component.querySelector('button')?.click();
12
16
  await elementUpdated(component);
13
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
17
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
18
+ const target = component.querySelector('button');
14
19
  expect(component.open).to.be.true;
15
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
20
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
21
+ expect(target?.ariaExpanded).to.equal('true');
16
22
  });
17
23
  it('does not open when clicked when its target is `disabled`', async () => {
18
24
  const component = await fixture(html `<glide-core-menu>
19
25
  <button slot="target" disabled>Target</button>
20
- <glide-core-menu-link label="Link"></glide-core-menu-link>
26
+
27
+ <glide-core-menu-options>
28
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
29
+ </glide-core-menu-options>
21
30
  </glide-core-menu>`);
22
31
  component.querySelector('button')?.click();
23
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
32
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
33
+ const options = component.querySelector('glide-core-menu-options');
24
34
  const target = component.querySelector('button');
25
35
  expect(component.open).to.be.false;
26
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.not.be.ok;
27
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
36
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
37
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
28
38
  expect(target?.ariaExpanded).to.equal('false');
29
39
  });
30
40
  it('does not open when clicked when its target is `aria-disabled`', async () => {
31
41
  const component = await fixture(html `<glide-core-menu>
32
42
  <button aria-disabled="true" slot="target">Target</button>
33
- <glide-core-menu-link label="Link"></glide-core-menu-link>
43
+
44
+ <glide-core-menu-options>
45
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
46
+ </glide-core-menu-options>
34
47
  </glide-core-menu>`);
35
48
  component.querySelector('button')?.click();
36
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
49
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
50
+ const options = component.querySelector('glide-core-menu-options');
37
51
  const target = component.querySelector('button');
38
52
  expect(component.open).to.be.false;
39
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.not.be.ok;
40
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
53
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
54
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
41
55
  expect(target?.ariaExpanded).to.equal('false');
42
56
  });
43
57
  it('opens on Enter', async () => {
44
58
  const component = await fixture(html `<glide-core-menu>
45
59
  <button slot="target">Target</button>
46
- <glide-core-menu-link label="Link"></glide-core-menu-link>
60
+
61
+ <glide-core-menu-options>
62
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
63
+ </glide-core-menu-options>
47
64
  </glide-core-menu>`);
48
65
  component.querySelector('button')?.focus();
49
66
  await sendKeys({ press: 'Enter' });
50
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
67
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
68
+ const options = component.querySelector('glide-core-menu-options');
51
69
  const target = component.querySelector('button');
52
70
  const link = component.querySelector('glide-core-menu-link');
53
71
  expect(component.open).to.be.true;
54
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
55
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(link?.id);
72
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
73
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
56
74
  expect(target?.ariaExpanded).to.equal('true');
57
75
  });
58
76
  it('opens on ArrowUp', async () => {
59
77
  const component = await fixture(html `<glide-core-menu>
60
78
  <button slot="target">Target</button>
61
- <glide-core-menu-link label="Link"></glide-core-menu-link>
79
+
80
+ <glide-core-menu-options>
81
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
82
+ </glide-core-menu-options>
62
83
  </glide-core-menu>`);
63
84
  component.querySelector('button')?.focus();
64
85
  await sendKeys({ press: 'ArrowUp' });
65
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
86
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
87
+ const options = component.querySelector('glide-core-menu-options');
66
88
  const target = component.querySelector('button');
67
89
  const link = component.querySelector('glide-core-menu-link');
68
90
  expect(component.open).to.be.true;
69
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
70
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(link?.id);
91
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
92
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
71
93
  expect(target?.ariaExpanded).to.equal('true');
72
94
  });
73
95
  it('opens on ArrowDown', async () => {
74
96
  const component = await fixture(html `<glide-core-menu>
75
97
  <button slot="target">Target</button>
76
- <glide-core-menu-link label="Link"></glide-core-menu-link>
98
+
99
+ <glide-core-menu-options>
100
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
101
+ </glide-core-menu-options>
77
102
  </glide-core-menu>`);
78
103
  component.querySelector('button')?.focus();
79
104
  await sendKeys({ press: 'ArrowDown' });
80
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
105
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
106
+ const options = component.querySelector('glide-core-menu-options');
81
107
  const target = component.querySelector('button');
82
108
  const link = component.querySelector('glide-core-menu-link');
83
109
  expect(component.open).to.be.true;
84
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
85
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(link?.id);
110
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
111
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
86
112
  expect(target?.ariaExpanded).to.equal('true');
87
113
  });
88
114
  it('opens on Space', async () => {
89
115
  const component = await fixture(html `<glide-core-menu>
90
116
  <button slot="target">Target</button>
91
- <glide-core-menu-link label="Link"></glide-core-menu-link>
117
+
118
+ <glide-core-menu-options>
119
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
120
+ </glide-core-menu-options>
92
121
  </glide-core-menu>`);
93
122
  component.querySelector('button')?.focus();
94
123
  await sendKeys({ press: ' ' });
95
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
124
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
125
+ const options = component.querySelector('glide-core-menu-options');
96
126
  const target = component.querySelector('button');
97
127
  const link = component.querySelector('glide-core-menu-link');
98
128
  expect(component.open).to.be.true;
99
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
100
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(link?.id);
129
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
130
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
101
131
  expect(target?.ariaExpanded).to.equal('true');
102
132
  });
103
133
  it('opens when opened programmatically', async () => {
104
134
  const component = await fixture(html `<glide-core-menu>
105
135
  <button slot="target">Target</button>
106
- <glide-core-menu-link label="Link"></glide-core-menu-link>
136
+
137
+ <glide-core-menu-options>
138
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
139
+ </glide-core-menu-options>
107
140
  </glide-core-menu>`);
108
141
  component.open = true;
109
142
  await elementUpdated(component);
110
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
143
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
144
+ const options = component.querySelector('glide-core-menu-options');
111
145
  const target = component.querySelector('button');
112
146
  const link = component.querySelector('glide-core-menu-link');
113
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
114
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(link?.id);
147
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
148
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
115
149
  expect(target?.ariaExpanded).to.equal('true');
116
150
  });
117
151
  it('does not open when opened programmatically and its target is `disabled`', async () => {
118
152
  const component = await fixture(html `<glide-core-menu>
119
153
  <button slot="target" disabled>Target</button>
120
- <glide-core-menu-link label="Link"></glide-core-menu-link>
154
+
155
+ <glide-core-menu-options>
156
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
157
+ </glide-core-menu-options>
121
158
  </glide-core-menu>`);
122
159
  component.open = true;
123
160
  await elementUpdated(component);
124
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
161
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
162
+ const options = component.querySelector('glide-core-menu-options');
125
163
  const target = component.querySelector('button');
126
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.not.be.ok;
127
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
164
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
165
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
128
166
  expect(target?.ariaExpanded).to.equal('false');
129
167
  });
130
168
  it('does not open when opened programmatically and its target is `aria-disabled`', async () => {
131
169
  const component = await fixture(html `<glide-core-menu>
132
170
  <button aria-disabled="true" slot="target">Target</button>
133
- <glide-core-menu-link label="Link"></glide-core-menu-link>
171
+
172
+ <glide-core-menu-options>
173
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
174
+ </glide-core-menu-options>
134
175
  </glide-core-menu>`);
135
176
  component.open = true;
136
177
  await elementUpdated(component);
137
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
178
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
179
+ const options = component.querySelector('glide-core-menu-options');
138
180
  const target = component.querySelector('button');
139
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.not.be.ok;
140
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
181
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
182
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
141
183
  expect(target?.ariaExpanded).to.equal('false');
142
184
  });
143
185
  // See the `document` click listener comment in `menu.ts` for an explanation.
@@ -145,79 +187,116 @@ it('opens when opened programmatically via the click handler of another element'
145
187
  const div = document.createElement('div');
146
188
  const component = await fixture(html `<glide-core-menu>
147
189
  <button slot="target">Target</button>
148
- <glide-core-menu-link label="Link"></glide-core-menu-link>
190
+
191
+ <glide-core-menu-options>
192
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
193
+ </glide-core-menu-options>
149
194
  </glide-core-menu>`, { parentNode: div });
150
195
  const anotherElement = document.createElement('button');
151
196
  anotherElement.addEventListener('click', () => (component.open = true));
152
197
  div.append(anotherElement);
153
198
  anotherElement.click();
154
199
  await elementUpdated(component);
155
- const menu = component.shadowRoot?.querySelector('[data-test="menu"]');
200
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
201
+ const options = component.querySelector('glide-core-menu-options');
156
202
  const target = component.querySelector('button');
157
203
  const link = component.querySelector('glide-core-menu-link');
158
204
  expect(component.open).to.be.true;
159
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
160
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(link?.id);
205
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).to.be.true;
206
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
161
207
  expect(target?.ariaExpanded).to.equal('true');
162
208
  });
209
+ it('sets `privateSize` on the options component when `size` is changed programmatically', async () => {
210
+ const component = await fixture(html `<glide-core-menu>
211
+ <button slot="target">Target</button>
212
+
213
+ <glide-core-menu-options>
214
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
215
+ </glide-core-menu-options>
216
+ </glide-core-menu>`);
217
+ component.size = 'small';
218
+ const options = component.querySelector('glide-core-menu-options');
219
+ expect(options?.privateSize).to.equal('small');
220
+ });
163
221
  it('closes when clicked', async () => {
164
222
  const component = await fixture(html `<glide-core-menu open>
165
223
  <button slot="target">Target</button>
166
- <glide-core-menu-link label="Link"></glide-core-menu-link>
224
+
225
+ <glide-core-menu-options>
226
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
227
+ </glide-core-menu-options>
167
228
  </glide-core-menu>`);
168
229
  component.querySelector('button')?.click();
169
230
  await elementUpdated(component);
170
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
231
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
232
+ const options = component.querySelector('glide-core-menu-options');
171
233
  const target = component.querySelector('button');
172
234
  expect(component.open).to.be.false;
173
- expect(menu?.checkVisibility({ checkVisibilityCSS: true })).to.be.false;
174
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
235
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
236
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
175
237
  expect(target?.ariaExpanded).to.equal('false');
176
238
  });
177
239
  it('closes when something outside of it is clicked', async () => {
178
240
  const component = await fixture(html `<glide-core-menu>
179
241
  <button slot="target">Target</button>
180
- <glide-core-menu-link label="Link"></glide-core-menu-link>
242
+
243
+ <glide-core-menu-options>
244
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
245
+ </glide-core-menu-options>
181
246
  </glide-core-menu>`);
182
247
  component.querySelector('button')?.click();
183
248
  document.body.click();
184
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
249
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
250
+ const options = component.querySelector('glide-core-menu-options');
185
251
  const target = component.querySelector('button');
186
252
  expect(component.open).to.be.false;
187
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
253
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
254
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
188
255
  expect(target?.ariaExpanded).to.equal('false');
189
256
  });
190
257
  it('closes on Escape when the button has focus', async () => {
191
258
  const component = await fixture(html `<glide-core-menu open>
192
259
  <button slot="target">Target</button>
193
- <glide-core-menu-link label="Link"></glide-core-menu-link>
260
+
261
+ <glide-core-menu-options>
262
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
263
+ </glide-core-menu-options>
194
264
  </glide-core-menu>`);
195
265
  component.querySelector('button')?.click();
196
266
  await sendKeys({ press: 'Escape' });
197
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
267
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
268
+ const options = component.querySelector('glide-core-menu-options');
198
269
  const target = component.querySelector('button');
199
270
  expect(component.open).to.be.false;
200
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
271
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
272
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
201
273
  expect(target?.ariaExpanded).to.equal('false');
202
274
  });
203
275
  it('closes when an option is selected via click', async () => {
204
276
  const component = await fixture(html `<glide-core-menu open>
205
277
  <button slot="target">Target</button>
206
- <glide-core-menu-link label="Link"></glide-core-menu-link>
278
+
279
+ <glide-core-menu-options>
280
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
281
+ </glide-core-menu-options>
207
282
  </glide-core-menu>`);
208
283
  component.querySelector('glide-core-menu-link')?.click();
209
284
  await elementUpdated(component);
210
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
285
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
286
+ const options = component.querySelector('glide-core-menu-options');
211
287
  const target = component.querySelector('button');
212
288
  expect(component.open).to.be.false;
213
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
214
- expect(target?.ariaExpanded).to.equal('false');
289
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
290
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
215
291
  expect(target?.ariaExpanded).to.equal('false');
216
292
  });
217
293
  it('closes when an option is selected via Enter', async () => {
218
294
  const component = await fixture(html `<glide-core-menu open>
219
295
  <button slot="target">Target</button>
220
- <glide-core-menu-link label="Link"></glide-core-menu-link>
296
+
297
+ <glide-core-menu-options>
298
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
299
+ </glide-core-menu-options>
221
300
  </glide-core-menu>`);
222
301
  component.focus();
223
302
  component
@@ -225,280 +304,340 @@ it('closes when an option is selected via Enter', async () => {
225
304
  ?.dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
226
305
  await sendKeys({ press: 'Enter' });
227
306
  await elementUpdated(component);
228
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
307
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
308
+ const options = component.querySelector('glide-core-menu-options');
229
309
  const target = component.querySelector('button');
230
310
  expect(component.open).to.be.false;
231
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
311
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
312
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
232
313
  expect(target?.ariaExpanded).to.equal('false');
233
314
  });
234
315
  it('closes when an option is selected via Space', async () => {
235
316
  const component = await fixture(html `<glide-core-menu open>
236
317
  <button slot="target">Target</button>
237
- <glide-core-menu-link label="Link"></glide-core-menu-link>
318
+
319
+ <glide-core-menu-options>
320
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
321
+ </glide-core-menu-options>
238
322
  </glide-core-menu>`);
239
323
  component.focus();
240
324
  await sendKeys({ press: ' ' });
241
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
325
+ const defaultSlot = component?.shadowRoot?.querySelector('slot:not([name])');
326
+ const options = component.querySelector('glide-core-menu-options');
242
327
  const target = component.querySelector('button');
243
328
  expect(component.open).to.be.false;
244
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
329
+ expect(defaultSlot?.checkVisibility({ checkVisibilityCSS: true })).not.ok;
330
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
245
331
  expect(target?.ariaExpanded).to.equal('false');
246
332
  });
247
333
  it('activates the first menu link by default', async () => {
248
334
  const component = await fixture(html `
249
335
  <glide-core-menu>
250
336
  <button slot="target">Target</button>
251
- <glide-core-menu-link label="One"></glide-core-menu-link>
252
- <glide-core-menu-link label="Two"></glide-core-menu-link>
337
+
338
+ <glide-core-menu-options>
339
+ <glide-core-menu-link label="One"></glide-core-menu-link>
340
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
341
+ </glide-core-menu-options>
253
342
  </glide-core-menu>
254
343
  `);
255
344
  component.querySelector('button')?.click();
256
345
  await elementUpdated(component);
257
- const options = component.querySelectorAll('glide-core-menu-link');
258
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
259
- expect(options[0].privateActive).to.be.true;
260
- expect(options[1].privateActive).to.be.false;
261
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[0].id);
346
+ const links = component.querySelectorAll('glide-core-menu-link');
347
+ const options = component.querySelector('glide-core-menu-options');
348
+ expect(links[0].privateActive).to.be.true;
349
+ expect(links[1].privateActive).to.be.false;
350
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[0]?.id);
262
351
  });
263
352
  it('activates the first menu button by default', async () => {
264
353
  const component = await fixture(html `
265
354
  <glide-core-menu>
266
355
  <button slot="target">Target</button>
267
- <glide-core-menu-button label="One"></glide-core-menu-button>
268
- <glide-core-menu-button label="Two"></glide-core-menu-button>
356
+
357
+ <glide-core-menu-options>
358
+ <glide-core-menu-button label="One"></glide-core-menu-button>
359
+ <glide-core-menu-button label="Two"></glide-core-menu-button>
360
+ </glide-core-menu-options>
269
361
  </glide-core-menu>
270
362
  `);
271
363
  component.querySelector('button')?.click();
272
364
  await elementUpdated(component);
273
- const options = component.querySelectorAll('glide-core-menu-button');
274
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
275
- expect(options[0].privateActive).to.be.true;
276
- expect(options[1].privateActive).to.be.false;
277
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[0].id);
365
+ const buttons = component.querySelectorAll('glide-core-menu-button');
366
+ const options = component.querySelector('glide-core-menu-options');
367
+ expect(buttons[0].privateActive).to.be.true;
368
+ expect(buttons[1].privateActive).to.be.false;
369
+ expect(options?.getAttribute('aria-activedescendant')).equal(buttons[0]?.id);
278
370
  });
279
371
  it('activates a menu link on "mouseover"', async () => {
280
372
  const component = await fixture(html `
281
373
  <glide-core-menu open>
282
374
  <button slot="target">Target</button>
283
- <glide-core-menu-link label="One"></glide-core-menu-link>
284
- <glide-core-menu-link label="Two"></glide-core-menu-link>
375
+
376
+ <glide-core-menu-options>
377
+ <glide-core-menu-link label="One"></glide-core-menu-link>
378
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
379
+ </glide-core-menu-options>
285
380
  </glide-core-menu>
286
381
  `);
287
- const options = component.querySelectorAll('glide-core-menu-link');
288
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
289
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
382
+ const links = component.querySelectorAll('glide-core-menu-link');
383
+ const options = component.querySelector('glide-core-menu-options');
384
+ links[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
290
385
  await elementUpdated(component);
291
- expect(options[0].privateActive).to.be.false;
292
- expect(options[1].privateActive).to.be.true;
293
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[1].id);
386
+ expect(links[0].privateActive).to.be.false;
387
+ expect(links[1].privateActive).to.be.true;
388
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[1].id);
294
389
  });
295
390
  it('activates a menu button on "mouseover"', async () => {
296
391
  const component = await fixture(html `
297
392
  <glide-core-menu open>
298
393
  <button slot="target">Target</button>
299
- <glide-core-menu-button label="One"></glide-core-menu-button>
300
- <glide-core-menu-button label="Two"></glide-core-menu-button>
394
+
395
+ <glide-core-menu-options>
396
+ <glide-core-menu-button label="One"></glide-core-menu-button>
397
+ <glide-core-menu-button label="Two"></glide-core-menu-button>
398
+ </glide-core-menu-options>
301
399
  </glide-core-menu>
302
400
  `);
303
- const options = component.querySelectorAll('glide-core-menu-button');
304
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
305
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
401
+ const buttons = component.querySelectorAll('glide-core-menu-button');
402
+ const options = component.querySelector('glide-core-menu-options');
403
+ buttons[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
306
404
  await elementUpdated(component);
307
- expect(options[0].privateActive).to.be.false;
308
- expect(options[1].privateActive).to.be.true;
309
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[1].id);
405
+ expect(buttons[0].privateActive).to.be.false;
406
+ expect(buttons[1].privateActive).to.be.true;
407
+ expect(options?.getAttribute('aria-activedescendant')).equal(buttons[1].id);
310
408
  });
311
409
  it('activates the next option on ArrowDown', async () => {
312
410
  const component = await fixture(html `
313
411
  <glide-core-menu>
314
412
  <button slot="target">Target</button>
315
- <glide-core-menu-link label="One"></glide-core-menu-link>
316
- <glide-core-menu-link label="Two"></glide-core-menu-link>
317
- <glide-core-menu-link label="Three"></glide-core-menu-link>
413
+
414
+ <glide-core-menu-options>
415
+ <glide-core-menu-link label="One"></glide-core-menu-link>
416
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
417
+ <glide-core-menu-link label="Three"></glide-core-menu-link>
418
+ </glide-core-menu-options>
318
419
  </glide-core-menu>
319
420
  `);
320
421
  component.querySelector('button')?.click();
321
422
  component.focus();
322
- const options = component.querySelectorAll('glide-core-menu-link');
323
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
324
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
423
+ const links = component.querySelectorAll('glide-core-menu-link');
424
+ const options = component.querySelector('glide-core-menu-options');
425
+ links[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
325
426
  await sendKeys({ press: 'ArrowDown' });
326
- expect(options[0].privateActive).to.be.false;
327
- expect(options[1].privateActive).to.be.false;
328
- expect(options[2].privateActive).to.be.true;
329
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[2].id);
427
+ expect(links[0].privateActive).to.be.false;
428
+ expect(links[1].privateActive).to.be.false;
429
+ expect(links[2].privateActive).to.be.true;
430
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[2].id);
330
431
  });
331
432
  it('activates the previous option on ArrowUp', async () => {
332
433
  const component = await fixture(html `
333
434
  <glide-core-menu>
334
435
  <button slot="target">Target</button>
335
- <glide-core-menu-link label="One"></glide-core-menu-link>
336
- <glide-core-menu-link label="Two"></glide-core-menu-link>
436
+
437
+ <glide-core-menu-options>
438
+ <glide-core-menu-link label="One"></glide-core-menu-link>
439
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
440
+ </glide-core-menu-options>
337
441
  </glide-core-menu>
338
442
  `);
339
443
  component.querySelector('button')?.click();
340
444
  component.focus();
341
- const options = component.querySelectorAll('glide-core-menu-link');
342
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
343
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
445
+ const links = component.querySelectorAll('glide-core-menu-link');
446
+ const options = component.querySelector('glide-core-menu-options');
447
+ links[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
344
448
  await sendKeys({ press: 'ArrowUp' });
345
- expect(options[0].privateActive).to.be.true;
346
- expect(options[1].privateActive).to.be.false;
347
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[0].id);
449
+ expect(links[0].privateActive).to.be.true;
450
+ expect(links[1].privateActive).to.be.false;
451
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[0].id);
348
452
  });
349
453
  it('activates the first option on Home', async () => {
350
454
  const component = await fixture(html `
351
455
  <glide-core-menu>
352
456
  <button slot="target">Target</button>
353
- <glide-core-menu-link label="One"></glide-core-menu-link>
354
- <glide-core-menu-link label="Two"></glide-core-menu-link>
457
+
458
+ <glide-core-menu-options>
459
+ <glide-core-menu-link label="One"></glide-core-menu-link>
460
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
461
+ </glide-core-menu-options>
355
462
  </glide-core-menu>
356
463
  `);
357
464
  component.querySelector('button')?.click();
358
465
  component.focus();
359
- const options = component.querySelectorAll('glide-core-menu-link');
360
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
361
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
466
+ const links = component.querySelectorAll('glide-core-menu-link');
467
+ const options = component.querySelector('glide-core-menu-options');
468
+ links[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
362
469
  await sendKeys({ press: 'Home' });
363
- expect(options[0].privateActive).to.be.true;
364
- expect(options[1].privateActive).to.be.false;
365
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[0].id);
470
+ expect(links[0].privateActive).to.be.true;
471
+ expect(links[1].privateActive).to.be.false;
472
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[0].id);
366
473
  });
367
474
  it('activates the first option on PageUp', async () => {
368
475
  const component = await fixture(html `
369
476
  <glide-core-menu>
370
477
  <button slot="target">Target</button>
371
- <glide-core-menu-link label="One"></glide-core-menu-link>
372
- <glide-core-menu-link label="Two"></glide-core-menu-link>
478
+
479
+ <glide-core-menu-options>
480
+ <glide-core-menu-link label="One"></glide-core-menu-link>
481
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
482
+ </glide-core-menu-options>
373
483
  </glide-core-menu>
374
484
  `);
375
485
  component.querySelector('button')?.click();
376
486
  component.focus();
377
- const options = component.querySelectorAll('glide-core-menu-link');
378
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
379
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
487
+ const links = component.querySelectorAll('glide-core-menu-link');
488
+ const options = component.querySelector('glide-core-menu-options');
489
+ links[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
380
490
  await sendKeys({ press: 'PageUp' });
381
- expect(options[0].privateActive).to.be.true;
382
- expect(options[1].privateActive).to.be.false;
383
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[0].id);
491
+ expect(links[0].privateActive).to.be.true;
492
+ expect(links[1].privateActive).to.be.false;
493
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[0].id);
384
494
  });
385
495
  it('activates the first option on ArrowUp + Meta', async () => {
386
496
  const component = await fixture(html `
387
497
  <glide-core-menu>
388
498
  <button slot="target">Target</button>
389
- <glide-core-menu-link label="One"></glide-core-menu-link>
390
- <glide-core-menu-link label="Two"></glide-core-menu-link>
499
+
500
+ <glide-core-menu-options>
501
+ <glide-core-menu-link label="One"></glide-core-menu-link>
502
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
503
+ </glide-core-menu-options>
391
504
  </glide-core-menu>
392
505
  `);
393
506
  component.querySelector('button')?.click();
394
507
  component.focus();
395
- const options = component.querySelectorAll('glide-core-menu-link');
396
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
397
- options[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
508
+ const links = component.querySelectorAll('glide-core-menu-link');
509
+ const options = component.querySelector('glide-core-menu-options');
510
+ links[1].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
398
511
  await sendKeys({ down: 'Meta' });
399
512
  await sendKeys({ press: 'ArrowUp' });
400
- expect(options[0].privateActive).to.be.true;
401
- expect(options[1].privateActive).to.be.false;
402
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[0].id);
513
+ expect(links[0].privateActive).to.be.true;
514
+ expect(links[1].privateActive).to.be.false;
515
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[0].id);
403
516
  });
404
517
  it('activates the last option on End', async () => {
405
518
  const component = await fixture(html `
406
519
  <glide-core-menu>
407
520
  <button slot="target">Target</button>
408
- <glide-core-menu-link label="One"></glide-core-menu-link>
409
- <glide-core-menu-link label="Two"></glide-core-menu-link>
521
+
522
+ <glide-core-menu-options>
523
+ <glide-core-menu-link label="One"></glide-core-menu-link>
524
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
525
+ </glide-core-menu-options>
410
526
  </glide-core-menu>
411
527
  `);
412
528
  component.querySelector('button')?.click();
413
529
  component.focus();
414
530
  await sendKeys({ press: 'End' });
415
- const options = component.querySelectorAll('glide-core-menu-link');
416
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
417
- expect(options[0].privateActive).to.be.false;
418
- expect(options[1].privateActive).to.be.true;
419
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[1].id);
531
+ const links = component.querySelectorAll('glide-core-menu-link');
532
+ const options = component.querySelector('glide-core-menu-options');
533
+ expect(links[0].privateActive).to.be.false;
534
+ expect(links[1].privateActive).to.be.true;
535
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[1].id);
420
536
  });
421
537
  it('activates the last option on PageDown', async () => {
422
538
  const component = await fixture(html `
423
539
  <glide-core-menu>
424
540
  <button slot="target">Target</button>
425
- <glide-core-menu-link label="One"></glide-core-menu-link>
426
- <glide-core-menu-link label="Two"></glide-core-menu-link>
541
+
542
+ <glide-core-menu-options>
543
+ <glide-core-menu-link label="One"></glide-core-menu-link>
544
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
545
+ </glide-core-menu-options>
427
546
  </glide-core-menu>
428
547
  `);
429
548
  component.querySelector('button')?.click();
430
549
  component.focus();
431
- const options = component.querySelectorAll('glide-core-menu-link');
432
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
433
- options[0].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
550
+ const links = component.querySelectorAll('glide-core-menu-link');
551
+ const options = component.querySelector('glide-core-menu-options');
552
+ links[0].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
434
553
  await sendKeys({ press: 'PageDown' });
435
- expect(options[0].privateActive).to.be.false;
436
- expect(options[1].privateActive).to.be.true;
437
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[1].id);
554
+ expect(links[0].privateActive).to.be.false;
555
+ expect(links[1].privateActive).to.be.true;
556
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[1].id);
438
557
  });
439
558
  it('activates the last option on Meta + ArrowDown', async () => {
440
559
  const component = await fixture(html `
441
560
  <glide-core-menu>
442
561
  <button slot="target">Target</button>
443
- <glide-core-menu-link label="One"></glide-core-menu-link>
444
- <glide-core-menu-link label="Two"></glide-core-menu-link>
562
+
563
+ <glide-core-menu-options>
564
+ <glide-core-menu-link label="One"></glide-core-menu-link>
565
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
566
+ </glide-core-menu-options>
445
567
  </glide-core-menu>
446
568
  `);
447
569
  component.querySelector('button')?.click();
448
570
  component.focus();
449
- const options = component.querySelectorAll('glide-core-menu-link');
450
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
451
- options[0].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
571
+ const links = component.querySelectorAll('glide-core-menu-link');
572
+ const options = component.querySelector('glide-core-menu-options');
573
+ links[0].dispatchEvent(new MouseEvent('mouseover', { bubbles: true }));
452
574
  await sendKeys({ down: 'Meta' });
453
575
  await sendKeys({ press: 'ArrowDown' });
454
576
  await sendKeys({ up: 'Meta' });
455
- expect(options[0].privateActive).to.be.false;
456
- expect(options[1].privateActive).to.be.true;
457
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(options[1].id);
577
+ expect(links[0].privateActive).to.be.false;
578
+ expect(links[1].privateActive).to.be.true;
579
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(links[1].id);
458
580
  });
459
581
  it('sets `aria-activedescendant` on open', async () => {
460
582
  const component = await fixture(html `<glide-core-menu>
461
583
  <button slot="target">Target</button>
462
- <glide-core-menu-link label="Link"></glide-core-menu-link>
584
+
585
+ <glide-core-menu-options>
586
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
587
+ </glide-core-menu-options>
463
588
  </glide-core-menu>`);
464
589
  component.querySelector('button')?.click();
465
590
  await elementUpdated(component);
466
- const option = component.querySelector('glide-core-menu-link');
467
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
468
- expect(menu?.getAttribute('aria-activedescendant')).to.equal(option?.id);
591
+ const link = component.querySelector('glide-core-menu-link');
592
+ const options = component.querySelector('glide-core-menu-options');
593
+ expect(options?.getAttribute('aria-activedescendant')).to.equal(link?.id);
469
594
  });
470
595
  it('sets `aria-activedescendant` on close', async () => {
471
596
  const component = await fixture(html `<glide-core-menu open>
472
597
  <button slot="target">Target</button>
473
- <glide-core-menu-link label="Link"></glide-core-menu-link>
598
+
599
+ <glide-core-menu-options>
600
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
601
+ </glide-core-menu-options>
474
602
  </glide-core-menu>`);
475
603
  component.querySelector('button')?.click();
476
604
  await elementUpdated(component);
477
- const menu = component?.shadowRoot?.querySelector('[data-test="menu"]');
478
- expect(menu?.getAttribute('aria-activedescendant')).to.equal('');
605
+ const options = component.querySelector('glide-core-menu-options');
606
+ expect(options?.getAttribute('aria-activedescendant')).to.equal('');
479
607
  });
480
608
  it('sets `aria-expanded` on open', async () => {
481
609
  const component = await fixture(html `<glide-core-menu>
482
610
  <button slot="target">Target</button>
483
- <glide-core-menu-link label="Link"></glide-core-menu-link>
611
+
612
+ <glide-core-menu-options>
613
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
614
+ </glide-core-menu-options>
484
615
  </glide-core-menu>`);
485
616
  component.querySelector('button')?.click();
486
- expect(component.querySelector('button')?.getAttribute('aria-expanded')).to.equal('true');
617
+ const button = component.querySelector('button');
618
+ expect(button?.getAttribute('aria-expanded')).to.equal('true');
487
619
  });
488
620
  it('sets `aria-expanded` on close', async () => {
489
621
  const component = await fixture(html `<glide-core-menu open>
490
622
  <button slot="target">Target</button>
491
- <glide-core-menu-link label="Link"></glide-core-menu-link>
623
+
624
+ <glide-core-menu-options>
625
+ <glide-core-menu-link label="Link"></glide-core-menu-link>
626
+ </glide-core-menu-options>
492
627
  </glide-core-menu>`);
493
628
  component.querySelector('button')?.click();
494
- expect(component.querySelector('button')?.getAttribute('aria-expanded')).to.equal('false');
629
+ const button = component.querySelector('button');
630
+ expect(button?.getAttribute('aria-expanded')).to.equal('false');
495
631
  });
496
632
  it('does not wrap on ArrowUp', async () => {
497
633
  const component = await fixture(html `
498
634
  <glide-core-menu>
499
635
  <button slot="target">Target</button>
500
- <glide-core-menu-link label="One"></glide-core-menu-link>
501
- <glide-core-menu-link label="Two"></glide-core-menu-link>
636
+
637
+ <glide-core-menu-options>
638
+ <glide-core-menu-link label="One"></glide-core-menu-link>
639
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
640
+ </glide-core-menu-options>
502
641
  </glide-core-menu>
503
642
  `);
504
643
  component.querySelector('button')?.click();
@@ -510,8 +649,11 @@ it('does not wrap on ArrowDown', async () => {
510
649
  const component = await fixture(html `
511
650
  <glide-core-menu>
512
651
  <button slot="target">Target</button>
513
- <glide-core-menu-link label="One"></glide-core-menu-link>
514
- <glide-core-menu-link label="Two"></glide-core-menu-link>
652
+
653
+ <glide-core-menu-options>
654
+ <glide-core-menu-link label="One"></glide-core-menu-link>
655
+ <glide-core-menu-link label="Two"></glide-core-menu-link>
656
+ </glide-core-menu-options>
515
657
  </glide-core-menu>
516
658
  `);
517
659
  component.querySelector('button')?.click();