{"$schema":"https://ui.shadcn.com/schema/registry-item.json","name":"pricing-9","type":"registry:block","title":"Pricing 9","description":"","dependencies":["lucide-react","motion"],"registryDependencies":["https://www.diarmuradi.com/r/styles/base-nova/badge.json","https://www.diarmuradi.com/r/styles/base-nova/button.json","https://www.diarmuradi.com/r/styles/base-nova/fancy-button.json","https://www.diarmuradi.com/r/styles/base-nova/switch.json"],"files":[{"path":"pricing.tsx","type":"registry:block","content":"\"use client\"\n\nimport { useState } from \"react\"\nimport { AnimatePresence, motion, type Variants } from \"motion/react\"\n\nimport { Badge } from \"@/components/ui/badge\"\nimport { Button } from \"@/components/ui/button\"\nimport { Switch } from \"@/components/ui/switch\"\nimport { FancyButton } from \"@/components/fancy-button\"\nimport { ArrowUpRightIcon, ChartLineIcon, CheckIcon, CodeIcon, DatabaseIcon, LockIcon, RepeatIcon, SettingsIcon } from 'lucide-react'\n\nconst animVariant: Variants = {\n  initial: { opacity: 0, y: 10, filter: \"blur(4px)\", scale: 0.98 },\n  animate: (i: number) => ({\n    opacity: 1,\n    y: 0,\n    filter: \"blur(0px)\",\n    scale: 1,\n    transition: {\n      delay: i * 0.03,\n      type: \"spring\",\n      damping: 22,\n      stiffness: 280,\n    },\n  }),\n  exit: {\n    opacity: 0,\n    y: -10,\n    filter: \"blur(4px)\",\n    scale: 0.98,\n    transition: { duration: 0.14 },\n  },\n}\n\ntype FeatureToggle = {\n  id: string\n  label: string\n  icon?: React.ReactNode\n  price: number\n  enabled: boolean\n}\n\nconst defaultFeatures: FeatureToggle[] = [\n  {\n    id: \"analytics\",\n    label: \"Analytics engine\",\n    icon: (\n      <ChartLineIcon  className=\"size-4\" />\n    ),\n    price: 15,\n    enabled: true,\n  },\n  {\n    id: \"api\",\n    label: \"API gateway\",\n    icon: (\n      <CodeIcon  className=\"size-4\" />\n    ),\n    price: 20,\n    enabled: true,\n  },\n  {\n    id: \"storage\",\n    label: \"Cloud storage (100 GB)\",\n    icon: (\n      <DatabaseIcon  className=\"size-4\" />\n    ),\n    price: 10,\n    enabled: false,\n  },\n  {\n    id: \"automation\",\n    label: \"Workflow automation\",\n    icon: (\n      <RepeatIcon  className=\"size-4\" />\n    ),\n    price: 25,\n    enabled: false,\n  },\n  {\n    id: \"security\",\n    label: \"Advanced security\",\n    icon: (\n      <LockIcon  className=\"size-4\" />\n    ),\n    price: 30,\n    enabled: false,\n  },\n  {\n    id: \"custom\",\n    label: \"Custom integrations\",\n    icon: (\n      <SettingsIcon  className=\"size-4\" />\n    ),\n    price: 20,\n    enabled: false,\n  },\n]\n\nconst includedFeatures = [\n  \"Unlimited team members\",\n  \"Core dashboard access\",\n  \"Email support\",\n  \"5 GB base storage\",\n]\n\nconst basePrice = 29\n\nexport function Pricing() {\n  const [features, setFeatures] = useState<FeatureToggle[]>(defaultFeatures)\n\n  const totalPrice =\n    basePrice +\n    features.filter((f) => f.enabled).reduce((sum, f) => sum + f.price, 0)\n\n  const priceChars = totalPrice.toString().split(\"\")\n\n  const toggleFeature = (id: string) => {\n    setFeatures((prev) =>\n      prev.map((f) => (f.id === id ? { ...f, enabled: !f.enabled } : f))\n    )\n  }\n\n  return (\n    <section aria-label=\"Pricing\" className=\"mx-auto w-full max-w-4xl\">\n      <div className=\"flex flex-col items-center gap-8\">\n        <div className=\"flex flex-col items-center gap-4 text-center\">\n          <Badge variant=\"secondary\" className=\"w-fit\">\n            Build your plan\n          </Badge>\n          <h2 className=\"text-4xl font-bold tracking-tight text-foreground sm:text-5xl\">\n            Only pay for what you need\n          </h2>\n          <p className=\"max-w-2xl text-lg text-muted-foreground\">\n            Start with a base plan and add modules as your infrastructure grows.\n            Full flexibility, zero waste.\n          </p>\n        </div>\n\n        <div className=\"grid w-full grid-cols-1 gap-4 lg:grid-cols-2\">\n          <div className=\"flex flex-col gap-6 rounded-4xl bg-card p-8 shadow-elevated-lg\">\n            <div className=\"flex flex-col gap-2\">\n              <h3 className=\"text-lg font-medium text-foreground\">\n                Add-on modules\n              </h3>\n              <p className=\"text-sm text-muted-foreground\">\n                Toggle the features you need. Price updates in real-time.\n              </p>\n            </div>\n\n            <div className=\"flex flex-col gap-4\">\n              {features.map((feature) => (\n                <div\n                  key={feature.id}\n                  className=\"flex items-center justify-between gap-4 rounded-lg p-2\"\n                >\n                  <Button\n                    type=\"button\"\n                    variant=\"ghost\"\n                    onClick={() => toggleFeature(feature.id)}\n                    className=\"h-auto flex-1 justify-start rounded-lg px-0 py-0 hover:bg-transparent\"\n                  >\n                    <div className=\"flex items-center gap-3 text-left\">\n                      <div\n                        className={`flex size-9 items-center justify-center rounded-full transition-colors ${\n                          feature.enabled\n                            ? \"bg-primary text-primary-foreground\"\n                            : \"bg-muted text-muted-foreground\"\n                        }`}\n                      >\n                        {feature.icon}\n                      </div>\n                      <div className=\"flex flex-col\">\n                        <span className=\"text-sm font-medium text-foreground\">\n                          {feature.label}\n                        </span>\n                        <span className=\"text-start text-xs text-muted-foreground\">\n                          +${feature.price}/mo\n                        </span>\n                      </div>\n                    </div>\n                  </Button>\n                  <Switch\n                    checked={feature.enabled}\n                    onCheckedChange={() => toggleFeature(feature.id)}\n                  />\n                </div>\n              ))}\n            </div>\n          </div>\n\n          <div className=\"flex flex-col gap-6 rounded-4xl bg-muted p-8\">\n            <div className=\"flex flex-col gap-2\">\n              <h3 className=\"text-xl font-medium text-foreground\">Your plan</h3>\n              <p className=\"text-sm text-muted-foreground\">\n                Base plan + {features.filter((f) => f.enabled).length} add-ons\n                selected\n              </p>\n            </div>\n\n            <div className=\"flex flex-col gap-1\">\n              <div className=\"flex items-baseline gap-1\">\n                <span className=\"text-7xl font-semibold tracking-tight text-foreground\">\n                  $\n                </span>\n                <AnimatePresence mode=\"popLayout\">\n                  {priceChars.map((char, idx) => (\n                    <motion.span\n                      key={`${totalPrice}-${char}-${idx}`}\n                      variants={animVariant}\n                      initial=\"initial\"\n                      animate=\"animate\"\n                      exit=\"exit\"\n                      custom={idx}\n                      className=\"inline-block text-7xl font-semibold tracking-tight text-foreground\"\n                    >\n                      {char}\n                    </motion.span>\n                  ))}\n                </AnimatePresence>\n                <span key=\"period\" className=\"text-xl text-muted-foreground\">\n                  /month\n                </span>\n              </div>\n              <p className=\"text-sm text-muted-foreground\">\n                Base: ${basePrice} + Add-ons: ${totalPrice - basePrice}\n              </p>\n            </div>\n\n            <FancyButton size=\"lg\" className=\"w-full\">\n              Start free trial\n              <ArrowUpRightIcon />\n            </FancyButton>\n\n            <div className=\"flex flex-col gap-3\">\n              <p className=\"text-sm font-medium text-foreground\">\n                Always included\n              </p>\n              <ul className=\"flex flex-col gap-3\">\n                {includedFeatures.map((feature) => (\n                  <li key={feature} className=\"flex items-start gap-3\">\n                    <div className=\"mt-0.5 flex size-5 shrink-0 items-center justify-center rounded-full bg-primary\">\n                      <CheckIcon  className=\"size-3 text-primary-foreground\" />\n                    </div>\n                    <span className=\"text-sm text-muted-foreground\">\n                      {feature}\n                    </span>\n                  </li>\n                ))}\n              </ul>\n            </div>\n          </div>\n        </div>\n      </div>\n    </section>\n  )\n}","target":"components/pricing.tsx"}]}