feat(frontend): Update analytics cards to match home page design consistency.

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Elisiário Couto
2025-09-17 22:23:34 +01:00
parent 155a48d7dc
commit d9a39c30ab
2 changed files with 53 additions and 38 deletions

View File

@@ -12,6 +12,7 @@ interface StatCardProps {
isPositive: boolean; isPositive: boolean;
}; };
className?: string; className?: string;
iconColor?: "green" | "blue" | "red" | "purple" | "orange" | "default";
} }
export default function StatCard({ export default function StatCard({
@@ -21,43 +22,58 @@ export default function StatCard({
icon: Icon, icon: Icon,
trend, trend,
className, className,
iconColor = "default",
}: StatCardProps) { }: StatCardProps) {
return ( return (
<Card className={cn(className)}> <Card className={cn(className)}>
<CardContent className="p-6"> <CardContent className="p-6">
<div className="flex items-center"> <div className="flex items-center justify-between">
<div className="flex-shrink-0"> <div>
<Icon className="h-8 w-8 text-primary" /> <p className="text-sm font-medium text-muted-foreground">
</div> {title}
<div className="ml-5 w-0 flex-1"> </p>
<dl> <div className="flex items-baseline">
<dt className="text-sm font-medium text-muted-foreground truncate"> <p className="text-2xl font-bold text-foreground">
{title} {value}
</dt> </p>
<dd className="flex items-baseline"> {trend && (
<div className="text-2xl font-semibold text-foreground"> <div
{value} className={cn(
"ml-2 flex items-baseline text-sm font-semibold",
trend.isPositive
? "text-green-600 dark:text-green-400"
: "text-red-600 dark:text-red-400",
)}
>
{trend.isPositive ? "+" : ""}
{trend.value}%
</div> </div>
{trend && (
<div
className={cn(
"ml-2 flex items-baseline text-sm font-semibold",
trend.isPositive
? "text-green-600 dark:text-green-400"
: "text-red-600 dark:text-red-400",
)}
>
{trend.isPositive ? "+" : ""}
{trend.value}%
</div>
)}
</dd>
{subtitle && (
<dd className="text-sm text-muted-foreground mt-1">
{subtitle}
</dd>
)} )}
</dl> </div>
{subtitle && (
<p className="text-sm text-muted-foreground mt-1">
{subtitle}
</p>
)}
</div>
<div className={cn(
"p-3 rounded-full",
iconColor === "green" && "bg-green-100 dark:bg-green-900/20",
iconColor === "blue" && "bg-blue-100 dark:bg-blue-900/20",
iconColor === "red" && "bg-red-100 dark:bg-red-900/20",
iconColor === "purple" && "bg-purple-100 dark:bg-purple-900/20",
iconColor === "orange" && "bg-orange-100 dark:bg-orange-900/20",
iconColor === "default" && "bg-muted"
)}>
<Icon className={cn(
"h-6 w-6",
iconColor === "green" && "text-green-600",
iconColor === "blue" && "text-blue-600",
iconColor === "red" && "text-red-600",
iconColor === "purple" && "text-purple-600",
iconColor === "orange" && "text-orange-600",
iconColor === "default" && "text-muted-foreground"
)} />
</div> </div>
</div> </div>
</CardContent> </CardContent>

View File

@@ -80,20 +80,21 @@ function AnalyticsDashboard() {
value={stats?.total_transactions || 0} value={stats?.total_transactions || 0}
subtitle={`Last ${stats?.period_days || 0} days`} subtitle={`Last ${stats?.period_days || 0} days`}
icon={Activity} icon={Activity}
iconColor="blue"
/> />
<StatCard <StatCard
title="Total Income" title="Total Income"
value={`${(stats?.total_income || 0).toLocaleString()}`} value={`${(stats?.total_income || 0).toLocaleString()}`}
subtitle="Inflows this period" subtitle="Inflows this period"
icon={TrendingUp} icon={TrendingUp}
className="border-green-200" iconColor="green"
/> />
<StatCard <StatCard
title="Total Expenses" title="Total Expenses"
value={`${(stats?.total_expenses || 0).toLocaleString()}`} value={`${(stats?.total_expenses || 0).toLocaleString()}`}
subtitle="Outflows this period" subtitle="Outflows this period"
icon={TrendingDown} icon={TrendingDown}
className="border-red-200" iconColor="red"
/> />
</div> </div>
@@ -104,23 +105,21 @@ function AnalyticsDashboard() {
value={`${(stats?.net_change || 0).toLocaleString()}`} value={`${(stats?.net_change || 0).toLocaleString()}`}
subtitle="Income minus expenses" subtitle="Income minus expenses"
icon={CreditCard} icon={CreditCard}
className={ iconColor={(stats?.net_change || 0) >= 0 ? "green" : "red"}
(stats?.net_change || 0) >= 0
? "border-green-200"
: "border-red-200"
}
/> />
<StatCard <StatCard
title="Average Transaction" title="Average Transaction"
value={`${Math.abs(stats?.average_transaction || 0).toLocaleString()}`} value={`${Math.abs(stats?.average_transaction || 0).toLocaleString()}`}
subtitle="Per transaction" subtitle="Per transaction"
icon={Activity} icon={Activity}
iconColor="purple"
/> />
<StatCard <StatCard
title="Active Accounts" title="Active Accounts"
value={stats?.accounts_included || 0} value={stats?.accounts_included || 0}
subtitle="With recent activity" subtitle="With recent activity"
icon={Users} icon={Users}
iconColor="orange"
/> />
</div> </div>