# Core/Badge - Design

Badges display an indicator/counter on an associated component.

## Properties

### Label

A label is required to indicate the number of notifications.

### Size

Badges support `md` and `sm` sizes. Use `sm` when composing with smaller controls, such as icon-only buttons, while keeping `md` for standard button and navigation attachments.

### Dot

Use a dot to show notifications without a count.

### Appearance

Badges can be colored based on their status. The `attention` appearance is the general purpose color used for numbered badges and does not necessarily communicate severity.

Using color as the only means to communicate status should be avoided (WCAG SC 1.4.1: Use of Color, Level A). Badges that communicate status must be accompanied by supplementary information that clearly communicates the status.

## Behavior

### Corner attachment

Badges are placed in the top-right of the parent component to avoid obscuring the parent content. Use `BadgeLayout`'s `offset` prop to nudge the badge inward or outward when the anchor component has a tighter visual target.

### Icon button composition

Use `size="sm"` when attaching badges to `IconButton`. Tertiary icon buttons may need a small `offset` so the badge overlaps the icon rather than floating too far outside the control.

### Inline

When used with text labels, badges are placed on the trailing side and vertically aligned to the text's line height.

## Content

### Maximum

The maximum number shown in 99. When there are more than 99 notifications a "+" is appended to the label.

## Best Practices

Do:

* Do cap displayed values at 99 with a "99+" label.
* Do use the dot variant for simple presence indicators.
* Do associate interactive anchors with badge count context using `aria-describedby`.

Don't:

* Don't use Badge for semantic status text — use Pill.
* Don't use Badge for labels or tags — use Tag.
* Don't place Badge on non-interactive decorative elements.
* Don't use Badge colors as the only method to communicate status.
* Don't include badge count context in the anchor's `aria-label`.

## Accessibility

* Badge requires an accessible label via `aria-label` or `aria-labelledby` that describes the count or status (e.g., "76 unread").
* When composing with interactive controls such as `Button` or `IconButton`, set `aria-describedby` on the anchor to the badge's `id`. Keep the anchor's accessible name limited to the control action or label (e.g., "Messages"), not the badge content.
* Use `aria-live="polite"` on the parent for dynamic badge updates.

## Content

* Numeric only.
* Max displayed value: 99; use "99+" for larger counts.

## Related components

* [Pill](?path=/docs/core-pill--design) — For semantic status labels.
* [Tag](?path=/docs/core-tag--design) — For removable text chips.