Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature: option to hide title bar (frameless/borderless) #3199

Closed
akz92 opened this issue Oct 26, 2017 · 19 comments
Closed

Feature: option to hide title bar (frameless/borderless) #3199

akz92 opened this issue Oct 26, 2017 · 19 comments
Labels
priority: 2 - low Issues which are currently not very important.

Comments

@akz92
Copy link

akz92 commented Oct 26, 2017

It would be great if there was an option to hide qute's title bar. I know that usually this is a task for the window manager but it would be a nice addition and would be great for people (like me) that doesn't use a window manager with support for this kind of customization.

Taking from this stackoverflow question it looks simple to implement. All we'd have to do is set this window flag:

setWindowFlags(Qt::Window | Qt::FramelessWindowHint)
@The-Compiler
Copy link
Member

I've tried that before, but it means you can't move/resize the window anymore, which isn't really acceptable.

@akz92
Copy link
Author

akz92 commented Oct 26, 2017

I didn't know about that, but wouldn't this be ok if the option description explained it? The user could revert this option to move/resize the window, or use an external tool.

@The-Compiler
Copy link
Member

Hmm, I guess it could work - however, the window needs to be hidden and re-shown to change those flags, so I'm not sure if moving/resizing like that would work. Out of curiosity, what window manager / DE do you use?

@The-Compiler The-Compiler added the priority: 2 - low Issues which are currently not very important. label Oct 26, 2017
@The-Compiler The-Compiler reopened this Oct 26, 2017
@akz92
Copy link
Author

akz92 commented Oct 26, 2017

I use macOS's default wm and betterSnapTool for moving/resizing windows.

Another option would be to use a command line argument for this behavior. There'd be no need to re-show the title bar, qb would be started as frameless and stay like that.

@The-Compiler
Copy link
Member

The-Compiler commented Oct 26, 2017

If you re-open qutebrowser, then do :debug-console and there do:

from PyQt5.QtCore import Qt
win = objreg.get('main-window', scope='window', window=0)
win.setWindowFlags(Qt.Window | Qt.FramelessWindowHint)
win.hide()
win.show()

it should be frameless, right? Can you then still resize/move it using betterSnapTool?

@akz92
Copy link
Author

akz92 commented Oct 26, 2017

It is frameless. I'm able to move it using betterSnapTool, but can't resize it.

@The-Compiler
Copy link
Member

What if you call win.setWindowFlags(Qt.Window), resize it, and call it with Qt.FramelessWindowHint again - does it stay with the new position/size?

@akz92
Copy link
Author

akz92 commented Oct 26, 2017

It stays with the new position/size.

The only issue that I noticed is that if I set the window to occupy the entire screen, after setting Qt.FramelessWindowHint the window (obviously) loses the height of the title bar leaving an empty space at the bottom, but I guess this could be handled when setting it to frameless.

@dsanson
Copy link

dsanson commented Nov 18, 2017

I use chunkwm to manage windows on a mac, and would also like this feature. When I tested the above, I could neither resize the resulting frameless window nor move it with chunkwm. Using the Accessibilty Inspector, I was able to figure out that the role of the window is AXWindow and the subrole is AXUnknown. With that, I was able to get chunkwm to move the window around. But it doesn't seem to be able to resize it.

@rien333
Copy link
Contributor

rien333 commented Feb 28, 2018

@dsanson adding chunkc tiling::rule --owner "Python" --state tile to my .chunkwmrc + entering the following console debug command made qutebrowser work together with chunkwm without a title bar:

from PyQt5.QtCore import Qt
window = objreg.get('main-window', scope='window', window=0)
window.setWindowFlags(Qt.Window | Qt.CustomizeWindowHint)
window.hide()
window.show()

(additional cool tip: add Qt.NoDropShadowWindowHint to disable shadows which are unneeded in tiling window managers)

The forced tiling rule for Python is not ideal, but maybe it is possible to change qutebrowser title to something other than "Python". I'm fine regardless as I don't really use any other Python apps anyway.

Now, if anyone could tell me how to apply these flags at start (preferably without compiling from source myself) that would be of great help.

@dsanson
Copy link

dsanson commented Mar 2, 2018

@rien333 Neat! That worked for me too!

@dsanson
Copy link

dsanson commented Mar 2, 2018

Now, if anyone could tell me how to apply these flags at start (preferably without compiling from source myself) that would be of great help.

If you are willing to run from source (or compile from source), adding the line

self.setWindowFlags(Qt.Window | Qt.CustomizeWindowHint)

to qutebrowser/mainwindow/mainwindow.py seems to do the trick.

diff --git a/qutebrowser/mainwindow/mainwindow.py b/qutebrowser/mainwindow/mainwindow.py
index 05482a1d5..c8de407f5 100644
--- a/qutebrowser/mainwindow/mainwindow.py
+++ b/qutebrowser/mainwindow/mainwindow.py
@@ -169,6 +169,7 @@ class MainWindow(QWidget):
         objreg.register('message-bridge', message_bridge, scope='window',
                         window=self.win_id)
 
+        self.setWindowFlags(Qt.Window | Qt.CustomizeWindowHint)
         self.setWindowTitle('qutebrowser')
         self._vbox = QVBoxLayout(self)
         self._vbox.setContentsMargins(0, 0, 0, 0)

@rien333
Copy link
Contributor

rien333 commented Mar 3, 2018

