fix: check actual GTK buffer to detect user edits in ghost text
The stale input check based on realInput was insufficient because realInput isn't updated until the debounced search-changed signal fires. Reading the actual buffer content detects user edits that happened between the search start and result delivery.
- commit
- 7eb8e318707657359d4e090662508f55315bf233
- author
- brice · · 2026-03-27 19:31 UTC
- parent
- 3a4e710
- signature
- GPG Verified
CD88F9E564E0102646FB6077A1A07C7C7C3E349D· arch-gpg Verified for the committer email
1 file · +10 -6
M internal/ui/component/omnibox.go +10 -6
| @@ -910,16 +910,20 @@ func (o *Omnibox) setGhostText(originalInput, suffix string) { | |||
| 910 | 910 | return | |
| 911 | 911 | } | |
| 912 | 912 | ||
| 913 | - | // Verify the user hasn't typed since this ghost was computed. | |
| 913 | + | // Verify the buffer hasn't been modified by user typing since this ghost | |
| 914 | + | // was computed. We check the actual buffer — not realInput, which may be | |
| 915 | + | // stale due to debounced search-changed signal. | |
| 916 | + | currentBuffer := o.entry.GetText() | |
| 914 | 917 | o.mu.RLock() | |
| 915 | - | currentInput := o.realInput | |
| 918 | + | existingGhost := o.ghostSuffix | |
| 916 | 919 | o.mu.RUnlock() | |
| 917 | - | if currentInput != originalInput { | |
| 920 | + | expectedWithGhost := originalInput + existingGhost | |
| 921 | + | if currentBuffer != originalInput && currentBuffer != expectedWithGhost { | |
| 918 | 922 | log.Debug(). | |
| 919 | - | Str("staleInput", originalInput). | |
| 920 | - | Str("currentInput", currentInput). | |
| 923 | + | Str("originalInput", originalInput). | |
| 924 | + | Str("currentBuffer", currentBuffer). | |
| 921 | 925 | Str("suffix", suffix). | |
| 922 | - | Msg("ghost: setGhostText skipped (stale input)") | |
| 926 | + | Msg("ghost: setGhostText skipped (buffer modified by user)") | |
| 923 | 927 | return | |
| 924 | 928 | } | |
| 925 | 929 | ||
| @@ -910,16 +910,20 @@ func (o *Omnibox) setGhostText(originalInput, suffix string) { | |||||
| 910 | return | 910 | return | ||
| 911 | } | 911 | } | ||
| 912 | 912 | ||||
| 913 | - | // Verify the user hasn't typed since this ghost was computed. | 913 | + | // Verify the buffer hasn't been modified by user typing since this ghost |
| 914 | + | // was computed. We check the actual buffer — not realInput, which may be | |||
| 915 | + | // stale due to debounced search-changed signal. | |||
| 916 | + | currentBuffer := o.entry.GetText() | |||
| 914 | o.mu.RLock() | 917 | o.mu.RLock() | ||
| 915 | - | currentInput := o.realInput | 918 | + | existingGhost := o.ghostSuffix |
| 916 | o.mu.RUnlock() | 919 | o.mu.RUnlock() | ||
| 917 | - | if currentInput != originalInput { | 920 | + | expectedWithGhost := originalInput + existingGhost |
| 921 | + | if currentBuffer != originalInput && currentBuffer != expectedWithGhost { | |||
| 918 | log.Debug(). | 922 | log.Debug(). | ||
| 919 | - | Str("staleInput", originalInput). | 923 | + | Str("originalInput", originalInput). |
| 920 | - | Str("currentInput", currentInput). | 924 | + | Str("currentBuffer", currentBuffer). |
| 921 | Str("suffix", suffix). | 925 | Str("suffix", suffix). | ||
| 922 | - | Msg("ghost: setGhostText skipped (stale input)") | 926 | + | Msg("ghost: setGhostText skipped (buffer modified by user)") |
| 923 | return | 927 | return | ||
| 924 | } | 928 | } | ||
| 925 | 929 | ||||