Deterministic SVG avatars

One seed in, the same avatar out — every time.

Cast is a tiny, dependency-free library that turns any string into a crisp SVG avatar. Many styles, deep traits, themeable palettes, and presence badges — all generated in the browser, no network required.

Open the playground
  • Zero dependencies
  • Many styles
  • Deterministic
  • TypeScript types
  • Web component
  • MIT

Playground

Tweak the seed and traits and watch the avatar resolve live. Everything here runs in your browser — copy the SVG, grab a data-URI, export a PNG, or share a link to this exact avatar.

Seed

Every style, one seed

Every style is deterministic from the seed. The same identity reads consistently across the illustrated faces, while the abstract styles derive their composition from the seed alone.

One mark for a team

Compose member seeds into a single group avatar — a clipped mosaic with a +N chip for larger teams. Perfect for squads, channels, and group DMs.

Or mergeSeeds() two identities into one stable, order-independent mark — for a pair, a connection, or a DM thread. merge(a, b) === merge(b, a).

Need a whole team at once? The Team Builder turns a pasted list of names into a styled set of avatars — tweak individuals, then export SVGs, a sprite, a group mark, or a code snippet. No code required.

Open the Team Builder →

Drop it in

Use it from npm, straight from a CDN, or as a custom element. Same deterministic output everywhere.

npm
import { createAvatar } from 'cast-avatar';

const svg = createAvatar('ada@example.com', {
  style: 'portrait',
  status: 'online',
});
CDN / web component
<script type="module"
  src="https://cdn.jsdelivr.net/npm/cast-avatar/element/+esm"></script>

<cast-avatar seed="ada@example.com" variant="portrait" size="96"></cast-avatar>
Theme a roster
import { createAvatarSprite } from 'cast-avatar';

const brand = { backgrounds: ['#0f172a'], shapeColors: ['#22d3ee', '#a78bfa'] };
const sheet = createAvatarSprite(agentIds, { style: 'bot', palette: brand, columns: 8 });
Persist by seed
import { avatarHash, encodeAvatar } from 'cast-avatar';

// store the seed for a stable avatar; encodeAvatar pins the exact config
const key = avatarHash('agent-7');
const config = encodeAvatar('agent-7', { style: 'portrait' });
Serve from the edge
// Cloudflare Workers / Vercel Edge / Deno — no DOM, zero deps
export default {
  fetch(req) {
    const seed = new URL(req.url).searchParams.get('seed') ?? 'cast';
    return new Response(createAvatar(seed, { style: 'portrait' }), {
      headers: { 'content-type': 'image/svg+xml' },
    });
  },
};