fix: allow editing custom email in Select component

When a custom value (not in the items list) is selected, reopening
the dropdown now pre-fills the filter with the current value so users
can directly edit it. Also hide the "Use custom email" create option
when the filter matches the current value, and show the regular
placeholder instead of the value when editing a custom entry.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Guilhem
2026-02-16 11:52:54 +00:00
parent b54bea7192
commit bfb65fc8b4
2 changed files with 20 additions and 5 deletions
@@ -95,7 +95,7 @@
let inputEl: HTMLInputElement | undefined = $state()
let processedItems: ProcessedItem<Value>[] = $derived.by(() => {
let args = { items, createText, filterText, groupBy, onCreateItem, sortBy }
let args = { items, createText, filterText, groupBy, onCreateItem, sortBy, currentValue: value }
return untrack(() => processItems(args))
})
@@ -103,7 +103,15 @@
if (filterText) open = true
})
$effect(() => {
if (!open) filterText = ''
if (!open) {
filterText = ''
} else {
untrack(() => {
if (value && !valueEntry) {
filterText = inputText
}
})
}
})
let valueEntry = $derived(value && processedItems?.find((item) => deepEqual(item.value, value)))
@@ -163,7 +171,7 @@
bind:value={() => (open ? filterText : inputText), (v) => open && (filterText = v)}
placeholder={loading && !value
? 'Loading...'
: value && !showPlaceholderOnOpen
: value && !showPlaceholderOnOpen && !(open && !valueEntry)
? inputText
: placeholder}
style={containerStyle}
@@ -4,7 +4,8 @@ export function processItems<Item extends { label?: string; value: any }>({
groupBy,
sortBy,
onCreateItem,
createText
createText,
currentValue
}: {
items?: Item[]
filterText?: string
@@ -12,6 +13,7 @@ export function processItems<Item extends { label?: string; value: any }>({
sortBy?: (a: Item, b: Item) => number
onCreateItem?: (value: string) => void
createText?: string
currentValue?: any
}): ProcessedItem<Item['value']>[] {
let items2 =
items?.map((item) => ({
@@ -28,7 +30,12 @@ export function processItems<Item extends { label?: string; value: any }>({
if (sortBy) {
items2 = items2?.sort(sortBy)
}
if (onCreateItem && filterText && !items2.some((item) => item.label === filterText)) {
if (
onCreateItem &&
filterText &&
filterText !== currentValue &&
!items2.some((item) => item.label === filterText)
) {
items2.push({
label: createText ?? `Add new: "${filterText}"`,
value: filterText,