cretz / doogie

A Chromium-based web browser with tree-style pages
https://cretz.github.io/doogie
MIT License
279 stars 28 forks source link

Address Bar Autocompleter Focus #76

Open terinjokes opened 6 years ago

terinjokes commented 6 years ago

The address bar is a QLineEdit that spawns a new QListWidget for the autocomplete. Various window hints are set on the QListWidget's window, to always display on top, be frameless, and to not accept focus. On Windows these hints are absolutely applied, however on Linux these are mere hints to the Window Manager.

With Window Managers for Linux (I'm testing with AwesomeWM, though I believe this is also true on i3) a NET_WM_WINDOW_TYPE_NORMAL window will appear in window switchers and be able to take focus. We can implement a handler for the WM_TAKE_FOCUS protocol by calling QWidget::FocusPolicy(Qt::NoPolicy), which will reject focus and send it back to the previous window.

Unfortunately, it seems the UrlEdit::focusInEvent(QFocusEvent*) and UrlEdit::focusOutEvent(QFocusEvent*) methods are still called with the autocomplete's focus policy is Qt::NoPolicy. The good news is that this happens fast enough my keystrokes aren't lost anymore. The bad news is the autocomplete is always hidden.

My next thought is to try replacing the autocomplete functionality using QLineEdit's support for using QCompleter. By default, this will give us popups using QListViews, like we're drawing now, though it looks like we can customize this behavior by subclassing QCompleter.

cretz commented 6 years ago

@terinjokes - I am OK with switching to QCompleter if it has all features, but I wonder what settings that uses to make the focus work that we cannot use? I haven't tested with anything else (and primarily only use it on Windows and default Ubuntu WM). I am definitely open to PRs, but would like to see what Qt does to alleviate the issue internally that we could also apply.

terinjokes commented 6 years ago

@cretz I tried a bunch of options, such as disabling focus, marking it as a "dropdown" window, marking it as a utility window, setting up a transient parent. In no way was I able to get it to behave like a normal autocomplete.

If there's a way of drawing the QListView widget without making it a new window, and I'm sure there is, that will probably work much better.

cretz commented 6 years ago

@terinjokes - I haven't investigated (and may not for a bit because I'll first have to set a WM to replicate), but you might be able to make the QListWidget not its own window and still show it. I quick look at QCompleter shows they just show() a view.

terinjokes commented 6 years ago

Yeah, was wondering what might happen if we don't set any of the window hints. I'll give it a shot.