X11 Atoms will be lost after the window is unmapped
Describe the bug
I don't know whether it's a bug or not, so I think I should discuss the solution here.
Related links:
Assume that we're setting such properties on a window:
public MainWindow()
{
InitializeComponent();
ShowInTaskbar = false;
Topmost = true;
WindowState = WindowState.FullScreen;
}
We're expecting that the window will be shown in full screen mode, topmost, and not shown in the taskbar. However, after Hide and Show the window, all the properties are lost. The window is shown in maximized mode, not topmost, and shown in the taskbar. This behavior is quitely different from the behavior running on Windows.
Let's see deeper.
The properties above emit the following X11 atoms:
_NET_WM_STATE_SKIP_TASKBAR_NET_WM_STATE_ABOVE_NET_WM_STATE_FULLSCREEN
After the XUnmapWindow is called, all the atoms are lost. Furthermore, after the XMapWindow is called, two new atoms are added:
_NET_WM_STATE_MAXIMIZED_HORZ_NET_WM_STATE_MAXIMIZED_VERT
As a result, the window is shown in maximized mode(not fullscreen), not topmost, and shown in the taskbar.
To Reproduce
- Set the properties on a window as above.
- Call
HideandShowon the window. - The window is shown in maximized mode, not topmost, and shown in the taskbar.
Expected behavior
The window should be shown in full screen mode, topmost, and not shown in the taskbar even after Hide and Show which is the same behavior as running on Windows.
Avalonia version
11.0.10, 11.0.11, 11.1.0-beta1, 11.1.0-beta2, 11.1.0-rc1
OS
Linux
Additional context
See the link here and search for _NET_WM_STATE section:
The Window Manager should remove the property whenever a window is withdrawn, but it should leave the property in place when it is shutting down
I can't understand the meaning of "withdrawn" here. But after several debugging on the ControlCatalog.NetCore project, I think it's very likely that it means the window is unmapped which means that the Window Manager should remove the atoms properties whenever a window is unmapped.
See another link here:
The author of the topic is suffering from the same problem as what Avalonia UI is facing.
I have two naive solutions:
Solution 1:
- Add a
HashSet<nint>into theX11Windowclass to store the atoms. - Whenever any properties which affect the atoms are set, change the atoms of the
HashSet. - Every time before the
XMapWindowis called, set the atoms in theHashSetto the window.
Solution 2:
- Store the atoms in the
X11Windowclass before theXUnmapWindowis called. - Every time before the
XMapWindowis called, set the atoms back to the window.
The two solutions are both not perfect.
For solution 1, if the developer add some Atoms themselves, we will drop them after the window is mapped. For solution 2, if the developer set some properties when the window is invisible, the properties will be lost after the window is mapped.
I think we should discuss a better solution here. Thanks.
I prefer Solution one.
I also think solution 1 is good enough. Hope this gets fixed soon :)
At least for Topmost a workaround is following:
window.Show();
window.Topmost = False;
window.Topmost = true;
Setting it to true isn't enought to get the relevant ATOM's set