{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "hero-mileone",
  "title": "Hero · Mileone",
  "description": "Hero · Mileone section.",
  "dependencies": [
    "lucide-react"
  ],
  "files": [
    {
      "path": "registry/talizen/hero/hero-mileone/hero-mileone.tsx",
      "content": "import { Menu, X } from \"lucide-react\"\nimport { useState } from \"react\"\n\nimport { ParticleButterfly } from \"./ParticleButterfly\"\n\nexport type HeroMileoneProps = {\n  className?: string\n}\n\nconst navItems = [\"Product\", \"Solutions\", \"Resources\", \"Customers\", \"Pricing\"]\n\nfunction MileoneMark() {\n  return (\n    <svg\n      width=\"28\"\n      height=\"20\"\n      viewBox=\"0 0 28 20\"\n      fill=\"none\"\n      xmlns=\"http://www.w3.org/2000/svg\"\n      aria-hidden=\"true\"\n      className=\"shrink-0\"\n    >\n      <path\n        d=\"M2.5 18C2.5 13.5 6 9.5 10.5 9.5C15 9.5 18 13.5 18 18\"\n        stroke=\"#eaff80\"\n        strokeLinecap=\"round\"\n        strokeWidth=\"3\"\n      />\n      <path\n        d=\"M10.5 18C10.5 13.5 14 9.5 18.5 9.5C23 9.5 26 13.5 26 18\"\n        stroke=\"#eaff80\"\n        strokeLinecap=\"round\"\n        strokeWidth=\"3\"\n      />\n    </svg>\n  )\n}\n\nexport function HeroMileone({ className = \"\" }: HeroMileoneProps) {\n  const [menuOpen, setMenuOpen] = useState(false)\n  const MenuIcon = menuOpen ? X : Menu\n\n  return (\n    <section\n      className={`relative min-h-[100svh] w-full overflow-hidden bg-black text-white sm:min-h-[660px] ${className}`}\n    >\n      <div className=\"absolute inset-0 z-0\">\n        <ParticleButterfly />\n      </div>\n      <div\n        className=\"pointer-events-none absolute inset-0 z-[1] bg-[radial-gradient(circle_at_50%_45%,transparent_0%,rgba(0,0,0,0.1)_48%,rgba(0,0,0,0.72)_100%),linear-gradient(180deg,rgba(0,0,0,0.2)_0%,transparent_34%,rgba(0,0,0,0.72)_100%)]\"\n        aria-hidden=\"true\"\n      />\n\n      <div className=\"relative z-10 mx-auto flex min-h-[100svh] w-full max-w-[1400px] flex-col px-4 py-4 sm:min-h-[660px] sm:px-8 md:py-8 lg:px-10\">\n        <header className=\"relative grid grid-cols-[minmax(0,1fr)_auto] items-center gap-4 min-[920px]:grid-cols-[auto_minmax(0,1fr)_auto] min-[920px]:gap-5\">\n          <a\n            href=\"#\"\n            className=\"flex min-w-0 items-center gap-2 text-white transition hover:opacity-82\"\n            aria-label=\"Mileone home\"\n          >\n            <MileoneMark />\n            <span className=\"truncate text-base font-bold uppercase leading-none tracking-[0.15em] sm:text-lg\">\n              Mileone\n            </span>\n          </a>\n\n          <nav className=\"hidden items-center justify-self-center gap-8 text-[13px] font-medium tracking-wide text-zinc-400 min-[920px]:flex lg:gap-10\">\n            {navItems.map((item) => (\n              <a key={item} href=\"#\" className=\"transition duration-300 hover:text-white\">\n                {item}\n              </a>\n            ))}\n          </nav>\n\n          <a\n            href=\"#\"\n            className=\"hidden min-h-11 shrink-0 items-center justify-center justify-self-end rounded-[4px] bg-white px-5 text-[13px] font-semibold text-black shadow-[0_0_15px_rgba(255,255,255,0.1)] transition duration-300 hover:bg-zinc-200 min-[920px]:inline-flex\"\n          >\n            Get Started Free\n          </a>\n\n          <button\n            type=\"button\"\n            onClick={() => setMenuOpen((open) => !open)}\n            aria-label={menuOpen ? \"Close menu\" : \"Open menu\"}\n            aria-expanded={menuOpen}\n            aria-controls=\"mileone-mobile-menu\"\n            className=\"inline-flex h-11 w-11 shrink-0 items-center justify-center justify-self-end rounded-[4px] border border-[#eaff80]/45 bg-[#eaff80]/12 text-[#eaff80] shadow-[0_0_18px_rgba(234,255,128,0.12)] backdrop-blur transition hover:bg-[#eaff80]/20 min-[920px]:hidden\"\n          >\n            <MenuIcon className=\"h-5 w-5\" aria-hidden=\"true\" />\n          </button>\n\n          <div\n            id=\"mileone-mobile-menu\"\n            className={`absolute left-0 right-0 top-[calc(100%+14px)] z-20 overflow-hidden rounded-[6px] border border-white/12 bg-black/82 shadow-[0_24px_80px_rgba(0,0,0,0.48)] backdrop-blur-xl transition duration-200 min-[920px]:hidden ${\n              menuOpen\n                ? \"translate-y-0 opacity-100\"\n                : \"pointer-events-none -translate-y-2 opacity-0\"\n            }`}\n          >\n            <nav className=\"grid p-2 text-sm font-medium text-zinc-300\">\n              {navItems.map((item) => (\n                <a\n                  key={item}\n                  href=\"#\"\n                  onClick={() => setMenuOpen(false)}\n                  className=\"rounded-[4px] px-3 py-3 transition hover:bg-white/8 hover:text-white\"\n                >\n                  {item}\n                </a>\n              ))}\n            </nav>\n            <div className=\"border-t border-white/10 p-2\">\n              <a\n                href=\"#\"\n                onClick={() => setMenuOpen(false)}\n                className=\"flex min-h-11 w-full items-center justify-center rounded-[4px] bg-white px-4 text-sm font-semibold text-black transition hover:bg-zinc-200\"\n              >\n                Get Started Free\n              </a>\n            </div>\n          </div>\n        </header>\n\n        <main className=\"flex flex-1 items-end justify-between gap-8 pb-7 pt-14 sm:pt-20 md:gap-10 md:pb-12\">\n          <div className=\"max-w-[42rem] min-w-0\">\n            <p className=\"mb-5 max-w-[22rem] text-sm font-medium leading-6 text-[#eaff80]/80 md:hidden\">\n              Build, observe, and scale intelligent products with one adaptive AI\n              systems layer.\n            </p>\n            <h1 className=\"[font-family:Georgia,serif] text-[34px] font-normal leading-[1.06] tracking-[-0.02em] text-[#f4f4f4] min-[380px]:text-[38px] min-[420px]:text-[42px] sm:text-[52px] lg:text-[56px]\">\n              The Intelligent\n              <br />\n              <span className=\"text-[#a0a0a0]\">Layer For AI</span>\n              <span className=\"hidden sm:inline\"> </span>\n              <span className=\"block text-[#a0a0a0] sm:inline\">Systems</span>\n            </h1>\n          </div>\n\n          <p className=\"mb-2 hidden max-w-[320px] text-left text-[13px] font-medium leading-[1.8] text-[#888888] md:block\">\n            Build, observe, and scale intelligent products with one adaptive AI\n            systems layer for fast-moving product teams.\n          </p>\n        </main>\n      </div>\n    </section>\n  )\n}\n\nexport default HeroMileone\n",
      "type": "registry:component"
    },
    {
      "path": "registry/talizen/hero/hero-mileone/ParticleButterfly.tsx",
      "content": "import { useEffect, useRef } from \"react\"\n\ntype ParticleBlueprint = {\n  ox: number\n  oy: number\n  color: string\n  baseSize: number\n}\n\nconst SHAPE_SIZE = 800\n\nfunction getParticleBlueprints(): ParticleBlueprint[] {\n  const canvas = document.createElement(\"canvas\")\n  canvas.width = SHAPE_SIZE\n  canvas.height = SHAPE_SIZE\n\n  const ctx = canvas.getContext(\"2d\", { willReadFrequently: true })\n  if (!ctx) return []\n\n  const cx = SHAPE_SIZE / 2\n  const cy = SHAPE_SIZE / 2\n\n  const drawWing = (flipX: boolean) => {\n    ctx.save()\n    if (flipX) ctx.scale(-1, 1)\n\n    ctx.beginPath()\n    ctx.moveTo(10, -50)\n    ctx.bezierCurveTo(40, -180, 180, -260, 320, -200)\n    ctx.bezierCurveTo(340, -150, 330, -50, 250, 20)\n    ctx.bezierCurveTo(280, 50, 280, 80, 250, 120)\n    ctx.bezierCurveTo(220, 220, 140, 280, 60, 260)\n    ctx.bezierCurveTo(20, 220, 10, 120, 10, 50)\n    ctx.fill()\n\n    ctx.restore()\n  }\n\n  ctx.save()\n  ctx.translate(cx, cy)\n  ctx.fillStyle = \"white\"\n  drawWing(false)\n  drawWing(true)\n  ctx.beginPath()\n  ctx.ellipse(0, 0, 12, 80, 0, 0, Math.PI * 2)\n  ctx.fill()\n  ctx.restore()\n\n  ctx.globalCompositeOperation = \"source-in\"\n  const gradient = ctx.createRadialGradient(cx, cy, 0, cx, cy, 400)\n  gradient.addColorStop(0, \"#ffffff\")\n  gradient.addColorStop(0.1, \"#fff5ba\")\n  gradient.addColorStop(0.35, \"#ffd700\")\n  gradient.addColorStop(0.65, \"#ff69b4\")\n  gradient.addColorStop(0.9, \"#da70d6\")\n  gradient.addColorStop(1, \"#8a2be2\")\n\n  ctx.fillStyle = gradient\n  ctx.fillRect(0, 0, SHAPE_SIZE, SHAPE_SIZE)\n\n  const imageData = ctx.getImageData(0, 0, SHAPE_SIZE, SHAPE_SIZE).data\n  const blueprints: ParticleBlueprint[] = []\n  const step = 7\n\n  for (let y = 0; y < SHAPE_SIZE; y += step) {\n    for (let x = 0; x < SHAPE_SIZE; x += step) {\n      const index = (y * SHAPE_SIZE + x) * 4\n      const alpha = imageData[index + 3]\n      if (alpha <= 128 || Math.random() > 0.85) continue\n\n      const red = imageData[index]\n      const green = imageData[index + 1]\n      const blue = imageData[index + 2]\n      const distanceFromCenter = Math.hypot(x - cx, y - cy)\n      const sizeFalloff = Math.max(0.4, 1 - distanceFromCenter / 350)\n\n      blueprints.push({\n        ox: x - cx,\n        oy: y - cy,\n        color: `rgb(${red}, ${green}, ${blue})`,\n        baseSize: step * 0.45 + sizeFalloff * step * 0.35,\n      })\n    }\n  }\n\n  return blueprints\n}\n\nclass Particle {\n  private ox: number\n  private oy: number\n  private x: number\n  private y: number\n  private vx = 0\n  private vy = 0\n  private color: string\n  private baseSize: number\n  private currentSize: number\n  private friction: number\n  private ease: number\n  private driftAngle: number\n  private driftSpeed: number\n  private flickerAngle: number\n  private flickerSpeed: number\n\n  constructor(blueprint: ParticleBlueprint) {\n    this.ox = blueprint.ox\n    this.oy = blueprint.oy\n    this.color = blueprint.color\n    this.baseSize = blueprint.baseSize\n    this.currentSize = blueprint.baseSize\n\n    const randomRadius = 300 + Math.random() * 500\n    const randomAngle = Math.random() * Math.PI * 2\n    this.x = this.ox + Math.cos(randomAngle) * randomRadius\n    this.y = this.oy + Math.sin(randomAngle) * randomRadius\n\n    this.friction = 0.82 + Math.random() * 0.08\n    this.ease = 0.02 + Math.random() * 0.04\n    this.driftAngle = Math.random() * Math.PI * 2\n    this.driftSpeed = 0.005 + Math.random() * 0.015\n    this.flickerAngle = Math.random() * Math.PI * 2\n    this.flickerSpeed = 0.02 + Math.random() * 0.04\n  }\n\n  update(\n    mouseX: number,\n    mouseY: number,\n    canvasCx: number,\n    canvasCy: number,\n    scale: number,\n  ) {\n    this.driftAngle += this.driftSpeed\n    this.flickerAngle += this.flickerSpeed\n\n    let targetX = canvasCx + this.ox * scale + Math.sin(this.driftAngle) * 12 * scale\n    let targetY = canvasCy + this.oy * scale + Math.cos(this.driftAngle) * 12 * scale\n    const flickerScale = 0.6 + Math.sin(this.flickerAngle) * 0.4\n    this.currentSize = this.baseSize * scale * flickerScale\n\n    const dx = mouseX - this.x\n    const dy = mouseY - this.y\n    const distance = Math.hypot(dx, dy)\n    const repelRadius = 150 * scale\n\n    if (mouseX !== -1000 && distance < repelRadius) {\n      const force = (repelRadius - distance) / repelRadius\n      const angle = Math.atan2(dy, dx)\n      targetX -= Math.cos(angle) * force * 180 * scale\n      targetY -= Math.sin(angle) * force * 180 * scale\n    }\n\n    this.vx += (targetX - this.x) * this.ease\n    this.vy += (targetY - this.y) * this.ease\n    this.vx *= this.friction\n    this.vy *= this.friction\n    this.x += this.vx\n    this.y += this.vy\n  }\n\n  draw(ctx: CanvasRenderingContext2D) {\n    ctx.fillStyle = this.color\n    ctx.fillRect(Math.round(this.x), Math.round(this.y), this.currentSize, this.currentSize)\n  }\n}\n\nexport type ParticleButterflyProps = {\n  className?: string\n}\n\nexport function ParticleButterfly({ className = \"\" }: ParticleButterflyProps) {\n  const canvasRef = useRef<HTMLCanvasElement>(null)\n  const mousePos = useRef({ x: -1000, y: -1000 })\n\n  useEffect(() => {\n    const canvas = canvasRef.current\n    const ctx = canvas?.getContext(\"2d\", { alpha: false })\n    if (!canvas || !ctx) return\n\n    let animationFrameId = 0\n    let initTimer = 0\n    let particles: Particle[] = []\n    let canvasWidth = 0\n    let canvasHeight = 0\n    let isDestroyed = false\n\n    const resizeCanvas = () => {\n      const rect = canvas.getBoundingClientRect()\n      const dpr = Math.min(window.devicePixelRatio || 1, 2)\n      canvasWidth = rect.width\n      canvasHeight = rect.height\n      canvas.width = Math.max(1, Math.floor(rect.width * dpr))\n      canvas.height = Math.max(1, Math.floor(rect.height * dpr))\n      ctx.setTransform(dpr, 0, 0, dpr, 0, 0)\n    }\n\n    const init = () => {\n      resizeCanvas()\n      particles = getParticleBlueprints().map((blueprint) => new Particle(blueprint))\n    }\n\n    const resetMouse = () => {\n      mousePos.current = { x: -1000, y: -1000 }\n    }\n\n    const updatePointer = (clientX: number, clientY: number) => {\n      const rect = canvas.getBoundingClientRect()\n      mousePos.current = {\n        x: clientX - rect.left,\n        y: clientY - rect.top,\n      }\n    }\n\n    const handleMouseMove = (event: MouseEvent) => {\n      updatePointer(event.clientX, event.clientY)\n    }\n\n    const handleTouchMove = (event: TouchEvent) => {\n      const touch = event.touches[0]\n      if (touch) updatePointer(touch.clientX, touch.clientY)\n    }\n\n    const render = () => {\n      if (isDestroyed) return\n\n      ctx.fillStyle = \"#000000\"\n      ctx.fillRect(0, 0, canvasWidth, canvasHeight)\n\n      const isMobile = canvasWidth < 768\n      const baseScale = isMobile ? 650 : 850\n      const scale = Math.max(0.4, Math.min(canvasWidth, canvasHeight) / baseScale)\n      const cx = canvasWidth / 2\n      const cy = canvasHeight / 2\n\n      ctx.globalCompositeOperation = \"lighter\"\n      for (const particle of particles) {\n        particle.update(mousePos.current.x, mousePos.current.y, cx, cy, scale)\n        particle.draw(ctx)\n      }\n      ctx.globalCompositeOperation = \"source-over\"\n\n      animationFrameId = window.requestAnimationFrame(render)\n    }\n\n    initTimer = window.setTimeout(() => {\n      if (!isDestroyed) init()\n    }, 50)\n\n    resizeCanvas()\n    render()\n\n    window.addEventListener(\"resize\", resizeCanvas)\n    canvas.addEventListener(\"mousemove\", handleMouseMove)\n    canvas.addEventListener(\"mouseleave\", resetMouse)\n    canvas.addEventListener(\"touchmove\", handleTouchMove, { passive: true })\n    canvas.addEventListener(\"touchend\", resetMouse)\n\n    return () => {\n      isDestroyed = true\n      window.clearTimeout(initTimer)\n      window.cancelAnimationFrame(animationFrameId)\n      window.removeEventListener(\"resize\", resizeCanvas)\n      canvas.removeEventListener(\"mousemove\", handleMouseMove)\n      canvas.removeEventListener(\"mouseleave\", resetMouse)\n      canvas.removeEventListener(\"touchmove\", handleTouchMove)\n      canvas.removeEventListener(\"touchend\", resetMouse)\n    }\n  }, [])\n\n  return (\n    <canvas\n      ref={canvasRef}\n      aria-hidden=\"true\"\n      className={`block h-full w-full bg-black touch-none ${className}`}\n    />\n  )\n}\n\nexport default ParticleButterfly\n",
      "type": "registry:component"
    }
  ],
  "categories": [
    "hero"
  ],
  "type": "registry:block"
}