<!-- AvatarFactory Docs · https://avatarfactory.in/docs/sdk/react/avatar · Full map: https://avatarfactory.in/llms.txt -->

# Avatar

The component that displays your character and animates its mouth as it speaks.

`` renders the character and keeps it in sync with the session —
loading, connection status, captions, and lip-sync are all handled for you. It
reads everything it needs from the nearest `AvatarProvider`, so it takes no
required props.

## Basic usage

Place it anywhere inside `AvatarProvider`. **Always give its parent a width and
height** — the avatar fills its container, so without a size it is invisible.

```tsx
import { Avatar } from "@avatarfactory/react";

export default function TalkingCharacter() {
  return (
    <div style={{ width: 500, height: 500 }}>
      <Avatar />
    </div>
  );
}
```

> **Always wrap `` in a sized container.** The canvas reads its pixel
>   dimensions from the parent. Without explicit width and height it renders at
>   zero size. This is the most common setup mistake.

## Props

### Content and fallbacks

| Prop | Type | Default | Description |
| --- | --- | --- | --- |
| `className` | `string` | — | CSS class on the avatar container. |
| `style` | `React.CSSProperties` | — | Inline styles on the avatar container. |
| `loader` | `React.ReactNode` | — | Shown while the avatar is resolving, and again during connect. Defaults to the SDK's animated orb; pass null to render nothing. |
| `errorFallback` | `React.ReactNode` | — | Shown when the avatar failed to load at all. A session that ends after the avatar is painted keeps the avatar, so it never reaches this. |
| `fit` | `string` | — | Overrides the fit the avatar was published with — "contain", "cover", "fill", "fitWidth", "fitHeight", "scaleDown", "layout", "none". Leave unset to use the published value. |

### Camera

Only relevant when `perception.camera` is enabled — see
[Camera perception](/docs/sdk/react/perception).

| Prop | Type | Default | Description |
| --- | --- | --- | --- |
| `cameraPreviewCorner` | `CameraPreviewCorner` | `"bottom-right"` | Where the self-view sits while a camera session is open. Ignored in picture-in-picture. |
| `hideCameraPreview` | `boolean` | `false` | Hide the self-view. Discouraged — it is how the user sees that their camera is on, and capture continues regardless. Ignored in picture-in-picture. |
| `usePictureInPicture` | `boolean` | `false` | Camera on the stage, avatar in the corner, once a camera session opens. Takes precedence over the two props above. |
| `pictureInPictureCorner` | `CameraPreviewCorner` | `"bottom-right"` | The avatar's corner in picture-in-picture. Independent of cameraPreviewCorner, since the two modes place different things. |

### Overlay styling hooks

Each built-in overlay takes a class and a style, so you can restyle it without
reaching into the SDK's CSS.

| Prop | Type | Default | Description |
| --- | --- | --- | --- |
| `captionClassName` | `string` | — | Class on the caption overlay. Shown when transcript.captions is on. |
| `captionStyle` | `React.CSSProperties` | — | Inline styles on the caption overlay. |
| `statusBannerClassName` | `string` | — | Class on the connectivity banner. Shown when statusBanner.enabled is on. |
| `statusBannerStyle` | `React.CSSProperties` | — | Inline styles on the connectivity banner. |
| `thinkingIndicatorClassName` | `string` | — | Class on the thinking indicator. Shown unless thinkingIndicator.enabled is false. |
| `thinkingIndicatorStyle` | `React.CSSProperties` | — | Inline styles on the thinking indicator. |

> Whether an overlay exists at all is a **provider** decision
>   (`transcript`, `statusBanner`, `thinkingIndicator`); how it looks is an
>   **Avatar** prop. Enabling and styling are deliberately separate.

## What it renders

Layers are conditional — a bare `` with default config renders only
the canvas and the connectivity dot.

| Layer | Shown when | What it is |
| --- | --- | --- |
| Rive canvas | Always | The animated character, lip-synced from character-level alignment data. |
| Connectivity dot | Always | A small indicator: green connected, red disconnected. Styleable with CSS. |
| Connecting overlay | While connecting | Your loader, or the SDK's animated orb. |
| Captions | transcript.captions | The live caption overlay, at the configured anchor. |
| Status banner | statusBanner.enabled | Connectivity warnings, driven by live stream health. Appears only when something is wrong. |
| Thinking indicator | thinkingIndicator.enabled | Animated dots, shown only while a turn is running unusually slow. |
| Controls bar | controls.enabled, call mode | Start / stop, mic and speaker mute, and — with controls.stopSpeaking — an interrupt button. Swaps to a hold-to-talk bar in push-to-talk mode. |
| Camera self-view | perception.camera, camera open | The user's own camera preview, in the configured corner. |

## Custom loader

```tsx
<div style={{ width: 400, height: 400 }}>
  <Avatar
    loader={
      <div className="flex h-full w-full items-center justify-center">
        <p className="text-white/70">Warming up the avatar…</p>
      </div>
    }
  />
</div>
```

Pass `loader={null}` to render nothing during loading.

The SDK's own loader is exported if you want it somewhere else, or with
different copy:

```tsx
import { AvatarConnectingLoader } from "@avatarfactory/react";

<Avatar loader={<AvatarConnectingLoader label="Waking up" />} />
```

It sizes itself from a container query, so the same node works in a 64px bubble
and a full-bleed stage.

## Error fallback

```tsx
<Avatar errorFallback={<p>We couldn&apos;t load the avatar. Please refresh.</p>} />
```

`` decides when to show this by checking whether an avatar is actually
on screen — not by looking at the error code — so it stays right whichever error
fired and whenever it fired. If you do nothing, it renders a built-in card, so
you never ship a blank frame. See
[Error Handling](/docs/sdk/react/error-handling).

## Sizing

### Fixed

```tsx
<div style={{ width: 400, height: 400 }}>
  <Avatar />
</div>
```

### Responsive, square

```tsx
<div className="mx-auto aspect-square w-full max-w-md">
  <Avatar />
</div>
```

### Circular

```tsx
<div className="relative h-64 w-64">
  <Avatar className="overflow-hidden rounded-full shadow-lg shadow-purple-500/25" />
</div>
```

### Full-width hero

```tsx
<div className="relative h-[600px] w-full">
  <Avatar className="rounded-none" fit="cover" />
  <div className="absolute bottom-8 left-8">
    <h1 className="text-4xl font-bold text-white">Meet Luna</h1>
    <p className="text-white/70">Your AI travel assistant</p>
  </div>
</div>
```

> `fit="cover"` crops the artboard to fill the frame — that is what reads as
>   "zoomed in" on a wide hero. `fit="contain"` keeps the whole character visible.
>   Leave `fit` unset to respect whatever the avatar was published with.

## Styling the connectivity dot

The dot is a DOM element with stable class names:

```css
.connectivity-dot.connected    { background-color: #22c55e; }
.connectivity-dot.disconnected { background-color: #ef4444; }
```

> Colour alone is not an accessible status signal. If connection state matters
>   to your users, pair the dot with a text label or an icon rather than relying on
>   green-versus-red.
