[英]Angular mat-icon doesn't render svgs with masks
I have a series of .svgs
exported from Sketch (see sample below) that I've registered to the MatIconRegistry
, and am displaying using the mat-icon
component. 我有一系列的.svgs
从素描(见下面的示例),我已经注册到出口MatIconRegistry
,并使用我显示mat-icon
组成部分。
However I've noticed that any icons that use masks in Sketch (exported as <defs>
) don't show properly, and sometimes show the wrong icon altogether. 但是我注意到,任何在Sketch中使用遮罩的图标(导出为<defs>
)均无法正确显示,有时甚至完全显示错误的图标。
I know this is an issue with mat-icon
since the files render fine in the browser. 我知道这是mat-icon
的问题,因为文件在浏览器中呈现良好。 Also mat-icon
renders fine when the source file does not use masks (However we can't guarantee that the svgs
won't have a mask) 当源文件不使用遮罩时, mat-icon
很好地渲染(但是我们不能保证svgs
没有遮罩)
Does anyone know of a way to fix this, either in Sketch or in Angular? 有人知道在Sketch或Angular中解决此问题的方法吗?
icon-registry.service.ts
import { MatIconRegistry } from '@angular/material/icon';
import { DomSanitizer } from '@angular/platform-browser';
@Injectable({
providedIn: 'root',
})
export class MyIconRegistry {
constructor(
private matIconRegistry: MatIconRegistry,
private domSanitizer: DomSanitizer) {
this.matIconRegistry.addSvgIcon(
'dot',
'path/to/icon-dot.svg'
)
}
}
myComponent.component.ts
...
@Component({
selector: 'my-component',
template: `<mat-icon svgIcon="dot"></mat-icon>`,
styleUrls: ['./icon.scss'],
encapsulation: ViewEncapsulation.Emulated,
})
...
...
@NgModule({
declarations: [MyComponent],
providers: [MyIconRegistry],
imports: [CommonModule, MatIconModule, HttpClientModule],
exports: [MyComponent],
})
icon-dot.svg
<svg width="24px" height="24px" viewBox="0 0 24 24" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<!-- Generator: Sketch 53.2 (72643) - https://sketchapp.com -->
<title>icon-dot</title>
<desc>Created with Sketch.</desc>
<defs>
<circle id="path-1" cx="12" cy="12" r="8"></circle>
</defs>
<g id="Icons" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<g id="icon-dot">
<mask id="mask-2" fill="white">
<use xlink:href="#path-1"></use>
</mask>
<g id="Mask" fill-rule="nonzero"></g>
<g id="Blue/" mask="url(#mask-2)" fill="#0A4ACE">
<rect id="Rectangle" x="0" y="0" width="24" height="24"></rect>
</g>
</g>
</g>
</svg>
To anyone stumbling across this in the future: 对于以后遇到任何麻烦的人:
The issue was not technically with mat-icon
as I suspected. 正如我所怀疑的,从技术上讲,问题不在于mat-icon
。 The error in rendering svg
's was due to Sketch's non-unique mask and path id
's. 渲染svg
的错误是由于Sketch的非唯一蒙版和路径id
的。
So to resolve this I used ShadowDom encapsulation which makes each svg
unique within its own DOM, and wrote my own injection. 因此,为了解决此问题,我使用了ShadowDom封装,该封装使每个svg
在其自己的DOM中都是唯一的,并编写了自己的注入。
...
@Component({
...
encapsulation: ViewEncapsulation.ShadowDom,
})
...
ngOnChanges(changes: SimpleChanges){
this.iconRegistry.getNamedSvgIcon(this.name).pipe(take(1)).subscribe(
svg => {
this.setSvgElement(svg)
},
(err: Error) => console.warn(`Error retrieving icon: ${err.message}`)
)
}
private setSvgElement(svg: SVGElement){
this.elementRef.nativeElement.shadowRoot.appendChild(svg)
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.