@expressivecss/expressive 0.7.0-rc.0 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +1311 -1
- package/README.md +14 -11
- package/dist/css/expressive.css +4215 -1668
- package/dist/css/expressive.css.map +1 -1
- package/dist/css/expressive.min.css +1 -1
- package/dist/css/expressive.min.css.map +1 -1
- package/dist/js/expressive.cjs +1231 -1253
- package/dist/js/expressive.cjs.map +4 -4
- package/dist/js/expressive.js +1231 -1253
- package/dist/js/expressive.js.map +4 -4
- package/dist/js/expressive.min.js +12 -12
- package/dist/js/expressive.min.js.map +4 -4
- package/dist/js/expressive.mjs +1231 -1253
- package/dist/js/expressive.mjs.map +4 -4
- package/dist/types/behaviors/bottomSheets.d.ts +19 -11
- package/dist/types/behaviors/sheetDrag.d.ts +40 -0
- package/dist/types/behaviors/sideSheets.d.ts +2 -9
- package/dist/types/components/autocomplete.d.ts +15 -3
- package/dist/types/components/buttons.d.ts +5 -1
- package/dist/types/components/carousel.d.ts +87 -53
- package/dist/types/components/chips.d.ts +21 -1
- package/dist/types/components/expandingCard.d.ts +31 -0
- package/dist/types/components/index.d.ts +21 -20
- package/dist/types/components/lightbox.d.ts +1 -0
- package/dist/types/components/menu.d.ts +7 -1
- package/dist/types/components/{sidenav.d.ts → navigationDrawer.d.ts} +16 -16
- package/dist/types/components/registry.d.ts +8 -8
- package/dist/types/components/slider.d.ts +26 -85
- package/dist/types/components/snackbar.d.ts +20 -5
- package/dist/types/components/tabs.d.ts +12 -0
- package/dist/types/components/timepicker.d.ts +12 -9
- package/dist/types/core/utils.d.ts +64 -53
- package/dist/types/index.d.ts +8 -9
- package/package.json +15 -1
- package/src/sass/README.md +61 -11
- package/src/sass/abstracts/_breakpoints.scss +17 -19
- package/src/sass/abstracts/_mixins.scss +103 -21
- package/src/sass/abstracts/_variables.scss +50 -5
- package/src/sass/base/_global.scss +6 -24
- package/src/sass/base/_grid.scss +15 -12
- package/src/sass/base/_normalize.scss +34 -38
- package/src/sass/base/_typography.scss +4 -18
- package/src/sass/components/_badges.scss +2 -3
- package/src/sass/components/_banners.scss +298 -0
- package/src/sass/components/_bottom-app-bar.scss +180 -0
- package/src/sass/components/_bottom-sheet.scss +12 -4
- package/src/sass/components/_button-groups.scss +186 -0
- package/src/sass/components/_buttons.scss +245 -92
- package/src/sass/components/_cards.scss +494 -73
- package/src/sass/components/_carousel.scss +562 -68
- package/src/sass/components/_chips.scss +64 -5
- package/src/sass/components/_datepicker.scss +24 -24
- package/src/sass/components/_dialog.scss +17 -11
- package/src/sass/components/_drag-handle.scss +130 -0
- package/src/sass/components/_expanding-card.scss +260 -0
- package/src/sass/components/_fab-menu.scss +232 -0
- package/src/sass/components/_floating-sheet.scss +86 -0
- package/src/sass/components/_icon-buttons.scss +194 -0
- package/src/sass/components/_icons-material-design.scss +16 -4
- package/src/sass/components/_index.scss +22 -6
- package/src/sass/components/_list.scss +16 -13
- package/src/sass/components/_loading-indicator.scss +106 -0
- package/src/sass/components/_menu.scss +335 -61
- package/src/sass/components/_navbar.scss +71 -24
- package/src/sass/components/_navigation-bar.scss +13 -10
- package/src/sass/components/{_sidenav.scss → _navigation-drawer.scss} +123 -33
- package/src/sass/components/_navigation-rail.scss +22 -22
- package/src/sass/components/_page-footer.scss +19 -16
- package/src/sass/components/_pagination.scss +24 -6
- package/src/sass/components/_panes.scss +52 -11
- package/src/sass/components/{_preloader.scss → _progress.scss} +11 -3
- package/src/sass/components/_scrim.scss +37 -0
- package/src/sass/components/_search.scss +259 -0
- package/src/sass/components/_segmented-buttons.scss +188 -0
- package/src/sass/components/_side-sheet.scss +2 -2
- package/src/sass/components/_snackbar.scss +20 -15
- package/src/sass/components/_split-button.scss +196 -0
- package/src/sass/components/_tabs.scss +7 -8
- package/src/sass/components/_timepicker.scss +67 -58
- package/src/sass/components/_toolbar.scss +206 -80
- package/src/sass/components/forms/_checkboxes.scss +49 -12
- package/src/sass/components/forms/_fieldset.scss +4 -4
- package/src/sass/components/forms/_file-input.scss +8 -1
- package/src/sass/components/forms/_index.scss +1 -1
- package/src/sass/components/forms/_input-fields.scss +50 -44
- package/src/sass/components/forms/_radio-buttons.scss +42 -10
- package/src/sass/components/forms/_select.scss +0 -1
- package/src/sass/components/forms/{_range.scss → _slider.scss} +8 -9
- package/src/sass/components/forms/_switches.scss +6 -7
- package/src/sass/tokens/_index.scss +4 -1
- package/src/sass/tokens/_reference.scss +70 -61
- package/src/sass/tokens/_state.scss +24 -0
- package/src/sass/tokens/_theme.scss +6 -3
- package/src/sass/tokens/_vibrant.scss +76 -0
- package/src/sass/utilities/_colors.scss +14 -1
- package/src/sass/utilities/_helpers.scss +5 -5
- package/src/sass/utilities/_visibility.scss +48 -26
- package/dist/types/behaviors/waves.d.ts +0 -15
- package/dist/types/components/parallax.d.ts +0 -16
- package/dist/types/components/range.d.ts +0 -43
- package/dist/types/core/bounding.d.ts +0 -6
- package/dist/types/core/edges.d.ts +0 -6
- package/src/sass/components/_parallax.scss +0 -104
- package/src/sass/components/_pulse.scss +0 -37
- package/src/sass/components/_slider.scss +0 -129
|
@@ -4,18 +4,24 @@
|
|
|
4
4
|
//
|
|
5
5
|
// Anatomy is the HTML. A <menu id> is the surface; each <li> is an item.
|
|
6
6
|
// A leading <i> is the leading icon; a trailing <i> or <kbd> is trailing
|
|
7
|
-
// content. An <
|
|
7
|
+
// content. An <li class="divider" role="separator"> is a divider; a bare
|
|
8
|
+
// <hr> is the older form and still styled, though <menu> only permits <li>.
|
|
9
|
+
// A .gap <li> splits groups. A .label
|
|
8
10
|
// <li> is a 32dp group heading. A nested <menu> is a flyout. The trigger
|
|
9
11
|
// is .menu-trigger[data-target] — that is the JS contract.
|
|
10
12
|
//
|
|
11
|
-
// Tokens
|
|
12
|
-
//
|
|
13
|
-
//
|
|
14
|
-
//
|
|
13
|
+
// Tokens are md.comp.menus - the expressive family, not baseline
|
|
14
|
+
// md.comp.menu, which is a different component with its own values.
|
|
15
|
+
// https://m3.material.io/components/menus/specs
|
|
16
|
+
// container surface-container-low, 16dp corners, level 2, 112–280
|
|
17
|
+
// group 2dp padding, 2dp gap, 8dp corners
|
|
18
|
+
// item 44dp, 16dp insets, 4dp corners, label-large / on-surface
|
|
19
|
+
// end items 12dp outer corner, 4dp inner
|
|
20
|
+
// state layer hover 8%, focus / pressed 10%
|
|
15
21
|
// selected medium (12dp) corners, tertiary-container / on-tertiary
|
|
16
22
|
// icon 20dp, on-surface-variant
|
|
17
23
|
// divider 1dp outline-variant, inset (not full-bleed)
|
|
18
|
-
// gap
|
|
24
|
+
// gap 2dp, more expressive than a divider
|
|
19
25
|
// label 32dp, on-surface-variant
|
|
20
26
|
// vibrant tertiary-container surface; selected is tertiary
|
|
21
27
|
// submenu scale + fade; focused flyout rounds up, parent rounds down
|
|
@@ -29,24 +35,43 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
29
35
|
}
|
|
30
36
|
|
|
31
37
|
@mixin menu-surface {
|
|
32
|
-
--md-comp-menu-container-color: var(--md-sys-color-surface-container);
|
|
38
|
+
--md-comp-menu-container-color: var(--md-sys-color-surface-container-low);
|
|
33
39
|
--md-comp-menu-container-shape: 16px;
|
|
34
|
-
--md-comp-menu-
|
|
40
|
+
--md-comp-menu-group-shape: 8px;
|
|
41
|
+
--md-comp-menu-container-inactive-shape: var(--md-comp-menu-group-shape);
|
|
42
|
+
--md-comp-menu-group-padding: 2px;
|
|
43
|
+
--md-comp-menu-gap: 2px;
|
|
44
|
+
--md-comp-menu-item-container-height: 44px;
|
|
35
45
|
--md-comp-menu-item-container-shape: 4px;
|
|
46
|
+
--md-comp-menu-item-edge-shape: 12px;
|
|
36
47
|
--md-comp-menu-item-selected-container-shape: 12px;
|
|
48
|
+
--md-comp-menu-item-leading-space: 16px;
|
|
49
|
+
--md-comp-menu-item-trailing-space: 16px;
|
|
50
|
+
--md-comp-menu-item-between-space: 12px;
|
|
37
51
|
--md-comp-menu-item-label-text-color: var(--md-sys-color-on-surface);
|
|
38
|
-
--md-comp-menu-item-leading-icon-color: var(
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
--md-comp-menu-item-
|
|
42
|
-
|
|
52
|
+
--md-comp-menu-item-leading-icon-color: var(
|
|
53
|
+
--md-sys-color-on-surface-variant
|
|
54
|
+
);
|
|
55
|
+
--md-comp-menu-item-trailing-icon-color: var(
|
|
56
|
+
--md-sys-color-on-surface-variant
|
|
57
|
+
);
|
|
58
|
+
--md-comp-menu-item-selected-container-color: var(
|
|
59
|
+
--md-sys-color-tertiary-container
|
|
60
|
+
);
|
|
61
|
+
--md-comp-menu-item-selected-label-text-color: var(
|
|
62
|
+
--md-sys-color-on-tertiary-container
|
|
63
|
+
);
|
|
64
|
+
--md-comp-menu-item-selected-leading-icon-color: var(
|
|
65
|
+
--md-sys-color-on-tertiary-container
|
|
66
|
+
);
|
|
43
67
|
--md-comp-menu-item-icon-size: 20px;
|
|
44
68
|
--md-comp-menu-supporting-text-color: var(--md-sys-color-on-surface-variant);
|
|
45
69
|
|
|
46
70
|
box-sizing: border-box;
|
|
47
71
|
min-width: 112px;
|
|
72
|
+
max-width: 280px;
|
|
48
73
|
margin: 0;
|
|
49
|
-
padding:
|
|
74
|
+
padding: var(--md-comp-menu-group-padding);
|
|
50
75
|
list-style: none;
|
|
51
76
|
background-color: var(--md-comp-menu-container-color);
|
|
52
77
|
border-radius: var(--md-comp-menu-container-shape);
|
|
@@ -54,15 +79,37 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
54
79
|
@include z-depth("2");
|
|
55
80
|
transition: border-radius 200ms ease;
|
|
56
81
|
|
|
57
|
-
|
|
82
|
+
// The [vibrant] arms are not a second mapping - they are the statement that
|
|
83
|
+
// a menu on a vibrant surface IS a vibrant menu. Without them the foundation
|
|
84
|
+
// paints the container tertiary-container while the selected item keeps the
|
|
85
|
+
// same tertiary-container from menu-surface above, and the selected state
|
|
86
|
+
// disappears into its own menu. M3's menus-vibrant answers that by moving
|
|
87
|
+
// selection to solid tertiary, which is exactly what this block already did.
|
|
88
|
+
// FormSelect's option fill reads the same token, so it follows.
|
|
89
|
+
&.vibrant,
|
|
90
|
+
&[vibrant],
|
|
91
|
+
[vibrant] &,
|
|
92
|
+
:host([vibrant]) & {
|
|
58
93
|
--md-comp-menu-container-color: var(--md-sys-color-tertiary-container);
|
|
59
|
-
--md-comp-menu-item-label-text-color: var(
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
--md-comp-menu-
|
|
94
|
+
--md-comp-menu-item-label-text-color: var(
|
|
95
|
+
--md-sys-color-on-tertiary-container
|
|
96
|
+
);
|
|
97
|
+
--md-comp-menu-item-leading-icon-color: var(
|
|
98
|
+
--md-sys-color-on-tertiary-container
|
|
99
|
+
);
|
|
100
|
+
--md-comp-menu-item-trailing-icon-color: var(
|
|
101
|
+
--md-sys-color-on-tertiary-container
|
|
102
|
+
);
|
|
103
|
+
--md-comp-menu-supporting-text-color: var(
|
|
104
|
+
--md-sys-color-on-tertiary-container
|
|
105
|
+
);
|
|
63
106
|
--md-comp-menu-item-selected-container-color: var(--md-sys-color-tertiary);
|
|
64
|
-
--md-comp-menu-item-selected-label-text-color: var(
|
|
65
|
-
|
|
107
|
+
--md-comp-menu-item-selected-label-text-color: var(
|
|
108
|
+
--md-sys-color-on-tertiary
|
|
109
|
+
);
|
|
110
|
+
--md-comp-menu-item-selected-leading-icon-color: var(
|
|
111
|
+
--md-sys-color-on-tertiary
|
|
112
|
+
);
|
|
66
113
|
}
|
|
67
114
|
|
|
68
115
|
> li {
|
|
@@ -74,21 +121,31 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
74
121
|
text-align: left;
|
|
75
122
|
border-radius: var(--md-comp-menu-item-container-shape);
|
|
76
123
|
|
|
124
|
+
// The bare-span arm is the non-interactive item. It has to exclude icons,
|
|
125
|
+
// which are spans as well and are a legal direct child of the <li> (see
|
|
126
|
+
// the `> #{$icon}` arm below) - otherwise one gets stretched to a
|
|
127
|
+
// full-width 48dp row.
|
|
77
128
|
> a,
|
|
78
129
|
> button,
|
|
79
|
-
>
|
|
130
|
+
> #{$icon-label} {
|
|
80
131
|
display: flex;
|
|
81
132
|
align-items: center;
|
|
82
|
-
|
|
133
|
+
// A <button> takes the common button's centered flex layout; menu
|
|
134
|
+
// commands must line up with link items at the leading inset instead.
|
|
135
|
+
justify-content: flex-start;
|
|
136
|
+
gap: var(--md-comp-menu-item-between-space);
|
|
83
137
|
box-sizing: border-box;
|
|
84
138
|
width: 100%;
|
|
85
139
|
min-height: var(--md-comp-menu-item-container-height);
|
|
86
140
|
margin: 0;
|
|
87
|
-
padding:
|
|
141
|
+
padding-block: 8px;
|
|
142
|
+
padding-inline: var(--md-comp-menu-item-leading-space)
|
|
143
|
+
var(--md-comp-menu-item-trailing-space);
|
|
88
144
|
border: 0;
|
|
89
145
|
background: none;
|
|
90
146
|
color: var(--md-comp-menu-item-label-text-color);
|
|
91
147
|
text-decoration: none;
|
|
148
|
+
text-align: start;
|
|
92
149
|
cursor: pointer;
|
|
93
150
|
|
|
94
151
|
&:hover,
|
|
@@ -96,12 +153,24 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
96
153
|
background: none;
|
|
97
154
|
}
|
|
98
155
|
@include typescale("label-large");
|
|
99
|
-
font-family: $font-stack;
|
|
100
156
|
}
|
|
101
157
|
|
|
102
|
-
> a >
|
|
103
|
-
|
|
104
|
-
|
|
158
|
+
> :is(a, button) > .menu-item-text {
|
|
159
|
+
display: flex;
|
|
160
|
+
min-width: 0;
|
|
161
|
+
flex: 1 1 auto;
|
|
162
|
+
flex-direction: column;
|
|
163
|
+
align-items: flex-start;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
> :is(a, button) .supporting-text {
|
|
167
|
+
color: var(--md-comp-menu-supporting-text-color);
|
|
168
|
+
@include typescale("body-small");
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
> a > #{$icon},
|
|
172
|
+
> button > #{$icon},
|
|
173
|
+
> #{$icon} {
|
|
105
174
|
flex: 0 0 var(--md-comp-menu-item-icon-size);
|
|
106
175
|
font-size: var(--md-comp-menu-item-icon-size);
|
|
107
176
|
width: var(--md-comp-menu-item-icon-size);
|
|
@@ -110,7 +179,16 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
110
179
|
color: var(--md-comp-menu-item-leading-icon-color);
|
|
111
180
|
}
|
|
112
181
|
|
|
113
|
-
|
|
182
|
+
// A lone icon is ambiguous to CSS. In `<a>Label<span icon/></a>` and
|
|
183
|
+
// `<a><span icon/>Label</a>` the span is :first-child, :last-child AND
|
|
184
|
+
// :only-child in both cases - the label is a text node, and selectors
|
|
185
|
+
// cannot see text. So :not(:only-child) only ever caught rows carrying two
|
|
186
|
+
// icons, and every text-plus-trailing-icon row silently kept its icon
|
|
187
|
+
// butted against the label instead of flush right.
|
|
188
|
+
//
|
|
189
|
+
// Leading stays the default; a trailing icon names its side, the same way
|
|
190
|
+
// a field icon must (see rule 3 in CLAUDE.md).
|
|
191
|
+
> :is(a, button) > #{$icon}:is(.suffix, :last-child:not(:only-child)) {
|
|
114
192
|
margin-inline-start: auto;
|
|
115
193
|
color: var(--md-comp-menu-item-trailing-icon-color);
|
|
116
194
|
}
|
|
@@ -124,15 +202,39 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
124
202
|
font-family: inherit;
|
|
125
203
|
@include typescale("label-large");
|
|
126
204
|
}
|
|
205
|
+
|
|
206
|
+
> :is(a, button) > .badge {
|
|
207
|
+
margin-inline-start: auto;
|
|
208
|
+
}
|
|
127
209
|
}
|
|
128
210
|
|
|
129
|
-
> li:not(.
|
|
211
|
+
> li:not(.divider, .optgroup, .gap, .label) {
|
|
130
212
|
min-height: var(--md-comp-menu-item-container-height);
|
|
131
213
|
}
|
|
132
214
|
|
|
215
|
+
> li:not(.divider, .optgroup, .gap, .label):first-child {
|
|
216
|
+
border-radius: var(--md-comp-menu-item-edge-shape)
|
|
217
|
+
var(--md-comp-menu-item-edge-shape)
|
|
218
|
+
var(--md-comp-menu-item-container-shape)
|
|
219
|
+
var(--md-comp-menu-item-container-shape);
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
> li:not(.divider, .optgroup, .gap, .label):last-child {
|
|
223
|
+
border-radius: var(--md-comp-menu-item-container-shape)
|
|
224
|
+
var(--md-comp-menu-item-container-shape)
|
|
225
|
+
var(--md-comp-menu-item-edge-shape) var(--md-comp-menu-item-edge-shape);
|
|
226
|
+
}
|
|
227
|
+
|
|
133
228
|
// Hover / press sit on extra-small corners and do not span the container.
|
|
134
|
-
> li:not(
|
|
135
|
-
|
|
229
|
+
> li:not(
|
|
230
|
+
.disabled,
|
|
231
|
+
[aria-disabled="true"],
|
|
232
|
+
.divider,
|
|
233
|
+
.optgroup,
|
|
234
|
+
.gap,
|
|
235
|
+
.label
|
|
236
|
+
):hover,
|
|
237
|
+
> li.active:not(.selected, [aria-selected="true"], [aria-checked="true"]) {
|
|
136
238
|
background-color: color-mix(
|
|
137
239
|
in oklab,
|
|
138
240
|
var(--md-comp-menu-item-label-text-color) 8%,
|
|
@@ -140,7 +242,14 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
140
242
|
);
|
|
141
243
|
}
|
|
142
244
|
|
|
143
|
-
> li:not(
|
|
245
|
+
> li:not(
|
|
246
|
+
.disabled,
|
|
247
|
+
[aria-disabled="true"],
|
|
248
|
+
.divider,
|
|
249
|
+
.optgroup,
|
|
250
|
+
.gap,
|
|
251
|
+
.label
|
|
252
|
+
):active {
|
|
144
253
|
background-color: color-mix(
|
|
145
254
|
in oklab,
|
|
146
255
|
var(--md-comp-menu-item-label-text-color) 10%,
|
|
@@ -148,24 +257,31 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
148
257
|
);
|
|
149
258
|
}
|
|
150
259
|
|
|
151
|
-
|
|
152
|
-
|
|
260
|
+
// :not(.divider) only buys specificity: menu-item.selected.shape is 12dp
|
|
261
|
+
// unconditionally, so it has to outrank the first/last-child edge rule that
|
|
262
|
+
// would otherwise leave a selected end item with 4dp inner corners.
|
|
263
|
+
> li:is(.selected, [aria-selected="true"], [aria-checked="true"]):not(
|
|
264
|
+
.divider
|
|
265
|
+
) {
|
|
153
266
|
border-radius: var(--md-comp-menu-item-selected-container-shape);
|
|
154
267
|
background-color: var(--md-comp-menu-item-selected-container-color);
|
|
155
268
|
color: var(--md-comp-menu-item-selected-label-text-color);
|
|
156
269
|
|
|
157
|
-
> :is(a, button,
|
|
270
|
+
> :is(a, button, #{$icon-label}) {
|
|
158
271
|
color: var(--md-comp-menu-item-selected-label-text-color);
|
|
159
272
|
}
|
|
160
273
|
|
|
161
|
-
> :is(a, button,
|
|
162
|
-
>
|
|
274
|
+
> :is(a, button, #{$icon-label}) > #{$icon},
|
|
275
|
+
> #{$icon} {
|
|
163
276
|
color: var(--md-comp-menu-item-selected-leading-icon-color);
|
|
164
277
|
}
|
|
278
|
+
|
|
279
|
+
> :is(a, button, #{$icon-label}) :is(.supporting-text, kbd, .shortcut) {
|
|
280
|
+
color: var(--md-comp-menu-item-selected-label-text-color);
|
|
281
|
+
}
|
|
165
282
|
}
|
|
166
283
|
|
|
167
|
-
> li.selected:hover
|
|
168
|
-
> li[aria-selected="true"]:hover {
|
|
284
|
+
> li:is(.selected, [aria-selected="true"], [aria-checked="true"]):hover {
|
|
169
285
|
background-color: color-mix(
|
|
170
286
|
in oklab,
|
|
171
287
|
var(--md-comp-menu-item-selected-label-text-color) 8%,
|
|
@@ -173,12 +289,24 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
173
289
|
);
|
|
174
290
|
}
|
|
175
291
|
|
|
292
|
+
> li:is(.selected, [aria-selected="true"], [aria-checked="true"]):is(
|
|
293
|
+
:focus,
|
|
294
|
+
:focus-visible,
|
|
295
|
+
:active
|
|
296
|
+
) {
|
|
297
|
+
background-color: color-mix(
|
|
298
|
+
in oklab,
|
|
299
|
+
var(--md-comp-menu-item-selected-label-text-color) 10%,
|
|
300
|
+
var(--md-comp-menu-item-selected-container-color)
|
|
301
|
+
);
|
|
302
|
+
}
|
|
303
|
+
|
|
176
304
|
> li:focus-visible {
|
|
177
305
|
outline: 3px solid var(--md-sys-color-secondary);
|
|
178
306
|
outline-offset: -3px;
|
|
179
307
|
}
|
|
180
308
|
|
|
181
|
-
> li.disabled {
|
|
309
|
+
> li:is(.disabled, [aria-disabled="true"]) {
|
|
182
310
|
pointer-events: none;
|
|
183
311
|
opacity: 0.38;
|
|
184
312
|
}
|
|
@@ -201,9 +329,9 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
201
329
|
|
|
202
330
|
// Gap: more expressive than a divider. One or two per menu; not in a scroller.
|
|
203
331
|
> li.gap {
|
|
204
|
-
height:
|
|
205
|
-
min-height:
|
|
206
|
-
margin: 0 -
|
|
332
|
+
height: var(--md-comp-menu-gap);
|
|
333
|
+
min-height: var(--md-comp-menu-gap);
|
|
334
|
+
margin: 0 calc(-1 * var(--md-comp-menu-group-padding));
|
|
207
335
|
padding: 0;
|
|
208
336
|
pointer-events: none;
|
|
209
337
|
cursor: default;
|
|
@@ -221,14 +349,126 @@ $_menu-chevron: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg
|
|
|
221
349
|
cursor: default;
|
|
222
350
|
color: var(--md-comp-menu-supporting-text-color);
|
|
223
351
|
@include typescale("label-large");
|
|
224
|
-
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
// Grouped layout: each run of items between .gap separators becomes its
|
|
355
|
+
// own coplanar surface. Standard remains the default continuous surface.
|
|
356
|
+
&.grouped {
|
|
357
|
+
padding: 0;
|
|
358
|
+
background-color: transparent;
|
|
359
|
+
box-shadow: none;
|
|
360
|
+
filter: drop-shadow(0 3px 3px rgba(0, 0, 0, 0.14))
|
|
361
|
+
drop-shadow(0 1px 4px rgba(0, 0, 0, 0.12));
|
|
362
|
+
|
|
363
|
+
> li:not(.divider, .optgroup, .gap, .label) {
|
|
364
|
+
padding-inline: var(--md-comp-menu-group-padding);
|
|
365
|
+
background-color: var(--md-comp-menu-container-color);
|
|
366
|
+
border-radius: 0;
|
|
367
|
+
}
|
|
368
|
+
|
|
369
|
+
> li:not(.divider, .optgroup, .gap, .label):first-child,
|
|
370
|
+
> li.gap + li:not(.divider, .optgroup, .gap, .label) {
|
|
371
|
+
padding-block-start: var(--md-comp-menu-group-padding);
|
|
372
|
+
border-start-start-radius: var(--md-comp-menu-group-shape);
|
|
373
|
+
border-start-end-radius: var(--md-comp-menu-group-shape);
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
> li:not(.divider, .optgroup, .gap, .label):has(+ li.gap),
|
|
377
|
+
> li:not(.divider, .optgroup, .gap, .label):last-child {
|
|
378
|
+
padding-block-end: var(--md-comp-menu-group-padding);
|
|
379
|
+
border-end-start-radius: var(--md-comp-menu-group-shape);
|
|
380
|
+
border-end-end-radius: var(--md-comp-menu-group-shape);
|
|
381
|
+
}
|
|
382
|
+
|
|
383
|
+
> li.gap {
|
|
384
|
+
margin: 0;
|
|
385
|
+
}
|
|
386
|
+
|
|
387
|
+
// State layers belong to the inset item while the group surface remains.
|
|
388
|
+
> li:not(
|
|
389
|
+
.disabled,
|
|
390
|
+
[aria-disabled="true"],
|
|
391
|
+
.divider,
|
|
392
|
+
.optgroup,
|
|
393
|
+
.gap,
|
|
394
|
+
.label
|
|
395
|
+
):hover,
|
|
396
|
+
> li.active,
|
|
397
|
+
> li.selected,
|
|
398
|
+
> li[aria-selected="true"],
|
|
399
|
+
> li[aria-checked="true"] {
|
|
400
|
+
background-color: var(--md-comp-menu-container-color);
|
|
401
|
+
}
|
|
402
|
+
|
|
403
|
+
> li:not(
|
|
404
|
+
.disabled,
|
|
405
|
+
[aria-disabled="true"],
|
|
406
|
+
.divider,
|
|
407
|
+
.optgroup,
|
|
408
|
+
.gap,
|
|
409
|
+
.label
|
|
410
|
+
):hover
|
|
411
|
+
> :is(a, button, #{$icon-label}),
|
|
412
|
+
> li.active:not(.selected, [aria-selected="true"], [aria-checked="true"])
|
|
413
|
+
> :is(a, button, #{$icon-label}) {
|
|
414
|
+
border-radius: var(--md-comp-menu-item-container-shape);
|
|
415
|
+
background-color: color-mix(
|
|
416
|
+
in oklab,
|
|
417
|
+
var(--md-comp-menu-item-label-text-color) 8%,
|
|
418
|
+
transparent
|
|
419
|
+
);
|
|
420
|
+
}
|
|
421
|
+
|
|
422
|
+
> li:not(
|
|
423
|
+
.disabled,
|
|
424
|
+
[aria-disabled="true"],
|
|
425
|
+
.divider,
|
|
426
|
+
.optgroup,
|
|
427
|
+
.gap,
|
|
428
|
+
.label
|
|
429
|
+
):active
|
|
430
|
+
> :is(a, button, #{$icon-label}) {
|
|
431
|
+
background-color: color-mix(
|
|
432
|
+
in oklab,
|
|
433
|
+
var(--md-comp-menu-item-label-text-color) 10%,
|
|
434
|
+
transparent
|
|
435
|
+
);
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
> li:is(.selected, [aria-selected="true"], [aria-checked="true"])
|
|
439
|
+
> :is(a, button, #{$icon-label}) {
|
|
440
|
+
border-radius: var(--md-comp-menu-item-selected-container-shape);
|
|
441
|
+
background-color: var(--md-comp-menu-item-selected-container-color);
|
|
442
|
+
}
|
|
443
|
+
|
|
444
|
+
> li:is(.selected, [aria-selected="true"], [aria-checked="true"]):hover
|
|
445
|
+
> :is(a, button, #{$icon-label}) {
|
|
446
|
+
background-color: color-mix(
|
|
447
|
+
in oklab,
|
|
448
|
+
var(--md-comp-menu-item-selected-label-text-color) 8%,
|
|
449
|
+
var(--md-comp-menu-item-selected-container-color)
|
|
450
|
+
);
|
|
451
|
+
}
|
|
452
|
+
|
|
453
|
+
> li:is(.selected, [aria-selected="true"], [aria-checked="true"]):is(
|
|
454
|
+
:focus,
|
|
455
|
+
:focus-visible,
|
|
456
|
+
:active
|
|
457
|
+
)
|
|
458
|
+
> :is(a, button, #{$icon-label}) {
|
|
459
|
+
background-color: color-mix(
|
|
460
|
+
in oklab,
|
|
461
|
+
var(--md-comp-menu-item-selected-label-text-color) 10%,
|
|
462
|
+
var(--md-comp-menu-item-selected-container-color)
|
|
463
|
+
);
|
|
464
|
+
}
|
|
225
465
|
}
|
|
226
466
|
|
|
227
467
|
li:has(> menu) {
|
|
228
468
|
position: relative;
|
|
229
469
|
}
|
|
230
470
|
|
|
231
|
-
li:has(> menu) > :is(a, button,
|
|
471
|
+
li:has(> menu) > :is(a, button, #{$icon-label})::after {
|
|
232
472
|
content: "";
|
|
233
473
|
flex: 0 0 var(--md-comp-menu-item-icon-size);
|
|
234
474
|
width: var(--md-comp-menu-item-icon-size);
|
|
@@ -259,7 +499,9 @@ menu[id] {
|
|
|
259
499
|
|
|
260
500
|
// Unfocused parent rounds down while a flyout is the focus.
|
|
261
501
|
&:has(> li:is(:hover, :focus-within, .open) > menu) {
|
|
262
|
-
--md-comp-menu-container-shape:
|
|
502
|
+
--md-comp-menu-container-shape: var(
|
|
503
|
+
--md-comp-menu-container-inactive-shape
|
|
504
|
+
);
|
|
263
505
|
}
|
|
264
506
|
}
|
|
265
507
|
|
|
@@ -293,7 +535,7 @@ menu[id] li > menu {
|
|
|
293
535
|
opacity: 1;
|
|
294
536
|
pointer-events: auto;
|
|
295
537
|
transform: none;
|
|
296
|
-
--md-comp-menu-container-shape:
|
|
538
|
+
--md-comp-menu-container-shape: 16px;
|
|
297
539
|
}
|
|
298
540
|
}
|
|
299
541
|
|
|
@@ -302,7 +544,7 @@ menu[id] li.open > menu {
|
|
|
302
544
|
opacity: 1;
|
|
303
545
|
pointer-events: auto;
|
|
304
546
|
transform: none;
|
|
305
|
-
--md-comp-menu-container-shape:
|
|
547
|
+
--md-comp-menu-container-shape: 16px;
|
|
306
548
|
}
|
|
307
549
|
|
|
308
550
|
menu[id] li.submenu-start > menu {
|
|
@@ -315,22 +557,46 @@ menu[id] li.submenu-start:is(:hover, :focus-within, .open) > menu {
|
|
|
315
557
|
transform: none;
|
|
316
558
|
}
|
|
317
559
|
|
|
318
|
-
body.keyboard-focused
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
560
|
+
// Keyboard focus only. This used to be nested under `body.keyboard-focused`, a
|
|
561
|
+
// class the bundle stamped from four capture-phase document listeners; the
|
|
562
|
+
// browser answers the same question. A programmatic focus - which is how a menu
|
|
563
|
+
// item gets focus here - inherits :focus-visible from the element that had it,
|
|
564
|
+
// so opening the menu by keyboard still lights the item and opening it by
|
|
565
|
+
// pointer still does not.
|
|
566
|
+
menu[id] > li:focus-visible {
|
|
567
|
+
background-color: color-mix(
|
|
568
|
+
in oklab,
|
|
569
|
+
var(--md-comp-menu-item-label-text-color) 10%,
|
|
570
|
+
transparent
|
|
571
|
+
);
|
|
572
|
+
}
|
|
326
573
|
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
574
|
+
menu[id]
|
|
575
|
+
> li:focus-visible:not(.selected, [aria-selected="true"], [aria-checked="true"]) {
|
|
576
|
+
outline: 3px solid var(--md-sys-color-secondary);
|
|
577
|
+
outline-offset: -3px;
|
|
578
|
+
}
|
|
579
|
+
|
|
580
|
+
menu[id].grouped > li:focus-visible {
|
|
581
|
+
background-color: var(--md-comp-menu-container-color);
|
|
582
|
+
}
|
|
583
|
+
|
|
584
|
+
menu[id].grouped
|
|
585
|
+
> li:focus-visible:not(.selected, [aria-selected="true"], [aria-checked="true"])
|
|
586
|
+
> :is(a, button, span:not(.material-symbols, .badge, .supporting-text)) {
|
|
587
|
+
border-radius: var(--md-comp-menu-item-container-shape);
|
|
588
|
+
background-color: color-mix(
|
|
589
|
+
in oklab,
|
|
590
|
+
var(--md-comp-menu-item-label-text-color) 10%,
|
|
591
|
+
transparent
|
|
592
|
+
);
|
|
331
593
|
}
|
|
332
594
|
|
|
333
595
|
@media (prefers-reduced-motion: reduce) {
|
|
596
|
+
menu[id] {
|
|
597
|
+
transition: none !important;
|
|
598
|
+
}
|
|
599
|
+
|
|
334
600
|
menu[id] li > menu {
|
|
335
601
|
transition: none;
|
|
336
602
|
}
|
|
@@ -338,4 +604,12 @@ body.keyboard-focused {
|
|
|
338
604
|
|
|
339
605
|
.menu-trigger {
|
|
340
606
|
cursor: pointer;
|
|
607
|
+
|
|
608
|
+
// The trigger stays in its pressed state for as long as its menu is open.
|
|
609
|
+
&[aria-expanded="true"] {
|
|
610
|
+
background-image: linear-gradient(
|
|
611
|
+
color-mix(in oklab, currentcolor 10%, transparent),
|
|
612
|
+
color-mix(in oklab, currentcolor 10%, transparent)
|
|
613
|
+
);
|
|
614
|
+
}
|
|
341
615
|
}
|