Skip to main content

An avatar represents a user profile picture. It displays an image or fallback content in a container.

Avatar supports fallback text or elements when the image fails to load or when no image is provided.

Loading...

Installation

Install the avatar package:

npm install @zag-js/avatar @zag-js/react # or yarn add @zag-js/avatar @zag-js/react

Anatomy

Check the avatar anatomy and part names.

Each part includes a data-part attribute to help identify them in the DOM.

Usage

Import the avatar package:

import * as avatar from "@zag-js/avatar"

The avatar package exports two key functions:

  • machine - State machine logic.
  • connect - Maps machine state to JSX props and event handlers.

Pass a unique id to useMachine so generated element ids stay predictable.

Then use the framework integration helpers:

import * as avatar from "@zag-js/avatar" import { useMachine, normalizeProps } from "@zag-js/react" function Avatar() { const service = useMachine(avatar.machine, { id: "1" }) const api = avatar.connect(service, normalizeProps) return ( <div {...api.getRootProps()}> <span {...api.getFallbackProps()}>PA</span> <img alt="PA" src={src} {...api.getImageProps()} /> </div> ) }

Listening for loading status changes

When the image loads or fails, onStatusChange is invoked.

const service = useMachine(avatar.machine, { onStatusChange(details) { // details => { status: "error" | "loaded" } }, })

Updating the image source programmatically

Use api.setSrc when the image source changes after mount.

api.setSrc(nextSrc)

Styling guide

Each avatar part includes a data-part attribute you can target in CSS.

[data-scope="avatar"][data-part="root"] { /* Styles for the root part */ } [data-scope="avatar"][data-part="image"] { /* Styles for the image part */ } [data-scope="avatar"][data-part="fallback"] { /* Styles for the fallback part */ }

Creating a component

Create your avatar component by abstracting the machine into your own component.

Usage

import { Avatar } from "./your-avatar" function Demo() { return ( <Avatar src="https://avatars.githubusercontent.com/u/139426" name="John Doe" /> ) }

Implementation

Use the splitProps utility to separate the machine's props from the component's props.

import * as avatar from "@zag-js/avatar" import { useMachine, normalizeProps } from "@zag-js/react" export interface AvatarProps extends Omit<avatar.Context, "id"> { /** * The src of the avatar image */ src?: string /** * The srcSet of the avatar image */ srcSet?: string /** * The name of the avatar */ name: string } function Avatar(props: AvatarProps) { const [machineProps, localProps] = avatar.splitProps(props) const service = useMachine(avatar.machine, { id: useId(), ...machineProps, }) const api = avatar.connect(service, normalizeProps) return ( <div {...api.getRootProps()}> <span {...api.getFallbackProps()}>{getInitials(localProps.name)}</span> <img alt="PA" src={localProps.src} srcSet={localProps.srcSet} {...api.getImageProps()} /> </div> ) } function getInitials(name: string) { return name .split(" ") .map((word) => word[0]) .join("") }

Methods and Properties

Machine Context

The avatar machine exposes the following context properties:

  • onStatusChange(details: StatusChangeDetails) => voidFunctional called when the image loading status changes.
  • idsPartial<{ root: string; image: string; fallback: string; }>The ids of the elements in the avatar. Useful for composition.
  • idstringThe unique identifier of the machine.
  • getRootNode() => ShadowRoot | Node | DocumentA root node to correctly resolve document in custom environments. E.x.: Iframes, Electron.
  • dir"ltr" | "rtl"The document's text/writing direction.

Machine API

The avatar api exposes the following methods:

  • loadedbooleanWhether the image is loaded.
  • setSrc(src: string) => voidFunction to set new src.
  • setLoadedVoidFunctionFunction to set loaded state.
  • setErrorVoidFunctionFunction to set error state.

Data Attributes

Image
data-scope
avatar
data-part
image
data-state
"visible" | "hidden"
Fallback
data-scope
avatar
data-part
fallback
data-state
"hidden" | "visible"
Edit this page on GitHub