Avatar Group
thegridcn/avatar-groupFreeComponent
thegridcn publishes no description for this item.
Install it
npx shadcn@latest add https://thegridcn.com/r/avatar-group.jsonSource
1"use client";23import * as React from "react";4import { cn } from "@/lib/utils";56interface AvatarGroupUser {7 avatar?: string | React.ReactNode;8 name: string;9 status?: "online" | "offline" | "away";10}1112interface AvatarGroupProps extends React.HTMLAttributes<HTMLDivElement> {13 max?: number;14 size?: "sm" | "md" | "lg";15 users: AvatarGroupUser[];16}1718const sizeConfig: Record<19 string,20 { dim: number; text: string; ring: string; badge: string }21> = {22 lg: { badge: "h-3 w-3", dim: 44, ring: "ring-2", text: "text-xs" },23 md: { badge: "h-2.5 w-2.5", dim: 36, ring: "ring-2", text: "text-[10px]" },24 sm: { badge: "h-2 w-2", dim: 28, ring: "ring-1", text: "text-[9px]" },25};2627const statusColors: Record<string, string> = {28 away: "bg-amber-500 shadow-[0_0_4px_rgba(245,158,11,0.6)]",29 offline: "bg-foreground/30",30 online: "bg-green-500 shadow-[0_0_4px_rgba(34,197,94,0.6)]",31};3233export function AvatarGroup({34 users,35 max = 5,36 size = "md",37 className,38 ...props39}: AvatarGroupProps) {40 const visible = users.slice(0, max);41 const remaining = users.length - max;42 const config = sizeConfig[size];4344 function getInitials(name: string) {45 return name46 .split(" ")47 .map((w) => w[0])48 .join("")49 .toUpperCase()50 .slice(0, 2);51 }5253 // Stagger reveal54 const [revealedIdx, setRevealedIdx] = React.useState(-1);55 React.useEffect(() => {56 let idx = 0;57 const total = visible.length + (remaining > 0 ? 1 : 0);58 const interval = setInterval(() => {59 setRevealedIdx(idx);60 idx++;61 if (idx >= total) {62 clearInterval(interval);63 }64 }, 80);65 return () => clearInterval(interval);66 }, [visible.length, remaining]);6768 return (69 <div70 data-slot="tron-avatar-group"71 className={cn("flex items-center", className)}72 {...props}73 >74 {visible.map((user, i) => (75 <div76 key={i}77 className={cn(78 "relative shrink-0 rounded-full ring-background transition-all duration-300",79 config.ring,80 i > 0 && "-ml-2",81 i <= revealedIdx ? "scale-100 opacity-100" : "scale-75 opacity-0"82 )}83 style={{ height: config.dim, width: config.dim }}84 title={user.name}85 >86 {user.avatar ? (87 typeof user.avatar === "string" ? (88 <img89 src={user.avatar}90 alt={user.name}91// … truncated
Files it writes
More from thegridcn
All 139 items| Component | Registry | Kind | Access | Installs | Command |
|---|---|---|---|---|---|
| Accordionaccordion | thegridcn | Components | Free | 2 deps | |
| Agent Avataragent-avatar | thegridcn | Components | Free | no deps | |
| Alertalert | thegridcn | Components | Free | 1 dep | |
| Alert Dialogalert-dialog | thegridcn | Components | Free | 1 dep | |
| Announcement Barannouncement-bar | thegridcn | Components | Free | no deps | |
| Anomaly Banneranomaly-banner | thegridcn | Components | Free | no deps | |
| Arrival Panelarrival-panel | thegridcn | Components | Free | no deps | |
| Aspect Ratioaspect-ratio | thegridcn | Components | Free | 1 dep |
