【发布时间】:2021-05-11 20:50:17
【问题描述】:
我的 DOM 看起来像这样:
<app>
<router-outlet></router-outlet>
<project>...</project>
</app>
project 元素被路由器插入的位置。
如何向该元素添加类?
【问题讨论】:
我的 DOM 看起来像这样:
<app>
<router-outlet></router-outlet>
<project>...</project>
</app>
project 元素被路由器插入的位置。
如何向该元素添加类?
【问题讨论】:
假设你总是希望类应用到这个组件,你可以在你的组件元数据中使用host:
@Component({
selector:'project',
host: {
class:'classYouWantApplied'
}
})
导致:
<app>
<router-outlet></router-outlet>
<project class="classYouWantApplied">...</project>
</app>
【讨论】:
<router-outlet class="...">... 不起作用:/
【讨论】:
[_nghost_c1]-like 属性限定元素,例如router-outlet + *[_nghost_c1]。这也被添加到我的 css 中(我正在编译 scss,也许这就是原因),并且它不会应用于以另一种方式作用域的以下元素。
::ng-deep router-outlet.router-flex + * { display: flex; flex: 1 1 auto; flex-direction: column } 之类的东西并在组件中定义它。并且不要有人敢说它已被弃用。
<router-outlet> 有两个同级组件。传入和传出。要解决这个问题,只需将“+”替换为“~”即可。那是router-outlet ~ *。
关键是/deep/关键字:
:host /deep/ router-outlet + project {
display: block;
border: 10px solid black;
}
这无需任何额外配置即可工作。
:host /deep/ router-outlet + * 用于 Angular 路由器动态创建的任何组件。
由于Angular 4.3.0 已弃用/deep/,因此建议的替代方案是::ng-deep。还有一个long discussion 与此有关。
【讨论】:
/deep/ 已被弃用。根据这个issue,::ng-deep 可能是它现在的替代品。
::ng-deep 现在也已弃用 (v8.0.0)
你可以使用相邻兄弟选择器
router-outlet + project { ... }
https://developer.mozilla.org/en/docs/Web/CSS/Adjacent_sibling_selectors
但前提是@drewmoore 的方法不适用。
【讨论】:
您可以使用HostBinding 执行此操作,这实际上与使用已经提到的host 属性相同,尽管该方法使用默认列表规则会引发 TSLint 错误。
在要应用类的组件中:
import { Component, HostBinding, Host (optional for typing) } from '@angular/core';
@Component({...})
export class GiveMeAClassComponent {
@HostBinding('class.some-class') someClass: Host = true;
...
}
然后在您的根styles.scss 文件中,您可以添加以下内容:
.some-class {
// Styles in here will now be applied to your GiveMeAClassComponent at a root level
}
【讨论】:
<app>
<div class="your css class">
<router-outlet></router-outlet>
</div>
</app>
这对我有用
【讨论】:
如果您需要有条件地添加一个类,您可以从组件中以编程方式添加它:
constructor(private renderer: Renderer2, private elemRef: ElementRef) {
if(someCondition){
renderer.addClass(elemRef.nativeElement, 'myClass');
}
}
【讨论】:
由于路由器在 router-outler 元素之后注入组件, 如果我们想用相同的规则集为所有注入的组件设置样式,那么以下规则可能会有所帮助。
css "+" 操作符选择特定类型的第一个兄弟元素,而星号 (*) 用作通配符来选择 router-outlet 的任何第一个兄弟元素
router-outlet + * {
// your rules
}
【讨论】:
目前,Angular 6 建议我使用 @HostBindings 和 @HostListeners 而不是主机属性:
export class ProjectComponent {
@HostBinding('class') classes = 'classYouWantApplied';
}
【讨论】:
我创建了一个RouterOutletHelperDirective,可以根据需要进行修改。
您的用例可能会有所不同,但对我来说:
ActivatedRoute 数据)的这种默认设置。你这样使用它(类是可选的):
<router-outlet routerOutletHelper
[routerOutletHelperClass]="'blue-border'"></router-outlet>
然后创建指令,添加并导出到您的应用模块。
import { Directive, ElementRef, Renderer2, Input } from "@angular/core";
import { RouterOutlet } from "@angular/router";
import { Subscription } from "rxjs";
@Directive({
selector: 'router-outlet[routerOutletHelper]'
})
export class RouterOutletHelperDirective
{
constructor(private routerOutlet: RouterOutlet,
private element: ElementRef<HTMLElement>,
private renderer: Renderer2) { }
subscription = new Subscription();
@Input('routerOutletHelperClass')
customClassName: string | undefined;
ngOnInit()
{
this.subscription.add(this.routerOutlet.activateEvents.subscribe((_evt: any) => {
// find the component element that was just added
const componentElement = this.element.nativeElement.nextSibling;
// add a custom class
if (this.customClassName)
{
this.renderer.addClass(componentElement, this.customClassName);
}
// add my default classes, unless the activated route data
// (specified in module routing file) has { addDefaultClasses: false }
if (this.routerOutlet.activatedRouteData && this.routerOutlet.activatedRouteData.addDefaultClasses !== false)
{
// these are my application's default classes (material / theming)
// (an additional data parameter could be 'darkTheme: boolean')
this.renderer.addClass(componentElement, 'mat-typography');
this.renderer.addClass(componentElement, 'rr-theme-light');
}
}));
}
ngOnDestroy()
{
this.subscription.unsubscribe();
}
}
【讨论】:
对我来说,它有助于将路由器插座包装到另一个容器中。
<div class="classYouWantApplied">
<router-outlet>
</div>
像这样,您可以将类应用到周围的容器。
【讨论】:
添加主机类名,它将向组件添加一个类,然后使用相邻来定位元素。
@Component({
selector:'project',
host: {
class:'Project-wrapper'
}
})
现在使用与 angular 相邻的 CSS
::ng-deep to target it:
::ng-deep .Project-wrapper {}
【讨论】: