maverick-wave 5.26.0 → 5.27.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.
@@ -1,51 +1,8 @@
1
1
  @use '../abstracts' as *;
2
2
 
3
3
  @layer mw.components {
4
- .mw-tiles {
5
- width: 100%;
6
- margin: spacing('0') auto;
7
- padding: spacing('0');
8
- display: grid;
9
- gap: spacing('4');
10
- grid-template-columns: 1fr;
11
-
12
- @include media-up('sm') {
13
- grid-template-columns: repeat(2, 1fr);
14
- width: 80%;
15
- padding: spacing('3');
16
- gap: spacing('6');
17
- }
18
-
19
- @include media-up('lg') {
20
- grid-template-columns: repeat(3, 1fr);
21
- }
22
-
23
- // The page gutter is the container's job, a second inset only narrows the tile
24
- &-4col {
25
- @include media-up('sm') {
26
- width: 85%;
27
- grid-template-columns: repeat(2, 1fr);
28
- }
29
-
30
- @include media-up('md') {
31
- grid-template-columns: repeat(3, 1fr);
32
- }
33
-
34
- @include media-up('lg') {
35
- grid-template-columns: repeat(4, 1fr);
36
- }
37
- }
38
-
39
- &-2col {
40
- @include media-up('sm') {
41
- width: 75%;
42
- grid-template-columns: repeat(2, 1fr);
43
- }
44
- }
45
- }
46
-
47
4
  // The tile sizes its type off its own width, not the window's. In
48
- // `.mw-tiles-4col` on a wide desktop a tile is a quarter of 85% of the page -
5
+ // `.mw-tiles-4col` on a wide desktop a tile is a quarter of the container -
49
6
  // narrower than the same tile alone on a phone, where it used to be the one
50
7
  // getting the small type.
51
8
  //
@@ -69,7 +26,6 @@
69
26
  overflow: hidden;
70
27
  display: flex;
71
28
  flex-direction: column;
72
- cursor: pointer;
73
29
 
74
30
  // Ahead of the size modifiers below, which take over from 'sm'
75
31
  @include media-up('sm') {
@@ -90,13 +46,22 @@
90
46
 
91
47
  @include hover-move {
92
48
  transform: translateY(-2px);
49
+
50
+ // The whole tile is the target, unlike a card where the image frame
51
+ // owns its own hover - a tile is one face, not a stack of regions.
52
+ .mw-tile-img img {
53
+ transform: scale(1.05);
54
+ }
93
55
  }
94
56
 
95
57
  // A tile is tapped, so it needs a press of its own - the lift above never
96
- // runs on a finger.
97
- &:active {
98
- transform: scale(0.985);
99
- transition-duration: var(--mw-duration-instant);
58
+ // runs on a finger. Guarded like every other travel in the framework; what
59
+ // is left without it is the latched hover, which is feedback enough.
60
+ @media (prefers-reduced-motion: no-preference) {
61
+ &:active {
62
+ transform: scale(0.985);
63
+ transition-duration: var(--mw-duration-instant);
64
+ }
100
65
  }
101
66
 
102
67
  &-img {
@@ -145,6 +110,13 @@
145
110
  font-size: font-size('sm');
146
111
  line-height: 1.3;
147
112
 
113
+ // The ramp the header takes: a tile filling a phone is a wide
114
+ // container and reads at full size, one squeezed into a desktop
115
+ // column stays small.
116
+ @container mw-tile (width >= #{$_mw-tile-narrow}) {
117
+ font-size: font-size('base');
118
+ }
119
+
148
120
  &:last-child {
149
121
  margin-bottom: spacing('0');
150
122
  }
@@ -186,6 +158,10 @@
186
158
 
187
159
  p {
188
160
  font-size: font-size('xs');
161
+
162
+ @container mw-tile (width >= #{$_mw-tile-narrow}) {
163
+ font-size: font-size('sm');
164
+ }
189
165
  }
190
166
  }
191
167
  }
@@ -225,6 +201,24 @@
225
201
  }
226
202
  }
227
203
 
