Avatar
A user or entity representation showing initials, an image, or an icon. Avatars are visual atoms — they identify, they don't act.
When to use
Use an avatar wherever you need to put a face (or stand-in) next to a
name: comment threads, member lists, ownership chips, presence
indicators. When the avatar should navigate to a profile, the AUTHOR
wraps it in <a>. The avatar component itself stays semantic-neutral.
Variants
| Variant | Class | Use for |
|---|---|---|
| Default | .avatar |
Neutral fallback (raised surface) |
| Accent | .avatar.-accent |
Self, current user, highlight |
| Bone | .avatar.-bone |
Warm fallback, secondary identity |
| Neutral | .avatar.-neutral |
Disabled, archived, system |
Sizes
| Size | Class | Use for |
|---|---|---|
| Small | .avatar.-s |
Inline lists, table rows |
| Medium | (default) | Most cases |
| Large | .avatar.-l |
Profile headers, comment authors |
| XL | .avatar.-xl |
Hero / detail page header |
Pixel sizes follow size-control.s/m/l/xl from the semantic tier so
avatars align with buttons, inputs, and other controls on the same row.
Anatomy
Initials:
<span class="avatar -accent">KM</span>
<span class="avatar -bone -l">DR</span>
Image:
<span class="avatar -l">
<img src="/avatar.jpg" alt="Kazimir Malevich" />
</span>
Icon (placeholder for Phase 4 morph-icons):
<span class="avatar -accent">
<svg aria-hidden="true" viewBox="0 0 24 24">…</svg>
</span>
The CSS handles all three content types: initials center via flexbox,
<img> fills the circle with object-fit: cover, and <svg> shrinks
to 60% of the avatar so it reads as an icon rather than a background.
Tokens used
color.accent,color.surface-raised,color.surface-float,color.border-mutedcolor.ink-strong,color.ink-inversefont.caption,font.body-support,font.body-regular,font.heading-block(for-xlinitials)radius.avatar(9999px, full pill)size-control.s,size-control.m,size-control.l,size-control.xl
Tier 3 (component-specific): none.
Accessibility
- Initials avatars — the parent context must supply the full name
(tooltip, adjacent text, or
aria-labelon the wrapping link). Initials alone are not an accessible name. - Image avatars —
<img alt="…">is mandatory; the alt should describe the person (e.g."Kazimir Malevich"), not the visual ("profile picture"). - Icon avatars —
aria-hidden="true"on the<svg>; the label comes from context.
Edge cases
- Initials length — best with 1–2 characters. Three letters still
fit at default size but truncate visually at
-s. - Image fallback — when an image fails to load, the browser shows
the
<img>'s alt text inside the circle. Style remains consistent because the avatar's own typography applies to the alt fallback. - Status dot / ring — not part of v1.0. Compose with a wrapper
block (
UserChip) when needed.
Do
- Use the same size for every avatar in a list — mixed sizes break rhythm.
- Provide a real
altfor image avatars; describe who, not what. - Use
-accentsparingly — it's the "this is you" highlight, not a decorative color.
Don't
- Don't bake the user's name into the avatar's class or data attribute;
use real DOM text or
aria-labelon the wrapping link. - Don't put interactive elements inside the avatar; wrap the avatar in a link or button instead.
- Don't override the radius — avatars are always full circles in v1.0.
Related
Badge— companion element for status labelsButton— when an avatar is a clickable trigger, wrap or compose