Profile photo fallback
Most people never upload a photo. Show their avatar instead of a grey silhouette, and the list of faces in your app tells people apart at a glance.
When there's no photo
import { botlingDataUri } from 'seedkin/botling';
<img src={user.photoUrl ?? botlingDataUri(user.id, { size: 40, title: null })} alt="" width={40} height={40} />
Seed with the same id everywhere, so the person keeps one avatar across the app.
When the photo won't load
A photo URL can break: a deleted file, an expired link, a blocked host. Swap in the avatar when it does:
import { useState } from 'react';
import { botlingDataUri } from 'seedkin/botling';
export function UserAvatar({ user, size = 40 }: { user: { id: string; photoUrl?: string }; size?: number }) {
const [failed, setFailed] = useState(false);
const src = user.photoUrl && !failed ? user.photoUrl : botlingDataUri(user.id, { size, title: null });
return <img src={src} onError={() => setFailed(true)} alt="" width={size} height={size} />;
}
Render it with key={user.id} in lists, so a failure for one person doesn't carry over to the next.
Instead of initials
Coloured initials collide: two Alexes look the same. A seeded avatar comes from the whole id, so it doesn't. Keep the person's name next to it as text, which is what screen readers and search use.