@justeattakeaway/pie-css 0.31.1 → 0.32.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/dist/components/button.css +552 -0
- package/docs/components/BUTTON.md +260 -0
- package/docs/typography-utility-classes.md +2 -2
- package/package.json +2 -2
- package/scss/_internal/components/button.scss +95 -0
- package/scss/_internal/{radio.scss → components/radio.scss} +1 -1
- package/scss/_internal/{typography.scss → helpers/typography.scss} +1 -1
- package/scss/mixins/_interactiveStates.scss +2 -2
- package/scss/mixins/components/_button.scss +434 -0
- package/scss/mixins/components/index.scss +1 -0
|
@@ -0,0 +1,434 @@
|
|
|
1
|
+
// INTERNAL USE ONLY
|
|
2
|
+
// These mixins are intended for internal use by PIE components (e.g., pie-button).
|
|
3
|
+
// They are not part of the public API and may change without notice.
|
|
4
|
+
// For styling elements as buttons in your application, use the pre-compiled CSS classes
|
|
5
|
+
// from @justeattakeaway/pie-css/dist/components/button.css instead.
|
|
6
|
+
// See: packages/tools/pie-css/docs/components/BUTTON.md
|
|
7
|
+
|
|
8
|
+
@use '../interactiveStates' as *;
|
|
9
|
+
@use '../focus' as *;
|
|
10
|
+
@use '../../functions' as *;
|
|
11
|
+
@use '../../settings' as *;
|
|
12
|
+
|
|
13
|
+
// ============================================================================
|
|
14
|
+
// Button Base
|
|
15
|
+
// ============================================================================
|
|
16
|
+
|
|
17
|
+
/// Core mixin that applies all base button styles including layout, typography,
|
|
18
|
+
/// custom properties, and focus ring.
|
|
19
|
+
/// @param {Boolean} $include-icon-selector [true] - Whether to include the `.c-pieIcon` sizing rule.
|
|
20
|
+
/// Set to `false` when consuming from pie-button (which handles icon sizing via `::slotted(svg)`).
|
|
21
|
+
/// @example scss - Basic usage
|
|
22
|
+
/// .my-button {
|
|
23
|
+
/// @include button-base();
|
|
24
|
+
/// }
|
|
25
|
+
@mixin button-base($include-icon-selector: true) {
|
|
26
|
+
// CSS custom properties for theming
|
|
27
|
+
--btn-border-radius: var(--dt-radius-rounded-e);
|
|
28
|
+
--btn-font-family: var(--dt-font-interactive-l-family);
|
|
29
|
+
--btn-font-weight: var(--dt-font-interactive-l-weight);
|
|
30
|
+
|
|
31
|
+
// Default background and text colour (primary variant)
|
|
32
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-brand);
|
|
33
|
+
--btn-text-color: var(--dt-color-content-interactive-light-solid);
|
|
34
|
+
|
|
35
|
+
// Vertical padding values per size
|
|
36
|
+
--btn-padding-vertical-xsmall: 6px;
|
|
37
|
+
--btn-padding-vertical-small-expressive: 8px;
|
|
38
|
+
--btn-padding-vertical-small-productive: 10px;
|
|
39
|
+
--btn-padding-vertical-medium: 12px;
|
|
40
|
+
--btn-padding-vertical-large: 16px;
|
|
41
|
+
|
|
42
|
+
// Horizontal padding values per size
|
|
43
|
+
--btn-padding-horizontal-small: var(--dt-spacing-b);
|
|
44
|
+
--btn-padding-horizontal-medium: var(--dt-spacing-d);
|
|
45
|
+
--btn-padding-horizontal-large: var(--dt-spacing-e);
|
|
46
|
+
|
|
47
|
+
// Layout
|
|
48
|
+
position: relative;
|
|
49
|
+
display: inline-flex;
|
|
50
|
+
gap: var(--dt-spacing-b);
|
|
51
|
+
align-items: center;
|
|
52
|
+
justify-content: center;
|
|
53
|
+
|
|
54
|
+
// Appearance
|
|
55
|
+
border: none;
|
|
56
|
+
border-radius: var(--btn-border-radius);
|
|
57
|
+
outline: none;
|
|
58
|
+
background-color: var(--int-states-mixin-bg-color);
|
|
59
|
+
cursor: pointer;
|
|
60
|
+
user-select: none;
|
|
61
|
+
text-decoration: none;
|
|
62
|
+
|
|
63
|
+
// Typography
|
|
64
|
+
font-family: var(--btn-font-family);
|
|
65
|
+
font-size: var(--btn-font-size);
|
|
66
|
+
font-weight: var(--btn-font-weight);
|
|
67
|
+
color: var(--btn-text-color);
|
|
68
|
+
line-height: var(--btn-line-height);
|
|
69
|
+
|
|
70
|
+
// Width control
|
|
71
|
+
inline-size: var(--btn-inline-size);
|
|
72
|
+
|
|
73
|
+
// Focus styles
|
|
74
|
+
&:focus-visible {
|
|
75
|
+
@include focus;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
// Icon sizing via .c-pieIcon (CSS-only buttons using pie-icons-webc)
|
|
79
|
+
@if $include-icon-selector {
|
|
80
|
+
.c-pieIcon {
|
|
81
|
+
height: var(--btn-icon-size);
|
|
82
|
+
width: var(--btn-icon-size);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
// ============================================================================
|
|
88
|
+
// Button Sizes
|
|
89
|
+
// ============================================================================
|
|
90
|
+
|
|
91
|
+
/// Internal mixin for setting font-size, line-height, and icon size per size.
|
|
92
|
+
/// @param {String} $size - The size name
|
|
93
|
+
/// @access private
|
|
94
|
+
@mixin button-font-size($size) {
|
|
95
|
+
@if $size == 'xsmall' {
|
|
96
|
+
--btn-font-size: #{font-size(--dt-font-interactive-xs-size)};
|
|
97
|
+
--btn-line-height: calc(var(--dt-font-interactive-xs-line-height) * 1px);
|
|
98
|
+
--btn-icon-size: 16px;
|
|
99
|
+
--icon-size-override: 16px;
|
|
100
|
+
} @else if $size == 'small-expressive' {
|
|
101
|
+
--btn-font-size: #{font-size(--dt-font-interactive-l-size)};
|
|
102
|
+
--btn-line-height: calc(var(--dt-font-interactive-l-line-height) * 1px);
|
|
103
|
+
--btn-icon-size: 20px;
|
|
104
|
+
--icon-size-override: 20px;
|
|
105
|
+
} @else if $size == 'small-productive' {
|
|
106
|
+
--btn-font-size: #{font-size(--dt-font-interactive-s-size)};
|
|
107
|
+
--btn-line-height: calc(var(--dt-font-interactive-s-line-height) * 1px);
|
|
108
|
+
--btn-icon-size: 20px;
|
|
109
|
+
--icon-size-override: 20px;
|
|
110
|
+
} @else if $size == 'medium' {
|
|
111
|
+
--btn-font-size: #{font-size(--dt-font-interactive-l-size)};
|
|
112
|
+
--btn-line-height: calc(var(--dt-font-interactive-l-line-height) * 1px);
|
|
113
|
+
--btn-icon-size: 24px;
|
|
114
|
+
--icon-size-override: 24px;
|
|
115
|
+
} @else if $size == 'large' {
|
|
116
|
+
--btn-font-size: #{font-size(--dt-font-interactive-l-size)};
|
|
117
|
+
--btn-line-height: calc(var(--dt-font-interactive-l-line-height) * 1px);
|
|
118
|
+
--btn-icon-size: 24px;
|
|
119
|
+
--icon-size-override: 24px;
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
/// Internal mixin for setting padding per size.
|
|
124
|
+
/// @param {String} $size - The size name
|
|
125
|
+
/// @param {Boolean} $offset-padding-for-border [false] - Whether to offset padding by 1px for bordered variants
|
|
126
|
+
/// @access private
|
|
127
|
+
@mixin button-padding($size, $offset-padding-for-border: false) {
|
|
128
|
+
$vertical-padding: '';
|
|
129
|
+
$horizontal-padding: '';
|
|
130
|
+
|
|
131
|
+
@if $size == 'xsmall' {
|
|
132
|
+
$vertical-padding: '--btn-padding-vertical-xsmall';
|
|
133
|
+
$horizontal-padding: '--btn-padding-horizontal-small';
|
|
134
|
+
} @else if $size == 'small-expressive' {
|
|
135
|
+
$vertical-padding: '--btn-padding-vertical-small-expressive';
|
|
136
|
+
$horizontal-padding: '--btn-padding-horizontal-medium';
|
|
137
|
+
} @else if $size == 'small-productive' {
|
|
138
|
+
$vertical-padding: '--btn-padding-vertical-small-productive';
|
|
139
|
+
$horizontal-padding: '--btn-padding-horizontal-medium';
|
|
140
|
+
} @else if $size == 'medium' {
|
|
141
|
+
$vertical-padding: '--btn-padding-vertical-medium';
|
|
142
|
+
$horizontal-padding: '--btn-padding-horizontal-large';
|
|
143
|
+
} @else if $size == 'large' {
|
|
144
|
+
$vertical-padding: '--btn-padding-vertical-large';
|
|
145
|
+
$horizontal-padding: '--btn-padding-horizontal-large';
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
@if $offset-padding-for-border {
|
|
149
|
+
padding: calc(var(#{$vertical-padding}) - 1px) var(#{$horizontal-padding});
|
|
150
|
+
} @else {
|
|
151
|
+
padding: var(#{$vertical-padding}) var(#{$horizontal-padding});
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
/// Mixin for responsive behaviour.
|
|
156
|
+
/// When the responsive modifier class is present and viewport is >md, applies the content.
|
|
157
|
+
/// @param {String} $prefix ['c-button'] - The class prefix for modifier selectors
|
|
158
|
+
/// @access private
|
|
159
|
+
@mixin responsive-wide($prefix: 'c-button') {
|
|
160
|
+
&.#{$prefix}--responsive {
|
|
161
|
+
@include media('>md') {
|
|
162
|
+
@content;
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
/// Size mixin that sets font-size, line-height, padding, icon size and responsive behaviour.
|
|
168
|
+
/// @param {String} $size - One of: xsmall, small-productive, small-expressive, medium, large
|
|
169
|
+
/// @param {String} $prefix ['c-button'] - The class prefix for modifier selectors
|
|
170
|
+
/// @example scss - Basic usage
|
|
171
|
+
/// .my-button--medium {
|
|
172
|
+
/// @include button-size('medium');
|
|
173
|
+
/// }
|
|
174
|
+
@mixin button-size($size, $prefix: 'c-button') {
|
|
175
|
+
@include button-font-size($size);
|
|
176
|
+
@include button-padding($size);
|
|
177
|
+
|
|
178
|
+
@if $size == 'xsmall' {
|
|
179
|
+
@include responsive-wide($prefix) {
|
|
180
|
+
// productive is the default responsive size
|
|
181
|
+
@include button-font-size('small-productive');
|
|
182
|
+
@include button-padding('small-productive');
|
|
183
|
+
|
|
184
|
+
&.#{$prefix}--expressive {
|
|
185
|
+
@include button-font-size('small-expressive');
|
|
186
|
+
@include button-padding('small-expressive');
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
&.#{$prefix}--outline,
|
|
191
|
+
&.#{$prefix}--outline-inverse {
|
|
192
|
+
@include button-padding('xsmall', true);
|
|
193
|
+
|
|
194
|
+
@include responsive-wide($prefix) {
|
|
195
|
+
@include button-padding('small-productive', true);
|
|
196
|
+
|
|
197
|
+
&.#{$prefix}--expressive {
|
|
198
|
+
@include button-padding('small-expressive', true);
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
} @else if $size == 'small-expressive' {
|
|
203
|
+
@include responsive-wide($prefix) {
|
|
204
|
+
@include button-font-size('medium');
|
|
205
|
+
@include button-padding('medium');
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
&.#{$prefix}--outline,
|
|
209
|
+
&.#{$prefix}--outline-inverse {
|
|
210
|
+
@include button-padding('small-expressive', true);
|
|
211
|
+
|
|
212
|
+
@include responsive-wide($prefix) {
|
|
213
|
+
@include button-padding('medium', true);
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
} @else if $size == 'small-productive' {
|
|
217
|
+
@include responsive-wide($prefix) {
|
|
218
|
+
@include button-font-size('medium');
|
|
219
|
+
@include button-padding('medium');
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
&.#{$prefix}--outline,
|
|
223
|
+
&.#{$prefix}--outline-inverse {
|
|
224
|
+
@include button-padding('small-productive', true);
|
|
225
|
+
|
|
226
|
+
@include responsive-wide($prefix) {
|
|
227
|
+
@include button-padding('medium', true);
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
} @else if $size == 'medium' {
|
|
231
|
+
@include responsive-wide($prefix) {
|
|
232
|
+
@include button-font-size('large');
|
|
233
|
+
@include button-padding('large');
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
&.#{$prefix}--outline,
|
|
237
|
+
&.#{$prefix}--outline-inverse {
|
|
238
|
+
@include button-padding('medium', true);
|
|
239
|
+
|
|
240
|
+
@include responsive-wide($prefix) {
|
|
241
|
+
@include button-padding('large', true);
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
} @else if $size == 'large' {
|
|
245
|
+
&.#{$prefix}--outline,
|
|
246
|
+
&.#{$prefix}--outline-inverse {
|
|
247
|
+
@include button-padding('large', true);
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
// ============================================================================
|
|
253
|
+
// Button Variants
|
|
254
|
+
// ============================================================================
|
|
255
|
+
|
|
256
|
+
/// Variant mixin that sets background colour, text colour and interactive states.
|
|
257
|
+
/// @param {String} $variant - One of: primary, primary-alternative, primary-alternative-dark,
|
|
258
|
+
/// secondary, outline, ghost, ghost-dark, inverse, ghost-inverse, outline-inverse,
|
|
259
|
+
/// ghost-inverse-light, destructive, destructive-ghost
|
|
260
|
+
/// @param {String} $prefix ['c-button'] - The class prefix for modifier selectors
|
|
261
|
+
/// @example scss - Basic usage
|
|
262
|
+
/// .my-button--primary {
|
|
263
|
+
/// @include button-variant('primary');
|
|
264
|
+
/// }
|
|
265
|
+
@mixin button-variant($variant, $prefix: 'c-button') {
|
|
266
|
+
@if $variant == 'primary' {
|
|
267
|
+
@include interactive-states('--dt-color-interactive-brand');
|
|
268
|
+
|
|
269
|
+
// Where the font-size is smaller, update the button backgrounds
|
|
270
|
+
// so that the text is accessible
|
|
271
|
+
&.#{$prefix}--xsmall,
|
|
272
|
+
&.#{$prefix}--small-productive {
|
|
273
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-primary);
|
|
274
|
+
--btn-text-color: var(--dt-color-content-interactive-primary-solid);
|
|
275
|
+
|
|
276
|
+
@include interactive-states('--dt-color-interactive-primary', 'inverse', '02');
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
// Handle the background colour change getting overridden above
|
|
280
|
+
// but then being put in responsive mode
|
|
281
|
+
&.#{$prefix}--xsmall.#{$prefix}--expressive,
|
|
282
|
+
&.#{$prefix}--small-productive {
|
|
283
|
+
@include responsive-wide($prefix) {
|
|
284
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-brand);
|
|
285
|
+
|
|
286
|
+
@include interactive-states('--dt-color-interactive-brand');
|
|
287
|
+
}
|
|
288
|
+
}
|
|
289
|
+
} @else if $variant == 'primary-alternative' {
|
|
290
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-primary);
|
|
291
|
+
--btn-text-color: var(--dt-color-content-interactive-primary);
|
|
292
|
+
|
|
293
|
+
@include interactive-states('--dt-color-interactive-primary', 'inverse', '02');
|
|
294
|
+
} @else if $variant == 'primary-alternative-dark' {
|
|
295
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-dark);
|
|
296
|
+
--btn-text-color: var(--dt-color-content-interactive-light);
|
|
297
|
+
|
|
298
|
+
@include interactive-states('--dt-color-interactive-dark', 'inverse', '02');
|
|
299
|
+
} @else if $variant == 'secondary' {
|
|
300
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-secondary);
|
|
301
|
+
--btn-text-color: var(--dt-color-content-interactive-secondary);
|
|
302
|
+
|
|
303
|
+
@include interactive-states('--dt-color-interactive-secondary');
|
|
304
|
+
} @else if $variant == 'outline' {
|
|
305
|
+
--int-states-mixin-bg-color: transparent;
|
|
306
|
+
--btn-text-color: var(--dt-color-content-interactive-secondary-solid);
|
|
307
|
+
|
|
308
|
+
border: 1px solid var(--dt-color-border-strong);
|
|
309
|
+
|
|
310
|
+
@include interactive-states('--dt-color-transparent', 'transparent', '01');
|
|
311
|
+
} @else if $variant == 'ghost' {
|
|
312
|
+
--int-states-mixin-bg-color: transparent;
|
|
313
|
+
--btn-text-color: var(--dt-color-content-interactive-secondary-solid);
|
|
314
|
+
|
|
315
|
+
@include interactive-states('--dt-color-transparent', 'transparent', '01');
|
|
316
|
+
} @else if $variant == 'ghost-dark' {
|
|
317
|
+
--int-states-mixin-bg-color: transparent;
|
|
318
|
+
--btn-text-color: var(--dt-color-content-interactive-dark-solid);
|
|
319
|
+
|
|
320
|
+
@include interactive-states('--dt-color-transparent', 'transparent', '01');
|
|
321
|
+
} @else if $variant == 'inverse' {
|
|
322
|
+
--int-states-mixin-bg-color: var(--dt-color-interactive-inverse);
|
|
323
|
+
--btn-text-color: var(--dt-color-content-interactive-secondary);
|
|
324
|
+
|
|
325
|
+
@include interactive-states('--dt-color-interactive-inverse');
|
|
326
|
+
} @else if $variant == 'ghost-inverse' {
|
|
327
|
+
--int-states-mixin-bg-color: transparent;
|
|
328
|
+
--btn-text-color: var(--dt-color-content-interactive-primary-solid);
|
|
329
|
+
|
|
330
|
+
@include interactive-states('--dt-color-transparent', 'transparent-inverse', '02');
|
|
331
|
+
} @else if $variant == 'outline-inverse' {
|
|
332
|
+
--int-states-mixin-bg-color: transparent;
|
|
333
|
+
--btn-text-color: var(--dt-color-content-interactive-primary-solid);
|
|
334
|
+
|
|
335
|
+
border: 1px solid var(--dt-color-border-strong);
|
|
336
|
+
|
|
337
|
+
@include interactive-states('--dt-color-transparent', 'transparent-inverse', '02');
|
|
338
|
+
} @else if $variant == 'ghost-inverse-light' {
|
|
339
|
+
--int-states-mixin-bg-color: transparent;
|
|
340
|
+
--btn-text-color: var(--dt-color-content-interactive-light-solid);
|
|
341
|
+
|
|
342
|
+
@include interactive-states('--dt-color-transparent', 'transparent-inverse', '02');
|
|
343
|
+
} @else if $variant == 'destructive' {
|
|
344
|
+
--int-states-mixin-bg-color: var(--dt-color-support-error);
|
|
345
|
+
|
|
346
|
+
@include interactive-states('--dt-color-support-error');
|
|
347
|
+
} @else if $variant == 'destructive-ghost' {
|
|
348
|
+
--int-states-mixin-bg-color: transparent;
|
|
349
|
+
--btn-text-color: var(--dt-color-content-interactive-error-solid);
|
|
350
|
+
|
|
351
|
+
@include interactive-states('--dt-color-transparent', 'transparent', '01');
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
// ============================================================================
|
|
356
|
+
// Button Disabled
|
|
357
|
+
// ============================================================================
|
|
358
|
+
|
|
359
|
+
/// Disabled state modifier that overrides colours and cursor.
|
|
360
|
+
/// @param {String} $prefix ['c-button'] - The class prefix for modifier selectors.
|
|
361
|
+
/// For pie-button, pass 'o-btn'.
|
|
362
|
+
/// @param {Boolean} $include-pointer-events [true] - Whether to set `pointer-events: none`.
|
|
363
|
+
/// Set to `false` for pie-button which uses the native `[disabled]` attribute instead.
|
|
364
|
+
/// @example scss - Basic usage
|
|
365
|
+
/// .my-button--disabled {
|
|
366
|
+
/// @include button-disabled();
|
|
367
|
+
/// }
|
|
368
|
+
@mixin button-disabled($prefix: 'c-button', $include-pointer-events: true) {
|
|
369
|
+
--btn-text-color: var(--dt-color-content-disabled-solid);
|
|
370
|
+
|
|
371
|
+
cursor: not-allowed;
|
|
372
|
+
|
|
373
|
+
@if $include-pointer-events {
|
|
374
|
+
pointer-events: none;
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
// For every variant except ghost variants, set the disabled background colour
|
|
378
|
+
&:not(
|
|
379
|
+
.#{$prefix}--ghost,
|
|
380
|
+
.#{$prefix}--ghost-dark,
|
|
381
|
+
.#{$prefix}--ghost-inverse,
|
|
382
|
+
.#{$prefix}--ghost-inverse-light,
|
|
383
|
+
.#{$prefix}--destructive-ghost
|
|
384
|
+
) {
|
|
385
|
+
--int-states-mixin-bg-color: var(--dt-color-disabled-01);
|
|
386
|
+
--btn-text-color: var(--dt-color-content-disabled);
|
|
387
|
+
}
|
|
388
|
+
|
|
389
|
+
// For outline variants, set the border to the disabled colour
|
|
390
|
+
&.#{$prefix}--outline,
|
|
391
|
+
&.#{$prefix}--outline-inverse {
|
|
392
|
+
border-color: var(--dt-color-disabled-01);
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
|
|
396
|
+
// ============================================================================
|
|
397
|
+
// Button Full Width
|
|
398
|
+
// ============================================================================
|
|
399
|
+
|
|
400
|
+
/// Full-width modifier that makes the button span 100% of its container.
|
|
401
|
+
/// @example scss - Basic usage
|
|
402
|
+
/// .my-button--fullWidth {
|
|
403
|
+
/// @include button-full-width();
|
|
404
|
+
/// }
|
|
405
|
+
@mixin button-full-width() {
|
|
406
|
+
--btn-inline-size: 100%;
|
|
407
|
+
}
|
|
408
|
+
|
|
409
|
+
// ============================================================================
|
|
410
|
+
// Button Truncate
|
|
411
|
+
// ============================================================================
|
|
412
|
+
|
|
413
|
+
/// Optional modifier that truncates the button label with an ellipsis when the
|
|
414
|
+
/// text overflows the button's width. This only takes effect when the button's
|
|
415
|
+
/// width is constrained externally (e.g. via `button-full-width` inside a sized
|
|
416
|
+
/// container, or a `max-width` on a parent element).
|
|
417
|
+
///
|
|
418
|
+
/// The `> span` selector is required because `text-overflow: ellipsis` does not
|
|
419
|
+
/// work directly on flex containers. The label must be wrapped in a `<span>`.
|
|
420
|
+
///
|
|
421
|
+
/// `white-space: nowrap` is required because, unlike pie-button (which has a
|
|
422
|
+
/// shadow DOM host set to inline-block that constrains the inner flex container),
|
|
423
|
+
/// the CSS-only button IS the flex container with no outer wrapper.
|
|
424
|
+
/// @example scss - Basic usage
|
|
425
|
+
/// .my-button--truncate {
|
|
426
|
+
/// @include button-truncate();
|
|
427
|
+
/// }
|
|
428
|
+
@mixin button-truncate() {
|
|
429
|
+
> span {
|
|
430
|
+
text-overflow: ellipsis;
|
|
431
|
+
overflow: hidden;
|
|
432
|
+
white-space: nowrap;
|
|
433
|
+
}
|
|
434
|
+
}
|