diff --git a/src/dev-app/theme/theme-demo.html b/src/dev-app/theme/theme-demo.html
index 008ca1f8b68a..2ea1c66c3b4c 100644
--- a/src/dev-app/theme/theme-demo.html
+++ b/src/dev-app/theme/theme-demo.html
@@ -229,3 +229,11 @@
Elevation
box-shadow: var(--mat-app-level{{level}})
}
+
+Overrides
+
+
+ This container has several system variables applied and includes the
+ mat.theme-overrides mixin
+ to change their values from the existing theme.
+
diff --git a/src/dev-app/theme/theme-demo.scss b/src/dev-app/theme/theme-demo.scss
index 7d94e2bde30e..cb3a320dc129 100644
--- a/src/dev-app/theme/theme-demo.scss
+++ b/src/dev-app/theme/theme-demo.scss
@@ -1,4 +1,4 @@
-@use '@angular/material';
+@use '@angular/material' as mat;
:host {
display: block;
@@ -82,7 +82,8 @@ a {
.demo-surface-variable {
display: inline-block;
font-family: monospace;
- background: var(--mat-app-surface-dim);
+ background: var(--mat-app-primary-container);
+ color: var(--mat-app-on-primary-container);
padding: 2px 6px;
margin: 0 2px;
border-radius: 4px;
@@ -91,7 +92,7 @@ a {
mat-expansion-panel {
margin-top: 24px;
overflow: visible;
- @include material.expansion-overrides((
+ @include mat.expansion-overrides((
'container-text-font': var(--mat-app-body-medium-font),
'container-text-size': var(--mat-app-body-medium-size),
'container-text-weight': var(--mat-app-body-medium-weight),
@@ -165,6 +166,9 @@ mat-expansion-panel {
display: flex;
align-items: center;
justify-content: center;
+ background: var(--mat-app-surface-container);
+ color: var(--mat-app-on-surface);
+ border-radius: var(--mat-app-corner-extra-small);
}
.demo-code-block {
@@ -173,3 +177,20 @@ mat-expansion-panel {
border-radius: var(--mat-app-corner-small);
border: 1px solid var(--mat-app-outline);
}
+
+.demo-overrides {
+ background-color: var(--mat-app-primary);
+ color: var(--mat-app-on-primary);
+ font: var(--mat-app-body-medium);
+ border-radius: var(--mat-app-corner-large);
+ box-shadow: var(--mat-app-level3);
+ padding: 16px;
+
+ @include mat.theme-overrides((
+ primary: #ebdcff,
+ on-primary: #230f46,
+ body-medium: 600 1.5rem / 2.25rem Arial,
+ corner-large: 32px,
+ level3: 0 4px 6px 1px var(--mat-app-surface-dim),
+ ));
+}
diff --git a/src/material/_index.scss b/src/material/_index.scss
index 3278a881b836..91e90ff18ba9 100644
--- a/src/material/_index.scss
+++ b/src/material/_index.scss
@@ -20,7 +20,7 @@
@forward './core/tokens/m2' show m2-tokens-from-theme;
@forward './core/tokens/m3-system' show system-level-colors,
system-level-typography, system-level-elevation, system-level-shape,
- system-level-motion, system-level-state, theme;
+ system-level-motion, system-level-state, theme, theme-overrides;
// Private/Internal
@forward './core/density/private/all-density' show all-component-densities;
diff --git a/src/material/core/tokens/_m3-system.scss b/src/material/core/tokens/_m3-system.scss
index d3768927874a..70d874aaa94f 100644
--- a/src/material/core/tokens/_m3-system.scss
+++ b/src/material/core/tokens/_m3-system.scss
@@ -84,6 +84,25 @@ $_system-level-prefix: sys;
@include system-level-state($overrides: $overrides, $prefix: $_system-fallback-prefix);
}
+/// Emits the system-level CSS variables for each of the provided override values. E.g. to
+/// change the primary color to red, use `mat.theme-overrides((primary: red));`
+@mixin theme-overrides($overrides, $prefix: $_system-fallback-prefix) {
+ $sys-names: map-merge-all(
+ definitions.md-sys-color-values-light(),
+ definitions.md-sys-typescale-values(),
+ definitions.md-sys-elevation-values(),
+ definitions.md-sys-shape-values(),
+ definitions.md-sys-state-values());
+
+ & {
+ @each $name, $value in $overrides {
+ @if (map.has-key($sys-names, $name)) {
+ --#{$prefix}-#{$name}: #{map.get($overrides, $name)};
+ }
+ }
+ }
+}
+
@mixin system-level-colors($theme, $overrides: (), $prefix: null) {
$palettes: map.get($theme, _mat-theming-internals-do-not-access, palettes);
$base-palettes: (
@@ -226,3 +245,12 @@ $_system-level-prefix: sys;
m3-tokens.generate-density-tokens(0)
);
}
+
+/// Creates a single merged map from the provided variable-length map arguments
+@function map-merge-all($maps...) {
+ $result: ();
+ @each $map in $maps {
+ $result: map.merge($result, $map);
+ }
+ @return $result;
+}