@vaadin/menu-bar 25.3.0 → 25.4.0-dev.55bb86e155

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.
@@ -50,9 +50,9 @@
50
50
  "name": "i18n",
51
51
  "privacy": "public",
52
52
  "type": {
53
- "text": "Object"
53
+ "text": "Object | undefined"
54
54
  },
55
- "description": "The object used to localize this component. To change the default\nlocalization, replace this with an object that provides all properties, or\njust the individual properties you want to change.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
55
+ "description": "The object used to localize this component. To change the default\nlocalization, set this to an object that provides all properties, or\njust the individual properties you want to change.\n\nWhen not set, defaults to `undefined`.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
56
56
  "attribute": "i18n",
57
57
  "inheritedFrom": {
58
58
  "name": "I18nMixin",
@@ -124,9 +124,9 @@
124
124
  {
125
125
  "name": "i18n",
126
126
  "type": {
127
- "text": "Object"
127
+ "text": "Object | undefined"
128
128
  },
129
- "description": "The object used to localize this component. To change the default\nlocalization, replace this with an object that provides all properties, or\njust the individual properties you want to change.\n\nShould be overridden by subclasses to provide a custom JSDoc with the\ndefault I18N properties.",
129
+ "description": "The object used to localize this component. To change the default\nlocalization, set this to an object that provides all properties, or\njust the individual properties you want to change.\n\nWhen not set, defaults to `undefined`.\n\nShould be overridden by subclasses to provide a custom JSDoc with the\ndefault I18N properties.",
130
130
  "fieldName": "i18n",
131
131
  "inheritedFrom": {
132
132
  "name": "I18nMixin",
@@ -303,7 +303,7 @@
303
303
  "declarations": [
304
304
  {
305
305
  "kind": "class",
306
- "description": "`<vaadin-menu-bar>` is a Web Component providing a set of horizontally stacked buttons offering\nthe user quick access to a consistent set of commands. Each button can toggle a submenu with\nsupport for additional levels of nested menus.\n\nTo create the menu bar, first add the component to the page:\n\n```html\n<vaadin-menu-bar></vaadin-menu-bar>\n```\n\nAnd then use [`items`](#/elements/vaadin-menu-bar#property-items) property to initialize the structure:\n\n```js\ndocument.querySelector('vaadin-menu-bar').items = [{text: 'File'}, {text: 'Edit'}];\n```\n\n### Styling\n\nThe following shadow DOM parts are exposed for styling:\n\nPart name | Description\n------------------|----------------\n`container` | The container wrapping menu bar buttons.\n\nThe following state attributes are available for styling:\n\nAttribute | Description\n--------------------|----------------------------------\n`disabled` | Set when the menu bar is disabled\n`has-single-button` | Set when there is only one button visible\n\nThe following custom CSS properties are available for styling:\n\nCustom CSS property |\n:---------------------------|\n| `--vaadin-menu-bar-gap` |\n\nSee [Styling Components](https://vaadin.com/docs/latest/styling/styling-components) documentation.\n\n### Internal components\n\nIn addition to `<vaadin-menu-bar>` itself, the following internal\ncomponents are themable:\n\n- `<vaadin-menu-bar-button>` - has the same API as [`<vaadin-button>`](#/elements/vaadin-button).\n- `<vaadin-menu-bar-item>` - has the same API as [`<vaadin-item>`](#/elements/vaadin-item).\n- `<vaadin-menu-bar-list-box>` - has the same API as [`<vaadin-list-box>`](#/elements/vaadin-list-box).\n- `<vaadin-menu-bar-submenu>` - has the same API as [`<vaadin-context-menu>`](#/elements/vaadin-context-menu).\n\nThe `<vaadin-menu-bar-item>` sub-menu elements have the following additional state attributes\non top of the built-in `<vaadin-item>` state attributes:\n\nAttribute | Description\n---------- |-------------\n`expanded` | Expanded parent item.",
306
+ "description": "`<vaadin-menu-bar>` is a Web Component providing a set of horizontally stacked buttons offering\nthe user quick access to a consistent set of commands. Each button can toggle a submenu with\nsupport for additional levels of nested menus.\n\nTo create the menu bar, first add the component to the page:\n\n```html\n<vaadin-menu-bar></vaadin-menu-bar>\n```\n\nAnd then use [`items`](#/elements/vaadin-menu-bar#property-items) property to initialize the structure:\n\n```js\ndocument.querySelector('vaadin-menu-bar').items = [{text: 'File'}, {text: 'Edit'}];\n```\n\n### Styling\n\nThe following shadow DOM parts are exposed for styling:\n\nPart name | Description\n------------------|----------------\n`container` | The container wrapping menu bar buttons.\n\nThe following state attributes are available for styling:\n\nAttribute | Description\n--------------------|----------------------------------\n`disabled` | Set when the menu bar is disabled\n`has-overflow` | Set when one or more buttons are collapsed into the overflow sub-menu\n`has-single-button` | Set when there is only one button visible\n\nThe following custom CSS properties are available for styling:\n\nCustom CSS property |\n:---------------------------|\n| `--vaadin-menu-bar-gap` |\n\nSee [Styling Components](https://vaadin.com/docs/latest/styling/styling-components) documentation.\n\n### Internal components\n\nIn addition to `<vaadin-menu-bar>` itself, the following internal\ncomponents are themable:\n\n- `<vaadin-menu-bar-button>` - has the same API as [`<vaadin-button>`](#/elements/vaadin-button).\n- `<vaadin-menu-bar-item>` - has the same API as [`<vaadin-item>`](#/elements/vaadin-item).\n- `<vaadin-menu-bar-list-box>` - has the same API as [`<vaadin-list-box>`](#/elements/vaadin-list-box).\n- `<vaadin-menu-bar-submenu>` - has the same API as [`<vaadin-context-menu>`](#/elements/vaadin-context-menu).\n\nThe `<vaadin-menu-bar-item>` sub-menu elements have the following additional state attributes\non top of the built-in `<vaadin-item>` state attributes:\n\nAttribute | Description\n---------- |-------------\n`expanded` | Expanded parent item.",
307
307
  "name": "MenuBar",
308
308
  "members": [
309
309
  {
@@ -334,9 +334,9 @@
334
334
  "name": "i18n",
335
335
  "privacy": "public",
336
336
  "type": {
337
- "text": "Object"
337
+ "text": "Object | undefined"
338
338
  },
339
- "description": "The object used to localize this component. To change the default\nlocalization, replace this with an object that provides all properties, or\njust the individual properties you want to change.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
339
+ "description": "The object used to localize this component. To change the default\nlocalization, set this to an object that provides all properties, or\njust the individual properties you want to change.\n\nWhen not set, defaults to `undefined`.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
340
340
  "attribute": "i18n",
341
341
  "inheritedFrom": {
342
342
  "name": "I18nMixin",
@@ -429,9 +429,9 @@
429
429
  {
430
430
  "name": "i18n",
431
431
  "type": {
432
- "text": "Object"
432
+ "text": "Object | undefined"
433
433
  },
434
- "description": "The object used to localize this component. To change the default\nlocalization, replace this with an object that provides all properties, or\njust the individual properties you want to change.\n\nShould be overridden by subclasses to provide a custom JSDoc with the\ndefault I18N properties.",
434
+ "description": "The object used to localize this component. To change the default\nlocalization, set this to an object that provides all properties, or\njust the individual properties you want to change.\n\nWhen not set, defaults to `undefined`.\n\nShould be overridden by subclasses to provide a custom JSDoc with the\ndefault I18N properties.",
435
435
  "fieldName": "i18n",
436
436
  "inheritedFrom": {
437
437
  "name": "I18nMixin",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vaadin/menu-bar",
3
- "version": "25.3.0",
3
+ "version": "25.4.0-dev.55bb86e155",
4
4
  "publishConfig": {
5
5
  "access": "public"
6
6
  },
@@ -35,23 +35,23 @@
35
35
  ],
36
36
  "dependencies": {
37
37
  "@open-wc/dedupe-mixin": "^1.3.0",
38
- "@vaadin/a11y-base": "~25.3.0",
39
- "@vaadin/button": "~25.3.0",
40
- "@vaadin/component-base": "~25.3.0",
41
- "@vaadin/context-menu": "~25.3.0",
42
- "@vaadin/item": "~25.3.0",
43
- "@vaadin/list-box": "~25.3.0",
44
- "@vaadin/overlay": "~25.3.0",
45
- "@vaadin/vaadin-themable-mixin": "~25.3.0",
38
+ "@vaadin/a11y-base": "25.4.0-dev.55bb86e155",
39
+ "@vaadin/button": "25.4.0-dev.55bb86e155",
40
+ "@vaadin/component-base": "25.4.0-dev.55bb86e155",
41
+ "@vaadin/context-menu": "25.4.0-dev.55bb86e155",
42
+ "@vaadin/item": "25.4.0-dev.55bb86e155",
43
+ "@vaadin/list-box": "25.4.0-dev.55bb86e155",
44
+ "@vaadin/overlay": "25.4.0-dev.55bb86e155",
45
+ "@vaadin/vaadin-themable-mixin": "25.4.0-dev.55bb86e155",
46
46
  "lit": "^3.0.0"
47
47
  },
48
48
  "devDependencies": {
49
- "@vaadin/aura": "~25.3.0",
50
- "@vaadin/chai-plugins": "~25.3.0",
51
- "@vaadin/icon": "~25.3.0",
52
- "@vaadin/test-runner-commands": "~25.3.0",
49
+ "@vaadin/aura": "25.4.0-dev.55bb86e155",
50
+ "@vaadin/chai-plugins": "25.4.0-dev.55bb86e155",
51
+ "@vaadin/icon": "25.4.0-dev.55bb86e155",
52
+ "@vaadin/test-runner-commands": "25.4.0-dev.55bb86e155",
53
53
  "@vaadin/testing-helpers": "^2.0.0",
54
- "@vaadin/vaadin-lumo-styles": "~25.3.0",
54
+ "@vaadin/vaadin-lumo-styles": "25.4.0-dev.55bb86e155",
55
55
  "sinon": "^22.0.0"
56
56
  },
57
57
  "customElements": "custom-elements.json",
@@ -59,5 +59,5 @@
59
59
  "web-types.json",
60
60
  "web-types.lit.json"
61
61
  ],
62
- "gitHead": "4133747243c03bf544f6e82cc2ec9f295aaccd65"
62
+ "gitHead": "5db8e58fb088121b067290b0ed90d12d7d4084f2"
63
63
  }
@@ -158,9 +158,11 @@ export declare class MenuBarMixinClass<TItem extends MenuBarItem = MenuBarItem>
158
158
 
159
159
  /**
160
160
  * The object used to localize this component. To change the default
161
- * localization, replace this with an object that provides all properties, or
161
+ * localization, set this to an object that provides all properties, or
162
162
  * just the individual properties you want to change.
163
163
  *
164
+ * When not set, defaults to `undefined`.
165
+ *
164
166
  * The object has the following JSON structure and default values:
165
167
  * ```js
166
168
  * {
@@ -168,7 +170,7 @@ export declare class MenuBarMixinClass<TItem extends MenuBarItem = MenuBarItem>
168
170
  * }
169
171
  * ```
170
172
  */
171
- i18n: MenuBarI18n;
173
+ i18n: MenuBarI18n | undefined;
172
174
 
173
175
  /**
174
176
  * If true, the submenu will open on hover (mouseover) instead of click.
@@ -57,6 +57,9 @@ const DEFAULT_I18N = {
57
57
  moreOptions: 'More options',
58
58
  };
59
59
 
60
+ // Two client rects of the same edge can differ by float noise, a few 1e-5 px under browser zoom
61
+ const OVERFLOW_TOLERANCE = 0.1;
62
+
60
63
  export const MenuBarMixin = (superClass) =>
61
64
  class MenuBarMixinClass extends I18nMixin(
62
65
  KeyboardDirectionMixin(ResizeMixin(FocusMixin(DisabledMixin(superClass)))),
@@ -203,16 +206,18 @@ export const MenuBarMixin = (superClass) =>
203
206
 
204
207
  /**
205
208
  * The object used to localize this component. To change the default
206
- * localization, replace this with an object that provides all properties, or
209
+ * localization, set this to an object that provides all properties, or
207
210
  * just the individual properties you want to change.
208
211
  *
212
+ * When not set, defaults to `undefined`.
213
+ *
209
214
  * The object has the following JSON structure and default values:
210
215
  * ```js
211
216
  * {
212
217
  * moreOptions: 'More options'
213
218
  * }
214
219
  * ```
215
- * @type {!MenuBarI18n}
220
+ * @type {MenuBarI18n | undefined}
216
221
  */
217
222
  get i18n() {
218
223
  return super.i18n;
@@ -469,6 +474,20 @@ export const MenuBarMixin = (superClass) =>
469
474
  });
470
475
  }
471
476
 
477
+ /**
478
+ * Restores all buttons, the overflow button and the state attributes, so that
479
+ * the measurement does not use the button margins of the previous state.
480
+ *
481
+ * @param {!Array<!HTMLElement>} buttons
482
+ * @private
483
+ */
484
+ __restoreState(buttons) {
485
+ this.__restoreButtons(buttons);
486
+ this.__updateOverflow([]);
487
+ this.toggleAttribute('has-single-button', buttons.length === 1);
488
+ this.__updateVisibleAttributes(buttons);
489
+ }
490
+
472
491
  /** @private */
473
492
  __restoreItem(button, item) {
474
493
  button.appendChild(item);
@@ -482,51 +501,133 @@ export const MenuBarMixin = (superClass) =>
482
501
  __updateOverflow(items) {
483
502
  this._overflow.item = { children: items };
484
503
  this._hasOverflow = items.length > 0;
504
+ this.toggleAttribute('has-overflow', this._hasOverflow);
485
505
  }
486
506
 
487
- /** @private */
488
- __setOverflowItems(buttons, overflow) {
489
- const container = this._container;
490
-
491
- // Prevent the container from shrinking while buttons are being hidden.
492
- // The host has min-width: 0 so it can shrink inside flex/grid layouts.
493
- // Without this lock, hiding a button reduces the host width, which
494
- // shrinks the container (width: 100%), shifting all button positions
495
- // and causing a cascading collapse where every button appears to overflow.
496
- container.style.minWidth = `${container.offsetWidth}px`;
497
-
498
- if (container.offsetWidth < container.scrollWidth) {
499
- this._hasOverflow = true;
500
-
501
- const isRTL = this.__isRTL;
502
- const containerLeft = container.offsetLeft;
503
- const containerWidth = container.offsetWidth;
504
-
505
- const remaining = [...buttons];
506
- while (remaining.length) {
507
- // The overflow button follows the last remaining one, so its far edge is what has
508
- // to fit. Auto margins move the whole row but cannot push that edge past the end.
509
- const overflowEnd = isRTL
510
- ? containerWidth - (overflow.offsetLeft - containerLeft)
511
- : overflow.offsetLeft + overflow.offsetWidth - containerLeft;
512
-
513
- if (overflowEnd <= containerWidth) {
514
- break;
515
- }
507
+ /**
508
+ * Inline end edge of the element, mirrored in RTL. Unlike `offsetWidth` and `scrollWidth`,
509
+ * the rect keeps the fraction that browser zoom leaves on the width.
510
+ *
511
+ * @param {!HTMLElement} el
512
+ * @return {number}
513
+ * @private
514
+ */
515
+ __getInlineEnd(el) {
516
+ const { left, right } = el.getBoundingClientRect();
517
+ return this.__isRTL ? -left : right;
518
+ }
519
+
520
+ /**
521
+ * Whether the element ends past the container, with the tolerance for fractional widths.
522
+ *
523
+ * @param {!HTMLElement} el
524
+ * @return {boolean}
525
+ * @private
526
+ */
527
+ __isPastContainerEnd(el) {
528
+ return this.__getInlineEnd(el) > this.__getInlineEnd(this._container) + OVERFLOW_TOLERANCE;
529
+ }
530
+
531
+ /**
532
+ * Positions of the buttons, read in one batch before any of them is hidden.
533
+ * Mirrored in RTL so that a larger value is always further along the inline axis.
534
+ *
535
+ * @typedef {object} MenuBarOverflowLayout
536
+ * @property {number[]} starts Inline start of each button
537
+ * @property {number[]} ends Inline end of each button
538
+ * @property {number[]} margins Inline start margin of each button
539
+ * @property {number} overflowExtent Space the overflow button adds after the last button
540
+ * @property {number} containerWidth Width of the container
541
+ */
542
+
543
+ /**
544
+ * @param {!Array<!HTMLElement>} buttons
545
+ * @param {!HTMLElement} overflow
546
+ * @return {!MenuBarOverflowLayout}
547
+ * @private
548
+ */
549
+ __measureButtons(buttons, overflow) {
550
+ const isRTL = this.__isRTL;
551
+ const rects = buttons.map((btn) => btn.getBoundingClientRect());
552
+ const ends = rects.map(({ left, right }) => (isRTL ? -left : right));
516
553
 
517
- const btn = this.reverseCollapse ? remaining.shift() : remaining.pop();
554
+ return {
555
+ starts: rects.map(({ left, right }) => (isRTL ? -right : left)),
556
+ ends,
557
+ // `auto` resolves to 0 while the content overflows.
558
+ margins: buttons.map((btn) => parseFloat(getComputedStyle(btn).marginInlineStart) || 0),
559
+ overflowExtent: this.__getInlineEnd(overflow) - ends.at(-1),
560
+ containerWidth: this._container.getBoundingClientRect().width,
561
+ };
562
+ }
518
563
 
519
- // Save width for buttons with component
520
- btn.style.width = getComputedStyle(btn).width;
521
- btn.style.visibility = 'hidden';
522
- btn.style.position = 'absolute';
564
+ /**
565
+ * Picks the buttons to collapse so that the rest plus the overflow button end inside
566
+ * the container. Hiding a button only shifts the buttons after it, so the end of any
567
+ * kept range follows from one measurement.
568
+ *
569
+ * @param {!Array<!HTMLElement>} buttons
570
+ * @param {!MenuBarOverflowLayout} layout
571
+ * @return {!Array<!HTMLElement>} buttons to collapse, in DOM order
572
+ * @private
573
+ */
574
+ __getButtonsToCollapse(buttons, { starts, ends, margins, overflowExtent, containerWidth }) {
575
+ let lo = 0;
576
+ let hi = buttons.length - 1;
577
+
578
+ // The first kept button keeps its own start margin in front of the range.
579
+ while (lo <= hi && margins[lo] + ends[hi] - starts[lo] + overflowExtent > containerWidth + OVERFLOW_TOLERANCE) {
580
+ if (this.reverseCollapse) {
581
+ lo += 1;
582
+ } else {
583
+ hi -= 1;
523
584
  }
585
+ }
586
+
587
+ return buttons.filter((_, i) => i < lo || i > hi);
588
+ }
524
589
 
525
- const items = buttons.filter((b) => !remaining.includes(b)).map((b) => b.item);
526
- this.__updateOverflow(items);
590
+ /**
591
+ * Hides the buttons that do not fit next to the overflow button.
592
+ *
593
+ * @param {!Array<!HTMLElement>} buttons
594
+ * @param {!MenuBarOverflowLayout} layout
595
+ * @return {!Array<!HTMLElement>} hidden buttons, in DOM order
596
+ * @private
597
+ */
598
+ __collapseButtons(buttons, layout) {
599
+ const collapsed = this.__getButtonsToCollapse(buttons, layout);
600
+ // Read button widths once outside of the loop to avoid repetitive layout
601
+ const widths = collapsed.map((btn) => getComputedStyle(btn).width);
602
+
603
+ // Write the DOM state
604
+ collapsed.forEach((btn, i) => {
605
+ btn.style.width = widths[i];
606
+ btn.style.visibility = 'hidden';
607
+ btn.style.position = 'absolute';
608
+ });
609
+ return collapsed;
610
+ }
611
+
612
+ /**
613
+ * Shows the overflow button and collapses buttons into it when the last button
614
+ * does not fit in the container.
615
+ *
616
+ * @param {!Array<!HTMLElement>} buttons
617
+ * @param {!HTMLElement} overflow
618
+ * @private
619
+ */
620
+ __setOverflowItems(buttons, overflow) {
621
+ const lastButton = buttons.at(-1);
622
+ if (!lastButton || !this.__isPastContainerEnd(lastButton)) {
623
+ return;
527
624
  }
625
+ this._hasOverflow = true;
528
626
 
529
- container.style.minWidth = '';
627
+ // Read the layout once the overflow button is in flow
628
+ const layout = this.__measureButtons(buttons, overflow);
629
+ const collapsed = this.__collapseButtons(buttons, layout);
630
+ this.__updateOverflow(collapsed.map((btn) => btn.item));
530
631
  }
531
632
 
532
633
  /** @private */
@@ -542,9 +643,7 @@ export const MenuBarMixin = (superClass) =>
542
643
  const buttons = this._buttons.filter((btn) => btn !== overflow);
543
644
  const oldOverflowCount = this.__getOverflowCount(overflow);
544
645
 
545
- // Reset all buttons in the menu bar and the overflow button
546
- this.__restoreButtons(buttons);
547
- this.__updateOverflow([]);
646
+ this.__restoreState(buttons);
548
647
 
549
648
  // Hide any overflowing buttons and put them in the 'overflow' button
550
649
  this.__setOverflowItems(buttons, overflow);
@@ -573,6 +672,11 @@ export const MenuBarMixin = (superClass) =>
573
672
  this._setTabindex(visibleButtons[visibleButtons.length - 1], true);
574
673
  }
575
674
 
675
+ this.__updateVisibleAttributes(visibleButtons);
676
+ }
677
+
678
+ /** @private */
679
+ __updateVisibleAttributes(visibleButtons) {
576
680
  visibleButtons.forEach((btn, index) => {
577
681
  btn.toggleAttribute('first-visible', index === 0);
578
682
  btn.toggleAttribute('last-visible', !this._hasOverflow && index === visibleButtons.length - 1);
@@ -52,6 +52,7 @@ export interface MenuBarEventMap<TItem extends MenuBarItem = MenuBarItem>
52
52
  * Attribute | Description
53
53
  * --------------------|----------------------------------
54
54
  * `disabled` | Set when the menu bar is disabled
55
+ * `has-overflow` | Set when one or more buttons are collapsed into the overflow sub-menu
55
56
  * `has-single-button` | Set when there is only one button visible
56
57
  *
57
58
  * The following custom CSS properties are available for styling:
@@ -44,6 +44,7 @@ import { MenuBarMixin } from './vaadin-menu-bar-mixin.js';
44
44
  * Attribute | Description
45
45
  * --------------------|----------------------------------
46
46
  * `disabled` | Set when the menu bar is disabled
47
+ * `has-overflow` | Set when one or more buttons are collapsed into the overflow sub-menu
47
48
  * `has-single-button` | Set when there is only one button visible
48
49
  *
49
50
  * The following custom CSS properties are available for styling:
package/web-types.json CHANGED
@@ -1,14 +1,14 @@
1
1
  {
2
2
  "$schema": "https://json.schemastore.org/web-types",
3
3
  "name": "@vaadin/menu-bar",
4
- "version": "25.3.0",
4
+ "version": "25.4.0-dev.55bb86e155",
5
5
  "description-markup": "markdown",
6
6
  "contributions": {
7
7
  "html": {
8
8
  "elements": [
9
9
  {
10
10
  "name": "vaadin-menu-bar",
11
- "description": "`<vaadin-menu-bar>` is a Web Component providing a set of horizontally stacked buttons offering\nthe user quick access to a consistent set of commands. Each button can toggle a submenu with\nsupport for additional levels of nested menus.\n\nTo create the menu bar, first add the component to the page:\n\n```html\n<vaadin-menu-bar></vaadin-menu-bar>\n```\n\nAnd then use [`items`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-menu-bar#property-items) property to initialize the structure:\n\n```js\ndocument.querySelector('vaadin-menu-bar').items = [{text: 'File'}, {text: 'Edit'}];\n```\n\n### Styling\n\nThe following shadow DOM parts are exposed for styling:\n\nPart name | Description\n------------------|----------------\n`container` | The container wrapping menu bar buttons.\n\nThe following state attributes are available for styling:\n\nAttribute | Description\n--------------------|----------------------------------\n`disabled` | Set when the menu bar is disabled\n`has-single-button` | Set when there is only one button visible\n\nThe following custom CSS properties are available for styling:\n\nCustom CSS property |\n:---------------------------|\n| `--vaadin-menu-bar-gap` |\n\nSee [Styling Components](https://vaadin.com/docs/latest/styling/styling-components) documentation.\n\n### Internal components\n\nIn addition to `<vaadin-menu-bar>` itself, the following internal\ncomponents are themable:\n\n- `<vaadin-menu-bar-button>` - has the same API as [`<vaadin-button>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-button).\n- `<vaadin-menu-bar-item>` - has the same API as [`<vaadin-item>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-item).\n- `<vaadin-menu-bar-list-box>` - has the same API as [`<vaadin-list-box>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-list-box).\n- `<vaadin-menu-bar-submenu>` - has the same API as [`<vaadin-context-menu>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-context-menu).\n\nThe `<vaadin-menu-bar-item>` sub-menu elements have the following additional state attributes\non top of the built-in `<vaadin-item>` state attributes:\n\nAttribute | Description\n---------- |-------------\n`expanded` | Expanded parent item.",
11
+ "description": "`<vaadin-menu-bar>` is a Web Component providing a set of horizontally stacked buttons offering\nthe user quick access to a consistent set of commands. Each button can toggle a submenu with\nsupport for additional levels of nested menus.\n\nTo create the menu bar, first add the component to the page:\n\n```html\n<vaadin-menu-bar></vaadin-menu-bar>\n```\n\nAnd then use [`items`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-menu-bar#property-items) property to initialize the structure:\n\n```js\ndocument.querySelector('vaadin-menu-bar').items = [{text: 'File'}, {text: 'Edit'}];\n```\n\n### Styling\n\nThe following shadow DOM parts are exposed for styling:\n\nPart name | Description\n------------------|----------------\n`container` | The container wrapping menu bar buttons.\n\nThe following state attributes are available for styling:\n\nAttribute | Description\n--------------------|----------------------------------\n`disabled` | Set when the menu bar is disabled\n`has-overflow` | Set when one or more buttons are collapsed into the overflow sub-menu\n`has-single-button` | Set when there is only one button visible\n\nThe following custom CSS properties are available for styling:\n\nCustom CSS property |\n:---------------------------|\n| `--vaadin-menu-bar-gap` |\n\nSee [Styling Components](https://vaadin.com/docs/latest/styling/styling-components) documentation.\n\n### Internal components\n\nIn addition to `<vaadin-menu-bar>` itself, the following internal\ncomponents are themable:\n\n- `<vaadin-menu-bar-button>` - has the same API as [`<vaadin-button>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-button).\n- `<vaadin-menu-bar-item>` - has the same API as [`<vaadin-item>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-item).\n- `<vaadin-menu-bar-list-box>` - has the same API as [`<vaadin-list-box>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-list-box).\n- `<vaadin-menu-bar-submenu>` - has the same API as [`<vaadin-context-menu>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-context-menu).\n\nThe `<vaadin-menu-bar-item>` sub-menu elements have the following additional state attributes\non top of the built-in `<vaadin-item>` state attributes:\n\nAttribute | Description\n---------- |-------------\n`expanded` | Expanded parent item.",
12
12
  "attributes": [
13
13
  {
14
14
  "name": "disabled",
@@ -69,10 +69,11 @@
69
69
  },
70
70
  {
71
71
  "name": "i18n",
72
- "description": "The object used to localize this component. To change the default\nlocalization, replace this with an object that provides all properties, or\njust the individual properties you want to change.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
72
+ "description": "The object used to localize this component. To change the default\nlocalization, set this to an object that provides all properties, or\njust the individual properties you want to change.\n\nWhen not set, defaults to `undefined`.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
73
73
  "value": {
74
74
  "type": [
75
- "Object"
75
+ "Object",
76
+ "undefined"
76
77
  ]
77
78
  }
78
79
  },
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "$schema": "https://json.schemastore.org/web-types",
3
3
  "name": "@vaadin/menu-bar",
4
- "version": "25.3.0",
4
+ "version": "25.4.0-dev.55bb86e155",
5
5
  "description-markup": "markdown",
6
6
  "framework": "lit",
7
7
  "framework-config": {
@@ -16,7 +16,7 @@
16
16
  "elements": [
17
17
  {
18
18
  "name": "vaadin-menu-bar",
19
- "description": "`<vaadin-menu-bar>` is a Web Component providing a set of horizontally stacked buttons offering\nthe user quick access to a consistent set of commands. Each button can toggle a submenu with\nsupport for additional levels of nested menus.\n\nTo create the menu bar, first add the component to the page:\n\n```html\n<vaadin-menu-bar></vaadin-menu-bar>\n```\n\nAnd then use [`items`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-menu-bar#property-items) property to initialize the structure:\n\n```js\ndocument.querySelector('vaadin-menu-bar').items = [{text: 'File'}, {text: 'Edit'}];\n```\n\n### Styling\n\nThe following shadow DOM parts are exposed for styling:\n\nPart name | Description\n------------------|----------------\n`container` | The container wrapping menu bar buttons.\n\nThe following state attributes are available for styling:\n\nAttribute | Description\n--------------------|----------------------------------\n`disabled` | Set when the menu bar is disabled\n`has-single-button` | Set when there is only one button visible\n\nThe following custom CSS properties are available for styling:\n\nCustom CSS property |\n:---------------------------|\n| `--vaadin-menu-bar-gap` |\n\nSee [Styling Components](https://vaadin.com/docs/latest/styling/styling-components) documentation.\n\n### Internal components\n\nIn addition to `<vaadin-menu-bar>` itself, the following internal\ncomponents are themable:\n\n- `<vaadin-menu-bar-button>` - has the same API as [`<vaadin-button>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-button).\n- `<vaadin-menu-bar-item>` - has the same API as [`<vaadin-item>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-item).\n- `<vaadin-menu-bar-list-box>` - has the same API as [`<vaadin-list-box>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-list-box).\n- `<vaadin-menu-bar-submenu>` - has the same API as [`<vaadin-context-menu>`](https://cdn.vaadin.com/vaadin-web-components/25.3.0/#/elements/vaadin-context-menu).\n\nThe `<vaadin-menu-bar-item>` sub-menu elements have the following additional state attributes\non top of the built-in `<vaadin-item>` state attributes:\n\nAttribute | Description\n---------- |-------------\n`expanded` | Expanded parent item.",
19
+ "description": "`<vaadin-menu-bar>` is a Web Component providing a set of horizontally stacked buttons offering\nthe user quick access to a consistent set of commands. Each button can toggle a submenu with\nsupport for additional levels of nested menus.\n\nTo create the menu bar, first add the component to the page:\n\n```html\n<vaadin-menu-bar></vaadin-menu-bar>\n```\n\nAnd then use [`items`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-menu-bar#property-items) property to initialize the structure:\n\n```js\ndocument.querySelector('vaadin-menu-bar').items = [{text: 'File'}, {text: 'Edit'}];\n```\n\n### Styling\n\nThe following shadow DOM parts are exposed for styling:\n\nPart name | Description\n------------------|----------------\n`container` | The container wrapping menu bar buttons.\n\nThe following state attributes are available for styling:\n\nAttribute | Description\n--------------------|----------------------------------\n`disabled` | Set when the menu bar is disabled\n`has-overflow` | Set when one or more buttons are collapsed into the overflow sub-menu\n`has-single-button` | Set when there is only one button visible\n\nThe following custom CSS properties are available for styling:\n\nCustom CSS property |\n:---------------------------|\n| `--vaadin-menu-bar-gap` |\n\nSee [Styling Components](https://vaadin.com/docs/latest/styling/styling-components) documentation.\n\n### Internal components\n\nIn addition to `<vaadin-menu-bar>` itself, the following internal\ncomponents are themable:\n\n- `<vaadin-menu-bar-button>` - has the same API as [`<vaadin-button>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-button).\n- `<vaadin-menu-bar-item>` - has the same API as [`<vaadin-item>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-item).\n- `<vaadin-menu-bar-list-box>` - has the same API as [`<vaadin-list-box>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-list-box).\n- `<vaadin-menu-bar-submenu>` - has the same API as [`<vaadin-context-menu>`](https://cdn.vaadin.com/vaadin-web-components/25.4.0-dev.55bb86e155/#/elements/vaadin-context-menu).\n\nThe `<vaadin-menu-bar-item>` sub-menu elements have the following additional state attributes\non top of the built-in `<vaadin-item>` state attributes:\n\nAttribute | Description\n---------- |-------------\n`expanded` | Expanded parent item.",
20
20
  "extension": true,
21
21
  "attributes": [
22
22
  {
@@ -28,7 +28,7 @@
28
28
  },
29
29
  {
30
30
  "name": ".i18n",
31
- "description": "The object used to localize this component. To change the default\nlocalization, replace this with an object that provides all properties, or\njust the individual properties you want to change.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
31
+ "description": "The object used to localize this component. To change the default\nlocalization, set this to an object that provides all properties, or\njust the individual properties you want to change.\n\nWhen not set, defaults to `undefined`.\n\nThe object has the following JSON structure and default values:\n```js\n{\n moreOptions: 'More options'\n}\n```",
32
32
  "value": {
33
33
  "kind": "expression"
34
34
  }