<script lang="ts">
	export interface Command {
		id: string;
		label: string;
		description?: string;
		keywords?: string[];
		action: () => void;
	}

	interface Props {
		commands: Command[];
		open: boolean;
		onclose: () => void;
	}

	let { commands, open, onclose }: Props = $props();

	let query = $state('');
	let selectedIdx = $state(0);
	let inputEl = $state<HTMLInputElement | null>(null);

	const filtered = $derived(
		query.trim()
			? commands.filter(c =>
				c.label.toLowerCase().includes(query.toLowerCase()) ||
				c.keywords?.some(k => k.toLowerCase().includes(query.toLowerCase()))
			)
			: commands
	);

	$effect(() => {
		if (open) {
			query = '';
			selectedIdx = 0;
			setTimeout(() => inputEl?.focus(), 50);
		}
	});

	// Reset selection when filter changes
	$effect(() => { filtered; selectedIdx = 0; });

	function execute(cmd: Command) {
		onclose();
		cmd.action();
	}

	function handleKeydown(e: KeyboardEvent) {
		if (e.key === 'Escape') { onclose(); return; }
		if (e.key === 'ArrowDown') { e.preventDefault(); selectedIdx = Math.min(selectedIdx + 1, filtered.length - 1); }
		if (e.key === 'ArrowUp') { e.preventDefault(); selectedIdx = Math.max(selectedIdx - 1, 0); }
		if (e.key === 'Enter' && filtered[selectedIdx]) { e.preventDefault(); execute(filtered[selectedIdx]); }
	}
</script>

{#if open}
	<!-- Backdrop -->
	<div
		class="fixed inset-0 z-50 bg-black/60 backdrop-blur-sm"
		onclick={onclose}
	></div>

	<!-- Palette -->
	<div class="fixed top-[20%] left-1/2 -translate-x-1/2 z-50 w-full max-w-md px-4 pointer-events-none">
		<div class="bg-zinc-900 border border-zinc-700 rounded-2xl shadow-2xl overflow-hidden pointer-events-auto">
			<!-- Input -->
			<div class="flex items-center gap-2.5 px-4 py-3 border-b border-zinc-800">
				<svg class="w-4 h-4 text-zinc-500 shrink-0" fill="none" stroke="currentColor" viewBox="0 0 24 24">
					<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M21 21l-6-6m2-5a7 7 0 11-14 0 7 7 0 0114 0z" />
				</svg>
				<input
					bind:this={inputEl}
					bind:value={query}
					onkeydown={handleKeydown}
					placeholder="Type a command…"
					class="flex-1 bg-transparent text-zinc-100 placeholder-zinc-500 focus:outline-none text-sm"
				/>
				<kbd class="text-xs text-zinc-600 border border-zinc-700 rounded px-1.5 py-0.5">esc</kbd>
			</div>

			<!-- Commands -->
			<ul class="py-1 max-h-72 overflow-y-auto">
				{#each filtered as cmd, i (cmd.id)}
					<li>
						<button
							onclick={() => execute(cmd)}
							onmouseenter={() => selectedIdx = i}
							class="w-full flex items-center gap-3 px-4 py-2.5 text-left transition-colors {i === selectedIdx ? 'bg-zinc-800' : 'hover:bg-zinc-800/50'}"
						>
							<div class="flex-1 min-w-0">
								<p class="text-sm text-zinc-100">{cmd.label}</p>
								{#if cmd.description}
									<p class="text-xs text-zinc-500 mt-0.5 truncate">{cmd.description}</p>
								{/if}
							</div>
						</button>
					</li>
				{/each}

				{#if filtered.length === 0}
					<li class="px-4 py-4 text-sm text-zinc-500 text-center">No commands found</li>
				{/if}
			</ul>

			<!-- Footer hint -->
			<div class="px-4 py-2 border-t border-zinc-800 flex gap-4 text-xs text-zinc-600">
				<span><kbd class="border border-zinc-700 rounded px-1">↑↓</kbd> navigate</span>
				<span><kbd class="border border-zinc-700 rounded px-1">↵</kbd> select</span>
			</div>
		</div>
	</div>
{/if}
