Icon

The icon component is used to display any Dynatrace icon within the UI.

The icon component provides an easy way to use SVG (not font or bitmap) icons in your app. It does so by directly inlining the SVG content into the page as a child of the component (rather than using a tag or a div background image). This makes it easier to apply CSS styles to SVG icons.

´ Loading interactive demo...
<dt-icon name="agent"></dt-icon> export class IconDefaultExample {} <dt-icon name="agent"></dt-icon> export class IconDefaultExample {}

Imports

You have to import the DtIconModule in your AppModule. Note: It needs a bit of configuration to work. Read more in the configuration section below.

@NgModule({
  imports: [
    DtIconModule.forRoot({
      svgIconLocation: `/path/to/your/icons/{{name}}.svg`,
    }),
  ],
})
class MyModule {}

Inputs

Name Type Default Description
name string '' The name of the icon.

Configuration

DtIcons uses a service called DtIconRegistry under the hood. This service loads, parses and stores the icons you want to use in your template. To work properly DtIconRegistry needs a bit of configuration. To provide this configuration please use the static forRoot method on the module class in your AppModule imports. Pass the configuration object to the forRoot method:

@NgModule({
  imports: [
    DtIconModule.forRoot({
      svgIconLocation: `/path/to/your/icons/{{name}}.svg`,
    }),
  ],
})
class MyModule {}

Configuration options

Name Type Example Description
svgIconLocation string /assets/icons/.svg Location where the icons will be loaded. Use the placeholder for the icon name.

If you don't want to use the forRoot method, you can also provide the configuration via the DT_ICON_CONFIGURATION injection token in the DI.

DtIconpack

All Dynatrace icons are shipped with the @dynatrace/dt-iconpack npm package. This npm package is a peerDependency for the angular-components. And can be installed using the following command:

// yarn
yarn add @dynatrace/dt-iconpack

// npm
npm install @dynatrace/dt-iconpack

After installation you can import the dt-iconpack in your typescript files if you need to set a type for a property or want to use the enumeration.

import { DtIconType, Icons } from '@dynatrace/dt-iconpack';

Exports

Name Description
DtIconType Typescript Type with all icon names as possible values.
Icons Enumeration with all icon names.

Accessibility

Similar to an <img> element, an icon alone does not convey any useful information for a screen-reader user. The user of <dt-icon> must provide additional information on to how the icon is used. Based on this, <dt-icon> is marked as aria-hidden="true" by default, but this can be overriden by adding aria-hidden="false" to the element.

Icons in use

Icons are used all over the UI to support the visual respresentation of the content. They can be part of buttons, info groups, chart legends, the show more component, table headers, and many more.

All Icons

Below you can find all icons that are currently shipped within the @dynatrace/dt-iconpack package. You can use these names as the name property for the dt-icon component.

´ Loading interactive demo...
<ng-container> <dt-icon [name]="name" *ngIf="_show"></dt-icon> <p>{{ name }}</p> </ng-container> export class DocsAsyncIcon implements OnDestroy { @Input() name: DtIconType; _show = false; private _viewportEnterSub: Subscription; constructor( viewport: Viewport, el: ElementRef, changeDetector: ChangeDetectorRef, ) { this._viewportEnterSub = viewport .elementEnter(el) .pipe(take(1)) .subscribe(() => { this._show = true; changeDetector.detectChanges(); }); } ngOnDestroy(): void { if (this._viewportEnterSub) { this._viewportEnterSub.unsubscribe(); } } } @Component({ moduleId: module.id, selector: 'component-barista-example', template: ` <input #input type="text" dtInput placeholder="Filter by" (input)="_onInputChange($event)" aria-label="Filter icons" /> <div class="all-icons-container"> <docs-async-icon *ngFor="let name of _icons$ | async" [name]="name" ></docs-async-icon> </div> `, styles: [ ` .all-icons-container { display: grid; grid-auto-columns: max-content; grid-gap: 10px; grid-template-columns: repeat(auto-fill, minmax(min-content, 200px)); } `, 'docs-async-icon { display: inline-block; padding: 1.5rem; text-align: center; }', ], changeDetection: ChangeDetectionStrategy.OnPush, providers: [Viewport], }) export class IconAllExample implements OnDestroy { @ViewChild('input', { static: true }) _inputEl: ElementRef; _icons$: Observable<string[]>; private _filterValue = new BehaviorSubject<string>(''); constructor(private _httpClient: HttpClient, viewport: Viewport) { this._icons$ = combineLatest([ this._httpClient .get('/assets/icons/metadata.json') .pipe(map((res: { icons: string[] }) => res.icons || [])), this._filterValue.pipe( debounceTime(200), map(value => value.toUpperCase()), ), ]).pipe( map(([icons, filterValue]) => icons.filter( icon => filterValue === '' || icon.toUpperCase().indexOf(filterValue) !== -1, ), ), tap(() => { setTimeout(() => { viewport.refresh(); }, 0); }), ); } ngOnDestroy(): void { this._filterValue.complete(); } _onInputChange(event: Event): void { // We always have to stop propagation on the change event. // Otherwise the change event, from the input element, will bubble up and // emit its event object to the `change` output. event.stopPropagation(); this._filterValue.next(this._inputEl.nativeElement.value || ''); } } <ng-container> <dt-icon [name]="name" *ngIf="_show"></dt-icon> <p>{{ name }}</p> </ng-container> export class DocsAsyncIcon implements OnDestroy { @Input() name: DtIconType; _show = false; private _viewportEnterSub: Subscription; constructor( viewport: Viewport, el: ElementRef, changeDetector: ChangeDetectorRef, ) { this._viewportEnterSub = viewport .elementEnter(el) .pipe(take(1)) .subscribe(() => { this._show = true; changeDetector.detectChanges(); }); } ngOnDestroy(): void { if (this._viewportEnterSub) { this._viewportEnterSub.unsubscribe(); } } } @Component({ moduleId: module.id, selector: 'component-barista-example', template: ` <input #input type="text" dtInput placeholder="Filter by" (input)="_onInputChange($event)" aria-label="Filter icons" /> <div class="all-icons-container"> <docs-async-icon *ngFor="let name of _icons$ | async" [name]="name" ></docs-async-icon> </div> `, styles: [ ` .all-icons-container { display: grid; grid-auto-columns: max-content; grid-gap: 10px; grid-template-columns: repeat(auto-fill, minmax(min-content, 200px)); } `, 'docs-async-icon { display: inline-block; padding: 1.5rem; text-align: center; }', ], changeDetection: ChangeDetectionStrategy.OnPush, providers: [Viewport], }) export class IconAllExample implements OnDestroy { @ViewChild('input', { static: true }) _inputEl: ElementRef; _icons$: Observable<string[]>; private _filterValue = new BehaviorSubject<string>(''); constructor(private _httpClient: HttpClient, viewport: Viewport) { this._icons$ = combineLatest([ this._httpClient .get('/assets/icons/metadata.json') .pipe(map((res: { icons: string[] }) => res.icons || [])), this._filterValue.pipe( debounceTime(200), map(value => value.toUpperCase()), ), ]).pipe( map(([icons, filterValue]) => icons.filter( icon => filterValue === '' || icon.toUpperCase().indexOf(filterValue) !== -1, ), ), tap(() => { setTimeout(() => { viewport.refresh(); }, 0); }), ); } ngOnDestroy(): void { this._filterValue.complete(); } _onInputChange(event: Event): void { // We always have to stop propagation on the change event. // Otherwise the change event, from the input element, will bubble up and // emit its event object to the `change` output. event.stopPropagation(); this._filterValue.next(this._inputEl.nativeElement.value || ''); } }