diff --git a/webview-ui/src/components/settings/ApiConfigManager.tsx b/webview-ui/src/components/settings/ApiConfigManager.tsx index e57bfd8175..6db79f761a 100644 --- a/webview-ui/src/components/settings/ApiConfigManager.tsx +++ b/webview-ui/src/components/settings/ApiConfigManager.tsx @@ -1,20 +1,26 @@ import { memo, useEffect, useRef, useState } from "react" import { VSCodeTextField } from "@vscode/webview-ui-toolkit/react" +import { ChevronsUpDown, Check, X } from "lucide-react" import { ApiConfigMeta } from "../../../../src/shared/ExtensionMessage" import { useAppTranslation } from "@/i18n/TranslationContext" +import { cn } from "@/lib/utils" import { Button, Input, Dialog, DialogContent, DialogTitle, - Select, - SelectTrigger, - SelectValue, - SelectContent, - SelectItem, + Command, + CommandEmpty, + CommandGroup, + CommandInput, + CommandItem, + CommandList, + Popover, + PopoverContent, + PopoverTrigger, } from "@/components/ui" interface ApiConfigManagerProps { @@ -41,8 +47,11 @@ const ApiConfigManager = ({ const [inputValue, setInputValue] = useState("") const [newProfileName, setNewProfileName] = useState("") const [error, setError] = useState(null) + const [open, setOpen] = useState(false) + const [searchValue, setSearchValue] = useState("") const inputRef = useRef(null) const newProfileInputRef = useRef(null) + const searchInputRef = useRef(null) const validateName = (name: string, isNewProfile: boolean): string | null => { const trimmed = name.trim() @@ -95,8 +104,31 @@ const ApiConfigManager = ({ useEffect(() => { resetCreateState() resetRenameState() + // Reset search value when current profile changes + setTimeout(() => setSearchValue(""), 100) }, [currentApiConfigName]) + const onOpenChange = (open: boolean) => { + setOpen(open) + + // Reset search when closing the popover + if (!open) { + setTimeout(() => setSearchValue(""), 100) + } + } + + const onClearSearch = () => { + setSearchValue("") + searchInputRef.current?.focus() + } + + const handleSelectConfig = (configName: string) => { + if (!configName) return + + setOpen(false) + onSelectConfig(configName) + } + const handleAdd = () => { resetCreateState() setIsCreating(true) @@ -206,18 +238,76 @@ const ApiConfigManager = ({ ) : ( <>
- + + + + + + +
+ + {searchValue.length > 0 && ( +
+ +
+ )} +
+ + + {searchValue && ( +
+ {t("settings:providers.noMatchFound")} +
+ )} +
+ + {listApiConfigMeta + .filter((config) => + searchValue + ? config.name.toLowerCase().includes(searchValue.toLowerCase()) + : true, + ) + .map((config) => ( + + {config.name} + + + ))} + +
+
+
+