Files
twotalesanimation 0fbe856dce Initial commit
2026-05-19 22:20:29 +02:00

95 lines
3.1 KiB
TypeScript

"use client";
import { Avatar, AvatarFallback, AvatarImage } from "@/components/ui/avatar";
import { cn, getInitials, formatRelativeDate } from "@/lib/utils";
import { ScrollArea } from "@/components/ui/scroll-area";
import {
Film,
MessageSquare,
CheckCircle2,
XCircle,
Upload,
Bell,
AtSign,
} from "lucide-react";
interface ActivityItem {
id: string;
type: string;
title: string;
message: string;
createdAt: Date;
user?: {
name: string | null;
image: string | null;
} | null;
}
interface RecentActivityProps {
activities: ActivityItem[];
}
const ACTIVITY_ICONS: Record<string, { icon: React.ElementType; color: string }> = {
VERSION_UPLOADED: { icon: Upload, color: "text-blue-400 bg-blue-500/10" },
FEEDBACK_ADDED: { icon: MessageSquare, color: "text-amber-400 bg-amber-500/10" },
SHOT_APPROVED: { icon: CheckCircle2, color: "text-emerald-400 bg-emerald-500/10" },
SHOT_REJECTED: { icon: XCircle, color: "text-red-400 bg-red-500/10" },
COMMENT_REPLY: { icon: MessageSquare, color: "text-purple-400 bg-purple-500/10" },
MENTION: { icon: AtSign, color: "text-primary bg-primary/10" },
REVISION_REQUESTED: { icon: Film, color: "text-orange-400 bg-orange-500/10" },
};
export function RecentActivity({ activities }: RecentActivityProps) {
if (activities.length === 0) {
return (
<div className="flex flex-col items-center justify-center py-10 text-zinc-500">
<Bell className="h-8 w-8 mb-3 opacity-30" />
<p className="text-sm">No recent activity</p>
</div>
);
}
return (
<ScrollArea className="h-full">
<div className="space-y-1 p-1">
{activities.map((item) => {
const cfg = ACTIVITY_ICONS[item.type] ?? { icon: Bell, color: "text-muted-foreground bg-muted/20" };
const Icon = cfg.icon;
return (
<div
key={item.id}
className="flex gap-3 px-2 py-2.5 rounded-lg hover:bg-secondary/30 transition-colors"
>
<div className={cn("p-1.5 rounded-md shrink-0 mt-0.5", cfg.color.split(" ")[1])}>
<Icon className={cn("h-3 w-3", cfg.color.split(" ")[0])} />
</div>
<div className="flex-1 min-w-0">
<p className="text-sm font-medium truncate">{item.title}</p>
<p className="text-xs text-muted-foreground line-clamp-2 mt-0.5">
{item.message}
</p>
</div>
<div className="flex flex-col items-end gap-1 shrink-0">
{item.user && (
<Avatar className="h-5 w-5">
{item.user.image && <AvatarImage src={item.user.image} />}
<AvatarFallback className="text-[8px]">
{getInitials(item.user.name)}
</AvatarFallback>
</Avatar>
)}
<span className="text-xs text-muted-foreground whitespace-nowrap">
{formatRelativeDate(item.createdAt)}
</span>
</div>
</div>
);
})}
</div>
</ScrollArea>
);
}