feat: add IconGrid, EntityPicker controls and enhance search panel
CI / lint-and-check (push) Failing after 4m56s
CI / test (push) Has been skipped
CI / docker-build (push) Has been skipped

Port icon grid and entity picker patterns from wled-screen-controller.
IconGrid replaces plain <select> elements with visual icon grids for
known item sets (widget type, icon type, healthcheck method, permission
level). EntityPicker replaces search dropdowns with a command-palette
style overlay with keyboard navigation and filtering.

Enhance SearchDialog with keyboard navigation (arrow keys, Enter,
Escape), grouped results with section headers, active highlight,
and a footer with shortcut hints.
This commit is contained in:
2026-03-25 11:58:21 +03:00
parent 54a30ca4ca
commit 8d7847889e
11 changed files with 744 additions and 195 deletions
+13 -9
View File
@@ -4,6 +4,8 @@
import type { z } from 'zod';
import type { createAppSchema } from '$lib/utils/validators.js';
import AppIconPicker from './AppIconPicker.svelte';
import IconGrid from '$lib/components/ui/IconGrid.svelte';
import type { IconGridItem } from '$lib/components/ui/IconGrid.svelte';
type AppSchema = z.infer<typeof createAppSchema>;
@@ -19,6 +21,11 @@
});
let showAdvanced = $state(false);
const healthcheckMethodItems: IconGridItem[] = [
{ value: 'GET', icon: '🔍', label: 'GET', desc: 'Full response' },
{ value: 'HEAD', icon: '📋', label: 'HEAD', desc: 'Headers only' }
];
</script>
<form method="POST" {action} use:enhance class="space-y-4">
@@ -140,20 +147,17 @@
<div class="grid grid-cols-1 gap-4 sm:grid-cols-3">
<div>
<label
for="healthcheckMethod"
class="mb-1 block text-sm font-medium text-card-foreground"
>
{$t('app.healthcheck_method')}
</label>
<select
id="healthcheckMethod"
<IconGrid
items={healthcheckMethodItems}
value={$form.healthcheckMethod ?? 'GET'}
onchange={(v) => ($form.healthcheckMethod = v as 'GET' | 'HEAD')}
name="healthcheckMethod"
bind:value={$form.healthcheckMethod}
class="w-full rounded-md border border-input bg-background px-3 py-2 text-sm text-foreground focus:outline-none focus:ring-2 focus:ring-ring"
>
<option value="GET">GET</option>
<option value="HEAD">HEAD</option>
</select>
columns={2}
/>
</div>
<div>