如何让它使用我的主题的
primary
和 accent
颜色?
我已经使用 Material 2 自定义调色板设置了我的主题。为了简洁起见,我排除了调色板设置
$theme: mat.m2-define-dark-theme(
(
color: (
primary: $primary,
accent: $accent,
warn: $warn,
),
typography: mat.m2-define-typography-config(),
density: -2,
)
);
@include mat.core();
@include mat.all-component-themes($theme);
@include shared.shared-themes($theme);
@include components.component-themes($theme);
Angular 材质垫菜单项使用主题的前景色和背景色。这就是为什么当您在 Angular Material 网站上切换主题时,它不使用
primary
或 accent
颜色,而是根据选择的是浅色还是深色主题在白色和灰色之间切换:
在其网站上选择紫色主题时查看选择,您可以看到每个选项在浅色模式下为灰色或在深色模式下为黑色:
@node_modules/@angular/material/core/tokens/m2/mat_menu.scss
中的源代码来证实(如果使用材质 2,则为 Angular 18)
我们看到颜色通常取决于前景色和背景色:
这些颜色可以通过
$primary
调色板的主题对比度在应用程序范围内进行更改。不推荐,因为依赖它的组件数量。这里的答案之一提到了这一点:Angular 2 Material Foreground
还有一个关于如何对此进行彻底更改的 github 问题:https://github.com/angular/components/issues/6244
在某些情况下您想要进行彻底的改变时,上述内容可能会对您有所帮助。
但是让我们看看修改一个垫菜单项。
现在我们还假设您想要在一个非常特定的组件上进行更改,而不是在应用程序范围内进行更改,例如使用
mat-menu-item
的导航栏
许多解决方案如果无法使用调色板来完成,就会放弃干净,而只是尝试直接覆盖
background-color
。但是,您现在在 CSS 中依赖于角度材质的类。因此,如果 Angular Material 在版本更新中更改了它们的类名,您的代码将会崩溃。此外,您还需要使用已弃用的 ng-deep
。
要解决此问题,您可以添加一个类,并覆盖该类上的
background-color
或 color
。这更好。但您最终可能仍然需要编写很长的 CSS,以确保您的覆盖比 Angular Material 的 CSS 具有更高的特异性才能生效。
技巧是使用您自己的类并覆盖
html
级别的 CSS 变量,因此没有您需要与之竞争的特异性。
因此,如果您检查 mat-menu-item 的 css,您会看到聚焦状态颜色,例如设置如下:
如果我们在
mat-menu-item
上进一步搜索 CSS,我们会在 HTML 级别找到以下部分:
假设我们想要改变背景颜色。我们可能有兴趣更改
--mat-menu-item-focus-state-layer-color
和 --mat-menu-item-hover-state-layer-color
所以这个问题的最终解决方案如下:
<button class="custom-menu-list-item"
mat-menu-item
My item
</button>
在我们的 *component.theme.scss 中:
.custom-menu-list-item{
--mat-menu-item-focus-state-layer-color: red;
--mat-menu-item-hover-state-layer-color: red;
}
或者最好是从调色板中举一个例子:
--mat-menu-item-hover-state-layer-color: #{mat.m2-get-color-from-palette($my-blue-palette, 500)}
这就是全部内容。
如果您想在系统范围内对所有
mat-menu
进行更改,则可以将其放在应用程序根主题文件之一的 body
元素上,以覆盖 html
元素上的 CSS 变量。
如果您由于有多个主题而定义了特定的主题类(这很常见),则覆盖该变量将不会立即起作用。
这是因为你的主题类将定义在
div
上,例如下面可观察到的 themeClass$
<div class="mat-app-background" [class]="themeClass$ | async">
<app-nav-menu></app-nav-menu>
<div class="scroll-container">
<router-outlet></router-outlet>
</div>
</div>
.my-light-theme{
--mat-menu-item-hover-state-layer-color: red;
}
这是因为使用 CDK 覆盖的组件(例如选择、模式和菜单项中的
mat-option
)会在角度应用程序之外呈现。
因此,您必须使用将主题类也放在 CDKOverlay 上的解决方案之一。还有其他 stackoverflow 解决方案解释了如何执行此操作。 它涉及将
private overlayContainer: OverlayContainer
注入到高级组件中并将类添加到overlayContainers classList