feat(ui): reconcile backup UI changes with current routing and interaction features
This commit is contained in:
@@ -4,6 +4,15 @@ import {
|
||||
TooltipTrigger,
|
||||
TooltipContent,
|
||||
} from "@/components/ui/tooltip";
|
||||
import {
|
||||
Dialog,
|
||||
DialogContent,
|
||||
DialogHeader,
|
||||
DialogTitle,
|
||||
DialogDescription,
|
||||
DialogFooter,
|
||||
} from "@/components/ui/dialog";
|
||||
import { Button } from "@/components/ui/button";
|
||||
import { HelpCircle, ChevronDown, ChevronRight } from "lucide-react";
|
||||
import { cn } from "../lib/utils";
|
||||
|
||||
@@ -23,10 +32,9 @@ export const help: Record<string, string> = {
|
||||
dangerouslySkipPermissions: "Run Claude without permission prompts. Required for unattended operation.",
|
||||
dangerouslyBypassSandbox: "Run Codex without sandbox restrictions. Required for filesystem/network access.",
|
||||
search: "Enable Codex web search capability during runs.",
|
||||
bootstrapPrompt: "Prompt used only on the first run (no existing session). Used for initial agent setup.",
|
||||
maxTurnsPerRun: "Maximum number of agentic turns (tool calls) per heartbeat run.",
|
||||
command: "The command to execute (e.g. node, python).",
|
||||
localCommand: "Override the local CLI command (e.g. claude, /usr/local/bin/claude, codex).",
|
||||
localCommand: "Override the path to the CLI command you want the adapter to call (e.g. /usr/local/bin/claude, codex).",
|
||||
args: "Command-line arguments, comma-separated.",
|
||||
extraArgs: "Extra CLI arguments for local adapters, comma-separated.",
|
||||
envVars: "Environment variables injected into the adapter process. Use plain values or secret references.",
|
||||
@@ -372,3 +380,87 @@ export function DraftNumberInput({
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* "Choose" button that opens a dialog explaining the user must manually
|
||||
* type the path due to browser security limitations.
|
||||
*/
|
||||
export function ChoosePathButton() {
|
||||
const [open, setOpen] = useState(false);
|
||||
return (
|
||||
<>
|
||||
<button
|
||||
type="button"
|
||||
className="inline-flex items-center rounded-md border border-border px-2 py-0.5 text-xs text-muted-foreground hover:bg-accent/50 transition-colors shrink-0"
|
||||
onClick={() => setOpen(true)}
|
||||
>
|
||||
Choose
|
||||
</button>
|
||||
<Dialog open={open} onOpenChange={setOpen}>
|
||||
<DialogContent>
|
||||
<DialogHeader>
|
||||
<DialogTitle>Specify path manually</DialogTitle>
|
||||
<DialogDescription>
|
||||
Browser security blocks apps from reading full local paths via a file picker.
|
||||
Copy the absolute path and paste it into the input.
|
||||
</DialogDescription>
|
||||
</DialogHeader>
|
||||
<div className="space-y-4 text-sm">
|
||||
<section className="space-y-1.5">
|
||||
<p className="font-medium">macOS (Finder)</p>
|
||||
<ol className="list-decimal space-y-1 pl-5 text-muted-foreground">
|
||||
<li>Find the folder in Finder.</li>
|
||||
<li>Hold <kbd>Option</kbd> and right-click the folder.</li>
|
||||
<li>Click "Copy <folder name> as Pathname".</li>
|
||||
<li>Paste the result into the path input.</li>
|
||||
</ol>
|
||||
<p className="rounded-md bg-muted px-2 py-1 font-mono text-xs">
|
||||
/Users/yourname/Documents/project
|
||||
</p>
|
||||
</section>
|
||||
<section className="space-y-1.5">
|
||||
<p className="font-medium">Windows (File Explorer)</p>
|
||||
<ol className="list-decimal space-y-1 pl-5 text-muted-foreground">
|
||||
<li>Find the folder in File Explorer.</li>
|
||||
<li>Hold <kbd>Shift</kbd> and right-click the folder.</li>
|
||||
<li>Click "Copy as path".</li>
|
||||
<li>Paste the result into the path input.</li>
|
||||
</ol>
|
||||
<p className="rounded-md bg-muted px-2 py-1 font-mono text-xs">
|
||||
C:\Users\yourname\Documents\project
|
||||
</p>
|
||||
</section>
|
||||
<section className="space-y-1.5">
|
||||
<p className="font-medium">Terminal fallback (macOS/Linux)</p>
|
||||
<ol className="list-decimal space-y-1 pl-5 text-muted-foreground">
|
||||
<li>Run <code>cd /path/to/folder</code>.</li>
|
||||
<li>Run <code>pwd</code>.</li>
|
||||
<li>Copy the output and paste it into the path input.</li>
|
||||
</ol>
|
||||
</section>
|
||||
</div>
|
||||
<DialogFooter>
|
||||
<Button variant="outline" onClick={() => setOpen(false)}>
|
||||
OK
|
||||
</Button>
|
||||
</DialogFooter>
|
||||
</DialogContent>
|
||||
</Dialog>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Label + input rendered on the same line (inline layout for compact fields).
|
||||
*/
|
||||
export function InlineField({ label, hint, children }: { label: string; hint?: string; children: React.ReactNode }) {
|
||||
return (
|
||||
<div className="flex items-center gap-3">
|
||||
<div className="flex items-center gap-1.5 shrink-0">
|
||||
<label className="text-xs text-muted-foreground">{label}</label>
|
||||
{hint && <HintIcon text={hint} />}
|
||||
</div>
|
||||
<div className="w-24 ml-auto">{children}</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user