@lattice-ui/avatar Part of the stable direction toward v1.0.
What It Is For
Use Avatar for profile chips, player lists, or presence surfaces where image loading and fallback timing need to stay consistent.
The package separates image state from rendering, so you can fully own the Roblox instances used for the picture and the fallback.
import { Avatar } from "@lattice-ui/avatar";
import React from "@rbxts/react";
export function AvatarExample() {
const [broken, setBroken] = React.useState(false);
const src = broken
? "rbxassetid://0"
: "rbxasset://textures/ui/GuiImagePlaceholder.png";
return (
<frame BackgroundTransparency={1} Size={UDim2.fromOffset(360, 170)}>
<Avatar.Root delayMs={250} src={src}>
<frame
BackgroundColor3={Color3.fromRGB(34, 41, 54)}
BorderSizePixel={0}
Size={UDim2.fromOffset(64, 64)}
>
<uicorner CornerRadius={new UDim(1, 0)} />
<Avatar.Image asChild>
<imagelabel
BackgroundTransparency={1}
BorderSizePixel={0}
Size={UDim2.fromScale(1, 1)}
>
<uicorner CornerRadius={new UDim(1, 0)} />
</imagelabel>
</Avatar.Image>
<Avatar.Fallback asChild>
<textlabel
BackgroundTransparency={1}
BorderSizePixel={0}
Size={UDim2.fromScale(1, 1)}
Text="UI"
TextColor3={Color3.fromRGB(236, 240, 248)}
TextSize={18}
/>
</Avatar.Fallback>
</frame>
</Avatar.Root>
<textbutton
AutoButtonColor={false}
BackgroundColor3={Color3.fromRGB(34, 41, 54)}
BorderSizePixel={0}
Position={UDim2.fromOffset(0, 84)}
Size={UDim2.fromOffset(220, 36)}
Text={broken ? "Use valid image" : "Use broken image"}
TextColor3={Color3.fromRGB(236, 240, 248)}
TextSize={14}
Event={{
Activated: () => setBroken((value) => !value),
}}
>
<uicorner CornerRadius={new UDim(0, 8)} />
</textbutton>
</frame>
);
} Live demo is experimental and may contain bugs.
Install
Global CLI command: lattice add avatar
Monorepo local script
Use your package manager wrapper when running the local lattice command.
pnpm lattice add avatarPublic Exports
-
Avatar -
Avatar.Root -
Avatar.Image -
Avatar.Fallback -
resolveAvatarFallbackVisible
State Model
Avatar.Roottrackssrc, imagestatus, and whether the fallback delay has elapsed.Avatar.ImageandAvatar.Fallbackread the same state, so they stay synchronized without manual branching in the caller.delayMscontrols when the fallback becomes visible while the image is still unresolved.
Key API
Avatar.Root
Pass src and optional delayMs to control image loading behavior and fallback reveal timing.
Avatar.Image
Use asChild to bind the avatar state onto your own ImageLabel or similar host element.
Avatar.Fallback
Render initials, status dots, or silhouette content only when the shared avatar state says the fallback should appear.
Composition Patterns
Player roster rows
Keep the host image primitive small and let the fallback render initials or a status badge without duplicating load/error state outside the avatar tree.
Dense status chips
Short delayMs values work well when a missing image should reveal fallback content quickly in compact, frequently changing lists.
Cautions / Limits
- Fallback visibility is state-driven; do not mount a separate unconditional fallback outside
Avatar.Fallbackif you want consistent behavior. - A missing or failed image source resolves to fallback immediately, while a loading image waits for the configured delay.