Angular Material 3 自定义主题
1. 什么是 Material 3
Material 3 (M3)是 Google 开源设计系统 Material Design 的最新版本。它是 Angular Material 所遵循的设计系统 Material 2 (M2)的继承者。
从 v17.2.0 开始,Angular Material 除了 M2 之外还包括对 M3 样式的实验性支持。该团队计划在短暂的实验后稳定对 M3 的支持,以获得有关设计和 API 的反馈。
2. 如何在您的应用中使用 Material 3
作为许多应用程序已使用的同一组 Angular Material 组件的备用 Sass 主题。要将 M3 与 Angular Material 结合使用,请使用函数@angular/material-experimental 包中的 define-theme 创建主题,而不是 使用 @angular/material 的 define-light-theme 或 define-dark-theme 用于创建 M2 主题。
2.1. 定义您的主题
API 最简单的用法$theme: matx.define-theme()是定义具有默认值的主题。但是,与 M2 对应项一样,define-theme 允许您通过传递主题配置对象,沿着三个主题维度配置 Angular Material 应用程序的外观:颜色、排版和密度。配置对象可以具有以下属性。
属性 | 描述 |
---|---|
color | [可选] 颜色选项。有关详细信息,请参阅自定义颜色。 |
typography | [可选] 颜色选项。有关详细信息,请参阅自定义排版。 |
density | [可选] 密度选项。有关详细信息,请参阅自定义密度。 |
@use "@angular/material-experimental" as matx;
$theme: matx.define-theme(
(
color: (
theme-type: dark,
primary: matx.$m3-violet-palette,
),
typography: (
brand-family: "Comic Sans",
bold-weight: 900,
),
density: (
scale: -1,
),
)
);
2.2. 定制您的颜色
您的应用程序颜色的以下方面可以通过 color 主题配置对象的属性进行自定义(请参阅M3 颜色规范以了解有关这些术语的更多信息):
颜色属性 | 描述 |
---|---|
theme-type | [可选] 指定主题的类型,light 或 dark. |
primary | [可选] 指定用于应用程序主要调色板的调色板。 (注意:M3 规范中描述的辅助调色板、中性调色板和中性变体调色板将根据您的主调色板自动选择,以确保和谐的颜色组合)。 |
tertiary | [可选] 指定用于应用程序的第三调色板的调色板。 |
有许多可用的调色板@angular/material-experimental 可以与 primary 和 tertiary 选项一起使用:
- $m3-red-palette 红色
- $m3-green-palette 绿色
- $m3-blue-palette 蓝色
- $m3-yellow-palette 黄色
- $m3-cyan-palette 青色主题
- $m3-magenta-palette 洋红色
- $m3-orange-palette 橙色
- $m3-chartreuse-palette 浅黄色/浅绿色
- $m3-azure-palette 天蓝色的/蔚蓝色的
- $m3-violet-palette 蓝紫色/紫罗兰色
- $m3-rose-palette 玫红色
2.3. 定制 typography
您的应用程序排版的以下方面可以通过 typography 主题配置对象的属性进行自定义(请参阅 M3 排版规范以了解有关这些术语的更多信息):
版式属性 | 描述 |
---|---|
plain-family | [可选] 用于纯文本(例如正文)的字体系列。 |
brand-family | [可选] 用于品牌文本(例如标题)的字体系列。 |
bold-weight | [可选] 用于粗体文本的字体粗细。 |
medium-weight | [可选] 用于中等文本的字体粗细。 |
regular-weight | [可选] 用于常规文本的字体粗细。 |
2.4. 定制密度
您的应用程序密度的以下方面可以通过 density 主题配置对象的属性进行自定义:
密度特性 | 描述 |
---|---|
scale | [可选] 应用程序中组件的紧凑程度,从 0(最多空间)到-5(最紧凑)。 |
3. 应用主题
创建主题后,您可以使用与应用 M2 相同的-theme、-color、-typography、 density 以及 -base mixin 来应用主题(在主题通用指南中了解有关这些 mixins 的更多信息)。对于 M3 主题,这些 mixins 对生成的样式做出了一些保证。这些保证对 M2 主题时不适用。
mixins 在您指定的确切选择器下生成属性。它们不会被添加到选择器或增加规则的特殊性。
mixin 只生成 CSS 自定义属性声明 (例如--some-prop: xyz)。它们不发出任何标准 CSS 属性,例如 color、 width 等。
3.1. 使用组件颜色变体
许多组件都有一个 color 属性,允许开发人员应用组件的不同颜色变体。当使用 M3 主题时,此属性仍然向组件添加 CSS 类(例如.mat-accent)。但是,没有针对这些类的内置样式。您可以通过将$color-variant 选项传递给组件-theme 或 -color mixin 来应用颜色变体。
<mat-checkbox class="tertiary-checkbox" />
<section class="tertiary-checkbox">
<mat-checkbox />
</section>
@use "@angular/material" as mat;
@use "@angular/material-experimental" as matx;
$theme: matx.define-theme();
.tertiary-checkbox {
@include mat.checkbox-color($theme, $color-variant: tertiary);
}
此 API 更灵活,并且生成的 CSS 更少。例如,.tertiary-checkbox 上面显示的类可以应用于任何复选框或包含复选框的任何元素,以更改该元素内所有复选框的颜色。
虽然您应该更喜欢显式应用具有颜色变体的 mixins,但您也可以使用 mixins 提供的向后兼容性 ,将样式直接应用于现有 CSS 类(mat-primary、mat-accent 和 mat-warn)。
下表显示了$color-variant 每个组件支持的值。 (未列出的组件不支持任何颜色变体。)
组件 | 支持的$color-variant 值 | 默认 |
---|---|---|
Badge 徽章 | primary, secondary, tertiary,error | error |
Button 按钮 | primary, secondary, tertiary,error | primary |
Button-toggle | primary, secondary, tertiary,error | secondary |
Checkbox 复选框 | primary, secondary, tertiary,error | primary |
Chips | primary, secondary, tertiary,error | secondary |
Datepicker 日期选择器 | primary, secondary, tertiary,error | primary |
Fab | primary, secondary,tertiary | primary |
Form-field | primary, secondary, tertiary,error | primary |
Icon 图标 | surface, primary, secondary, tertiary,error | surface |
Option 选项 | primary, secondary, tertiary,error | secondary |
Progress-bar 进度条 | primary, secondary, tertiary,error | primary |
Progress-spinner | primary, secondary, tertiary,error | primary |
Pseudo-checkbox | primary, secondary, tertiary,error | primary |
Radio 单选框 | primary, secondary, tertiary,error | primary |
Select | primary, secondary, tertiary,error | primary |
Slide-toggle | primary, secondary, tertiary,error | primary |
Slide | primary, secondary, tertiary,error | primary |
Stepper | primary, secondary, tertiary,error | primary |
Tabs | primary, secondary, tertiary,error | primary |
3.2. 使用 CSS 自定义属性进行精细自定义
主题 mixin 生成的 CSS 自定义属性源自 M3 的设计令牌。要在 API 之外进一步自定义 UI define-theme,您可以在样式中手动设置这些自定义属性。
主题 mixin 做出的保证意味着您不需要以组件的内部选择器为目标,也不需要使用过多的特异性来覆盖任何这些标记化属性。始终将基本主题应用到应用程序的根元素(通常为 html 或 body),并将任何覆盖应用到适用的最高级别选择器上。
<mat-sidenav-container>
Some content...
<mat-sidenav>
Some sidenav content...
<mat-checkbox class="danger">Enable admin mode</mat-checkbox>
</mat-sidenav>
</mat-sidenav-container>
@use "@angular/material" as mat;
@use "@angular/material-experimental" as matx;
$light-theme: matx.define-theme();
$dark-theme: matx.define-theme(
(
color: (
theme-type: dark,
),
)
);
html {
// Apply the base theme at the root, so it will be inherited by the whole app.
@include mat.all-component-themes($light-theme);
}
mat-sidenav {
// Override the colors to create a dark sidenav.
@include mat.all-component-colors($dark-theme);
}
.danger {
// Override the checkbox hover state to indicate that this is a dangerous setting. No need to
// target the internal selectors for the elements that use these variables.
--mdc-checkbox-unselected-hover-state-layer-color: red;
--mdc-checkbox-unselected-hover-icon-color: red;
}
4. 使用 Material 3 主题为您自己的组件设置主题
用于读取 M2 主题属性的相同实用程序函数(在 我们的组件主题化指南中描述)可用于从 M3 主题读取属性。然而,根据规范,M3 主题的可用命名调色板、排版级别等有所不同。
主题对象的结构被视为实现细节。代码不应依赖于直接读取其属性,例如使用 map.get.始终使用 Angular Material 提供的实用函数来访问主题的属性。
@use "@anuglar/material" as mat;
@use "@anuglar/material-experimental" as matx;
@mixin my-comp-theme($theme) {
.my-comp {
font: mat.get-theme-typography($theme, body-large, font);
letter-spacing: mat.get-theme-typography(
$theme,
body-large,
letter-spacing
);
background: mat.get-theme-color($theme, surface);
@if mat.get-theme-type($theme) == dark {
color: mat.get-theme-color($theme, primary, 20);
} @else {
color: mat.get-theme-color($theme, primary, 80);
}
padding: 48px + (2px * mat.get-theme-density($theme));
}
}
4.1. 读取色调调色板颜色
要从主题中读取 色调调色板颜色 get-theme-color,请使用带有三个参数的函数:
参数 | 描述 |
---|---|
$theme | 要读取的 M3 主题。 |
$palette | 要读取的调色板的名称。这可以是任何标准 M3 调色板: |
primary | |
secondary | |
tertiary | |
error | |
neutral | |
neutral-variant | |
$hue | 在调色板中读取的色相编号。这可以是任何标准色调: |
0 | |
10 | |
20 | |
30 | |
40 | |
50 | |
60 | |
70 | |
80 | |
90 | |
95 | |
99 | |
100 |
4.2. 解读色彩角色
要读取颜色角色,请 使用 get-theme-color 与两个参数一起使用:
参数 | 描述 |
---|---|
$theme | 要读取的 M3 主题。 |
$role | 颜色角色的名称。这可以是任何 M3 颜色角色: |
primary | |
on-primary | |
primary-container | |
on-primary-container | |
primary-fixed | |
primary-fixed-dim | |
on-primary-fixed | |
on-primary-fixed-variant | |
secondary | |
on-secondary | |
secondary-container | |
on-secondary-container | |
secondary-fixed | |
secondary-fixed-dim | |
on-secondary-fixed | |
on-secondary-fixed-variant | |
tertiary | |
on-tertiary | |
tertiary-container | |
on-tertiary-container | |
tertiary-fixed | |
tertiary-fixed-dim | |
on-tertiary-fixed | |
on-tertiary-fixed-variant | |
error | |
on-error | |
error-container | |
on-error-container | |
surface-dim | |
surface | |
surface-bright | |
surface-container-lowest | |
surface-container-low | |
surface-container | |
surface-container-high | |
surface-container-highest | |
on-surface | |
on-surface-variant | |
outline | |
outline-variant | |
inverse-surface | |
inverse-on-surface | |
inverse-primary | |
scrim | |
shadow |
4.3. 读取主题类型
要读取主题类型(light 或 dark),请 使用 get-theme-type 并存入一个参数进行调用:
参数 | 描述 |
---|---|
$theme | 要读取的 M3 主题。 |
4.4. 读取类型比例属性
要从主题读取 typescale 请使用 get-theme-typography 方法,并传入三个参数进行调用:
参数 | 描述 |
---|---|
$theme | 要读取的 M3 主题。 |
$level | 字体级别。这可以是任何 M3 类型级别: |
display-large | |
display-medium | |
display-small | |
headline-large | |
headline-medium | |
headline-small | |
title-large | |
title-medium | |
title-small | |
body-large | |
body-medium | |
body-small | |
label-large | |
label-medium | |
label-small | |
$property | 要获取值的 CSS 字体属性。这可以是以下 CSS 属性之一: |
font(CSS 字体简写,包括除字母间距之外的所有字体属性) | |
font-family | |
font-size | |
font-weight | |
line-height | |
letter-spacing |
4.5. 读取密度标尺
要从主题 读取密度标度(0、-1、-2、-3、-4 或 -5),请使用单个参数进行调用:get-theme-density
| 参数 | 描述 |
| $theme | 要读取的 M3 主题。|
5. 如何将应用程序从 Material 2 迁移到 Material 3
Angular Material 不提供从 M2 到 M3 的自动迁移,因为应用程序的设计是主观的。 Material Design 提供了一般原则和约束来指导您,但最终由您决定如何在您的应用程序中应用这些原则和约束。也就是说,Angular Material 的 M3 主题在设计时就考虑到了最大兼容性。
5.1. 更新使用 Angular Material 主题的组件以与 Material 3 兼容
为了促进从 M2 到 M3 的平滑过渡,让您的组件同时支持 M2 和 M3 主题可能是有意义的。迁移整个应用程序后,可以删除对 M2 主题的支持。
实现此目的的最简单方法是检查主题版本并为 M2 和 M3 发出不同的样式。您可以使用 的 get-theme-version 功能 检查主题版本@angular/material。该函数将返回 0M2 主题或 1M3 主题(请参阅 使用 Material 3 主题主题您自己的组件, 了解如何从 M3 主题读取值)。
@use "@angular/material" as mat;
@mixin my-comp-theme($theme) {
@if (mat.get-theme-version($theme) == 1) {
// Add your new M3 styles here.
} @else {
// Keep your old M2 styles here.
}
}
5.2. 在您的全局主题样式中传递新的 M3 主题
使用创建一个新的 M3 主题对象 define-theme 并将其传递到您之前传递 M2 主题的任何地方。所有采用 M2 主题的 Angular Material mixins 也与 M3 主题兼容。
5.3. 更新 Material 3 主题不支持的 API
由于 Material 3 是作为 Material 2 所用相同组件的替代主题实现的,因此两者的 API 基本相同。但是,有一些差异需要注意:
- M3 期望任何@include、-theme、-color、-typography 或-densitymixin-base 都应包装在选择器中。如果您的应用程序@include 在根级别包含这样的内容,我们建议将其包装在 html
- M3 有一个不同的 API 用于设置组件的颜色变体(有关更多信息,请参阅 使用组件颜色变体)。
不支持 backgroundColor 属性,并且不应与 M3 主题一起使用。 不支持 appearance="legacy" 变量,并且不应与 M3 主题一起使用。 - 对于 M3 主题,调用 all-component-typographies 不会生成样式 typography-hierarchy ,因为这会违反 M3 不添加选择器的保证。相反, 如果您希望在应用程序中使用 typography-hierarchy 的这些样式,则必须显式调用 mixin。
- mixintypography-hierarchy 输出对应于 M3 字体级别而不是 M2 字体级别名称的 CSS 类名称。如果您依赖 M2 类来设计应用程序的样式,则可能需要更新类名称。
5.4. 为颜色变体添加向后兼容样式(可选)
我们建议不要依赖许多 Angular Material 组件提供的的 color="primary"、color="accent"或 color="warn" M2 主题选项。但是,如果您想快速更新到 M3 并愿意接受为这些变体生成的额外 CSS,您可以启用向后兼容样式来恢复此 API 的行为。使用您想要为其生成颜色变体样式的 M3 主题调用 @angular/material-experimental
的 color-variants-back-compat mixin 。
@use "@angular/material" as mat;
@use "@angular/material-experimental" as matx;
$theme: matx.define-theme();
html {
@include mat.all-component-themes($theme);
@include matx.color-variants-back-compat($theme);
}
5.5. 为排版层次结构添加向后兼容样式(可选)
使用 M3 主题调用 typography-hierarchy mixin 会生成与 M3 typescale 名称(例如.mat-headline-large)相匹配的 CSS 类样式,而不是与 M2 类型规模名称匹配的 CSS 类样式(.mat-headline-1)。如果您在应用程序中使用 M2 类名称,我们建议将所有用法更新为新类名称。然而,为了使迁移更容易, typography-hierarchy mixin 除了新的类名之外还支持生成旧的类名。我们已尽最大努力将 M2 类映射到 M3 中合理的等效项。要启用这些样式,请将附加参数$back-compat: true 传递 给 mixin。
@use "@angular/material" as mat;
@use "@angular/material-experimental" as matx;
$theme: matx.define-theme();
@include mat.typography-hierarchy($theme, $back-compat: true);
5.6. 常问问题
-
我可以使用预定义的 Material 3 调色板以外的颜色吗?
目前,我们仅提供预定义的调色板,但我们计划添加对使用自定义生成的调色板的支持.
-
我可以依赖稳定的 CSS 自定义属性名称吗?
在将 Material 3 API 走出实验阶段之前,我们可能会对自定义属性名称进行更改,但伴随着这些更改我们将提供相应的 schematic,以便在您的应用程序中方便的替换旧名称为新名称。
-
Material 2 样式和 API 会消失吗?
Material 2 样式及其 API 将继续受到支持,并且我们没有立即计划弃用它们。我们知道应用程序切换到最新的 Material 3 样式需要一些时间,我们希望为迁移提供足够的时间。当我们决定删除这些 API 时,它们将被标记为已弃用,并在以下两个主要版本中继续受支持。截至目前,它们尚未被视为已弃用。
6. Angular 系列文章
最新更新以及更多 Angular 相关文章请访问 Angular 合集 | 鹏叔的技术博客
7. 参考文档
posted on 2024-04-09 06:11 eagle.supper 阅读(145) 评论(0) 编辑 收藏 举报