Avatar Group - Overlapping avatar group
A horizontal row of overlapping circular avatars with spacing variants, hover spread, and an overflow count badge.
components/shadcnblocks/avatar-group.tsx
import { cva, type VariantProps } from "class-variance-authority";
import { Children, type ReactNode } from "react";
import { cn } from "cn";
const AvatarGroupVariants = cva("flex items-center", {
variants: {
spacing: {
tight: "-space-x-2",
default: "-space-x-1",
loose: "-space-x-0.5",
none: "space-x-0",
},
},
defaultVariants: {
spacing: "default",
},
});
export type AvatarGroupProps = {
children: ReactNode;
className?: string;
animate?: boolean;
size?: number;
} & VariantProps<typeof AvatarGroupVariants>;
export type AvatarMoreProps = {
count: number;
className?: string;
size?: number;
};
export const AvatarMore = ({
count,
className,
size = 40,
...props
}: AvatarMoreProps) => (
<div
data-slot="avatar"
className={cn(
"flex shrink-0 items-center justify-center overflow-hidden rounded-full bg-muted text-xs font-medium text-muted-foreground",
className,
)}
style={{
width: size,
height: size,
}}
{...props}
>
+{count}
</div>
);
export const AvatarGroup = ({
children,
className,
animate = false,
spacing,
...props
}: AvatarGroupProps) => (
<div
className={cn(
"h-14",
AvatarGroupVariants({ spacing }),
animate && "hover:space-x-0 [&>*]:transition-all",
className,
)}
{...props}
>
{Children.map(children, (child) => {
if (!child) {
return null;
}
return child;
})}
</div>
);
No selection tags yet — empty means no evidence, not lack of support.
More from ShadcnBlocks
About 1 - Intro With Story ColumnsblockAbout 10 - Sticky Sidebar Company ProfileblockAbout 11 - Creative Agency PortfolioblockAbout 12 - Agency Profile with Process CardsblockAbout 13 - Story with Avatar ProfileblockAbout 14 - About with Hero ImageblockAbout 15 - Tilted Photo Profile CardblockAbout 16 - Why Us Stats Sectionblock
Browse all components in this library →