我们如何将 angular 组件的样式加载到 iframe 中?
How do we load an angular component's styles into an iframe?
我正在开发一个将其他组件呈现为 iframe
的组件。它成功呈现,但我注意到样式没有传递给它。我尝试在 @Component
中使用 styles
数组,而不是链接到失败的外部样式表。我还将它们添加到 <style>
标记内的模板中,但也失败了。我看到我们如何访问 contentDocument
和/或 contentWindow
以将数据传递到 iframe
的 DOM 中,我计划使用 service
来代替一旦它们进入 iframe
,我就不得不四处挖掘我什至无法触摸的东西。有没有一种方法可以将样式传递给它而不必创建数据对象,然后在嵌套组件中使用几个函数来创建和应用它们?到目前为止,这就是我的代码的样子。
组件
import { PropertyDisplayComponent } from './components/property-display/property-display.component';
@Component({
selector: 'responsive-shell',
templateUrl: './responsive-shell.component.html',
styleUrls: ['./responsive-shell.component.css']
})
export class ResponsiveShellComponent implements OnInit, AfterViewInit {
@ViewChild('compFrame', {static: false}) CompFrame: ElementRef | undefined;
doc: any;
compRef: ComponentRef<PropertyDisplayComponent> | undefined;
constructor(private VcRef: ViewContainerRef, private resolver: ComponentFactoryResolver) { }
public onLoad(){
this.doc = this.CompFrame?.nativeElement.contentDocument || this.CompFrame?.nativeElement.CompFrame.contentWindow;
this.createComponent();
}
private createComponent():void{
const compFactory = this.resolver.resolveComponentFactory(PropertyDisplayComponent);
this.compRef = this.VcRef.createComponent(compFactory);
this.compRef.location.nativeElement.id = 'propertyDisplay';
this.doc.body.appendChild(this.compRef.location.nativeElement);
}
ngOnInit(): void {
}
ngAfterViewInit():void{
this.onLoad();
}
}
模板
<section class="shell">
<iframe class="iframeShell" #compFrame></iframe>
</section>
有什么我应该做的不同的事情吗?有人看到我可以在样式表中添加什么吗?
更新
我发现如果我们以内联方式进行样式设置,样式会起作用,但如果我们可以通过某种方式传递样式表,我会更喜欢不同的解决方案。
尝试从这个改变组件装饰...
@Component({
selector: 'responsive-shell',
templateUrl: './responsive-shell.component.html',
styleUrls: ['./responsive-shell.component.css']
})
对此...
@Component({
selector: 'responsive-shell',
templateUrl: './responsive-shell.component.html',
styleUrls: ['./responsive-shell.component.css'],
encapsulation: ViewEncapsulation.ShadowDom
})
More on the topic of ViewEncapsulation.
注意:这个only works for modern browsers因为它依赖于浏览器对Shadow的支持DOMAPI。如果您从组件的 SCSS 加载多个 SCSS 文件但本地样式运行良好,我遇到过不稳定的行为。
我正在开发一个将其他组件呈现为 iframe
的组件。它成功呈现,但我注意到样式没有传递给它。我尝试在 @Component
中使用 styles
数组,而不是链接到失败的外部样式表。我还将它们添加到 <style>
标记内的模板中,但也失败了。我看到我们如何访问 contentDocument
和/或 contentWindow
以将数据传递到 iframe
的 DOM 中,我计划使用 service
来代替一旦它们进入 iframe
,我就不得不四处挖掘我什至无法触摸的东西。有没有一种方法可以将样式传递给它而不必创建数据对象,然后在嵌套组件中使用几个函数来创建和应用它们?到目前为止,这就是我的代码的样子。
组件
import { PropertyDisplayComponent } from './components/property-display/property-display.component';
@Component({
selector: 'responsive-shell',
templateUrl: './responsive-shell.component.html',
styleUrls: ['./responsive-shell.component.css']
})
export class ResponsiveShellComponent implements OnInit, AfterViewInit {
@ViewChild('compFrame', {static: false}) CompFrame: ElementRef | undefined;
doc: any;
compRef: ComponentRef<PropertyDisplayComponent> | undefined;
constructor(private VcRef: ViewContainerRef, private resolver: ComponentFactoryResolver) { }
public onLoad(){
this.doc = this.CompFrame?.nativeElement.contentDocument || this.CompFrame?.nativeElement.CompFrame.contentWindow;
this.createComponent();
}
private createComponent():void{
const compFactory = this.resolver.resolveComponentFactory(PropertyDisplayComponent);
this.compRef = this.VcRef.createComponent(compFactory);
this.compRef.location.nativeElement.id = 'propertyDisplay';
this.doc.body.appendChild(this.compRef.location.nativeElement);
}
ngOnInit(): void {
}
ngAfterViewInit():void{
this.onLoad();
}
}
模板
<section class="shell">
<iframe class="iframeShell" #compFrame></iframe>
</section>
有什么我应该做的不同的事情吗?有人看到我可以在样式表中添加什么吗?
更新 我发现如果我们以内联方式进行样式设置,样式会起作用,但如果我们可以通过某种方式传递样式表,我会更喜欢不同的解决方案。
尝试从这个改变组件装饰...
@Component({
selector: 'responsive-shell',
templateUrl: './responsive-shell.component.html',
styleUrls: ['./responsive-shell.component.css']
})
对此...
@Component({
selector: 'responsive-shell',
templateUrl: './responsive-shell.component.html',
styleUrls: ['./responsive-shell.component.css'],
encapsulation: ViewEncapsulation.ShadowDom
})
More on the topic of ViewEncapsulation.
注意:这个only works for modern browsers因为它依赖于浏览器对Shadow的支持DOMAPI。如果您从组件的 SCSS 加载多个 SCSS 文件但本地样式运行良好,我遇到过不稳定的行为。