Improve search autocomplete UX
- Tab key accepts autocomplete suggestion (like right arrow) - Prevent search from firing while autocomplete suggestion is visible
This commit is contained in:
@@ -160,7 +160,6 @@ class SearchPanel(Widget):
|
||||
width: auto;
|
||||
padding: 0 1;
|
||||
color: $primary;
|
||||
height: 1;
|
||||
}
|
||||
|
||||
SearchPanel Input {
|
||||
@@ -178,7 +177,6 @@ class SearchPanel(Widget):
|
||||
width: auto;
|
||||
padding: 0 1;
|
||||
color: $text-muted;
|
||||
height: 1;
|
||||
}
|
||||
"""
|
||||
|
||||
@@ -231,6 +229,34 @@ class SearchPanel(Widget):
|
||||
yield Button("?", variant="default", id="help-btn")
|
||||
yield Button("Cancel", variant="warning", id="cancel-btn")
|
||||
|
||||
def _has_suggestion(self) -> bool:
|
||||
"""Check if the search input currently has an autocomplete suggestion."""
|
||||
try:
|
||||
input_widget = self.query_one("#search-input", Input)
|
||||
return bool(input_widget._suggestion and input_widget._cursor_at_end)
|
||||
except Exception:
|
||||
return False
|
||||
|
||||
def _accept_suggestion(self) -> bool:
|
||||
"""Accept the current autocomplete suggestion if present. Returns True if accepted."""
|
||||
try:
|
||||
input_widget = self.query_one("#search-input", Input)
|
||||
if input_widget._suggestion and input_widget._cursor_at_end:
|
||||
input_widget.value = input_widget._suggestion
|
||||
input_widget.cursor_position = len(input_widget.value)
|
||||
return True
|
||||
except Exception:
|
||||
pass
|
||||
return False
|
||||
|
||||
def on_key(self, event) -> None:
|
||||
"""Handle key events to intercept Tab for autocomplete."""
|
||||
if event.key == "tab":
|
||||
# Try to accept suggestion; if successful, prevent default tab behavior
|
||||
if self._accept_suggestion():
|
||||
event.prevent_default()
|
||||
event.stop()
|
||||
|
||||
def show(self, initial_query: str = "") -> None:
|
||||
"""Show the search panel and focus the input."""
|
||||
self.add_class("visible")
|
||||
@@ -268,6 +294,10 @@ class SearchPanel(Widget):
|
||||
|
||||
def _trigger_search(self) -> None:
|
||||
"""Trigger the actual search after debounce."""
|
||||
# Don't search if an autocomplete suggestion is visible
|
||||
if self._has_suggestion():
|
||||
return
|
||||
|
||||
query = self.query_one("#search-input", Input).value.strip()
|
||||
if query and query != self._last_query:
|
||||
self._last_query = query
|
||||
|
||||
Reference in New Issue
Block a user