@dsanson I've been running a similar built like that for a bit now, and it's been working great. Thanks anyway! Would be cool if this were to become an official option maybe (@The-Compiler), so that I don't have to deal with multiple python versions/binaries and virtual environments and the like. Oh and, an additional stupid quirk of this method is that tool tips will be floated as well due to chunkwm forcing all Python windows to be floated, which can be really annoying. EDIT: (I think building qutebrowser as an .app fixes this, but this has been quite a pain so far)

Bit off topic maybe, but it does really bother me now that there is no way to let chunkwm/skhd spawn new qutebrowser windows as far as I know of (say, by means of scripting). EDIT: stupid me, you can spawn a new window globally by just calling $ qutebrowser

@The-Compiler
Copy link
Member

Hmm, still not sure how an option for this would look. I suppose there could just be an option to set any window type/flags, but I'm not looking forward to the issues people will get themselves into with that 😉

What I don't really understand so far: What's the difference between Qt::FramelessWindowHint and Qt::CustomizeWindowHint?

@rien333
Copy link
Contributor

rien333 commented Mar 12, 2018

I wasn't really suggesting an option to set any QT window flags, but more something along the lines of c.window.hide_wayland_decoration = True for hiding the macOS titlebar. Say something like c.window.hide_cocoa_titlebar = True/c.window.hide_cocoa_decoration = True. Or make a general option to hide window decorations, and possibly document it as only working under wayland and macOS (for now).

The difference between those two types of window hints is that the QT documentation states Qt::FramelessWindowHint to not be resizable:

Produces a borderless window. The user cannot move or resize a borderless window via the window system.

The QT::CustomizeWindowHint on the other hand produces a window that only disables the window title (in the case of cocoa, the titlebar)

Turns off the default window title hints.

In practice, a window with Qt::FramelessWindowHint set produces a window that is fairly unusable and only meant for very specific purposes such as dialogue boxes. It's a pretty specific cocoa window type probably. Qt::FramelessWindowHint still allows window control (resizing, moving, mouse resizing), especially in conjunction with the various linux-y window managers and snapping tools available for macOS. In essence it's like any other cocoa window, but without the aqua/standard UI titlebar. The idea of the option mentioned above should therefore probably stay clear of using the Qt::FramelessWindowHint and use something like the code provided by @dsanson.

@The-Compiler
Copy link
Member

Hm, I like the more general window.hide_decoration option, and adding migrations to configfiles.py for that should be straightforward too. Anyone here feels like picking this up? I'm currently busy with other stuff and reviewing PRs, so it'll probably take a while until I get to this.

@rien333, also let me note that you linked to some ~2009 version of Qt Jambi (Qt for Java) documentation there 😉 The up-to-date docs are here: http://doc.qt.io/qt-5/qt.html#WindowType-enum

@rien333
Copy link
Contributor

rien333 commented Mar 21, 2018

I'm picking this up, but I have some questions. As this is relatively easy I hope answering my questions doesn't take you longer than implementing it yourself.

Firstly, does migrating the old settings entail that the old value for window.wayland_decoration should be copied over to window.hide_decoration? (I already wrote the code for this behavior I think)

Secondly, I don't think it makes much sense conceptually to have window shadows when using tiling window managers, which I think make up the fair majority of the people hiding window decorations given that (most) other types of window managers lack the options to deal with borderless windows. Is it a good idea to disable window shadows when the user wants to hide window decorations? iTerm and mpv (at least on non macOS systems, and on older versions) for example also have this behavior when the window decorations are hidden.

Borderless windows can look a bit odd under some circumstances though, so it might also be a possibility to add another config item which determines window shadow visibility. Or just always leave shadows on, it's your call. (I'm pretty sure most people would prefer hiding shadows though)

@The-Compiler
Copy link
Member

Argh, something went wrong when trying to write my answer before, let's try again.

I'm picking this up, but I have some questions. As this is relatively easy I hope answering my questions doesn't take you longer than implementing it yourself.

That happens from time to time (with reviews and all), but it's not necessarily bad - I like getting people to contribute to open source (and qutebrowser) - and some of those people stick around and become regular contributors 😄

Firstly, does migrating the old settings entail that the old value for window.wayland_decoration should be copied over to window.hide_decoration? (I already wrote the code for this behavior I think)

Indeed - this would be in qutebrowser/config/configfiles.py in _handle_migrations. Make sure to also add a test in tests/unit/config/test_configfiles.py (similar to test_merge_persist).

Secondly, I don't think it makes much sense conceptually to have window shadows when using tiling window managers, which I think make up the fair majority of the people hiding window decorations given that (most) other types of window managers lack the options to deal with borderless windows. Is it a good idea to disable window shadows when the user wants to hide window decorations? iTerm and mpv (at least on non macOS systems, and on older versions) for example also have this behavior when the window decorations are hidden.

Borderless windows can look a bit odd under some circumstances though, so it might also be a possibility to add another config item which determines window shadow visibility. Or just always leave shadows on, it's your call. (I'm pretty sure most people would prefer hiding shadows though)

Let's just hide them for borderless windows and see if someone complains 😉

@Msouza91
Copy link

Just giving a data point for the discussion, I was searching for this option and found the issue.

I have config.set ("window.hide_decoration", True) and I am able to use the keyboard shortcuts to resize the screen if I want to, but turns out to not be an issue for me, since I use this option for maximum real estate in a maximized setting which I can activate/deactivate with keybindings as well (super+up or down).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
priority: 2 - low Issues which are currently not very important.
Projects
None yet
Development

No branches or pull requests

5 participants