-
Notifications
You must be signed in to change notification settings - Fork 13.4k
Expand file tree
/
Copy pathcore.ionic.scss
More file actions
393 lines (334 loc) · 11.2 KB
/
core.ionic.scss
File metadata and controls
393 lines (334 loc) · 11.2 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
@use "../../themes/ionic/ionic.globals.scss" as globals;
// Ionic Global Styles
// --------------------------------------------------
:root {
/**
* Set the theme colors from the
* `ionic.theme.default.scss` file.
*/
@include globals.set-theme-colors(globals.$ionic-colors);
@include globals.generate-color-variables();
@each $color-name, $value in globals.$ionic-colors {
.ion-color-#{$color-name} {
@include globals.generate-color($color-name);
}
}
/* Default background color of all components to default background surface token */
--background: #{globals.$ion-bg-surface-default};
}
html {
--ion-dynamic-font: -apple-system-body;
}
body {
background: var(--ion-background-color, #{globals.$ion-bg-body});
color: var(--ion-text-color, #{globals.$ion-text-default});
}
body.backdrop-no-scroll {
overflow: hidden;
}
// Modal - Card Style
// --------------------------------------------------
html.ionic ion-modal ion-header {
box-shadow: none;
}
/**
* Modals need additional padding on the
* top of the header. We accomplish this by targeting
* the first toolbar in the header.
* Footer also needs this. We do not adjust the bottom
* padding though because of the safe area.
*/
html.ionic ion-modal.modal-card ion-header ion-toolbar:first-of-type,
html.ionic ion-modal.modal-sheet ion-header ion-toolbar:first-of-type,
html.ionic ion-modal ion-footer ion-toolbar:first-of-type,
html.ionic ion-footer.modal-footer-moving ion-toolbar:first-of-type {
padding-top: globals.$ion-space-400;
}
/**
* Modals need additional padding on the
* bottom of the header. We accomplish this by targeting
* the last toolbar in the header.
*/
html.ionic ion-modal.modal-card ion-header ion-toolbar:last-of-type,
html.ionic ion-modal.modal-sheet ion-header ion-toolbar:last-of-type,
html.ionic ion-modal ion-footer ion-toolbar:last-of-type {
padding-bottom: globals.$ion-space-400;
}
/**
* Add padding on the left and right
* of toolbars while accounting for
* safe area values when in landscape.
*/
html.ionic ion-modal ion-toolbar,
html.ionic .modal-footer-moving ion-toolbar {
padding-right: calc(var(--ion-safe-area-right) + #{globals.$ion-space-400});
padding-left: calc(var(--ion-safe-area-left) + #{globals.$ion-space-400});
}
/**
* Add padding to the left, right, and bottom of `ion-content`
* within a modal.
*/
html.ionic ion-modal.modal-sheet ion-content {
--padding-start: #{globals.$ion-space-400};
--padding-end: #{globals.$ion-space-400};
--padding-bottom: #{globals.$ion-space-400};
}
/**
* Card style modal on iPadOS
* should only have backdrop on first instance.
*/
@media screen and (min-width: 768px) {
html.ionic ion-modal.modal-card:first-of-type {
--backdrop-opacity: 0.18;
}
}
/**
* Subsequent modals should not have a backdrop/box shadow
* as it will cause the screen to appear to get progressively
* darker. With Ionic 6, declarative modals made it
* possible to have multiple non-presented modals in the DOM,
* so we could no longer rely on ion-modal:first-of-type.
* Here we disable the opacity/box-shadow for every modal
* that comes after the first presented modal.
*
* Note: ion-modal:not(.overlay-hidden):first-of-type
* does not match the first modal to not have
* the .overlay-hidden class, it will match the
* first modal in general only if it does not
* have the .overlay-hidden class.
* The :nth-child() pseudo-class has support
* for selectors which would help us here. At the
* time of writing it does not have great cross browser
* support.
*
* Note 2: This should only apply to non-card and
* non-sheet modals. Card and sheet modals have their
* own criteria for displaying backdrops/box shadows.
*
* Do not use :not(.overlay-hidden) in place of
* .show-modal because that triggers a memory
* leak in Blink: https://bugs.chromium.org/p/chromium/issues/detail?id=1418768
*/
ion-modal.modal-default.show-modal ~ ion-modal.modal-default {
--backdrop-opacity: 0;
--box-shadow: none;
}
/**
* This works around a bug in WebKit where the
* content will overflow outside of the bottom border
* radius when re-painting. As long as a single
* border radius value is set on .ion-page, this
* issue does not happen. We set the top left radius
* here because the top left corner will always have a
* radius no matter the platform.
* This behavior only applies to card modals.
*/
html.ionic ion-modal.modal-card .ion-page {
border-top-left-radius: var(--border-radius);
}
// Page Container Structure
// --------------------------------------------------
.ion-page {
@include globals.position(0, 0, 0, 0);
display: flex;
position: absolute;
flex-direction: column;
justify-content: space-between;
contain: layout size style;
z-index: 0;
}
/**
* When making custom dialogs, using
* ion-content is not required. As a result,
* some developers may wish to have dialogs
* that are automatically sized by the browser.
* These changes allow certain dimension values
* such as fit-content to work correctly.
*/
ion-modal > .ion-page {
position: relative;
height: 100%;
contain: layout style;
}
.split-pane-visible > .ion-page.split-pane-main {
position: relative;
}
ion-route,
ion-route-redirect,
ion-router,
ion-select-option,
ion-nav-controller,
ion-menu-controller,
ion-action-sheet-controller,
ion-alert-controller,
ion-loading-controller,
ion-modal-controller,
ion-picker-controller,
ion-popover-controller,
ion-toast-controller,
.ion-page-hidden {
/* stylelint-disable-next-line declaration-no-important */
display: none !important;
}
.ion-page-invisible {
opacity: 0;
}
.can-go-back > ion-header ion-back-button {
display: block;
}
// Ionic Safe Margins
// --------------------------------------------------
html.plt-ios.plt-hybrid,
html.plt-ios.plt-pwa {
--ion-statusbar-padding: #{globals.$ion-space-500};
}
@supports (padding-top: 20px) {
html {
--ion-safe-area-top: var(--ion-statusbar-padding);
}
}
@supports (padding-top: env(safe-area-inset-top)) {
html {
// `--safe-area-inset-*` are set by Capacitor
// @see https://capacitorjs.com/docs/apis/system-bars#android-note
--ion-safe-area-top: var(--safe-area-inset-top, env(safe-area-inset-top));
--ion-safe-area-bottom: var(--safe-area-inset-bottom, env(safe-area-inset-bottom));
--ion-safe-area-left: var(--safe-area-inset-left, env(safe-area-inset-left));
--ion-safe-area-right: var(--safe-area-inset-right, env(safe-area-inset-right));
}
}
// Global Card Styles
// --------------------------------------------------
ion-card.ion-color .ion-inherit-color,
ion-card-header.ion-color .ion-inherit-color {
color: inherit;
}
ion-card-header + ion-card-content {
padding-top: 0;
}
// Menu Styles
// --------------------------------------------------
.menu-content {
transform: translate3d(0, 0, 0);
}
.menu-content-open {
cursor: pointer;
touch-action: manipulation;
/**
* The containing element itself should be clickable but
* everything inside of it should not clickable when menu is open
*
* Setting pointer-events after scrolling has already started
* will not cancel scrolling which is why we also set
* overflow-y below.
*/
pointer-events: none;
/**
* This accounts for scenarios where the main content itself
* is scrollable.
*/
overflow-y: hidden;
}
/**
* Setting overflow cancels any in-progress scrolling
* when the menu opens. This prevents users from accidentally
* scrolling the main content while also dragging the menu open.
* The code below accounts for both ion-content and then custom
* scroll containers within ion-content (such as virtual scroll)
*/
.menu-content-open ion-content {
--overflow: hidden;
}
.menu-content-open .ion-content-scroll-host {
overflow: hidden;
}
.menu-content-reveal {
box-shadow: #{globals.$ion-elevation-1};
}
.menu-content-push {
box-shadow: #{globals.$ion-elevation-1};
}
// Accordion Styles
// --------------------------------------------------
// The toggle icon is nested in the accordion item so we need to
// style it from a global level.
ion-accordion > [slot="header"] .ion-accordion-toggle-icon {
color: globals.$ion-icon-default;
font-size: globals.$ion-scale-600;
}
ion-accordion.accordion-animated > [slot="header"] .ion-accordion-toggle-icon {
transition: globals.$ion-transition-time-300 transform globals.$ion-transition-curve-quick;
}
@media (prefers-reduced-motion: reduce) {
ion-accordion .ion-accordion-toggle-icon {
/* stylelint-disable declaration-no-important */
transition: none !important;
}
}
/**
* The > [slot="header"] selector ensures that we do
* not modify toggle icons for any nested accordions. The state
* of one accordion should not affect any accordions inside
* of a nested accordion group.
*/
ion-accordion.accordion-expanding > [slot="header"] .ion-accordion-toggle-icon,
ion-accordion.accordion-expanded > [slot="header"] .ion-accordion-toggle-icon {
transform: rotate(180deg);
}
// Items inside of an accordion should have reduced padding
// due to the padding added to the accordion content.
ion-accordion > [slot="content"] ion-item {
@include globals.typography(globals.$ion-body-md-regular);
color: globals.$ion-primitives-neutral-1000;
--padding-top: #{globals.$ion-space-300};
--padding-bottom: #{globals.$ion-space-300};
--min-height: #{globals.$ion-scale-700};
}
ion-accordion > [slot="content"] ion-item:not([slot="header"]) {
--padding-start: 0;
--padding-end: 0;
}
// Datetime Styles
// --------------------------------------------------
// Safari/iOS 15 changes the appearance of input[type="date"].
// For backwards compatibility from Ionic 5/Safari 14 designs,
// we override the appearance only when using within an ion-input.
ion-input input::-webkit-date-and-time-value {
text-align: start;
}
/**
* The .ion-datetime-button-overlay class contains
* styles that allow any modal/popover to be
* sized according to the dimensions of the datetime
* when used with ion-datetime-button.
*/
.ion-datetime-button-overlay {
--width: fit-content;
--height: fit-content;
}
/**
* The grid variant can scale down when inline.
* When used in a `fit-content` overlay, this causes
* the overlay to shrink when the month/year picker is open.
* Explicitly setting the dimensions lets us have a consistently
* sized grid interface.
*/
.ion-datetime-button-overlay ion-datetime.datetime-grid {
width: calc(#{globals.$ion-scale-7400} + #{globals.$ion-space-600});
min-height: calc(#{globals.$ion-scale-7400} + #{globals.$ion-space-600});
}
// Popover Styles
// --------------------------------------------------
/**
* If a popover has a child ion-content (or class equivalent) then the .popover-viewport element
* should not be scrollable to ensure the inner content does scroll. However, if the popover
* does not have a child ion-content (or class equivalent) then the .popover-viewport element
* should remain scrollable. This code exists globally because popover targets
* .popover-viewport using ::slotted which only supports simple selectors.
*
* Note that we do not need to account for .ion-content-scroll-host here because that
* class should always be placed within ion-content even if ion-content is not scrollable.
*/
.popover-viewport:has(> ion-content) {
overflow: hidden;
}