204
+ // A tile is only a control when the markup makes it one. The look above is a
205
+ // surface and stays on a div; everything a finger or a keyboard needs sits
206
+ // here, where the element itself answers for it - a hand cursor on a div
207
+ // promises a click nothing handles, and a ring on it would never be reached.
208
+ a.mw-tile,
209
+ button.mw-tile {
210
+ cursor: pointer;
211
+ // A button brings its own font, alignment and colour, and the tile's own
212
+ // children set none of the three
213
+ font: inherit;
214
+ color: inherit;
215
+ text-align: inherit;
216
+ text-decoration: none;
217
+
218
+ @include focus-ring;
219
+ @include tappable;
220
+ }
221
+
228
222
  // A cramped tile reads better ranged left whatever the window is doing - a
229
223
  // centred line inside 200px is two words and a gap. Every selector here is a
230
224
  // child: a container cannot answer a query about itself, and the tile *is* the
@@ -122,6 +122,28 @@ $_grid-from: ('sm', 'md', 'lg', 'xl');
122
122
  }
123
123
  }
124
124
 
125
+ // The container half of the tile component. Here and not in `_tiles.scss`,
126
+ // because it is one of the ramps above and a component file cannot reach them.
127
+ //
128
+ // The guard is what makes a modifier replace the bare ramp rather than layer
129
+ // on it: both step at the same breakpoints, so which one holds a given width
130
+ // would otherwise come down to media query order.
131
+ .mw-tiles {
132
+ @extend %grid-base;
133
+ }
134
+
135
+ .mw-tiles:not(.mw-tiles-2col):not(.mw-tiles-4col) {
136
+ @include _column-grid(map.get($_column-steps, 3));
137
+ }
138
+
139
+ .mw-tiles-2col {
140
+ @include _column-grid(map.get($_column-steps, 2));
141
+ }
142
+
143
+ .mw-tiles-4col {
144
+ @include _column-grid(map.get($_column-steps, 4));
145
+ }
146
+
125
147
  .mw-grid-flex {
126
148
  @extend %grid-base;
127
149
 
@@ -518,17 +518,6 @@
518
518
  }
519
519
  }
520
520
 
521
- @keyframes fadeIn {
522
- from {
523
- opacity: 0;
524
- transform: translateY(-10px);
525
- }
526
- to {
527
- opacity: 1;
528
- transform: translateY(0);
529
- }
530
- }
531
-
532
521
  // Profile button - a round avatar until there is room for the signed-in name
533
522
  // beside it
534
523
  .mw-profile-btn {
@@ -20,7 +20,7 @@
20
20
 
21
21
  &-fade {
22
22
  @extend .mw-home-content;
23
- animation: fadeIn var(--mw-duration-slower) var(--mw-ease-out);
23
+ animation: mw-home-fade var(--mw-duration-slower) var(--mw-ease-out);
24
24
  }
25
25
  }
26
26
 
@@ -47,7 +47,7 @@
47
47
  }
48
48
  }
49
49
 
50
- @keyframes fadeIn {
50
+ @keyframes mw-home-fade {
51
51
  from {
52
52
  opacity: 0;
53
53
  transform: translateX(-8px) translateY(-23px);
@@ -176,11 +176,17 @@
176
176
  @include scrollbar;
177
177
  }
178
178
 
179
- // The strip parks under the header, so a jump to a component clears both
179
+ // The strip parks under the header, so everything scrolled to - an anchor and
180
+ // a tab stop alike - has to clear both. The reset reserves the header, this
181
+ // adds the strip on top of it for as long as a page carries one.
182
+ html:has(.mw-section-nav) {
183
+ --mw-section-nav-offset: var(--mw-section-nav-height);
184
+ }
185
+
186
+ // The offset above lands a target flush under the strip; this is the air
187
+ // between the two.
180
188
  .mw-container > div:has(> .mw-section-subtitle) {
181
- scroll-margin-top: calc(
182
- var(--mw-header-height) + var(--mw-section-nav-height) + #{spacing('5')}
183
- );
189
+ scroll-margin-top: spacing('5');
184
190
  }
185
191
 
186
192
  .mw-section-btn {
@@ -215,6 +221,9 @@
215
221
 
216
222
  @include focus-ring;
217
223
  @include tappable;
224
+ // It sits under the floor on its own, in a strip that scrolls sideways
225
+ // under the thumb - a near miss here costs a jump, not just a retry
226
+ @include touch-floor;
218
227
 
219
228
  &:disabled {
220
229
  cursor: not-allowed;