diff --git a/resources/js/components/dashboard/account-balance-card.tsx b/resources/js/components/dashboard/account-balance-card.tsx index b87268a9..6c112d7f 100644 --- a/resources/js/components/dashboard/account-balance-card.tsx +++ b/resources/js/components/dashboard/account-balance-card.tsx @@ -1,8 +1,9 @@ import { EncryptedText } from '@/components/encrypted-text'; import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card'; import { Account } from '@/types/account'; -import { ArrowDownIcon, ArrowUpIcon } from 'lucide-react'; -import { Line, LineChart, ResponsiveContainer } from 'recharts'; +import { AmountTrendIndicator } from './amount-trend-indicator'; +import { AccountTypeIcon } from './account-type-icon'; +import { Line, LineChart, ResponsiveContainer, Tooltip } from 'recharts'; interface AccountBalanceCardProps { account: Account & { @@ -46,43 +47,55 @@ export function AccountBalanceCard({
- {account.type} +
-
-
-
+
+
+
{formatter.format(account.currentBalance / 100)}
-

- - {isPositive ? ( - - ) : ( - - )} - {formatter.format(Math.abs(account.diff) / 100)} - - vs last month -

+
-
+
+ { + if (!active || !payload?.length) + return null; + const data = payload[0].payload as { + date: string; + value: number; + }; + return ( +
+

+ {data.date} +

+

+ {formatter.format( + data.value / 100, + )} +

+
+ ); + }} + /> diff --git a/resources/js/components/dashboard/account-type-icon.tsx b/resources/js/components/dashboard/account-type-icon.tsx new file mode 100644 index 00000000..78070aa8 --- /dev/null +++ b/resources/js/components/dashboard/account-type-icon.tsx @@ -0,0 +1,20 @@ +import { cn } from "@/lib/utils"; +import { AccountType } from "@/types/account"; +import { BadgeQuestionMarkIcon, Building2, CreditCard, FolderKanban, Landmark, LucideIcon, PiggyBank } from "lucide-react"; + +export function AccountTypeIcon({ type, className }: { type: AccountType, className?: string }) { + const typeMap: Record = { + checking: Building2, // 🏦 - bank / institution + credit_card: CreditCard, // 💳 - card + loan: Landmark, // 🏠 - "institution/loan", or use Home if it's a mortgage + savings: PiggyBank, // 💰 - savings + others: FolderKanban, // 📁 - miscellaneous/other + }; + + const Icon = typeMap[type] || BadgeQuestionMarkIcon; + + return ; +} diff --git a/resources/js/components/dashboard/amount-trend-indicator.tsx b/resources/js/components/dashboard/amount-trend-indicator.tsx new file mode 100644 index 00000000..e288a6c3 --- /dev/null +++ b/resources/js/components/dashboard/amount-trend-indicator.tsx @@ -0,0 +1,38 @@ +import { cn } from "@/lib/utils"; +import { TrendingUp, TrendingDown } from "lucide-react"; + +export function AmountTrendIndicator({ + trend, + isPositive, + label, + className = '', +}: { + trend: string | null; + isPositive: boolean; + label: string; + className?: string; +}) { + if (trend === null) return null; + + const Icon = isPositive ? TrendingUp : TrendingDown; + const iconColorClass = isPositive + ? 'text-green-600/70 dark:text-green-400/70' + : 'text-red-600/70 dark:text-red-400/70'; + + return ( +
+ + {trend} + + {label} + +
+ ); +} diff --git a/resources/js/components/dashboard/net-worth-chart.tsx b/resources/js/components/dashboard/net-worth-chart.tsx index 8b24a8e0..ed20dcc2 100644 --- a/resources/js/components/dashboard/net-worth-chart.tsx +++ b/resources/js/components/dashboard/net-worth-chart.tsx @@ -12,8 +12,8 @@ import { StackedBarChart, } from '@/components/ui/stacked-bar-chart'; import { NetWorthEvolutionData } from '@/hooks/use-dashboard-data'; -import { TrendingDown, TrendingUp } from 'lucide-react'; import { useMemo } from 'react'; +import { PercentageTrendIndicator } from './percentage-trend-indicator'; interface NetWorthChartProps { data: NetWorthEvolutionData; @@ -71,37 +71,6 @@ function calculateTrend( return ((currentTotal - previousTotal) / Math.abs(previousTotal)) * 100; } -function TrendIndicator({ - trend, - label, -}: { - trend: number | null; - label: string; -}) { - if (trend === null) return null; - - const isPositive = trend >= 0; - const Icon = isPositive ? TrendingUp : TrendingDown; - const iconColorClass = isPositive - ? 'text-green-600/70 dark:text-green-400/70' - : 'text-red-600/70 dark:text-red-400/70'; - - return ( -
- - {isPositive ? '+' : ''} - {trend.toFixed(1)}% - - {label} - -
- ); -} - interface EncryptedLabelProps { account: { name: string; name_iv: string }; } @@ -261,11 +230,11 @@ export function NetWorthChart({ Net Worth Evolution
- - diff --git a/resources/js/components/dashboard/percentage-trend-indicator.tsx b/resources/js/components/dashboard/percentage-trend-indicator.tsx new file mode 100644 index 00000000..b3bae525 --- /dev/null +++ b/resources/js/components/dashboard/percentage-trend-indicator.tsx @@ -0,0 +1,32 @@ +import { TrendingUp, TrendingDown } from "lucide-react"; + +export function PercentageTrendIndicator({ + trend, + label, +}: { + trend: number | null; + label: string; +}) { + if (trend === null) return null; + + const isPositive = trend >= 0; + const Icon = isPositive ? TrendingUp : TrendingDown; + const iconColorClass = isPositive + ? 'text-green-600/70 dark:text-green-400/70' + : 'text-red-600/70 dark:text-red-400/70'; + + return ( +
+ + {isPositive ? '+' : ''} + {trend.toFixed(1)}% + + {label} + +
+ ); +}