{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "charts-3",
  "title": "Traffic Range Switcher",
  "description": "Stacked area chart of visitors and signups with a legend, hover tooltip, and a 7d, 30d, or 90d range select that swaps the dataset.",
  "dependencies": [
    "recharts",
    "@base-ui/react"
  ],
  "registryDependencies": [
    "badge",
    "card",
    "chart",
    "select"
  ],
  "files": [
    {
      "path": "registry/blocks/charts/3/charts-block.tsx",
      "content": "\"use client\"\n\nimport * as React from \"react\"\nimport { Area, AreaChart, CartesianGrid, XAxis, YAxis } from \"recharts\"\nimport { Badge } from \"@/components/ui/badge\"\nimport {\n  Card,\n  CardContent,\n  CardDescription,\n  CardHeader,\n  CardTitle,\n} from \"@/components/ui/card\"\nimport {\n  type ChartConfig,\n  ChartContainer,\n  ChartLegend,\n  ChartLegendContent,\n  ChartTooltip,\n  ChartTooltipContent,\n} from \"@/components/ui/chart\"\nimport {\n  Select,\n  SelectContent,\n  SelectItem,\n  SelectTrigger,\n  SelectValue,\n} from \"@/components/ui/select\"\nimport { IconPlaceholder } from \"@/components/icons/icon-placeholder\"\n\ntype RangeKey = \"7d\" | \"30d\" | \"90d\"\n\ntype DataPoint = {\n  label: string\n  visitors: number\n  signups: number\n}\n\nconst datasets: Record<RangeKey, DataPoint[]> = {\n  \"7d\": [\n    { label: \"Mon\", visitors: 4_120, signups: 312 },\n    { label: \"Tue\", visitors: 4_780, signups: 348 },\n    { label: \"Wed\", visitors: 5_240, signups: 401 },\n    { label: \"Thu\", visitors: 4_960, signups: 377 },\n    { label: \"Fri\", visitors: 6_310, signups: 489 },\n    { label: \"Sat\", visitors: 5_870, signups: 452 },\n    { label: \"Sun\", visitors: 5_120, signups: 398 },\n  ],\n  \"30d\": [\n    { label: \"Week 1\", visitors: 28_400, signups: 2_140 },\n    { label: \"Week 2\", visitors: 31_900, signups: 2_480 },\n    { label: \"Week 3\", visitors: 34_600, signups: 2_710 },\n    { label: \"Week 4\", visitors: 39_200, signups: 3_060 },\n  ],\n  \"90d\": [\n    { label: \"Jan\", visitors: 96_400, signups: 7_320 },\n    { label: \"Feb\", visitors: 104_800, signups: 8_010 },\n    { label: \"Mar\", visitors: 121_300, signups: 9_540 },\n  ],\n}\n\nconst ranges: { key: RangeKey; label: string }[] = [\n  { key: \"7d\", label: \"7 Days\" },\n  { key: \"30d\", label: \"30 Days\" },\n  { key: \"90d\", label: \"90 Days\" },\n]\n\nconst chartConfig = {\n  visitors: {\n    label: \"Visitors\",\n    color: \"var(--primary)\",\n  },\n  signups: {\n    label: \"Signups\",\n    color: \"var(--muted-foreground)\",\n  },\n} satisfies ChartConfig\n\nexport default function ChartsBlock() {\n  const [range, setRange] = React.useState<RangeKey>(\"30d\")\n  const data = datasets[range]\n\n  const totalVisitors = data.reduce((sum, d) => sum + d.visitors, 0)\n\n  const first = data[0]?.visitors ?? 0\n  const last = data[data.length - 1]?.visitors ?? 0\n  const deltaPct = first === 0 ? 0 : ((last - first) / first) * 100\n  const deltaUp = deltaPct >= 0\n\n  return (\n    <section className=\"flex w-full items-center justify-center bg-muted/30 px-6 py-16 text-foreground\">\n      <Card className=\"w-full max-w-3xl\">\n        <CardHeader className=\"flex flex-col gap-4 sm:flex-row sm:items-start sm:justify-between\">\n          <div className=\"space-y-1.5\">\n            <CardTitle>Traffic Overview</CardTitle>\n            <CardDescription>\n              Visitors and signups for Acme, last {range.replace(\"d\", \" days\")}\n            </CardDescription>\n            <div className=\"flex items-center gap-2 pt-2\">\n              <span className=\"text-2xl font-semibold tabular-nums\">\n                {totalVisitors.toLocaleString(\"en-US\")}\n              </span>\n              <Badge\n                variant={deltaUp ? \"secondary\" : \"destructive\"}\n                className=\"gap-1\"\n              >\n                {deltaUp ? (\n                  <IconPlaceholder\n                    lucide=\"ArrowUp\"\n                    tabler=\"IconArrowUp\"\n                    hugeicons=\"ArrowUpIcon\"\n                    phosphor=\"ArrowUp\"\n                    remixicon=\"RiArrowUpLine\"\n                    data-icon=\"inline-start\"\n                    className=\"size-3\"\n                  />\n                ) : (\n                  <IconPlaceholder\n                    lucide=\"ArrowDown\"\n                    tabler=\"IconArrowDown\"\n                    hugeicons=\"ArrowDownIcon\"\n                    phosphor=\"ArrowDown\"\n                    remixicon=\"RiArrowDownLine\"\n                    data-icon=\"inline-start\"\n                    className=\"size-3\"\n                  />\n                )}\n                {deltaUp ? \"+\" : \"\"}\n                {deltaPct.toFixed(1)}%\n              </Badge>\n            </div>\n          </div>\n          <Select\n            value={range}\n            onValueChange={(value) => setRange(value as RangeKey)}\n            items={ranges.map((r) => ({ value: r.key, label: r.label }))}\n          >\n            <SelectTrigger\n              className=\"w-28 shrink-0\"\n              aria-label=\"Select date range\"\n            >\n              <SelectValue />\n            </SelectTrigger>\n            <SelectContent>\n              {ranges.map((r) => (\n                <SelectItem key={r.key} value={r.key}>\n                  {r.label}\n                </SelectItem>\n              ))}\n            </SelectContent>\n          </Select>\n        </CardHeader>\n        <CardContent>\n          <ChartContainer\n            config={chartConfig}\n            className=\"h-72 w-full [&_.recharts-surface:focus-visible]:outline-2 [&_.recharts-surface:focus-visible]:outline-offset-2 [&_.recharts-surface:focus-visible]:outline-ring [&_.recharts-surface:focus-visible]:outline-solid\"\n          >\n            <AreaChart\n              aria-label=\"Visitors and signups over the selected range\"\n              data={data}\n              margin={{ left: 0, right: 8, top: 8 }}\n            >\n              <defs>\n                <linearGradient id=\"fillVisitors\" x1=\"0\" y1=\"0\" x2=\"0\" y2=\"1\">\n                  <stop\n                    offset=\"5%\"\n                    stopColor=\"var(--color-visitors)\"\n                    stopOpacity={0.35}\n                  />\n                  <stop\n                    offset=\"95%\"\n                    stopColor=\"var(--color-visitors)\"\n                    stopOpacity={0.02}\n                  />\n                </linearGradient>\n                <linearGradient id=\"fillSignups\" x1=\"0\" y1=\"0\" x2=\"0\" y2=\"1\">\n                  <stop\n                    offset=\"5%\"\n                    stopColor=\"var(--color-signups)\"\n                    stopOpacity={0.6}\n                  />\n                  <stop\n                    offset=\"95%\"\n                    stopColor=\"var(--color-signups)\"\n                    stopOpacity={0.1}\n                  />\n                </linearGradient>\n              </defs>\n              <CartesianGrid vertical={false} />\n              <XAxis\n                dataKey=\"label\"\n                tickLine={false}\n                axisLine={false}\n                tickMargin={8}\n              />\n              <YAxis\n                tickLine={false}\n                axisLine={false}\n                tickMargin={8}\n                width={44}\n                tickFormatter={(value) =>\n                  `${(Number(value) / 1000).toFixed(0)}k`\n                }\n              />\n              <ChartTooltip\n                cursor={false}\n                content={\n                  <ChartTooltipContent\n                    formatter={(value, name) => (\n                      <span className=\"flex w-full justify-between gap-4\">\n                        <span className=\"text-muted-foreground capitalize\">\n                          {String(name)}\n                        </span>\n                        <span className=\"font-medium tabular-nums\">\n                          {Number(value).toLocaleString(\"en-US\")}\n                        </span>\n                      </span>\n                    )}\n                  />\n                }\n              />\n              <Area\n                dataKey=\"visitors\"\n                type=\"monotone\"\n                stroke=\"var(--color-visitors)\"\n                strokeWidth={2}\n                fill=\"url(#fillVisitors)\"\n                stackId=\"a\"\n              />\n              <Area\n                dataKey=\"signups\"\n                type=\"monotone\"\n                stroke=\"var(--color-signups)\"\n                strokeWidth={2}\n                strokeDasharray=\"4 3\"\n                fill=\"url(#fillSignups)\"\n                stackId=\"b\"\n              />\n              <ChartLegend content={<ChartLegendContent />} />\n            </AreaChart>\n          </ChartContainer>\n        </CardContent>\n      </Card>\n    </section>\n  )\n}\n",
      "type": "registry:component",
      "target": "components/blocks/charts-3.tsx"
    }
  ],
  "meta": {
    "height": "564px",
    "tier": "free"
  },
  "categories": [
    "charts"
  ],
  "type": "registry:block"
}