1 /*
2 * Copyright 2021 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 package androidx.compose.material3
18
19 import androidx.compose.material3.tokens.ColorDarkTokens
20 import androidx.compose.material3.tokens.ColorLightTokens
21 import androidx.compose.material3.tokens.ColorSchemeKeyTokens
22 import androidx.compose.material3.tokens.PaletteTokens
23 import androidx.compose.runtime.Composable
24 import androidx.compose.runtime.Immutable
25 import androidx.compose.runtime.ReadOnlyComposable
26 import androidx.compose.runtime.Stable
27 import androidx.compose.runtime.staticCompositionLocalOf
28 import androidx.compose.ui.graphics.Color
29 import androidx.compose.ui.graphics.compositeOver
30 import androidx.compose.ui.graphics.takeOrElse
31 import androidx.compose.ui.unit.Dp
32 import androidx.compose.ui.unit.dp
33 import kotlin.math.ln
34
35 /**
36 * A color scheme holds all the named color parameters for a [MaterialTheme].
37 *
38 * Color schemes are designed to be harmonious, ensure accessible text, and distinguish UI elements
39 * and surfaces from one another. There are two built-in baseline schemes, [lightColorScheme] and a
40 * [darkColorScheme], that can be used as-is or customized.
41 *
42 * The Material color system and custom schemes provide default values for color as a starting point
43 * for customization.
44 *
45 * Example of extending color scheme, including implementing Fixed Accent colors:
46 *
47 * @sample androidx.compose.material3.samples.ColorSchemeFixedAccentColorSample
48 *
49 * To learn more about colors, see
50 * [Material Design colors](https://m3.material.io/styles/color/overview).
51 *
52 * @property primary The primary color is the color displayed most frequently across your app’s
53 * screens and components.
54 * @property onPrimary Color used for text and icons displayed on top of the primary color.
55 * @property primaryContainer The preferred tonal color of containers.
56 * @property onPrimaryContainer The color (and state variants) that should be used for content on
57 * top of [primaryContainer].
58 * @property inversePrimary Color to be used as a "primary" color in places where the inverse color
59 * scheme is needed, such as the button on a SnackBar.
60 * @property secondary The secondary color provides more ways to accent and distinguish your
61 * product. Secondary colors are best for:
62 * - Floating action buttons
63 * - Selection controls, like checkboxes and radio buttons
64 * - Highlighting selected text
65 * - Links and headlines
66 *
67 * @property onSecondary Color used for text and icons displayed on top of the secondary color.
68 * @property secondaryContainer A tonal color to be used in containers.
69 * @property onSecondaryContainer The color (and state variants) that should be used for content on
70 * top of [secondaryContainer].
71 * @property tertiary The tertiary color that can be used to balance primary and secondary colors,
72 * or bring heightened attention to an element such as an input field.
73 * @property onTertiary Color used for text and icons displayed on top of the tertiary color.
74 * @property tertiaryContainer A tonal color to be used in containers.
75 * @property onTertiaryContainer The color (and state variants) that should be used for content on
76 * top of [tertiaryContainer].
77 * @property background The background color that appears behind scrollable content.
78 * @property onBackground Color used for text and icons displayed on top of the background color.
79 * @property surface The surface color that affect surfaces of components, such as cards, sheets,
80 * and menus.
81 * @property onSurface Color used for text and icons displayed on top of the surface color.
82 * @property surfaceVariant Another option for a color with similar uses of [surface].
83 * @property onSurfaceVariant The color (and state variants) that can be used for content on top of
84 * [surface].
85 * @property surfaceTint This color will be used by components that apply tonal elevation and is
86 * applied on top of [surface]. The higher the elevation the more this color is used.
87 * @property inverseSurface A color that contrasts sharply with [surface]. Useful for surfaces that
88 * sit on top of other surfaces with [surface] color.
89 * @property inverseOnSurface A color that contrasts well with [inverseSurface]. Useful for content
90 * that sits on top of containers that are [inverseSurface].
91 * @property error The error color is used to indicate errors in components, such as invalid text in
92 * a text field.
93 * @property onError Color used for text and icons displayed on top of the error color.
94 * @property errorContainer The preferred tonal color of error containers.
95 * @property onErrorContainer The color (and state variants) that should be used for content on top
96 * of [errorContainer].
97 * @property outline Subtle color used for boundaries. Outline color role adds contrast for
98 * accessibility purposes.
99 * @property outlineVariant Utility color used for boundaries for decorative elements when strong
100 * contrast is not required.
101 * @property scrim Color of a scrim that obscures content.
102 * @property surfaceBright A [surface] variant that is always brighter than [surface], whether in
103 * light or dark mode.
104 * @property surfaceDim A [surface] variant that is always dimmer than [surface], whether in light
105 * or dark mode.
106 * @property surfaceContainer A [surface] variant that affects containers of components, such as
107 * cards, sheets, and menus.
108 * @property surfaceContainerHigh A [surface] variant for containers with higher emphasis than
109 * [surfaceContainer]. Use this role for content which requires more emphasis than
110 * [surfaceContainer].
111 * @property surfaceContainerHighest A [surface] variant for containers with higher emphasis than
112 * [surfaceContainerHigh]. Use this role for content which requires more emphasis than
113 * [surfaceContainerHigh].
114 * @property surfaceContainerLow A [surface] variant for containers with lower emphasis than
115 * [surfaceContainer]. Use this role for content which requires less emphasis than
116 * [surfaceContainer].
117 * @property surfaceContainerLowest A [surface] variant for containers with lower emphasis than
118 * [surfaceContainerLow]. Use this role for content which requires less emphasis than
119 * [surfaceContainerLow].
120 */
121 @Immutable
122 class ColorScheme(
123 val primary: Color,
124 val onPrimary: Color,
125 val primaryContainer: Color,
126 val onPrimaryContainer: Color,
127 val inversePrimary: Color,
128 val secondary: Color,
129 val onSecondary: Color,
130 val secondaryContainer: Color,
131 val onSecondaryContainer: Color,
132 val tertiary: Color,
133 val onTertiary: Color,
134 val tertiaryContainer: Color,
135 val onTertiaryContainer: Color,
136 val background: Color,
137 val onBackground: Color,
138 val surface: Color,
139 val onSurface: Color,
140 val surfaceVariant: Color,
141 val onSurfaceVariant: Color,
142 val surfaceTint: Color,
143 val inverseSurface: Color,
144 val inverseOnSurface: Color,
145 val error: Color,
146 val onError: Color,
147 val errorContainer: Color,
148 val onErrorContainer: Color,
149 val outline: Color,
150 val outlineVariant: Color,
151 val scrim: Color,
152 val surfaceBright: Color,
153 val surfaceDim: Color,
154 val surfaceContainer: Color,
155 val surfaceContainerHigh: Color,
156 val surfaceContainerHighest: Color,
157 val surfaceContainerLow: Color,
158 val surfaceContainerLowest: Color,
159 ) {
160 @Deprecated(
161 level = DeprecationLevel.WARNING,
162 message = "Use constructor with additional 'surfaceContainer' roles.",
163 replaceWith =
164 ReplaceWith(
165 "ColorScheme(primary,\n" +
166 "onPrimary,\n" +
167 "primaryContainer,\n" +
168 "onPrimaryContainer,\n" +
169 "inversePrimary,\n" +
170 "secondary,\n" +
171 "onSecondary,\n" +
172 "secondaryContainer,\n" +
173 "onSecondaryContainer,\n" +
174 "tertiary,\n" +
175 "onTertiary,\n" +
176 "tertiaryContainer,\n" +
177 "onTertiaryContainer,\n" +
178 "background,\n" +
179 "onBackground,\n" +
180 "surface,\n" +
181 "onSurface,\n" +
182 "surfaceVariant,\n" +
183 "onSurfaceVariant,\n" +
184 "surfaceTint,\n" +
185 "inverseSurface,\n" +
186 "inverseOnSurface,\n" +
187 "error,\n" +
188 "onError,\n" +
189 "errorContainer,\n" +
190 "onErrorContainer,\n" +
191 "outline,\n" +
192 "outlineVariant,\n" +
193 "scrim,\n" +
194 "surfaceBright,\n" +
195 "surfaceDim,\n" +
196 "surfaceContainer,\n" +
197 "surfaceContainerHigh,\n" +
198 "surfaceContainerHighest,\n" +
199 "surfaceContainerLow,\n" +
200 "surfaceContainerLowest,)"
201 )
202 )
203 constructor(
204 primary: Color,
205 onPrimary: Color,
206 primaryContainer: Color,
207 onPrimaryContainer: Color,
208 inversePrimary: Color,
209 secondary: Color,
210 onSecondary: Color,
211 secondaryContainer: Color,
212 onSecondaryContainer: Color,
213 tertiary: Color,
214 onTertiary: Color,
215 tertiaryContainer: Color,
216 onTertiaryContainer: Color,
217 background: Color,
218 onBackground: Color,
219 surface: Color,
220 onSurface: Color,
221 surfaceVariant: Color,
222 onSurfaceVariant: Color,
223 surfaceTint: Color,
224 inverseSurface: Color,
225 inverseOnSurface: Color,
226 error: Color,
227 onError: Color,
228 errorContainer: Color,
229 onErrorContainer: Color,
230 outline: Color,
231 outlineVariant: Color,
232 scrim: Color,
233 ) : this(
234 primary = primary,
235 onPrimary = onPrimary,
236 primaryContainer = primaryContainer,
237 onPrimaryContainer = onPrimaryContainer,
238 inversePrimary = inversePrimary,
239 secondary = secondary,
240 onSecondary = onSecondary,
241 secondaryContainer = secondaryContainer,
242 onSecondaryContainer = onSecondaryContainer,
243 tertiary = tertiary,
244 onTertiary = onTertiary,
245 tertiaryContainer = tertiaryContainer,
246 onTertiaryContainer = onTertiaryContainer,
247 background = background,
248 onBackground = onBackground,
249 surface = surface,
250 onSurface = onSurface,
251 surfaceVariant = surfaceVariant,
252 onSurfaceVariant = onSurfaceVariant,
253 surfaceTint = surfaceTint,
254 inverseSurface = inverseSurface,
255 inverseOnSurface = inverseOnSurface,
256 error = error,
257 onError = onError,
258 errorContainer = errorContainer,
259 onErrorContainer = onErrorContainer,
260 outline = outline,
261 outlineVariant = outlineVariant,
262 scrim = scrim,
263 surfaceBright = Color.Unspecified,
264 surfaceDim = Color.Unspecified,
265 surfaceContainer = Color.Unspecified,
266 surfaceContainerHigh = Color.Unspecified,
267 surfaceContainerHighest = Color.Unspecified,
268 surfaceContainerLow = Color.Unspecified,
269 surfaceContainerLowest = Color.Unspecified,
270 )
271
272 /** Returns a copy of this ColorScheme, optionally overriding some of the values. */
copynull273 fun copy(
274 primary: Color = this.primary,
275 onPrimary: Color = this.onPrimary,
276 primaryContainer: Color = this.primaryContainer,
277 onPrimaryContainer: Color = this.onPrimaryContainer,
278 inversePrimary: Color = this.inversePrimary,
279 secondary: Color = this.secondary,
280 onSecondary: Color = this.onSecondary,
281 secondaryContainer: Color = this.secondaryContainer,
282 onSecondaryContainer: Color = this.onSecondaryContainer,
283 tertiary: Color = this.tertiary,
284 onTertiary: Color = this.onTertiary,
285 tertiaryContainer: Color = this.tertiaryContainer,
286 onTertiaryContainer: Color = this.onTertiaryContainer,
287 background: Color = this.background,
288 onBackground: Color = this.onBackground,
289 surface: Color = this.surface,
290 onSurface: Color = this.onSurface,
291 surfaceVariant: Color = this.surfaceVariant,
292 onSurfaceVariant: Color = this.onSurfaceVariant,
293 surfaceTint: Color = this.surfaceTint,
294 inverseSurface: Color = this.inverseSurface,
295 inverseOnSurface: Color = this.inverseOnSurface,
296 error: Color = this.error,
297 onError: Color = this.onError,
298 errorContainer: Color = this.errorContainer,
299 onErrorContainer: Color = this.onErrorContainer,
300 outline: Color = this.outline,
301 outlineVariant: Color = this.outlineVariant,
302 scrim: Color = this.scrim,
303 surfaceBright: Color = this.surfaceBright,
304 surfaceDim: Color = this.surfaceDim,
305 surfaceContainer: Color = this.surfaceContainer,
306 surfaceContainerHigh: Color = this.surfaceContainerHigh,
307 surfaceContainerHighest: Color = this.surfaceContainerHighest,
308 surfaceContainerLow: Color = this.surfaceContainerLow,
309 surfaceContainerLowest: Color = this.surfaceContainerLowest,
310 ): ColorScheme =
311 ColorScheme(
312 primary = primary,
313 onPrimary = onPrimary,
314 primaryContainer = primaryContainer,
315 onPrimaryContainer = onPrimaryContainer,
316 inversePrimary = inversePrimary,
317 secondary = secondary,
318 onSecondary = onSecondary,
319 secondaryContainer = secondaryContainer,
320 onSecondaryContainer = onSecondaryContainer,
321 tertiary = tertiary,
322 onTertiary = onTertiary,
323 tertiaryContainer = tertiaryContainer,
324 onTertiaryContainer = onTertiaryContainer,
325 background = background,
326 onBackground = onBackground,
327 surface = surface,
328 onSurface = onSurface,
329 surfaceVariant = surfaceVariant,
330 onSurfaceVariant = onSurfaceVariant,
331 surfaceTint = surfaceTint,
332 inverseSurface = inverseSurface,
333 inverseOnSurface = inverseOnSurface,
334 error = error,
335 onError = onError,
336 errorContainer = errorContainer,
337 onErrorContainer = onErrorContainer,
338 outline = outline,
339 outlineVariant = outlineVariant,
340 scrim = scrim,
341 surfaceBright = surfaceBright,
342 surfaceDim = surfaceDim,
343 surfaceContainer = surfaceContainer,
344 surfaceContainerHigh = surfaceContainerHigh,
345 surfaceContainerHighest = surfaceContainerHighest,
346 surfaceContainerLow = surfaceContainerLow,
347 surfaceContainerLowest = surfaceContainerLowest,
348 )
349
350 @Deprecated(
351 message =
352 "Maintained for binary compatibility. Use overload with additional surface roles " +
353 "instead",
354 level = DeprecationLevel.HIDDEN
355 )
356 fun copy(
357 primary: Color = this.primary,
358 onPrimary: Color = this.onPrimary,
359 primaryContainer: Color = this.primaryContainer,
360 onPrimaryContainer: Color = this.onPrimaryContainer,
361 inversePrimary: Color = this.inversePrimary,
362 secondary: Color = this.secondary,
363 onSecondary: Color = this.onSecondary,
364 secondaryContainer: Color = this.secondaryContainer,
365 onSecondaryContainer: Color = this.onSecondaryContainer,
366 tertiary: Color = this.tertiary,
367 onTertiary: Color = this.onTertiary,
368 tertiaryContainer: Color = this.tertiaryContainer,
369 onTertiaryContainer: Color = this.onTertiaryContainer,
370 background: Color = this.background,
371 onBackground: Color = this.onBackground,
372 surface: Color = this.surface,
373 onSurface: Color = this.onSurface,
374 surfaceVariant: Color = this.surfaceVariant,
375 onSurfaceVariant: Color = this.onSurfaceVariant,
376 surfaceTint: Color = this.surfaceTint,
377 inverseSurface: Color = this.inverseSurface,
378 inverseOnSurface: Color = this.inverseOnSurface,
379 error: Color = this.error,
380 onError: Color = this.onError,
381 errorContainer: Color = this.errorContainer,
382 onErrorContainer: Color = this.onErrorContainer,
383 outline: Color = this.outline,
384 outlineVariant: Color = this.outlineVariant,
385 scrim: Color = this.scrim,
386 ): ColorScheme =
387 copy(
388 primary = primary,
389 onPrimary = onPrimary,
390 primaryContainer = primaryContainer,
391 onPrimaryContainer = onPrimaryContainer,
392 inversePrimary = inversePrimary,
393 secondary = secondary,
394 onSecondary = onSecondary,
395 secondaryContainer = secondaryContainer,
396 onSecondaryContainer = onSecondaryContainer,
397 tertiary = tertiary,
398 onTertiary = onTertiary,
399 tertiaryContainer = tertiaryContainer,
400 onTertiaryContainer = onTertiaryContainer,
401 background = background,
402 onBackground = onBackground,
403 surface = surface,
404 onSurface = onSurface,
405 surfaceVariant = surfaceVariant,
406 onSurfaceVariant = onSurfaceVariant,
407 surfaceTint = surfaceTint,
408 inverseSurface = inverseSurface,
409 inverseOnSurface = inverseOnSurface,
410 error = error,
411 onError = onError,
412 errorContainer = errorContainer,
413 onErrorContainer = onErrorContainer,
414 outline = outline,
415 outlineVariant = outlineVariant,
416 scrim = scrim,
417 )
418
419 override fun toString(): String {
420 return "ColorScheme(" +
421 "primary=$primary" +
422 "onPrimary=$onPrimary" +
423 "primaryContainer=$primaryContainer" +
424 "onPrimaryContainer=$onPrimaryContainer" +
425 "inversePrimary=$inversePrimary" +
426 "secondary=$secondary" +
427 "onSecondary=$onSecondary" +
428 "secondaryContainer=$secondaryContainer" +
429 "onSecondaryContainer=$onSecondaryContainer" +
430 "tertiary=$tertiary" +
431 "onTertiary=$onTertiary" +
432 "tertiaryContainer=$tertiaryContainer" +
433 "onTertiaryContainer=$onTertiaryContainer" +
434 "background=$background" +
435 "onBackground=$onBackground" +
436 "surface=$surface" +
437 "onSurface=$onSurface" +
438 "surfaceVariant=$surfaceVariant" +
439 "onSurfaceVariant=$onSurfaceVariant" +
440 "surfaceTint=$surfaceTint" +
441 "inverseSurface=$inverseSurface" +
442 "inverseOnSurface=$inverseOnSurface" +
443 "error=$error" +
444 "onError=$onError" +
445 "errorContainer=$errorContainer" +
446 "onErrorContainer=$onErrorContainer" +
447 "outline=$outline" +
448 "outlineVariant=$outlineVariant" +
449 "scrim=$scrim" +
450 "surfaceBright=$surfaceBright" +
451 "surfaceDim=$surfaceDim" +
452 "surfaceContainer=$surfaceContainer" +
453 "surfaceContainerHigh=$surfaceContainerHigh" +
454 "surfaceContainerHighest=$surfaceContainerHighest" +
455 "surfaceContainerLow=$surfaceContainerLow" +
456 "surfaceContainerLowest=$surfaceContainerLowest" +
457 ")"
458 }
459
460 internal var defaultButtonColorsCached: ButtonColors? = null
461 internal var defaultElevatedButtonColorsCached: ButtonColors? = null
462 internal var defaultFilledTonalButtonColorsCached: ButtonColors? = null
463 internal var defaultOutlinedButtonColorsCached: ButtonColors? = null
464 internal var defaultTextButtonColorsCached: ButtonColors? = null
465
466 internal var defaultCardColorsCached: CardColors? = null
467 internal var defaultElevatedCardColorsCached: CardColors? = null
468 internal var defaultOutlinedCardColorsCached: CardColors? = null
469
470 internal var defaultAssistChipColorsCached: ChipColors? = null
471 internal var defaultElevatedAssistChipColorsCached: ChipColors? = null
472 internal var defaultSuggestionChipColorsCached: ChipColors? = null
473 internal var defaultElevatedSuggestionChipColorsCached: ChipColors? = null
474 internal var defaultFilterChipColorsCached: SelectableChipColors? = null
475 internal var defaultElevatedFilterChipColorsCached: SelectableChipColors? = null
476 internal var defaultInputChipColorsCached: SelectableChipColors? = null
477
478 internal var defaultVerticalDragHandleColorsCached: DragHandleColors? = null
479
480 @OptIn(ExperimentalMaterial3Api::class)
481 internal var defaultTopAppBarColorsCached: TopAppBarColors? = null
482
483 internal var defaultCheckboxColorsCached: CheckboxColors? = null
484
485 @OptIn(ExperimentalMaterial3Api::class)
486 internal var defaultDatePickerColorsCached: DatePickerColors? = null
487
488 internal var defaultIconButtonColorsCached: IconButtonColors? = null
489 internal var defaultIconButtonVibrantColorsCached: IconButtonColors? = null
490 internal var defaultIconToggleButtonColorsCached: IconToggleButtonColors? = null
491 internal var defaultIconToggleButtonVibrantColorsCached: IconToggleButtonColors? = null
492 internal var defaultFilledIconButtonColorsCached: IconButtonColors? = null
493 internal var defaultFilledIconToggleButtonColorsCached: IconToggleButtonColors? = null
494 internal var defaultFilledTonalIconButtonColorsCached: IconButtonColors? = null
495 internal var defaultFilledTonalIconToggleButtonColorsCached: IconToggleButtonColors? = null
496 internal var defaultOutlinedIconButtonColorsCached: IconButtonColors? = null
497 internal var defaultOutlinedIconButtonVibrantColorsCached: IconButtonColors? = null
498 internal var defaultOutlinedIconToggleButtonColorsCached: IconToggleButtonColors? = null
499 internal var defaultOutlinedIconToggleButtonVibrantColorsCached: IconToggleButtonColors? = null
500
501 internal var defaultToggleButtonColorsCached: ToggleButtonColors? = null
502 internal var defaultElevatedToggleButtonColorsCached: ToggleButtonColors? = null
503 internal var defaultTonalToggleButtonColorsCached: ToggleButtonColors? = null
504 internal var defaultOutlinedToggleButtonColorsCached: ToggleButtonColors? = null
505
506 internal var defaultListItemColorsCached: ListItemColors? = null
507
508 internal var defaultMenuItemColorsCached: MenuItemColors? = null
509
510 internal var defaultNavigationBarItemColorsCached: NavigationBarItemColors? = null
511 internal var defaultShortNavigationBarItemColorsCached: NavigationItemColors? = null
512
513 internal var defaultNavigationRailItemColorsCached: NavigationRailItemColors? = null
514 internal var defaultWideWideNavigationRailColorsCached: WideNavigationRailColors? = null
515 internal var defaultWideNavigationRailItemColorsCached: NavigationItemColors? = null
516
517 internal var defaultRadioButtonColorsCached: RadioButtonColors? = null
518
519 internal var defaultSegmentedButtonColorsCached: SegmentedButtonColors? = null
520
521 internal var defaultSliderColorsCached: SliderColors? = null
522
523 internal var defaultSwitchColorsCached: SwitchColors? = null
524
525 internal var defaultOutlinedTextFieldColorsCached: TextFieldColors? = null
526 internal var defaultTextFieldColorsCached: TextFieldColors? = null
527
528 @OptIn(ExperimentalMaterial3Api::class)
529 internal var defaultTimePickerColorsCached: TimePickerColors? = null
530
531 @OptIn(ExperimentalMaterial3Api::class)
532 internal var defaultRichTooltipColorsCached: RichTooltipColors? = null
533
534 @OptIn(ExperimentalMaterial3ExpressiveApi::class)
535 internal var defaultFloatingToolbarStandardColorsCached: FloatingToolbarColors? = null
536 @OptIn(ExperimentalMaterial3ExpressiveApi::class)
537 internal var defaultFloatingToolbarVibrantColorsCached: FloatingToolbarColors? = null
538 }
539
540 /** Returns a light Material color scheme. */
lightColorSchemenull541 fun lightColorScheme(
542 primary: Color = ColorLightTokens.Primary,
543 onPrimary: Color = ColorLightTokens.OnPrimary,
544 primaryContainer: Color = ColorLightTokens.PrimaryContainer,
545 onPrimaryContainer: Color = ColorLightTokens.OnPrimaryContainer,
546 inversePrimary: Color = ColorLightTokens.InversePrimary,
547 secondary: Color = ColorLightTokens.Secondary,
548 onSecondary: Color = ColorLightTokens.OnSecondary,
549 secondaryContainer: Color = ColorLightTokens.SecondaryContainer,
550 onSecondaryContainer: Color = ColorLightTokens.OnSecondaryContainer,
551 tertiary: Color = ColorLightTokens.Tertiary,
552 onTertiary: Color = ColorLightTokens.OnTertiary,
553 tertiaryContainer: Color = ColorLightTokens.TertiaryContainer,
554 onTertiaryContainer: Color = ColorLightTokens.OnTertiaryContainer,
555 background: Color = ColorLightTokens.Background,
556 onBackground: Color = ColorLightTokens.OnBackground,
557 surface: Color = ColorLightTokens.Surface,
558 onSurface: Color = ColorLightTokens.OnSurface,
559 surfaceVariant: Color = ColorLightTokens.SurfaceVariant,
560 onSurfaceVariant: Color = ColorLightTokens.OnSurfaceVariant,
561 surfaceTint: Color = primary,
562 inverseSurface: Color = ColorLightTokens.InverseSurface,
563 inverseOnSurface: Color = ColorLightTokens.InverseOnSurface,
564 error: Color = ColorLightTokens.Error,
565 onError: Color = ColorLightTokens.OnError,
566 errorContainer: Color = ColorLightTokens.ErrorContainer,
567 onErrorContainer: Color = ColorLightTokens.OnErrorContainer,
568 outline: Color = ColorLightTokens.Outline,
569 outlineVariant: Color = ColorLightTokens.OutlineVariant,
570 scrim: Color = ColorLightTokens.Scrim,
571 surfaceBright: Color = ColorLightTokens.SurfaceBright,
572 surfaceContainer: Color = ColorLightTokens.SurfaceContainer,
573 surfaceContainerHigh: Color = ColorLightTokens.SurfaceContainerHigh,
574 surfaceContainerHighest: Color = ColorLightTokens.SurfaceContainerHighest,
575 surfaceContainerLow: Color = ColorLightTokens.SurfaceContainerLow,
576 surfaceContainerLowest: Color = ColorLightTokens.SurfaceContainerLowest,
577 surfaceDim: Color = ColorLightTokens.SurfaceDim,
578 ): ColorScheme =
579 ColorScheme(
580 primary = primary,
581 onPrimary = onPrimary,
582 primaryContainer = primaryContainer,
583 onPrimaryContainer = onPrimaryContainer,
584 inversePrimary = inversePrimary,
585 secondary = secondary,
586 onSecondary = onSecondary,
587 secondaryContainer = secondaryContainer,
588 onSecondaryContainer = onSecondaryContainer,
589 tertiary = tertiary,
590 onTertiary = onTertiary,
591 tertiaryContainer = tertiaryContainer,
592 onTertiaryContainer = onTertiaryContainer,
593 background = background,
594 onBackground = onBackground,
595 surface = surface,
596 onSurface = onSurface,
597 surfaceVariant = surfaceVariant,
598 onSurfaceVariant = onSurfaceVariant,
599 surfaceTint = surfaceTint,
600 inverseSurface = inverseSurface,
601 inverseOnSurface = inverseOnSurface,
602 error = error,
603 onError = onError,
604 errorContainer = errorContainer,
605 onErrorContainer = onErrorContainer,
606 outline = outline,
607 outlineVariant = outlineVariant,
608 scrim = scrim,
609 surfaceBright = surfaceBright,
610 surfaceContainer = surfaceContainer,
611 surfaceContainerHigh = surfaceContainerHigh,
612 surfaceContainerHighest = surfaceContainerHighest,
613 surfaceContainerLow = surfaceContainerLow,
614 surfaceContainerLowest = surfaceContainerLowest,
615 surfaceDim = surfaceDim,
616 )
617
618 @Deprecated(
619 message =
620 "Maintained for binary compatibility. Use overload with additional surface roles instead",
621 level = DeprecationLevel.HIDDEN
622 )
623 fun lightColorScheme(
624 primary: Color = ColorLightTokens.Primary,
625 onPrimary: Color = ColorLightTokens.OnPrimary,
626 primaryContainer: Color = ColorLightTokens.PrimaryContainer,
627 onPrimaryContainer: Color = ColorLightTokens.OnPrimaryContainer,
628 inversePrimary: Color = ColorLightTokens.InversePrimary,
629 secondary: Color = ColorLightTokens.Secondary,
630 onSecondary: Color = ColorLightTokens.OnSecondary,
631 secondaryContainer: Color = ColorLightTokens.SecondaryContainer,
632 onSecondaryContainer: Color = ColorLightTokens.OnSecondaryContainer,
633 tertiary: Color = ColorLightTokens.Tertiary,
634 onTertiary: Color = ColorLightTokens.OnTertiary,
635 tertiaryContainer: Color = ColorLightTokens.TertiaryContainer,
636 onTertiaryContainer: Color = ColorLightTokens.OnTertiaryContainer,
637 background: Color = ColorLightTokens.Background,
638 onBackground: Color = ColorLightTokens.OnBackground,
639 surface: Color = ColorLightTokens.Surface,
640 onSurface: Color = ColorLightTokens.OnSurface,
641 surfaceVariant: Color = ColorLightTokens.SurfaceVariant,
642 onSurfaceVariant: Color = ColorLightTokens.OnSurfaceVariant,
643 surfaceTint: Color = primary,
644 inverseSurface: Color = ColorLightTokens.InverseSurface,
645 inverseOnSurface: Color = ColorLightTokens.InverseOnSurface,
646 error: Color = ColorLightTokens.Error,
647 onError: Color = ColorLightTokens.OnError,
648 errorContainer: Color = ColorLightTokens.ErrorContainer,
649 onErrorContainer: Color = ColorLightTokens.OnErrorContainer,
650 outline: Color = ColorLightTokens.Outline,
651 outlineVariant: Color = ColorLightTokens.OutlineVariant,
652 scrim: Color = ColorLightTokens.Scrim,
653 ): ColorScheme =
654 lightColorScheme(
655 primary = primary,
656 onPrimary = onPrimary,
657 primaryContainer = primaryContainer,
658 onPrimaryContainer = onPrimaryContainer,
659 inversePrimary = inversePrimary,
660 secondary = secondary,
661 onSecondary = onSecondary,
662 secondaryContainer = secondaryContainer,
663 onSecondaryContainer = onSecondaryContainer,
664 tertiary = tertiary,
665 onTertiary = onTertiary,
666 tertiaryContainer = tertiaryContainer,
667 onTertiaryContainer = onTertiaryContainer,
668 background = background,
669 onBackground = onBackground,
670 surface = surface,
671 onSurface = onSurface,
672 surfaceVariant = surfaceVariant,
673 onSurfaceVariant = onSurfaceVariant,
674 surfaceTint = surfaceTint,
675 inverseSurface = inverseSurface,
676 inverseOnSurface = inverseOnSurface,
677 error = error,
678 onError = onError,
679 errorContainer = errorContainer,
680 onErrorContainer = onErrorContainer,
681 outline = outline,
682 outlineVariant = outlineVariant,
683 scrim = scrim,
684 )
685
686 /** Returns a dark Material color scheme. */
687 fun darkColorScheme(
688 primary: Color = ColorDarkTokens.Primary,
689 onPrimary: Color = ColorDarkTokens.OnPrimary,
690 primaryContainer: Color = ColorDarkTokens.PrimaryContainer,
691 onPrimaryContainer: Color = ColorDarkTokens.OnPrimaryContainer,
692 inversePrimary: Color = ColorDarkTokens.InversePrimary,
693 secondary: Color = ColorDarkTokens.Secondary,
694 onSecondary: Color = ColorDarkTokens.OnSecondary,
695 secondaryContainer: Color = ColorDarkTokens.SecondaryContainer,
696 onSecondaryContainer: Color = ColorDarkTokens.OnSecondaryContainer,
697 tertiary: Color = ColorDarkTokens.Tertiary,
698 onTertiary: Color = ColorDarkTokens.OnTertiary,
699 tertiaryContainer: Color = ColorDarkTokens.TertiaryContainer,
700 onTertiaryContainer: Color = ColorDarkTokens.OnTertiaryContainer,
701 background: Color = ColorDarkTokens.Background,
702 onBackground: Color = ColorDarkTokens.OnBackground,
703 surface: Color = ColorDarkTokens.Surface,
704 onSurface: Color = ColorDarkTokens.OnSurface,
705 surfaceVariant: Color = ColorDarkTokens.SurfaceVariant,
706 onSurfaceVariant: Color = ColorDarkTokens.OnSurfaceVariant,
707 surfaceTint: Color = primary,
708 inverseSurface: Color = ColorDarkTokens.InverseSurface,
709 inverseOnSurface: Color = ColorDarkTokens.InverseOnSurface,
710 error: Color = ColorDarkTokens.Error,
711 onError: Color = ColorDarkTokens.OnError,
712 errorContainer: Color = ColorDarkTokens.ErrorContainer,
713 onErrorContainer: Color = ColorDarkTokens.OnErrorContainer,
714 outline: Color = ColorDarkTokens.Outline,
715 outlineVariant: Color = ColorDarkTokens.OutlineVariant,
716 scrim: Color = ColorDarkTokens.Scrim,
717 surfaceBright: Color = ColorDarkTokens.SurfaceBright,
718 surfaceContainer: Color = ColorDarkTokens.SurfaceContainer,
719 surfaceContainerHigh: Color = ColorDarkTokens.SurfaceContainerHigh,
720 surfaceContainerHighest: Color = ColorDarkTokens.SurfaceContainerHighest,
721 surfaceContainerLow: Color = ColorDarkTokens.SurfaceContainerLow,
722 surfaceContainerLowest: Color = ColorDarkTokens.SurfaceContainerLowest,
723 surfaceDim: Color = ColorDarkTokens.SurfaceDim,
724 ): ColorScheme =
725 ColorScheme(
726 primary = primary,
727 onPrimary = onPrimary,
728 primaryContainer = primaryContainer,
729 onPrimaryContainer = onPrimaryContainer,
730 inversePrimary = inversePrimary,
731 secondary = secondary,
732 onSecondary = onSecondary,
733 secondaryContainer = secondaryContainer,
734 onSecondaryContainer = onSecondaryContainer,
735 tertiary = tertiary,
736 onTertiary = onTertiary,
737 tertiaryContainer = tertiaryContainer,
738 onTertiaryContainer = onTertiaryContainer,
739 background = background,
740 onBackground = onBackground,
741 surface = surface,
742 onSurface = onSurface,
743 surfaceVariant = surfaceVariant,
744 onSurfaceVariant = onSurfaceVariant,
745 surfaceTint = surfaceTint,
746 inverseSurface = inverseSurface,
747 inverseOnSurface = inverseOnSurface,
748 error = error,
749 onError = onError,
750 errorContainer = errorContainer,
751 onErrorContainer = onErrorContainer,
752 outline = outline,
753 outlineVariant = outlineVariant,
754 scrim = scrim,
755 surfaceBright = surfaceBright,
756 surfaceContainer = surfaceContainer,
757 surfaceContainerHigh = surfaceContainerHigh,
758 surfaceContainerHighest = surfaceContainerHighest,
759 surfaceContainerLow = surfaceContainerLow,
760 surfaceContainerLowest = surfaceContainerLowest,
761 surfaceDim = surfaceDim,
762 )
763
764 @Deprecated(
765 message =
766 "Maintained for binary compatibility. Use overload with additional surface roles instead",
767 level = DeprecationLevel.HIDDEN
768 )
769 fun darkColorScheme(
770 primary: Color = ColorDarkTokens.Primary,
771 onPrimary: Color = ColorDarkTokens.OnPrimary,
772 primaryContainer: Color = ColorDarkTokens.PrimaryContainer,
773 onPrimaryContainer: Color = ColorDarkTokens.OnPrimaryContainer,
774 inversePrimary: Color = ColorDarkTokens.InversePrimary,
775 secondary: Color = ColorDarkTokens.Secondary,
776 onSecondary: Color = ColorDarkTokens.OnSecondary,
777 secondaryContainer: Color = ColorDarkTokens.SecondaryContainer,
778 onSecondaryContainer: Color = ColorDarkTokens.OnSecondaryContainer,
779 tertiary: Color = ColorDarkTokens.Tertiary,
780 onTertiary: Color = ColorDarkTokens.OnTertiary,
781 tertiaryContainer: Color = ColorDarkTokens.TertiaryContainer,
782 onTertiaryContainer: Color = ColorDarkTokens.OnTertiaryContainer,
783 background: Color = ColorDarkTokens.Background,
784 onBackground: Color = ColorDarkTokens.OnBackground,
785 surface: Color = ColorDarkTokens.Surface,
786 onSurface: Color = ColorDarkTokens.OnSurface,
787 surfaceVariant: Color = ColorDarkTokens.SurfaceVariant,
788 onSurfaceVariant: Color = ColorDarkTokens.OnSurfaceVariant,
789 surfaceTint: Color = primary,
790 inverseSurface: Color = ColorDarkTokens.InverseSurface,
791 inverseOnSurface: Color = ColorDarkTokens.InverseOnSurface,
792 error: Color = ColorDarkTokens.Error,
793 onError: Color = ColorDarkTokens.OnError,
794 errorContainer: Color = ColorDarkTokens.ErrorContainer,
795 onErrorContainer: Color = ColorDarkTokens.OnErrorContainer,
796 outline: Color = ColorDarkTokens.Outline,
797 outlineVariant: Color = ColorDarkTokens.OutlineVariant,
798 scrim: Color = ColorDarkTokens.Scrim,
799 ): ColorScheme =
800 darkColorScheme(
801 primary = primary,
802 onPrimary = onPrimary,
803 primaryContainer = primaryContainer,
804 onPrimaryContainer = onPrimaryContainer,
805 inversePrimary = inversePrimary,
806 secondary = secondary,
807 onSecondary = onSecondary,
808 secondaryContainer = secondaryContainer,
809 onSecondaryContainer = onSecondaryContainer,
810 tertiary = tertiary,
811 onTertiary = onTertiary,
812 tertiaryContainer = tertiaryContainer,
813 onTertiaryContainer = onTertiaryContainer,
814 background = background,
815 onBackground = onBackground,
816 surface = surface,
817 onSurface = onSurface,
818 surfaceVariant = surfaceVariant,
819 onSurfaceVariant = onSurfaceVariant,
820 surfaceTint = surfaceTint,
821 inverseSurface = inverseSurface,
822 inverseOnSurface = inverseOnSurface,
823 error = error,
824 onError = onError,
825 errorContainer = errorContainer,
826 onErrorContainer = onErrorContainer,
827 outline = outline,
828 outlineVariant = outlineVariant,
829 scrim = scrim,
830 )
831
832 /**
833 * The Material color system contains pairs of colors that are typically used for the background and
834 * content color inside a component. For example, a [Button] typically uses `primary` for its
835 * background, and `onPrimary` for the color of its content (usually text or iconography).
836 *
837 * This function tries to match the provided [backgroundColor] to a 'background' color in this
838 * [ColorScheme], and then will return the corresponding color used for content. For example, when
839 * [backgroundColor] is [ColorScheme.primary], this will return [ColorScheme.onPrimary].
840 *
841 * If [backgroundColor] does not match a background color in the theme, this will return
842 * [Color.Unspecified].
843 *
844 * @return the matching content color for [backgroundColor]. If [backgroundColor] is not present in
845 * the theme's [ColorScheme], then returns [Color.Unspecified].
846 * @see contentColorFor
847 */
848 @Stable
849 fun ColorScheme.contentColorFor(backgroundColor: Color): Color =
850 when (backgroundColor) {
851 primary -> onPrimary
852 secondary -> onSecondary
853 tertiary -> onTertiary
854 background -> onBackground
855 error -> onError
856 primaryContainer -> onPrimaryContainer
857 secondaryContainer -> onSecondaryContainer
858 tertiaryContainer -> onTertiaryContainer
859 errorContainer -> onErrorContainer
860 inverseSurface -> inverseOnSurface
861 surface -> onSurface
862 surfaceVariant -> onSurfaceVariant
863 surfaceBright -> onSurface
864 surfaceContainer -> onSurface
865 surfaceContainerHigh -> onSurface
866 surfaceContainerHighest -> onSurface
867 surfaceContainerLow -> onSurface
868 surfaceContainerLowest -> onSurface
869 surfaceDim -> onSurface
870 else -> Color.Unspecified
871 }
872
873 /**
874 * The Material color system contains pairs of colors that are typically used for the background and
875 * content color inside a component. For example, a [Button] typically uses `primary` for its
876 * background, and `onPrimary` for the color of its content (usually text or iconography).
877 *
878 * This function tries to match the provided [backgroundColor] to a 'background' color in this
879 * [ColorScheme], and then will return the corresponding color used for content. For example, when
880 * [backgroundColor] is [ColorScheme.primary], this will return [ColorScheme.onPrimary].
881 *
882 * If [backgroundColor] does not match a background color in the theme, this will return the current
883 * value of [LocalContentColor] as a best-effort color.
884 *
885 * @return the matching content color for [backgroundColor]. If [backgroundColor] is not present in
886 * the theme's [ColorScheme], then returns the current value of [LocalContentColor].
887 * @see ColorScheme.contentColorFor
888 */
889 @Composable
890 @ReadOnlyComposable
contentColorFornull891 fun contentColorFor(backgroundColor: Color) =
892 MaterialTheme.colorScheme.contentColorFor(backgroundColor).takeOrElse {
893 LocalContentColor.current
894 }
895
896 /**
897 * Returns [ColorScheme.surfaceColorAtElevation] with the provided elevation if
898 * [LocalTonalElevationEnabled] is set to true, and the provided background color matches
899 * [ColorScheme.surface]. Otherwise, the provided color is returned unchanged.
900 *
901 * @param backgroundColor The background color to compare to [ColorScheme.surface]
902 * @param elevation The elevation provided to [ColorScheme.surfaceColorAtElevation] if
903 * [backgroundColor] matches surface.
904 * @return [ColorScheme.surfaceColorAtElevation] at [elevation] if [backgroundColor] ==
905 * [ColorScheme.surface] and [LocalTonalElevationEnabled] is set to true. Else [backgroundColor]
906 */
907 @Composable
908 @ReadOnlyComposable
applyTonalElevationnull909 internal fun ColorScheme.applyTonalElevation(backgroundColor: Color, elevation: Dp): Color {
910 val tonalElevationEnabled = LocalTonalElevationEnabled.current
911 return if (backgroundColor == surface && tonalElevationEnabled) {
912 surfaceColorAtElevation(elevation)
913 } else {
914 backgroundColor
915 }
916 }
917
918 /**
919 * Computes the surface tonal color at different elevation levels e.g. surface1 through surface5.
920 *
921 * @param elevation Elevation value used to compute alpha of the color overlay layer.
922 * @return the [ColorScheme.surface] color with an alpha of the [ColorScheme.surfaceTint] color
923 * overlaid on top of it.
924 */
925 @Stable
surfaceColorAtElevationnull926 fun ColorScheme.surfaceColorAtElevation(
927 elevation: Dp,
928 ): Color {
929 if (elevation == 0.dp) return surface
930 val alpha = ((4.5f * ln(elevation.value + 1)) + 2f) / 100f
931 return surfaceTint.copy(alpha = alpha).compositeOver(surface)
932 }
933
934 /**
935 * Returns a light Material color scheme.
936 *
937 * The default color scheme for [MaterialExpressiveTheme]. For dark mode, use [darkColorScheme].
938 *
939 * Example of MaterialExpressiveTheme toggling expressiveLightColorScheme and darkTheme.
940 *
941 * @sample androidx.compose.material3.samples.MaterialExpressiveThemeColorSchemeSample
942 */
943 @ExperimentalMaterial3ExpressiveApi
expressiveLightColorSchemenull944 fun expressiveLightColorScheme() =
945 lightColorScheme(
946 // TODO: Replace palette references with color token references when available.
947 onPrimaryContainer = PaletteTokens.Primary30,
948 onSecondaryContainer = PaletteTokens.Secondary30,
949 onTertiaryContainer = PaletteTokens.Tertiary30,
950 onErrorContainer = PaletteTokens.Error30
951 )
952
953 /**
954 * Helper function for component color tokens. Here is an example on how to use component color
955 * tokens: ``MaterialTheme.colorScheme.fromToken(ExtendedFabBranded.BrandedContainerColor)``
956 */
957 @Stable
958 internal fun ColorScheme.fromToken(value: ColorSchemeKeyTokens): Color {
959 return when (value) {
960 ColorSchemeKeyTokens.Background -> background
961 ColorSchemeKeyTokens.Error -> error
962 ColorSchemeKeyTokens.ErrorContainer -> errorContainer
963 ColorSchemeKeyTokens.InverseOnSurface -> inverseOnSurface
964 ColorSchemeKeyTokens.InversePrimary -> inversePrimary
965 ColorSchemeKeyTokens.InverseSurface -> inverseSurface
966 ColorSchemeKeyTokens.OnBackground -> onBackground
967 ColorSchemeKeyTokens.OnError -> onError
968 ColorSchemeKeyTokens.OnErrorContainer -> onErrorContainer
969 ColorSchemeKeyTokens.OnPrimary -> onPrimary
970 ColorSchemeKeyTokens.OnPrimaryContainer -> onPrimaryContainer
971 ColorSchemeKeyTokens.OnSecondary -> onSecondary
972 ColorSchemeKeyTokens.OnSecondaryContainer -> onSecondaryContainer
973 ColorSchemeKeyTokens.OnSurface -> onSurface
974 ColorSchemeKeyTokens.OnSurfaceVariant -> onSurfaceVariant
975 ColorSchemeKeyTokens.SurfaceTint -> surfaceTint
976 ColorSchemeKeyTokens.OnTertiary -> onTertiary
977 ColorSchemeKeyTokens.OnTertiaryContainer -> onTertiaryContainer
978 ColorSchemeKeyTokens.Outline -> outline
979 ColorSchemeKeyTokens.OutlineVariant -> outlineVariant
980 ColorSchemeKeyTokens.Primary -> primary
981 ColorSchemeKeyTokens.PrimaryContainer -> primaryContainer
982 ColorSchemeKeyTokens.Scrim -> scrim
983 ColorSchemeKeyTokens.Secondary -> secondary
984 ColorSchemeKeyTokens.SecondaryContainer -> secondaryContainer
985 ColorSchemeKeyTokens.Surface -> surface
986 ColorSchemeKeyTokens.SurfaceVariant -> surfaceVariant
987 ColorSchemeKeyTokens.SurfaceBright -> surfaceBright
988 ColorSchemeKeyTokens.SurfaceContainer -> surfaceContainer
989 ColorSchemeKeyTokens.SurfaceContainerHigh -> surfaceContainerHigh
990 ColorSchemeKeyTokens.SurfaceContainerHighest -> surfaceContainerHighest
991 ColorSchemeKeyTokens.SurfaceContainerLow -> surfaceContainerLow
992 ColorSchemeKeyTokens.SurfaceContainerLowest -> surfaceContainerLowest
993 ColorSchemeKeyTokens.SurfaceDim -> surfaceDim
994 ColorSchemeKeyTokens.Tertiary -> tertiary
995 ColorSchemeKeyTokens.TertiaryContainer -> tertiaryContainer
996 else -> Color.Unspecified
997 }
998 }
999
1000 /**
1001 * CompositionLocal used to pass [ColorScheme] down the tree.
1002 *
1003 * Setting the value here is typically done as part of [MaterialTheme]. To retrieve the current
1004 * value of this CompositionLocal, use [MaterialTheme.colorScheme].
1005 */
<lambda>null1006 internal val LocalColorScheme = staticCompositionLocalOf { lightColorScheme() }
1007
1008 /**
1009 * Composition Local used to check if [ColorScheme.applyTonalElevation] will be applied down the
1010 * tree.
1011 *
1012 * Setting this value to false will cause all subsequent surfaces down the tree to not apply
1013 * tonalElevation.
1014 */
<lambda>null1015 val LocalTonalElevationEnabled = staticCompositionLocalOf { true }
1016
1017 /**
1018 * A low level of alpha used to represent disabled components, such as text in a disabled Button.
1019 */
1020 internal const val DisabledAlpha = 0.38f
1021
1022 /**
1023 * Converts a color token key to the local color scheme provided by the theme The color is
1024 * subscribed to [LocalColorScheme] changes.
1025 */
1026 internal val ColorSchemeKeyTokens.value: Color
1027 @ReadOnlyComposable @Composable get() = MaterialTheme.colorScheme.fromToken(this)
1028