Finance
FX Exposure Card - Currency Risk
Monitor foreign exchange exposure and currency risk. Track hedging strategies and FX volatility impact.
Finance FX Exposure Card
The Finance FX Exposure Card monitors currency exposure across different markets, helping businesses manage foreign exchange risk.
Preview
Installation
npx shadcn@latest add https://vectormotion.vercel.app/registry/finance-fx-exposure-card.jsonFinance FX Exposure Card
'use client'import React from 'react';import { Globe, ArrowUpRight } from 'lucide-react';import { motion } from 'motion/react';import { clsx, type ClassValue } from "clsx"import { twMerge } from "tailwind-merge"import { ResponsiveContainer, PieChart, Pie, Cell, Tooltip } from 'recharts';function cn(...inputs: ClassValue[]) { return twMerge(clsx(inputs))}interface FXData { name: string; value: number; color: string; [key: string]: any;}interface FXExposureCardProps { isInteractive?: boolean; className?: string; title?: string; totalRisk?: string; riskLabel?: string; hedgedPercentage?: string; data?: FXData[];}const DEFAULT_TITLE = "FX Exposure";const DEFAULT_TOTAL_RISK = "$655k";const DEFAULT_RISK_LABEL = "Total Risk";const DEFAULT_HEDGED_PERCENTAGE = "65%";const DEFAULT_DATA: FXData[] = [ { name: 'EUR', value: 420, color: '#3b82f6' }, // Blue { name: 'GBP', value: 150, color: '#10b981' }, // Emerald { name: 'JPY', value: 85, color: '#f59e0b' }, // Amber];export const FXExposureCard: React.FC<FXExposureCardProps> = ({ isInteractive = true, className = "", title = DEFAULT_TITLE, totalRisk = DEFAULT_TOTAL_RISK, riskLabel = DEFAULT_RISK_LABEL, hedgedPercentage = DEFAULT_HEDGED_PERCENTAGE, data = DEFAULT_DATA,}) => { const index = 45; return ( <motion.div layoutId={isInteractive ? `card-${index}-${title}` : undefined} transition={{ duration: 0.4, ease: "easeOut" }} className={cn( "relative overflow-hidden rounded-xl border border-border bg-card text-card-foreground p-5 shadow-sm transition-all flex flex-col h-full group", isInteractive ? "cursor-pointer hover:border-primary/50 hover:shadow-md" : "", className )} > <div className="mb-2 flex items-start justify-between relative z-10"> <div> <h3 className="font-semibold text-lg text-foreground"> {title} </h3> <div className="flex items-center gap-2 mt-1"> <span className="text-2xl font-bold text-foreground">{totalRisk}</span> <span className="text-xs text-muted-foreground">{riskLabel}</span> </div> </div> <div className="rounded-lg bg-emerald-500/10 p-2 text-emerald-500"> <Globe className="h-5 w-5" /> </div> </div> <div className="relative z-10 flex-1 flex items-center justify-between gap-4"> <div className="h-24 w-24 flex-shrink-0"> <ResponsiveContainer width="100%" height="100%"> <PieChart> <Pie data={data} dataKey="value" innerRadius={20} outerRadius={35} stroke="none"> {data.map((entry, index) => ( <Cell key={`cell-${index}`} fill={entry.color} /> ))} </Pie> <Tooltip contentStyle={{ borderRadius: '8px', border: 'none', backgroundColor: 'var(--tooltip-bg)', color: 'var(--tooltip-text)', fontSize: '10px' }} /> </PieChart> </ResponsiveContainer> </div> <div className="flex-1 space-y-2"> {data.map((item) => ( <div key={item.name} className="flex items-center justify-between text-xs"> <div className="flex items-center gap-1.5"> <div className="w-1.5 h-1.5 rounded-full" style={{ backgroundColor: item.color }} /> <span className="text-muted-foreground font-medium">{item.name}</span> </div> <span className="font-medium text-foreground">${item.value}k</span> </div> ))} <div className="pt-1 border-t border-border"> <div className="flex items-center justify-between text-[10px] text-muted-foreground"> <span>Hedged</span> <span className="font-bold text-emerald-500">{hedgedPercentage}</span> </div> </div> </div> </div> </motion.div> );};Props
Prop
Type