@shortfuse/materialdesignweb 0.9.0 → 0.9.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +50 -206
- package/components/Badge.js +5 -2
- package/components/Body.js +4 -0
- package/components/BottomAppBar.js +6 -2
- package/components/BottomSheet.js +62 -14
- package/components/Button.js +20 -0
- package/components/Card.js +20 -3
- package/components/Checkbox.js +8 -0
- package/components/CheckboxIcon.js +9 -3
- package/components/Chip.js +5 -2
- package/components/Dialog.js +22 -3
- package/components/DialogActions.js +4 -0
- package/components/Display.js +9 -0
- package/components/Divider.js +5 -0
- package/components/Fab.js +11 -0
- package/components/FabContainer.js +9 -0
- package/components/FilterChip.js +9 -0
- package/components/Grid.js +11 -0
- package/components/Headline.js +4 -0
- package/components/Icon.js +27 -3
- package/components/IconButton.js +8 -2
- package/components/Input.js +87 -14
- package/components/InputChip.js +33 -1
- package/components/Label.js +4 -0
- package/components/List.js +10 -0
- package/components/ListItem.js +53 -0
- package/components/ListOption.js +62 -1
- package/components/Listbox.js +44 -13
- package/components/Menu.js +31 -9
- package/components/MenuItem.js +24 -10
- package/components/NavBar.js +14 -3
- package/components/NavBarItem.js +5 -0
- package/components/NavDrawer.js +17 -0
- package/components/NavDrawerItem.js +5 -0
- package/components/NavItem.js +22 -2
- package/components/NavRail.js +9 -0
- package/components/NavRailItem.js +5 -0
- package/components/Page.js +15 -1
- package/components/Pane.js +7 -1
- package/components/Popup.js +6 -0
- package/components/Progress.js +25 -5
- package/components/Radio.js +6 -2
- package/components/RadioIcon.js +14 -1
- package/components/Ripple.js +14 -0
- package/components/Root.js +16 -0
- package/components/Scrim.js +10 -2
- package/components/Search.js +18 -5
- package/components/SegmentedButton.js +22 -6
- package/components/SegmentedButtonGroup.js +7 -10
- package/components/Select.js +13 -3
- package/components/Shape.js +4 -0
- package/components/SideSheet.js +31 -2
- package/components/Slider.js +22 -2
- package/components/Snackbar.js +30 -4
- package/components/SnackbarContainer.js +9 -0
- package/components/Surface.js +5 -0
- package/components/Switch.js +18 -2
- package/components/SwitchIcon.js +22 -1
- package/components/Tab.js +21 -0
- package/components/TabContent.js +32 -12
- package/components/TabList.js +36 -3
- package/components/TabPanel.js +9 -0
- package/components/Table.js +38 -3
- package/components/TextArea.js +32 -1
- package/components/Title.js +4 -0
- package/components/Tooltip.js +9 -2
- package/components/TopAppBar.js +15 -0
- package/core/Composition.js +45 -16
- package/core/CompositionAdapter.js +24 -6
- package/core/CustomElement.js +77 -49
- package/core/customTypes.js +43 -26
- package/core/dom.js +1 -0
- package/core/jsonMergePatch.js +15 -1
- package/core/observe.js +28 -21
- package/dist/CustomElement.min.js +2 -0
- package/dist/CustomElement.min.js.map +7 -0
- package/dist/core/CustomElement.min.js +2 -0
- package/dist/core/CustomElement.min.js.map +7 -0
- package/dist/index.min.js +9 -9
- package/dist/index.min.js.map +3 -3
- package/dist/meta.json +1 -1
- package/dom/HTMLOptionsCollectionProxy.js +5 -3
- package/mixins/AriaReflectorMixin.js +22 -13
- package/mixins/AriaToolbarMixin.js +3 -0
- package/mixins/ControlMixin.js +3 -0
- package/mixins/DelegatesFocusMixin.js +9 -1
- package/mixins/DensityMixin.js +5 -1
- package/mixins/ElevationMixin.js +1 -2
- package/mixins/FlexableMixin.js +21 -2
- package/mixins/FormAssociatedMixin.js +19 -5
- package/mixins/HyperlinkMixin.js +11 -1
- package/mixins/InputMixin.js +22 -0
- package/mixins/KeyboardNavMixin.js +3 -1
- package/mixins/PopupMixin.js +41 -12
- package/mixins/RTLObserverMixin.js +2 -0
- package/mixins/ResizeObserverMixin.js +2 -0
- package/mixins/RippleMixin.js +3 -1
- package/mixins/ScrollListenerMixin.js +13 -1
- package/mixins/SemiStickyMixin.js +7 -0
- package/mixins/ShapeMaskedMixin.js +9 -1
- package/mixins/ShapeMixin.js +9 -0
- package/mixins/StateMixin.js +4 -0
- package/mixins/TextFieldMixin.js +21 -2
- package/mixins/ThemableMixin.js +13 -0
- package/mixins/TooltipTriggerMixin.js +17 -3
- package/mixins/TouchTargetMixin.js +4 -1
- package/mixins/TypographyMixin.js +8 -1
- package/package.json +53 -45
- package/services/theme.js +4 -5
- package/types/components/BottomAppBar.d.ts +3 -4
- package/types/components/BottomSheet.d.ts +33 -7
- package/types/components/BottomSheet.d.ts.map +1 -1
- package/types/components/Button.d.ts +3 -472
- package/types/components/Button.d.ts.map +1 -1
- package/types/components/Card.d.ts +9 -274
- package/types/components/Card.d.ts.map +1 -1
- package/types/components/Checkbox.d.ts +2 -0
- package/types/components/Checkbox.d.ts.map +1 -1
- package/types/components/Chip.d.ts +3 -1180
- package/types/components/Dialog.d.ts +8 -191
- package/types/components/Dialog.d.ts.map +1 -1
- package/types/components/Display.d.ts +5 -4
- package/types/components/Display.d.ts.map +1 -1
- package/types/components/Fab.d.ts +2 -470
- package/types/components/FilterChip.d.ts +5 -4032
- package/types/components/Grid.d.ts +1 -0
- package/types/components/Grid.d.ts.map +1 -1
- package/types/components/Headline.d.ts +3 -4
- package/types/components/Icon.d.ts +1 -49
- package/types/components/Icon.d.ts.map +1 -1
- package/types/components/IconButton.d.ts +3 -1205
- package/types/components/Input.d.ts +1485 -50245
- package/types/components/Input.d.ts.map +1 -1
- package/types/components/InputChip.d.ts +2 -160
- package/types/components/List.d.ts +8 -4
- package/types/components/List.d.ts.map +1 -1
- package/types/components/ListItem.d.ts +10 -235
- package/types/components/ListItem.d.ts.map +1 -1
- package/types/components/ListOption.d.ts +17 -1352
- package/types/components/ListOption.d.ts.map +1 -1
- package/types/components/Listbox.d.ts +199 -11448
- package/types/components/Listbox.d.ts.map +1 -1
- package/types/components/Menu.d.ts +21 -10
- package/types/components/Menu.d.ts.map +1 -1
- package/types/components/MenuItem.d.ts +17 -2894
- package/types/components/MenuItem.d.ts.map +1 -1
- package/types/components/NavBar.d.ts +2 -0
- package/types/components/NavBar.d.ts.map +1 -1
- package/types/components/NavBarItem.d.ts +1 -90
- package/types/components/NavDrawer.d.ts +3 -4
- package/types/components/NavDrawerItem.d.ts +1 -90
- package/types/components/NavItem.d.ts +1 -92
- package/types/components/NavItem.d.ts.map +1 -1
- package/types/components/NavRail.d.ts +3 -4
- package/types/components/NavRailItem.d.ts +1 -90
- package/types/components/Page.d.ts +1 -0
- package/types/components/Page.d.ts.map +1 -1
- package/types/components/Popup.d.ts +5 -3
- package/types/components/Popup.d.ts.map +1 -1
- package/types/components/Progress.d.ts +2 -0
- package/types/components/Progress.d.ts.map +1 -1
- package/types/components/Radio.d.ts +2 -0
- package/types/components/Radio.d.ts.map +1 -1
- package/types/components/Ripple.d.ts +1 -0
- package/types/components/Ripple.d.ts.map +1 -1
- package/types/components/Root.d.ts +1 -1
- package/types/components/Root.d.ts.map +1 -1
- package/types/components/Search.d.ts +502 -2
- package/types/components/Search.d.ts.map +1 -1
- package/types/components/SegmentedButton.d.ts +4 -470
- package/types/components/SegmentedButton.d.ts.map +1 -1
- package/types/components/SegmentedButtonGroup.d.ts +3 -4
- package/types/components/SegmentedButtonGroup.d.ts.map +1 -1
- package/types/components/Select.d.ts +5 -1208
- package/types/components/Select.d.ts.map +1 -1
- package/types/components/SideSheet.d.ts +9 -4
- package/types/components/SideSheet.d.ts.map +1 -1
- package/types/components/Slider.d.ts +10 -189
- package/types/components/Slider.d.ts.map +1 -1
- package/types/components/Snackbar.d.ts +13 -5
- package/types/components/Snackbar.d.ts.map +1 -1
- package/types/components/Switch.d.ts +4 -0
- package/types/components/Switch.d.ts.map +1 -1
- package/types/components/SwitchIcon.d.ts +2 -110
- package/types/components/SwitchIcon.d.ts.map +1 -1
- package/types/components/Tab.d.ts +12 -752
- package/types/components/Tab.d.ts.map +1 -1
- package/types/components/TabContent.d.ts +23 -21
- package/types/components/TabContent.d.ts.map +1 -1
- package/types/components/TabList.d.ts +646 -5801
- package/types/components/TabList.d.ts.map +1 -1
- package/types/components/TabPanel.d.ts +4 -4
- package/types/components/TabPanel.d.ts.map +1 -1
- package/types/components/Table.d.ts +24 -1
- package/types/components/Table.d.ts.map +1 -1
- package/types/components/TextArea.d.ts +15 -1208
- package/types/components/TextArea.d.ts.map +1 -1
- package/types/components/Title.d.ts +3 -4
- package/types/components/Tooltip.d.ts +4 -4
- package/types/components/Tooltip.d.ts.map +1 -1
- package/types/components/TopAppBar.d.ts +4 -5
- package/types/components/TopAppBar.d.ts.map +1 -1
- package/types/constants/shapes.d.ts.map +1 -1
- package/types/core/Composition.d.ts +19 -11
- package/types/core/Composition.d.ts.map +1 -1
- package/types/core/CompositionAdapter.d.ts +30 -8
- package/types/core/CompositionAdapter.d.ts.map +1 -1
- package/types/core/CustomElement.d.ts +27 -25
- package/types/core/CustomElement.d.ts.map +1 -1
- package/types/core/customTypes.d.ts +2 -6
- package/types/core/customTypes.d.ts.map +1 -1
- package/types/core/dom.d.ts.map +1 -1
- package/types/core/jsonMergePatch.d.ts.map +1 -1
- package/types/core/observe.d.ts +20 -19
- package/types/core/observe.d.ts.map +1 -1
- package/types/core/template.d.ts.map +1 -1
- package/types/dom/HTMLOptionsCollectionProxy.d.ts +4 -4
- package/types/dom/HTMLOptionsCollectionProxy.d.ts.map +1 -1
- package/types/mixins/AriaReflectorMixin.d.ts +18 -10
- package/types/mixins/AriaReflectorMixin.d.ts.map +1 -1
- package/types/mixins/AriaToolbarMixin.d.ts +6 -4
- package/types/mixins/AriaToolbarMixin.d.ts.map +1 -1
- package/types/mixins/ControlMixin.d.ts +1 -1
- package/types/mixins/ControlMixin.d.ts.map +1 -1
- package/types/mixins/DelegatesFocusMixin.d.ts +9 -1
- package/types/mixins/DelegatesFocusMixin.d.ts.map +1 -1
- package/types/mixins/DensityMixin.d.ts +4 -1
- package/types/mixins/DensityMixin.d.ts.map +1 -1
- package/types/mixins/ElevationMixin.d.ts +1 -2
- package/types/mixins/ElevationMixin.d.ts.map +1 -1
- package/types/mixins/FlexableMixin.d.ts +1 -0
- package/types/mixins/FlexableMixin.d.ts.map +1 -1
- package/types/mixins/FormAssociatedMixin.d.ts +3 -2
- package/types/mixins/FormAssociatedMixin.d.ts.map +1 -1
- package/types/mixins/HyperlinkMixin.d.ts +4 -1
- package/types/mixins/HyperlinkMixin.d.ts.map +1 -1
- package/types/mixins/InputMixin.d.ts +1 -7
- package/types/mixins/InputMixin.d.ts.map +1 -1
- package/types/mixins/KeyboardNavMixin.d.ts +4 -5
- package/types/mixins/KeyboardNavMixin.d.ts.map +1 -1
- package/types/mixins/PopupMixin.d.ts +22 -6
- package/types/mixins/PopupMixin.d.ts.map +1 -1
- package/types/mixins/RTLObserverMixin.d.ts +1 -0
- package/types/mixins/RTLObserverMixin.d.ts.map +1 -1
- package/types/mixins/ResizeObserverMixin.d.ts +1 -0
- package/types/mixins/ResizeObserverMixin.d.ts.map +1 -1
- package/types/mixins/RippleMixin.d.ts +3 -1
- package/types/mixins/RippleMixin.d.ts.map +1 -1
- package/types/mixins/ScrollListenerMixin.d.ts +7 -2
- package/types/mixins/ScrollListenerMixin.d.ts.map +1 -1
- package/types/mixins/SemiStickyMixin.d.ts +1 -1
- package/types/mixins/SemiStickyMixin.d.ts.map +1 -1
- package/types/mixins/ShapeMaskedMixin.d.ts +4 -1
- package/types/mixins/ShapeMaskedMixin.d.ts.map +1 -1
- package/types/mixins/ShapeMixin.d.ts +1 -0
- package/types/mixins/ShapeMixin.d.ts.map +1 -1
- package/types/mixins/StateMixin.d.ts +2 -0
- package/types/mixins/StateMixin.d.ts.map +1 -1
- package/types/mixins/TextFieldMixin.d.ts +7 -1208
- package/types/mixins/TextFieldMixin.d.ts.map +1 -1
- package/types/mixins/ThemableMixin.d.ts +1 -0
- package/types/mixins/ThemableMixin.d.ts.map +1 -1
- package/types/mixins/TooltipTriggerMixin.d.ts +12 -4
- package/types/mixins/TooltipTriggerMixin.d.ts.map +1 -1
- package/types/mixins/TouchTargetMixin.d.ts +4 -1
- package/types/mixins/TouchTargetMixin.d.ts.map +1 -1
- package/types/mixins/TypographyMixin.d.ts +4 -1
- package/types/mixins/TypographyMixin.d.ts.map +1 -1
- package/types/services/theme.d.ts.map +1 -1
- package/types/utils/jsx-runtime.d.ts +3 -3
- package/types/utils/jsx-runtime.d.ts.map +1 -1
- package/types/utils/material-color/hct/Hct.d.ts.map +1 -1
- package/types/utils/material-color/palettes/CorePalette.d.ts +1 -1
- package/types/utils/material-color/palettes/CorePalette.d.ts.map +1 -1
- package/types/utils/material-color/scheme/Scheme.d.ts.map +1 -1
- package/types/utils/pixelmatch.d.ts +3 -3
- package/types/utils/pixelmatch.d.ts.map +1 -1
- package/types/utils/searchParams.d.ts.map +1 -1
- package/utils/jsx-runtime.js +9 -4
- package/utils/pixelmatch.js +10 -7
- package/utils/searchParams.js +3 -0
- package/components/Button.md +0 -61
package/components/Headline.js
CHANGED
package/components/Icon.js
CHANGED
|
@@ -1,5 +1,3 @@
|
|
|
1
|
-
// import fontStyles from 'https://fonts.googleapis.com/css2?family=Material+Symbols+Outlined:FILL@0..1&display=block' assert { type: 'css'};
|
|
2
|
-
|
|
3
1
|
import CustomElement from '../core/CustomElement.js';
|
|
4
2
|
import ThemableMixin from '../mixins/ThemableMixin.js';
|
|
5
3
|
import { svgAliasMap, unaliased } from '../services/svgAlias.js';
|
|
@@ -10,7 +8,12 @@ const documentLoadedStyleSheets = new Set();
|
|
|
10
8
|
|
|
11
9
|
// https://html.spec.whatwg.org/multipage/embedded-content.html#htmlimageelement
|
|
12
10
|
|
|
13
|
-
/**
|
|
11
|
+
/**
|
|
12
|
+
* Material system icons represent actions, objects, and concepts; prefer
|
|
13
|
+
* the Material icon system (SVG or Material Symbols) for consistent visual language.
|
|
14
|
+
* implements {Omit<HTMLImageElement,DeprecatedHTMLImageElementProperties>}
|
|
15
|
+
* @see https://m3.material.io/styles/icons
|
|
16
|
+
*/
|
|
14
17
|
export default CustomElement
|
|
15
18
|
.extend()
|
|
16
19
|
.mixin(ThemableMixin)
|
|
@@ -27,27 +30,48 @@ export default CustomElement
|
|
|
27
30
|
decode() { return this._img.decode; },
|
|
28
31
|
})
|
|
29
32
|
.observe({
|
|
33
|
+
/** Icon name used with SVG aliases or font glyphs. */
|
|
30
34
|
icon: 'string',
|
|
35
|
+
/** Whether the icon is disabled; affects image appearance. */
|
|
31
36
|
disabled: 'boolean',
|
|
37
|
+
/** Alternative text for image-backed icons. */
|
|
32
38
|
alt: 'string',
|
|
39
|
+
/** Image source URL for an icon. */
|
|
33
40
|
src: 'string',
|
|
41
|
+
/** URL to an external SVG resource. */
|
|
34
42
|
svg: 'string',
|
|
43
|
+
/** Inline SVG path data to render as the icon. */
|
|
35
44
|
svgPath: 'string',
|
|
45
|
+
/** Image `srcset` attribute for responsive icon images. */
|
|
36
46
|
srcset: 'string',
|
|
47
|
+
/** Image `sizes` attribute for responsive icon images. */
|
|
37
48
|
sizes: 'string',
|
|
49
|
+
/** Variation suffix used when resolving icon aliases (e.g., 'filled'). */
|
|
38
50
|
variation: 'string',
|
|
51
|
+
/** `crossorigin` attribute for image requests. */
|
|
39
52
|
crossOrigin: { attr: 'crossorigin' },
|
|
53
|
+
/** `usemap` attribute for image maps. */
|
|
40
54
|
useMap: { attr: 'usemap' },
|
|
55
|
+
/** `ismap` boolean attribute for image maps. */
|
|
41
56
|
isMap: { type: 'boolean', attr: 'ismap' },
|
|
57
|
+
/** `referrerpolicy` attribute for image requests. */
|
|
42
58
|
referrerPolicy: { attr: 'referrerpolicy' },
|
|
59
|
+
/** Preferred image decoding mode: 'async' | 'sync' | 'auto'. */
|
|
43
60
|
decoding: { value: /** @type {'async'|'sync'|'auto'} */ (null) },
|
|
61
|
+
/** Image loading hint: 'eager' | 'lazy'. */
|
|
44
62
|
loading: { value: /** @type {'eager'|'lazy'} */ (null) },
|
|
63
|
+
/** Rendered width in CSS pixels. */
|
|
45
64
|
width: 'integer',
|
|
65
|
+
/** Rendered height in CSS pixels. */
|
|
46
66
|
height: 'integer',
|
|
67
|
+
/** Force using font glyphs instead of SVG when true. */
|
|
47
68
|
forceFont: 'boolean',
|
|
48
69
|
_linkLoaded: 'boolean',
|
|
70
|
+
/** viewBox used for SVG rendering. */
|
|
49
71
|
viewBox: 'string',
|
|
72
|
+
/** CSS class applied to font-based icons. */
|
|
50
73
|
fontClass: { empty: 'material-symbols-outlined' },
|
|
74
|
+
/** URL to Material Symbols CSS when using font-based icons. */
|
|
51
75
|
fontLibrary: { empty: 'https://fonts.googleapis.com/css2?family=Material+Symbols+Outlined:FILL@0..1&display=block' },
|
|
52
76
|
_isConnected: 'boolean',
|
|
53
77
|
})
|
package/components/IconButton.js
CHANGED
|
@@ -3,8 +3,10 @@ import TooltipTriggerMixin from '../mixins/TooltipTriggerMixin.js';
|
|
|
3
3
|
|
|
4
4
|
import Button from './Button.js';
|
|
5
5
|
|
|
6
|
-
|
|
7
|
-
|
|
6
|
+
/**
|
|
7
|
+
* Icon buttons are compact buttons that use an icon to represent an action.
|
|
8
|
+
* @see https://m3.material.io/components/icon-buttons/specs
|
|
9
|
+
*/
|
|
8
10
|
export default Button
|
|
9
11
|
.extend()
|
|
10
12
|
.mixin(TooltipTriggerMixin)
|
|
@@ -12,15 +14,19 @@ export default Button
|
|
|
12
14
|
_allowedTypes: ['button', 'submit', 'reset', 'checkbox', 'file'],
|
|
13
15
|
})
|
|
14
16
|
.observe({
|
|
17
|
+
/** ARIA pressed state for toggle buttons (checkbox type). */
|
|
15
18
|
_ariaPressed: {
|
|
16
19
|
get({ type, checked, indeterminate }) {
|
|
17
20
|
if (type !== 'checkbox') return null;
|
|
18
21
|
return indeterminate ? 'mixed' : (checked ? 'true' : 'false');
|
|
19
22
|
},
|
|
20
23
|
},
|
|
24
|
+
/** True when the underlying control behaves as a toggle (checkbox). */
|
|
21
25
|
_isToggle({ type }) {
|
|
22
26
|
return type === 'checkbox';
|
|
23
27
|
},
|
|
28
|
+
|
|
29
|
+
/** When present, enables automatic tooltip behavior from the mixin. */
|
|
24
30
|
autoTooltip: { empty: true },
|
|
25
31
|
})
|
|
26
32
|
.expressions({
|
package/components/Input.js
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
/* https://www.w3.org/WAI/ARIA/apg/patterns/combobox/ */
|
|
2
1
|
/* https://learn.microsoft.com/en-us/dotnet/api/system.windows.controls.combobox.iseditable?view=windowsdesktop-7.0#remarks */
|
|
3
2
|
|
|
4
3
|
import CustomElement from '../core/CustomElement.js';
|
|
@@ -12,6 +11,8 @@ import Popup from './Popup.js';
|
|
|
12
11
|
|
|
13
12
|
/** @typedef {import('./Listbox.js').default} Listbox */
|
|
14
13
|
|
|
14
|
+
/** @typedef {import('../mixins/RippleMixin.js').default} RippleMixin */
|
|
15
|
+
|
|
15
16
|
/** @type {InstanceType<import('./Popup.js').default>} */
|
|
16
17
|
let sharedPopup;
|
|
17
18
|
|
|
@@ -29,6 +30,12 @@ function getSharedPopup() {
|
|
|
29
30
|
return sharedPopup;
|
|
30
31
|
}
|
|
31
32
|
|
|
33
|
+
/**
|
|
34
|
+
* Text fields let users enter and edit text. This component implements
|
|
35
|
+
* autocomplete, suggestions, and listbox behaviors where applicable.
|
|
36
|
+
* @see https://m3.material.io/components/text-fields/specs
|
|
37
|
+
* @see https://www.w3.org/WAI/ARIA/apg/patterns/combobox/
|
|
38
|
+
*/
|
|
32
39
|
export default CustomElement
|
|
33
40
|
.extend()
|
|
34
41
|
.mixin(ThemableMixin)
|
|
@@ -37,31 +44,76 @@ export default CustomElement
|
|
|
37
44
|
.mixin(TextFieldMixin)
|
|
38
45
|
.mixin(ResizeObserverMixin)
|
|
39
46
|
.observe({
|
|
47
|
+
/**
|
|
48
|
+
* When true, the component inserts the best suggestion into the input field
|
|
49
|
+
* as inline text. The appended portion of the suggestion is selected so the
|
|
50
|
+
* user can accept it (e.g. press Enter) or continue typing to replace it.
|
|
51
|
+
* Typically combined with `autosuggestInline` to display candidates while
|
|
52
|
+
* typing.
|
|
53
|
+
* @see https://w3c.github.io/aria/#aria-autocomplete
|
|
54
|
+
*/
|
|
40
55
|
autocompleteInline: 'boolean',
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* When set and not `'custom'`, `applyAutocompleteList()` filters the
|
|
59
|
+
* listbox options to items that start * with the typed text. This controls
|
|
60
|
+
* dropdown filtering but does not itself cause inline insertion.
|
|
61
|
+
* @see https://w3c.github.io/aria/#aria-autocomplete
|
|
62
|
+
*/
|
|
41
63
|
autocompleteList: 'string',
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* When true, the component advances/searches suggestion candidates as the
|
|
67
|
+
* user types (calls `changeSuggestion({ startsWith })`). If
|
|
68
|
+
* `autosuggestInline` is true and `autocompleteInline` is also true the
|
|
69
|
+
* current candidate will be shown inline; if `autocompleteInline` is false
|
|
70
|
+
* only the candidate selection changes (no inline text insertion).
|
|
71
|
+
*/
|
|
42
72
|
autosuggestInline: 'boolean',
|
|
73
|
+
|
|
43
74
|
/** If true, when listbox is open, arrow navigation will automatically select options. */
|
|
44
75
|
autoSelect: 'boolean',
|
|
76
|
+
|
|
77
|
+
/** True when the listbox popup is currently expanded. */
|
|
45
78
|
_expanded: 'boolean',
|
|
46
|
-
|
|
79
|
+
|
|
80
|
+
/** If true, when listbox is open, <Esc> accepts current suggestion (same as Enter). */
|
|
47
81
|
acceptOnEscape: 'boolean',
|
|
82
|
+
|
|
48
83
|
_listbox: {
|
|
49
84
|
type: 'object',
|
|
50
85
|
/** @type {InstanceType<Listbox>} */
|
|
51
86
|
value: null,
|
|
52
87
|
},
|
|
88
|
+
|
|
89
|
+
/** Currently focused suggestion value in the listbox. */
|
|
53
90
|
_focusedValue: 'string',
|
|
91
|
+
|
|
92
|
+
/** Focus position in set (1-based) for aria-posinset. */
|
|
54
93
|
_focusedPosInSet: { value: -1 },
|
|
94
|
+
|
|
95
|
+
/** Computed size of the listbox (number of options). */
|
|
55
96
|
_listboxSize: { value: -1 },
|
|
97
|
+
|
|
98
|
+
/** Draft input text while composing suggestions. */
|
|
56
99
|
_draftInput: { type: 'string', nullable: false },
|
|
100
|
+
|
|
101
|
+
/** Whether a suggestion is currently available. */
|
|
57
102
|
_hasSuggestion: 'boolean',
|
|
103
|
+
|
|
104
|
+
/** The current selected/committed listbox value. */
|
|
58
105
|
_listboxValue: 'string',
|
|
106
|
+
|
|
107
|
+
/** Last computed listbox value (non-nullable string). */
|
|
59
108
|
_lastComputedListboxValue: { type: 'string', nullable: false },
|
|
109
|
+
|
|
60
110
|
_values: {
|
|
61
111
|
type: 'array',
|
|
62
112
|
/** @type {string[]} */
|
|
63
113
|
value: [],
|
|
64
114
|
},
|
|
115
|
+
|
|
116
|
+
/** Whether an input chip is currently selected in multi-select mode. */
|
|
65
117
|
_chipSelected: 'boolean',
|
|
66
118
|
})
|
|
67
119
|
.observe({
|
|
@@ -86,7 +138,7 @@ export default CustomElement
|
|
|
86
138
|
_onPopupFocusoutListener: null,
|
|
87
139
|
_suggestionText: '',
|
|
88
140
|
_suggestionValue: '',
|
|
89
|
-
/** @type {HTMLOptionElement} */
|
|
141
|
+
/** @type {Pick<HTMLOptionElement, 'label'|'value'|'selected'>} */
|
|
90
142
|
_suggestionOption: null,
|
|
91
143
|
})
|
|
92
144
|
.define({
|
|
@@ -203,7 +255,7 @@ export default CustomElement
|
|
|
203
255
|
}
|
|
204
256
|
},
|
|
205
257
|
/**
|
|
206
|
-
* @param {
|
|
258
|
+
* @param {Pick<HTMLOptionElement, 'label'|'value'|'selected'>} option
|
|
207
259
|
* @return {void}
|
|
208
260
|
*/
|
|
209
261
|
suggestOption(option) {
|
|
@@ -381,8 +433,7 @@ export default CustomElement
|
|
|
381
433
|
this.refs.chips.replaceChildren();
|
|
382
434
|
return;
|
|
383
435
|
}
|
|
384
|
-
/** @type {InstanceType<import('./InputChip.js').default>} */
|
|
385
|
-
let element = this.refs.chips.firstElementChild;
|
|
436
|
+
let element = /** @type {InstanceType<import('./InputChip.js').default>} */ (this.refs.chips.firstElementChild);
|
|
386
437
|
|
|
387
438
|
for (let i = 0; i < _values.length; i++) {
|
|
388
439
|
const currentValue = _values[i];
|
|
@@ -396,7 +447,7 @@ export default CustomElement
|
|
|
396
447
|
}
|
|
397
448
|
}
|
|
398
449
|
|
|
399
|
-
element ??= this.refs.chips.appendChild(document.createElement('mdw-input-chip'));
|
|
450
|
+
element ??= /** @type {InstanceType<import('./InputChip.js').default>} */ (this.refs.chips.appendChild(document.createElement('mdw-input-chip')));
|
|
400
451
|
element.closeButton = true;
|
|
401
452
|
element.textContent = foundOption?.label || currentValue;
|
|
402
453
|
element.textContent = foundOption?.label || currentValue;
|
|
@@ -404,11 +455,11 @@ export default CustomElement
|
|
|
404
455
|
element.readOnly = this.readOnly;
|
|
405
456
|
// eslint-disable-next-line unicorn/prefer-add-event-listener
|
|
406
457
|
element.onclose ??= this.onChipClose.bind(this);
|
|
407
|
-
element = element.nextElementSibling;
|
|
458
|
+
element = /** @type {InstanceType<import('./InputChip.js').default>} */ (element.nextElementSibling);
|
|
408
459
|
}
|
|
409
460
|
while (element) {
|
|
410
461
|
const prev = element;
|
|
411
|
-
element = element.nextElementSibling;
|
|
462
|
+
element = /** @type {InstanceType<import('./InputChip.js').default>} */ (element.nextElementSibling);
|
|
412
463
|
prev.remove();
|
|
413
464
|
}
|
|
414
465
|
this._chipSelected = false;
|
|
@@ -436,7 +487,9 @@ export default CustomElement
|
|
|
436
487
|
this._draftInput = option.label;
|
|
437
488
|
}
|
|
438
489
|
},
|
|
490
|
+
/** @param {CloseEvent & {currentTarget: HTMLElement}} event */
|
|
439
491
|
onChipClose({ currentTarget }) {
|
|
492
|
+
/** @type {Node} */
|
|
440
493
|
let prev = currentTarget;
|
|
441
494
|
let elementIndex = 0;
|
|
442
495
|
while ((prev = prev.previousSibling)) {
|
|
@@ -601,8 +654,7 @@ export default CustomElement
|
|
|
601
654
|
*/
|
|
602
655
|
slotchange({ currentTarget }) {
|
|
603
656
|
if (this._expanded) return;
|
|
604
|
-
/** @type {InstanceType<Listbox>[]} */
|
|
605
|
-
const [listbox] = currentTarget.assignedElements();
|
|
657
|
+
const [listbox] = /** @type {InstanceType<Listbox>[]} */ (currentTarget.assignedElements());
|
|
606
658
|
const _listbox = this._listbox;
|
|
607
659
|
if (_listbox === listbox) {
|
|
608
660
|
// Internal already matches
|
|
@@ -621,7 +673,7 @@ export default CustomElement
|
|
|
621
673
|
listbox.required = true; // Don't allow unclick
|
|
622
674
|
}
|
|
623
675
|
|
|
624
|
-
|
|
676
|
+
listbox._handleFormReset = false;
|
|
625
677
|
listbox.addEventListener('change', this._onListboxChangeListener);
|
|
626
678
|
listbox.addEventListener('click', this._onListboxChangeListener);
|
|
627
679
|
this.populateInputFromListbox();
|
|
@@ -686,7 +738,26 @@ export default CustomElement
|
|
|
686
738
|
if (!_hasListbox) return null;
|
|
687
739
|
return 'aria-listbox';
|
|
688
740
|
},
|
|
689
|
-
|
|
741
|
+
/**
|
|
742
|
+
* Compute `aria-autocomplete` to describe the widget's behavior to AT.
|
|
743
|
+
*
|
|
744
|
+
* ARIA values:
|
|
745
|
+
* - `none` : no autocomplete behavior is provided
|
|
746
|
+
* - `inline`: the textbox shows an inline completion the user can accept
|
|
747
|
+
* - `list` : a popup listbox provides choices (no inline insertion)
|
|
748
|
+
* - `both` : both inline completion and a listbox are available
|
|
749
|
+
*
|
|
750
|
+
* Component mapping:
|
|
751
|
+
* - `autocompleteInline` -> inline completion behavior
|
|
752
|
+
* - `autocompleteList` (non-null) -> listbox filtering / dropdown present
|
|
753
|
+
* - `autosuggestInline` -> drives candidate selection as user types
|
|
754
|
+
*
|
|
755
|
+
* Note: the current implementation reports `'both'` when a named
|
|
756
|
+
* `autocompleteList` is present (even if `autocompleteInline` is false).
|
|
757
|
+
* A stricter mapping would return `list` when only a listbox is present
|
|
758
|
+
* and `both` only when both `autocompleteInline` and a listbox exist.
|
|
759
|
+
*/
|
|
760
|
+
ariaAutocompleteAttrValue({ _hasListbox, autocompleteList, _isSelect, autocompleteInline }) {
|
|
690
761
|
if (!_hasListbox) return null;
|
|
691
762
|
if (_isSelect) return null;
|
|
692
763
|
if (autocompleteList != null) {
|
|
@@ -763,7 +834,7 @@ export default CustomElement
|
|
|
763
834
|
},
|
|
764
835
|
_chipSelectedChanged(previous, current) {
|
|
765
836
|
if (!this.multiple) return;
|
|
766
|
-
const element = this.refs.chips.lastElementChild;
|
|
837
|
+
const element = /** @type {HTMLOptionElement} */ (this.refs.chips.lastElementChild);
|
|
767
838
|
if (element) {
|
|
768
839
|
element.selected = current;
|
|
769
840
|
}
|
|
@@ -867,7 +938,9 @@ export default CustomElement
|
|
|
867
938
|
.extend((Base) => class Input extends Base {
|
|
868
939
|
/** @type {InstanceType<ReturnType<RippleMixin>>['addRipple']} */
|
|
869
940
|
addRipple(...args) {
|
|
941
|
+
// @ts-ignore TODO: Fix invalid cast
|
|
870
942
|
if (!this.active) return null;
|
|
943
|
+
// @ts-ignore TODO: Fix invalid cast
|
|
871
944
|
return super.addRipple(...args);
|
|
872
945
|
}
|
|
873
946
|
})
|
package/components/InputChip.js
CHANGED
|
@@ -8,25 +8,56 @@ import './Button.js';
|
|
|
8
8
|
import './Icon.js';
|
|
9
9
|
import './IconButton.js';
|
|
10
10
|
|
|
11
|
+
/**
|
|
12
|
+
* Input chips allow users to enter or edit information as a chip (tag-like).
|
|
13
|
+
* @see https://m3.material.io/components/chips/specs
|
|
14
|
+
*/
|
|
11
15
|
export default Box
|
|
12
16
|
.extend()
|
|
13
17
|
.mixin(ShapeMixin)
|
|
14
18
|
.mixin(DelegatesFocusMixin)
|
|
15
19
|
.mixin(HyperlinkMixin)
|
|
16
20
|
.observe({
|
|
21
|
+
/** Render the chip in avatar (larger) style. */
|
|
17
22
|
avatar: 'boolean',
|
|
23
|
+
|
|
24
|
+
/** Show a close action button inside the chip. */
|
|
18
25
|
closeButton: 'boolean',
|
|
26
|
+
|
|
27
|
+
/** Icon name to use for the close button (default: 'close'). */
|
|
19
28
|
closeIcon: { empty: 'close' },
|
|
29
|
+
|
|
30
|
+
/** Ink color used for the close icon (default: inherit). */
|
|
20
31
|
closeInk: { empty: 'inherit' },
|
|
32
|
+
|
|
33
|
+
/** Reflects the `readonly` attribute; prevents editing/closing when true. */
|
|
21
34
|
readOnly: { attr: 'readonly', type: 'boolean' },
|
|
35
|
+
|
|
36
|
+
/** Whether the chip is disabled. */
|
|
22
37
|
disabled: 'boolean',
|
|
38
|
+
|
|
39
|
+
/** Leading icon name for the chip. */
|
|
23
40
|
icon: 'string',
|
|
41
|
+
|
|
42
|
+
/** Ink color for the leading icon. */
|
|
24
43
|
iconInk: 'string',
|
|
44
|
+
|
|
45
|
+
/** Image `src` for an avatar or image-backed icon. */
|
|
25
46
|
src: 'string',
|
|
47
|
+
|
|
48
|
+
/** External SVG URL to render as the icon. */
|
|
26
49
|
svg: 'string',
|
|
50
|
+
|
|
51
|
+
/** SVG `viewBox` used for inline SVG rendering. */
|
|
27
52
|
viewBox: 'string',
|
|
53
|
+
|
|
54
|
+
/** SVG path data to render as the icon. */
|
|
28
55
|
svgPath: 'string',
|
|
56
|
+
|
|
57
|
+
/** Event handler/callback for the `close` event. */
|
|
29
58
|
onclose: EVENT_HANDLER_TYPE,
|
|
59
|
+
|
|
60
|
+
/** Selection state used by chip-selection patterns. */
|
|
30
61
|
selected: 'boolean',
|
|
31
62
|
})
|
|
32
63
|
.set({
|
|
@@ -144,7 +175,8 @@ export default Box
|
|
|
144
175
|
})
|
|
145
176
|
.on({
|
|
146
177
|
selectedChanged(previous, current) {
|
|
147
|
-
this.refs.action
|
|
178
|
+
const action = /** @type {InstanceType<typeof import('./Button.js').default>} */ (this.refs.action);
|
|
179
|
+
action._focused = current;
|
|
148
180
|
},
|
|
149
181
|
})
|
|
150
182
|
.recompose(({ refs: { anchor, slot, icon, outline } }) => {
|
package/components/Label.js
CHANGED
|
@@ -2,6 +2,10 @@ import TypographyMixin from '../mixins/TypographyMixin.js';
|
|
|
2
2
|
|
|
3
3
|
import Box from './Box.js';
|
|
4
4
|
|
|
5
|
+
/**
|
|
6
|
+
* Material Design Type scale: Label.
|
|
7
|
+
* @see https://m3.material.io/styles/typography/type-scale-tokens
|
|
8
|
+
*/
|
|
5
9
|
export default Box
|
|
6
10
|
.extend()
|
|
7
11
|
.mixin(TypographyMixin)
|
package/components/List.js
CHANGED
|
@@ -5,12 +5,22 @@ import Box from './Box.js';
|
|
|
5
5
|
|
|
6
6
|
/** @typedef {'compact'} DeprecatedHTMLMenuElementProperties */
|
|
7
7
|
|
|
8
|
+
/**
|
|
9
|
+
* Lists present a single column of related content, such as options or navigation.
|
|
10
|
+
* @see https://m3.material.io/components/lists/specs
|
|
11
|
+
*/
|
|
8
12
|
export default Box
|
|
9
13
|
.extend()
|
|
10
14
|
.mixin(DensityMixin)
|
|
11
15
|
.mixin(AriaReflectorMixin)
|
|
12
16
|
.set({
|
|
17
|
+
/** ARIA role applied to the host element (default: 'list'). */
|
|
13
18
|
_ariaRole: 'list',
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* Visual color token for list surfaces. Default is `surface` to match
|
|
22
|
+
* Material surface theming.
|
|
23
|
+
*/
|
|
14
24
|
color: { empty: 'surface' },
|
|
15
25
|
})
|
|
16
26
|
.css`
|
package/components/ListItem.js
CHANGED
|
@@ -13,6 +13,11 @@ import RippleMixin from '../mixins/RippleMixin.js';
|
|
|
13
13
|
import StateMixin from '../mixins/StateMixin.js';
|
|
14
14
|
import ThemableMixin from '../mixins/ThemableMixin.js';
|
|
15
15
|
|
|
16
|
+
/**
|
|
17
|
+
* List item representing a single row in a list; supports leading/trailing
|
|
18
|
+
* content, selection, and accessibility features.
|
|
19
|
+
* @see https://m3.material.io/components/lists/specs
|
|
20
|
+
*/
|
|
16
21
|
export default CustomElement
|
|
17
22
|
.extend()
|
|
18
23
|
.mixin(ThemableMixin)
|
|
@@ -21,32 +26,80 @@ export default CustomElement
|
|
|
21
26
|
.mixin(AriaReflectorMixin)
|
|
22
27
|
.mixin(HyperlinkMixin)
|
|
23
28
|
.set({
|
|
29
|
+
/** ARIA role applied to the host element (default: 'listitem'). */
|
|
24
30
|
_ariaRole: 'listitem',
|
|
31
|
+
|
|
32
|
+
/** When true, draw the Material state layer for interactive feedback. */
|
|
25
33
|
stateLayer: true,
|
|
26
34
|
})
|
|
27
35
|
.observe({
|
|
36
|
+
/** Leading slot content or shorthand string. */
|
|
28
37
|
leading: 'string',
|
|
38
|
+
|
|
39
|
+
/** Avatar label or shorthand content for a leading avatar. */
|
|
29
40
|
avatar: 'string',
|
|
41
|
+
|
|
42
|
+
/** Color token used for the avatar container (default: primary-container). */
|
|
30
43
|
avatarColor: { value: 'primary-container' },
|
|
44
|
+
|
|
45
|
+
/** Image source for the avatar. */
|
|
31
46
|
avatarSrc: 'string',
|
|
47
|
+
|
|
48
|
+
/** Image source URL for a leading image in the list item. */
|
|
32
49
|
src: 'string',
|
|
50
|
+
|
|
51
|
+
/** Alt text for the leading image. */
|
|
33
52
|
alt: 'string',
|
|
53
|
+
|
|
54
|
+
/** Icon name for a leading icon. */
|
|
34
55
|
icon: 'string',
|
|
56
|
+
|
|
57
|
+
/** Ink/color token used for the leading icon. */
|
|
35
58
|
iconInk: 'string',
|
|
59
|
+
|
|
60
|
+
/** External image/SVG source for the leading icon. */
|
|
36
61
|
iconSrc: 'string',
|
|
62
|
+
|
|
63
|
+
/** Icon variation (e.g., 'filled'). */
|
|
37
64
|
iconVariation: 'string',
|
|
65
|
+
|
|
66
|
+
/** Checkbox shorthand name or placement class for a selectable leading checkbox. */
|
|
38
67
|
checkbox: 'string',
|
|
68
|
+
|
|
69
|
+
/** Radio shorthand name or placement class for a selectable leading radio. */
|
|
39
70
|
radio: 'string',
|
|
71
|
+
|
|
72
|
+
/** Selection color token used when item is selected (default: primary). */
|
|
40
73
|
selectionColor: { value: 'primary' },
|
|
74
|
+
|
|
75
|
+
/** Selection state for the item. */
|
|
41
76
|
selected: 'boolean',
|
|
77
|
+
|
|
78
|
+
/** Supporting text (secondary line) for the list item. */
|
|
42
79
|
supporting: 'string',
|
|
80
|
+
|
|
81
|
+
/** Trailing text slot or shorthand. */
|
|
43
82
|
trailing: 'string',
|
|
83
|
+
|
|
84
|
+
/** Trailing icon name. */
|
|
44
85
|
trailingIcon: 'string',
|
|
86
|
+
|
|
87
|
+
/** Ink/color token for the trailing icon. */
|
|
45
88
|
trailingIconInk: 'string',
|
|
89
|
+
|
|
90
|
+
/** External image/SVG source for the trailing icon. */
|
|
46
91
|
trailingIconSrc: 'string',
|
|
92
|
+
|
|
93
|
+
/** Divider style identifier (e.g., 'inset'). */
|
|
47
94
|
divider: 'string',
|
|
95
|
+
|
|
96
|
+
/** If true, indicates the list item contains video content and adjusts layout. */
|
|
48
97
|
video: 'boolean',
|
|
98
|
+
|
|
99
|
+
/** Number of text lines the item should reserve for content (integer). */
|
|
49
100
|
lines: 'integer',
|
|
101
|
+
|
|
102
|
+
/** Internal flag set when supporting content is provided via slot. */
|
|
50
103
|
_supportingSlotted: 'boolean',
|
|
51
104
|
})
|
|
52
105
|
.observe({
|
package/components/ListOption.js
CHANGED
|
@@ -6,6 +6,10 @@ import ListItem from './ListItem.js';
|
|
|
6
6
|
|
|
7
7
|
// https://html.spec.whatwg.org/multipage/form-elements.html#htmloptionelement
|
|
8
8
|
|
|
9
|
+
/**
|
|
10
|
+
* List options represent selectable choices within a `mdw-listbox` or list.
|
|
11
|
+
* @see https://m3.material.io/components/lists/specs
|
|
12
|
+
*/
|
|
9
13
|
export default ListItem
|
|
10
14
|
.extend()
|
|
11
15
|
.mixin(DelegatesFocusMixin)
|
|
@@ -13,17 +17,48 @@ export default ListItem
|
|
|
13
17
|
formAssociated: true,
|
|
14
18
|
})
|
|
15
19
|
.set({
|
|
20
|
+
/** ARIA role applied to the option container (anchor receives role 'option'). */
|
|
16
21
|
_ariaRole: 'none',
|
|
22
|
+
|
|
23
|
+
/** Index of this option within its list/listbox (managed externally). */
|
|
17
24
|
_index: -1,
|
|
25
|
+
|
|
26
|
+
/** Internal flag indicating selection was modified via API rather than default. */
|
|
18
27
|
_selectedDirty: false,
|
|
28
|
+
|
|
29
|
+
/** Whether this option behaves as an interactive selectable item. */
|
|
19
30
|
isInteractive: true,
|
|
20
31
|
})
|
|
21
32
|
.observe({
|
|
22
33
|
// ListOption.prototype._form = ListOption.prop('_form');
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* Explicit label for accessibility. Reflected to attribute `label`.
|
|
37
|
+
* Falls back to `textContent` when not provided.
|
|
38
|
+
*/
|
|
23
39
|
_label: { attr: 'label', reflect: true, nullParser: String },
|
|
40
|
+
|
|
41
|
+
/**
|
|
42
|
+
* Explicit text content for the option. Reflected to attribute `text`.
|
|
43
|
+
*/
|
|
44
|
+
_text: { attr: 'text', reflect: true, nullParser: String },
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* Initial/default selection state (reflected to `selected` attribute).
|
|
48
|
+
* Use `selected` property to control runtime selection.
|
|
49
|
+
*/
|
|
24
50
|
defaultSelected: { attr: 'selected', reflect: true, type: 'boolean' },
|
|
51
|
+
|
|
52
|
+
/** Internal boolean representing the current selected state. */
|
|
25
53
|
_selected: 'boolean',
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Underlying option value (reflected to `value` attribute). Defaults to
|
|
57
|
+
* the option's text content when not provided.
|
|
58
|
+
*/
|
|
26
59
|
_value: { attr: 'value', reflect: true },
|
|
60
|
+
|
|
61
|
+
/** Set when form association disables the option. */
|
|
27
62
|
_formDisabled: 'boolean',
|
|
28
63
|
})
|
|
29
64
|
.observe({
|
|
@@ -46,15 +81,41 @@ export default ListItem
|
|
|
46
81
|
},
|
|
47
82
|
})
|
|
48
83
|
.define({
|
|
84
|
+
/** Numeric index of the option inside the parent listbox. */
|
|
49
85
|
index() { return this._index; },
|
|
86
|
+
|
|
87
|
+
/** Associated form owner (if any) for form-associated behavior. */
|
|
50
88
|
form() { return /** @type {HTMLInputElement} */ (this.parentElement)?.form; },
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* Text content for the option; setting updates the internal `_text` field.
|
|
92
|
+
* If not provided, the getter falls back to element textContent.
|
|
93
|
+
*/
|
|
94
|
+
text: {
|
|
95
|
+
// Incomplete
|
|
96
|
+
get() { return this._text ?? this.textContent; },
|
|
97
|
+
/** @param {string} value */
|
|
98
|
+
set(value) {
|
|
99
|
+
this._text = value;
|
|
100
|
+
},
|
|
101
|
+
},
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* Accessible label for the option. Falls back to `text` or the element
|
|
105
|
+
* content when not explicitly set.
|
|
106
|
+
*/
|
|
51
107
|
label: {
|
|
52
|
-
get() { return this._label ?? this.textContent; },
|
|
108
|
+
get() { return this._label ?? this._text ?? this.textContent; },
|
|
53
109
|
/** @param {string} value */
|
|
54
110
|
set(value) {
|
|
55
111
|
this._label = value;
|
|
56
112
|
},
|
|
57
113
|
},
|
|
114
|
+
|
|
115
|
+
/**
|
|
116
|
+
* Option `value` used when the option is selected in a form. Defaults to
|
|
117
|
+
* the option's text when not explicitly defined.
|
|
118
|
+
*/
|
|
58
119
|
value: {
|
|
59
120
|
get() { return this._value ?? this.textContent; },
|
|
60
121
|
/** @param {string} value */
|