{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "empty-state",
  "title": "Empty State",
  "description": "A compound blank-slate surface with card, plain, compact, and page variants.",
  "dependencies": [
    "class-variance-authority"
  ],
  "registryDependencies": [
    "button",
    "https://uaiblocks.dev/r/uai-theme.json",
    "https://uaiblocks.dev/r/uai-utils.json"
  ],
  "files": [
    {
      "path": "src/registry/uai/components/empty-state.tsx",
      "content": "import { cva } from \"class-variance-authority\";\nimport { type ComponentProps, createContext, useContext, useId } from \"react\";\n\nimport { Button } from \"@/components/ui/button\";\nimport { cn } from \"@/lib/uai-utils\";\n\nexport const EMPTY_STATE_VARIANTS = [\"card\", \"plain\", \"compact\", \"page\"] as const;\nexport const EMPTY_STATE_ACTION_EMPHASES = [\"primary\", \"secondary\"] as const;\n\nexport type EmptyStateVariant = (typeof EMPTY_STATE_VARIANTS)[number];\nexport type EmptyStateActionEmphasis = (typeof EMPTY_STATE_ACTION_EMPHASES)[number];\n\nexport type EmptyStateProps = ComponentProps<\"section\"> & {\n  variant?: EmptyStateVariant;\n};\n\nconst emptyStateVariants = cva(\"w-full min-w-0 text-foreground\", {\n  variants: {\n    variant: {\n      card: \"flex flex-col items-center gap-[18px] rounded-[14px] border bg-card px-7 py-8 text-center\",\n      plain:\n        \"flex flex-col items-center gap-[18px] rounded-none bg-transparent px-5 py-7 text-center\",\n      compact: \"flex items-start gap-3 rounded-xl border bg-card p-3.5 text-left\",\n      page: \"flex min-h-[400px] flex-wrap items-center justify-center gap-8 rounded-none bg-transparent px-8 py-12 text-left\",\n    },\n  },\n});\n\nconst emptyStateMediaVariants = cva(\"grid shrink-0 place-items-center border border-transparent\", {\n  variants: {\n    variant: {\n      card: \"size-11 rounded-xl\",\n      plain: \"size-11 rounded-xl\",\n      compact: \"size-9 rounded-[10px]\",\n      page: \"size-40 rounded-none bg-transparent [font-family:var(--font-geist-mono),ui-monospace,monospace] text-[clamp(3.5rem,10vw,6rem)] leading-none font-semibold tracking-[-0.035em] text-foreground tabular-nums\",\n    },\n  },\n  compoundVariants: [\n    {\n      variant: [\"card\", \"plain\", \"compact\"],\n      className:\n        \"bg-muted text-muted-foreground shadow-[inset_0_1px_0_color-mix(in_oklab,var(--foreground)_6%,transparent)] [&>svg]:size-[42%] [&>svg]:stroke-[1.75]\",\n    },\n  ],\n});\n\nconst emptyStateTitleVariants = cva(\"font-medium tracking-[-0.01em] text-balance wrap-anywhere\", {\n  variants: {\n    variant: {\n      card: \"text-[15px] leading-5\",\n      plain: \"text-[15px] leading-5\",\n      compact: \"text-[13px] leading-[18px]\",\n      page: \"text-xl leading-7 font-semibold tracking-tight\",\n    },\n  },\n});\n\nconst emptyStateDescriptionVariants = cva(\"text-pretty text-muted-foreground wrap-anywhere\", {\n  variants: {\n    variant: {\n      card: \"text-[13px] leading-[19px]\",\n      plain: \"text-[13px] leading-[19px]\",\n      compact: \"text-[12px] leading-[17px]\",\n      page: \"text-sm leading-5\",\n    },\n  },\n});\n\nconst emptyStateNoteVariants = cva(\"max-w-[50ch] text-subtle-foreground wrap-anywhere\", {\n  variants: {\n    variant: {\n      card: \"text-[11.5px] leading-4\",\n      plain: \"text-[11.5px] leading-4\",\n      compact: \"text-[11px] leading-4\",\n      page: \"text-[12px] leading-4\",\n    },\n  },\n});\n\nconst emptyStateActionVariants = cva(\n  \"h-auto gap-1.5 rounded-full py-0 no-underline transition-[scale,background-color,filter,opacity] duration-140 ease-out-quint focus-visible:ring-0 focus-visible:outline-2 focus-visible:outline-solid focus-visible:outline-offset-2 focus-visible:outline-ring active:scale-[0.97] motion-reduce:transition-none motion-reduce:active:scale-100 [&_svg:not([class*='size-'])]:size-3.5\",\n  {\n    variants: {\n      variant: {\n        card: \"min-h-8 px-3.5 text-[13px]/4 has-[>svg]:px-3.5\",\n        plain: \"min-h-8 px-3.5 text-[13px]/4 has-[>svg]:px-3.5\",\n        compact: \"min-h-7 px-3 text-[12.5px]/4 has-[>svg]:px-3\",\n        page: \"min-h-8.5 px-3.5 text-[13px]/4 has-[>svg]:px-3.5\",\n      },\n      emphasis: {\n        primary: \"bg-primary text-primary-foreground hover:bg-primary hover:brightness-[1.08]\",\n        secondary:\n          \"bg-secondary text-secondary-foreground hover:bg-[color-mix(in_oklab,var(--secondary)_85%,var(--foreground))]\",\n      },\n    },\n  },\n);\n\nconst leading = (variant: EmptyStateVariant) => variant === \"page\" || variant === \"compact\";\n\ntype EmptyStateContextValue = {\n  titleId: string;\n  variant: EmptyStateVariant;\n};\n\nconst EmptyStateContext = createContext<EmptyStateContextValue | null>(null);\n\nfunction useEmptyState(name: string) {\n  const context = useContext(EmptyStateContext);\n  if (!context) throw new Error(`${name} must be used within EmptyState`);\n  return context;\n}\n\nexport function EmptyState({\n  variant = \"card\",\n  children,\n  className,\n  \"aria-label\": ariaLabel,\n  \"aria-labelledby\": ariaLabelledby,\n  ...props\n}: EmptyStateProps) {\n  const titleId = useId();\n\n  return (\n    <EmptyStateContext.Provider value={{ titleId, variant }}>\n      <section\n        data-slot=\"empty-state\"\n        data-variant={variant}\n        className={cn(emptyStateVariants({ variant }), className)}\n        {...props}\n        aria-label={ariaLabel}\n        aria-labelledby={ariaLabelledby ?? (ariaLabel ? undefined : titleId)}\n      >\n        {children}\n      </section>\n    </EmptyStateContext.Provider>\n  );\n}\n\nexport type EmptyStateMediaProps = ComponentProps<\"div\">;\n\nexport function EmptyStateMedia({ children, className, ...props }: EmptyStateMediaProps) {\n  const { variant } = useEmptyState(\"EmptyStateMedia\");\n\n  return (\n    <div\n      data-slot=\"empty-state-media\"\n      className={cn(emptyStateMediaVariants({ variant }), className)}\n      {...props}\n    >\n      {children}\n    </div>\n  );\n}\n\nexport type EmptyStateContentProps = ComponentProps<\"div\">;\n\nexport function EmptyStateContent({ children, className, ...props }: EmptyStateContentProps) {\n  const { variant } = useEmptyState(\"EmptyStateContent\");\n\n  return (\n    <div\n      data-slot=\"empty-state-content\"\n      className={cn(\n        \"flex min-w-0 max-w-[48ch] flex-1 flex-col gap-4\",\n        leading(variant) ? \"items-start text-left\" : \"items-center text-center\",\n        variant === \"page\" && \"min-w-[min(100%,260px)]\",\n        className,\n      )}\n      {...props}\n    >\n      {children}\n    </div>\n  );\n}\n\nexport type EmptyStateHeaderProps = ComponentProps<\"header\">;\n\nexport function EmptyStateHeader({ children, className, ...props }: EmptyStateHeaderProps) {\n  return (\n    <header\n      data-slot=\"empty-state-header\"\n      className={cn(\"grid min-w-0 gap-1.5\", className)}\n      {...props}\n    >\n      {children}\n    </header>\n  );\n}\n\nexport type EmptyStateTitleProps = ComponentProps<\"h2\">;\n\nexport function EmptyStateTitle({ children, className, ...props }: EmptyStateTitleProps) {\n  const context = useEmptyState(\"EmptyStateTitle\");\n\n  return (\n    <h2\n      data-slot=\"empty-state-title\"\n      className={cn(emptyStateTitleVariants({ variant: context.variant }), className)}\n      {...props}\n      id={context.titleId}\n    >\n      {children}\n    </h2>\n  );\n}\n\nexport type EmptyStateDescriptionProps = ComponentProps<\"p\">;\n\nexport function EmptyStateDescription({\n  children,\n  className,\n  ...props\n}: EmptyStateDescriptionProps) {\n  const { variant } = useEmptyState(\"EmptyStateDescription\");\n\n  return (\n    <p\n      data-slot=\"empty-state-description\"\n      className={cn(emptyStateDescriptionVariants({ variant }), className)}\n      {...props}\n    >\n      {children}\n    </p>\n  );\n}\n\nexport type EmptyStateActionsProps = ComponentProps<\"div\">;\n\nexport function EmptyStateActions({ children, className, ...props }: EmptyStateActionsProps) {\n  const { variant } = useEmptyState(\"EmptyStateActions\");\n\n  return (\n    <div\n      data-slot=\"empty-state-actions\"\n      className={cn(\n        \"flex flex-wrap items-center gap-2\",\n        leading(variant) ? \"justify-start\" : \"justify-center\",\n        className,\n      )}\n      {...props}\n    >\n      {children}\n    </div>\n  );\n}\n\ntype EmptyStateActionAppearanceProps = {\n  emphasis?: EmptyStateActionEmphasis;\n};\n\ntype EmptyStateButtonActionProps = ComponentProps<\"button\"> &\n  EmptyStateActionAppearanceProps & {\n    href?: undefined;\n  };\n\ntype EmptyStateLinkActionProps = ComponentProps<\"a\"> &\n  EmptyStateActionAppearanceProps & {\n    href: string;\n  };\n\nexport type EmptyStateActionProps = EmptyStateButtonActionProps | EmptyStateLinkActionProps;\n\nexport function EmptyStateAction({\n  emphasis = \"primary\",\n  className,\n  ...props\n}: EmptyStateActionProps) {\n  const { variant } = useEmptyState(\"EmptyStateAction\");\n  const actionClassName = cn(emptyStateActionVariants({ variant, emphasis }), className);\n\n  const buttonVariant = emphasis === \"primary\" ? \"default\" : \"secondary\";\n\n  if (typeof props.href === \"string\") {\n    return (\n      <Button asChild variant={buttonVariant} className={actionClassName}>\n        <a data-slot=\"empty-state-action\" {...props} />\n      </Button>\n    );\n  }\n\n  const { type = \"button\", ...buttonProps } = props;\n  return (\n    <Button\n      data-slot=\"empty-state-action\"\n      variant={buttonVariant}\n      {...buttonProps}\n      type={type}\n      className={actionClassName}\n    />\n  );\n}\n\nexport type EmptyStateNoteProps = ComponentProps<\"p\">;\n\nexport function EmptyStateNote({ children, className, ...props }: EmptyStateNoteProps) {\n  const { variant } = useEmptyState(\"EmptyStateNote\");\n\n  return (\n    <p\n      data-slot=\"empty-state-note\"\n      className={cn(emptyStateNoteVariants({ variant }), className)}\n      {...props}\n    >\n      {children}\n    </p>\n  );\n}\n",
      "type": "registry:ui",
      "target": "@ui/uai/empty-state.tsx"
    }
  ],
  "categories": [
    "feedback",
    "data-display"
  ],
  "type": "registry:ui"
}