"use client"; import { sanitizeComposedHostProps, sanitizeInteractionHostProps, type SafeComposedHostElementProps } from "../primitives/sanitize-composed-host-props"; import * as React from "react"; import { Autocomplete as CommandPrimitive } from "@base-ui/react/autocomplete"; import { cn } from "../../lib/utils"; import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle, DialogTrigger, } from "./dialog"; import { MagnifyingGlassIcon, CheckIcon } from "@phosphor-icons/react"; import { ScrollFade, } from "../primitives"; const CommandReadOnlyContext = React.createContext(false); const commandWindowFrameClassName = "floating-popup-surface overflow-hidden rounded-3xl border popup-text-xs-plus text-[color:var(--popover-foreground)]"; const CommandWindowFrame = React.forwardRef< HTMLDivElement, SafeComposedHostElementProps<"div"> >( ({ className, ...props }, ref) => { return (
); }, ); CommandWindowFrame.displayName = "CommandWindowFrame"; /** Inline action search. Items and search state follow Base UI Autocomplete. */ function Command({ className, style, ref, children, ...props }: Omit, "open" | "defaultOpen" | "inline" | "items"> & { items: NonNullable["items"]>; className?: string; style?: React.CSSProperties; ref?: React.Ref; }) { return (
{children}
); } function CommandDialog({ title = "Command Palette", description = "Search for a command to run...", children, className, showCloseButton = false, trigger, initialFocus, finalFocus, ...props }: Omit, "children"> & { title?: string; description?: string; className?: string; showCloseButton?: boolean; trigger?: React.ReactElement; initialFocus?: React.ComponentProps["initialFocus"]; finalFocus?: React.ComponentProps["finalFocus"]; children: React.ReactNode; }) { return ( {trigger ? : null} {title} {description} {children} ); } const CommandInput = React.forwardRef< React.ElementRef, Omit & { className?: string; leadingVisual?: React.ReactNode; } >(({ className, leadingVisual, ...props }, ref) => { return ( ); }); CommandInput.displayName = "CommandInput"; const CommandTextInput = React.forwardRef< HTMLInputElement, React.ComponentPropsWithoutRef<"input"> & { leadingVisual?: React.ReactNode; typography?: "default" | "popup"; } >(({ className, leadingVisual, typography = "popup", ...props }, ref) => { return ( ); }); CommandTextInput.displayName = "CommandTextInput"; function CommandList({ className, scrollFade = false, scrollFadeClassName, scrollFadeContainerClassName, scrollFadeWatch = [], ...props }: Omit & React.RefAttributes & { className?: string; scrollFade?: boolean; scrollFadeClassName?: string; scrollFadeContainerClassName?: string; scrollFadeWatch?: readonly unknown[]; }) { const commandList = ( ); if (!scrollFade) { return commandList; } return ( {commandList} ); } function CommandEmpty({ className, ...props }: Omit & React.RefAttributes & { className?: string }) { return ( ); } function CommandGroup({ className, heading, children, ...props }: Omit & React.RefAttributes & { className?: string; heading?: React.ReactNode; }) { return ( {heading != null ? ( {heading} ) : null} {children} ); } const CommandCollection = CommandPrimitive.Collection; function CommandSeparator({ className, ...props }: Omit & React.RefAttributes & { className?: string }) { return ( ); } function CommandItem({ active = false, className, children, tintIconsOnSelect = true, value, onSelect, onClick, ...props }: Omit & React.RefAttributes & { className?: string; value: ItemValue; onSelect?: (value: ItemValue) => void; active?: boolean; tintIconsOnSelect?: boolean; }) { const readOnly = React.useContext(CommandReadOnlyContext); return ( { // Base UI's internal read-only guard runs after external click handlers. if (readOnly) return; onClick?.(event); if (!event.defaultPrevented) onSelect?.(value); }} data-active={active ? "true" : "false"} data-slot="command-item" className={cn( "group/command-item relative flex h-(--command-item-block-size) cursor-pointer items-center gap-2 rounded-md px-2.5 py-1.5 popup-text-xs-plus leading-normal tracking-tight font-medium outline-hidden select-none in-data-[slot=dialog-content]:rounded-md data-disabled:pointer-events-none data-disabled:opacity-50 data-highlighted:bg-[color:color-mix(in_oklab,var(--foreground)_4%,transparent)] data-highlighted:text-[color:var(--foreground)] data-[active=true]:bg-[color:color-mix(in_oklab,var(--foreground)_5%,transparent)] data-[active=true]:text-[color:var(--foreground)] [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-(--command-icon-size)", tintIconsOnSelect ? "data-highlighted:*:[svg]:text-[color:var(--foreground)] data-[active=true]:*:[svg]:text-[color:var(--foreground)]" : null, className, )} {...props} > {children} ); } function CommandShortcut({ className, ...props }: SafeComposedHostElementProps<"span">) { return ( ); } export { Command, CommandDialog, CommandCollection, CommandInput, CommandTextInput, CommandList, CommandWindowFrame, CommandEmpty, CommandGroup, CommandItem, CommandShortcut, CommandSeparator, };