Documentation

Documentation

Icon

SVG icon element with size steps, a name registry, and decorative-by-default semantics.

The <dsgn-icon> component renders one SVG icon inside a 24×24 viewBox. Give it an icon either as a Lit template (icon) or by name (icon-name), and it inherits its color from currentColor — so it takes the color of whatever contains it.

Usage

<dsgn-icon icon-name="check" size="md" label="Complete"></dsgn-icon>

Import the component module in your application entrypoint:

import '@ds-gn/ui/icon';

Props

Prop Type Default Description
size 'sm' | 'md' | 'lg' | 'xl' 'lg' Icon size: sm 16px, md 20px, lg 24px, xl 32px.
icon-name IconName | '' '' Icon to render, by name. Requires the icon registry (see below).
icon SVGTemplateResult undefined Icon as a Lit template. Property-only (no attribute); wins over icon-name.
label string '' Accessible label. When set, the icon is announced; when empty, it is decorative.
surface 'light' | 'dark' 'light' Semantic token surface to use.

icon-name is the attribute name; the matching JavaScript property is iconName.

The icon has no variant prop — color comes from the surrounding text color. Set it with CSS, or use a component that supplies one, such as <dsgn-feature-item>’s colored icon badge.

Slots

The component renders its own <svg> and takes no slotted content.

Methods

Method Description
Icon.registerIcons(registry) Static. Adds icons to the shared name registry. Merges with anything registered earlier.

Two ways to supply an icon

icon-name is markup, so it survives a CMS or a copy-paste — but names resolve through a registry you populate once at app entry:

import { Icon } from '@ds-gn/ui/icon';
import * as icons from '@ds-gn/ui/icon/icons';

const { iconNames, ...registry } = icons;
Icon.registerIcons(registry); // or just the ones you use, to keep the bundle small
<dsgn-icon icon-name="arrowRight"></dsgn-icon>

Custom icons work the same way — any SVGTemplateResult keyed by name:

import { svg } from 'lit';
import { Icon } from '@ds-gn/ui/icon';

Icon.registerIcons({ myIcon: svg`<path d="M4 12h16" />` });

icon takes a Lit template instead. It needs no registry and tree-shakes to the one icon you import, but it can only be set from JavaScript:

import { arrowRight } from '@ds-gn/ui/icon/icons';

html`<dsgn-icon .icon=${arrowRight}></dsgn-icon>`;

If both are set, icon wins. The name list is exported as iconNames from @ds-gn/ui/icon/icons.

Examples

Sizes

<dsgn-icon icon-name="check" size="sm"></dsgn-icon>
<dsgn-icon icon-name="check" size="md"></dsgn-icon>
<dsgn-icon icon-name="check" size="lg"></dsgn-icon>
<dsgn-icon icon-name="check" size="xl"></dsgn-icon>

Coloring an icon

<span style="color: var(--color-brand)">
  <dsgn-icon icon-name="circleCheck"></dsgn-icon>
</span>

Labeled versus decorative

<!-- Announced as an image named "Warning" -->
<dsgn-icon icon-name="triangleAlert" label="Warning"></dsgn-icon>

<!-- Decorative: hidden from assistive technology -->
<dsgn-icon icon-name="triangleAlert"></dsgn-icon>

Accessibility

An icon with no label renders role="presentation" and aria-hidden="true", which is the right default next to visible text. Set label only when the icon is the sole carrier of meaning — an icon-only control should instead get its name from the control (for example <dsgn-button>’s aria-label), so the name is not announced twice.

Esc