Files
reui-blocks/blocks/chart-card26.tsx
T

202 lines
5.5 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
"use client";
import {
Area,
AreaChart,
CartesianGrid,
ReferenceArea,
ReferenceLine,
XAxis,
YAxis,
} from "recharts";
import {
Card,
CardContent,
CardDescription,
CardHeader,
CardTitle,
} from "@/components/ui/card";
import {
type ChartConfig,
ChartContainer,
ChartTooltip,
ChartTooltipContent,
} from "@/components/ui/chart";
import { cn } from "@/lib/utils";
interface ChartCard26Props {
title?: string;
description?: string;
target?: number;
upperBound?: number;
lowerBound?: number;
className?: string;
}
const monthLabel = (monthIndex: number) =>
new Intl.DateTimeFormat("fa-IR", { month: "short" }).format(
new Date(2025, monthIndex, 1),
);
const currencyFormatter = new Intl.NumberFormat("fa-IR", {
style: "currency",
currency: "IRR",
minimumFractionDigits: 0,
maximumFractionDigits: 0,
});
const compactCurrencyFormatter = new Intl.NumberFormat("fa-IR", {
style: "currency",
currency: "IRR",
notation: "compact",
minimumFractionDigits: 0,
maximumFractionDigits: 0,
});
const chartData = [
{ month: monthLabel(0), value: 186 },
{ month: monthLabel(1), value: 305 },
{ month: monthLabel(2), value: 237 },
{ month: monthLabel(3), value: 273 },
{ month: monthLabel(4), value: 209 },
{ month: monthLabel(5), value: 314 },
{ month: monthLabel(6), value: 286 },
{ month: monthLabel(7), value: 320 },
{ month: monthLabel(8), value: 298 },
{ month: monthLabel(9), value: 342 },
];
const chartConfig = {
value: {
label: "درآمد",
color: "var(--chart-1)",
},
} satisfies ChartConfig;
const ChartCard26 = ({
title = "درآمد با باند هدف",
description = "درآمد ماهانه در بازه مجاز",
target = 280,
upperBound = 320,
lowerBound = 240,
className,
}: ChartCard26Props) => {
return (
<Card
dir="rtl"
lang="fa"
className={cn("w-full max-w-2xl text-start", className)}
>
<CardHeader>
<CardTitle>{title}</CardTitle>
<CardDescription>{description}</CardDescription>
</CardHeader>
<CardContent>
<ChartContainer config={chartConfig} className="h-64 w-full">
<AreaChart
data={chartData}
margin={{ top: 10, right: 10, left: 0, bottom: 0 }}
>
<defs>
<linearGradient id="chartGradient26" x1="0" y1="0" x2="0" y2="1">
<stop
offset="0%"
stopColor="var(--color-value)"
stopOpacity={0.3}
/>
<stop
offset="100%"
stopColor="var(--color-value)"
stopOpacity={0}
/>
</linearGradient>
</defs>
<CartesianGrid strokeDasharray="3 3" vertical={false} />
<XAxis
dataKey="month"
axisLine={false}
tickLine={false}
tickMargin={8}
fontSize={12}
/>
<YAxis
axisLine={false}
tickLine={false}
tickMargin={8}
fontSize={10}
width={48}
domain={[150, 400]}
tickFormatter={(value) =>
compactCurrencyFormatter.format(Number(value))
}
/>
<ReferenceArea
y1={lowerBound}
y2={upperBound}
fill="var(--chart-2)"
fillOpacity={0.1}
/>
<ReferenceLine
y={target}
stroke="var(--chart-2)"
strokeDasharray="4 4"
strokeWidth={2}
/>
<ReferenceLine
y={upperBound}
stroke="var(--chart-2)"
strokeOpacity={0.4}
strokeWidth={1}
/>
<ReferenceLine
y={lowerBound}
stroke="var(--chart-2)"
strokeOpacity={0.4}
strokeWidth={1}
/>
<ChartTooltip
content={
<ChartTooltipContent
formatter={(value) =>
currencyFormatter.format(Number(value))
}
/>
}
cursor={{ stroke: "var(--border)", strokeDasharray: "4 4" }}
/>
<Area
type="monotone"
dataKey="value"
stroke="var(--color-value)"
strokeWidth={2}
fill="url(#chartGradient26)"
/>
</AreaChart>
</ChartContainer>
<div className="mt-4 flex flex-wrap items-center justify-center gap-6 text-sm">
<div className="flex items-center gap-2">
<div className="h-0.5 w-4 bg-[var(--chart-1)]" />
<span className="text-muted-foreground">درآمد</span>
</div>
<div className="flex items-center gap-2">
<div className="h-0.5 w-4 border-t-2 border-dashed border-[var(--chart-2)]" />
<span className="text-muted-foreground tabular-nums">
هدف ({currencyFormatter.format(target)})
</span>
</div>
<div className="flex items-center gap-2">
<div className="h-3 w-4 rounded-sm bg-[var(--chart-2)] opacity-20" />
<span className="text-muted-foreground tabular-nums">
بازه ({currencyFormatter.format(lowerBound)}–
{currencyFormatter.format(upperBound)})
</span>
</div>
</div>
</CardContent>
</Card>
);
};
export { ChartCard26 };