Bug 186676 - [GTK] visibilitychange event not fired when window moved to a separate workspace
Summary: [GTK] visibilitychange event not fired when window moved to a separate workspace
Status: RESOLVED WONTFIX
Alias: None
Product: WebKit
Classification: Unclassified
Component: WebKitGTK (show other bugs)
Version: WebKit Nightly Build
Hardware: Unspecified Unspecified
: P2 Normal
Assignee: Nobody
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2018-06-15 10:02 PDT by Daniel
Modified: 2018-06-18 05:59 PDT (History)
3 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Daniel 2018-06-15 10:02:26 PDT
Steps to reproduce:
0. Open GNOME Web (formerly “Epiphany”) under a GNOME desktop
1. Install the following event handler in on about:blank:

document.addEventListener('visibilitychange', function() {
  document.body.appendChild(document.createTextNode(document.visibilityState));
  console.log(document.visibilityState);
});

2. Switch to a separate desktop workspace so that the GNOME Web window is no longer on the active workspace., and then switch back.

Expected results:
Should have logged two messages: "hidden" and "visible".

Actual results:
No visibilitychange event is fired when the window is no longer visible.

Notes:
This works with macOS workspaces but not with GNOME workspaces. The GNOME Web bug tracker referred me here stating that it was a bug in WebKit GTK and not on their end.

Some times console.log(document.visibilityState) will report "undefined" but document.body.appendChild(document.createTextNode(document.visibilityState)) will report the correct state. Not sure if this is the expected behaviour or a separate bug.
Comment 1 Michael Catanzaro 2018-06-15 10:56:48 PDT
I wonder if it's even possible for applications to detect this condition. We probably assume a focused window is visible, but obviously that's not true as it could be focused on a different workspace, or occluded by another window.
Comment 2 Daniel 2018-06-15 11:16:36 PDT
This also works as expected with Microsoft Edge and Internet Explorer with Windows 10 workspaces (I do believe they call them desktops, but it’s the same concept and workflow.)
Comment 3 Michael Catanzaro 2018-06-17 10:55:44 PDT
I think Microsoft Edge and Internet Explorer are not Wayland clients. :)

I compared Epiphany's behavior to Firefox's and found Epiphany's is identical. When opening your test in firefox-wayland, I see visibility notifications only if I switch to another tab within Firefox itself. Same with Epiphany. Firefox does not send any visibility change events when it is switched to another workspace.

I also tested the normal firefox binary, which is not directly relevant because it is an obsolete XWayland client. It had almost the same behavior. The difference was that the normal Firefox was additionally able to send visibility notifications when maximized and minimized. Neither firefox-wayland nor Epiphany were able to do this. I think we should be able to detect minimization ("iconification") by watching GtkWidget::window-state-event, but that's not what you requested here.

I asked the GTK+ developers for a way to detect if the window is visible, and sadly they say it is not possible. We would need to add a Wayland protocol to indicate visibility to clients (probably to xdg-shell), and they did not seem interested in adding that functionality to mutter/weston or to GTK+. So to progress this would need changes there. Here's the full conversation if you're interested:

mcatanzaro	Hey, is there a way in GTK+ Wayland to detect whether a focused window is currently visible? We need to know if it's e.g. focused but on a non-visible workspace, for https://bugs.webkit.org/show_bug.cgi?id=186676

Company	mcatanzaro: apart from mapped/unmapped I don't think there's a way to track it inside GTK

mcatanzaro	Company: gtk_widget_get_mapped()?

Company	yeah
and WMs don't usually unmap windows anymore
i think

mcatanzaro	Yeah that's the problem, so the window will be mapped even if it's offscreen, right?

Company	yes

ebassi	mcatanzaro: Yes
It's something that happens on X11 as well

mcatanzaro	So this is CANTFIX

ebassi	Since the advent of compositors

Company	I'm not aware of any API to track visibility

mcatanzaro	But on X11 at least you can query to see which workspace you are on

ebassi	mcatanzaro: If the WM is using workspaces

mcatanzaro	So I wouldn't be surprised if Firefox or Chromium had some hack to make this work

ebassi	Not if it's using viewports, for instance

mcatanzaro	Viewports aren't real anymore :)

Company	also
I don't like that API

ebassi	mcatanzaro: Isn't Compiz still using viewports?

Company	I don't need ad popups to stop their countown when i'm not looking at them...

mcatanzaro	It's probably important for battery life, though

ebassi	AFAIR, Chrome disables high performance counters on focus out; so the ads keep running, but they won't wake up your system just as often

mcatanzaro	We want to throttle timers when pages are not visible

ebassi	focus out/tab out

Company	that's focus though, not visibility

ebassi	I've definitely seen timers in JS not working when switching tabs

Company: Yeah

mcatanzaro	Using focus also fails because we have one  focused window per workspace
So it can be focused but not visible
Times like this make me wonder how software is supposed to work. In general.

Company	mcatanzaro: in general, my approach to visibility has been that it's impossible to do from inside the app and needs explicit compositor support
mcatanzaro: and generally compositors have not been very interested in tracking that - mostly because apps didn't really care about it

mcatanzaro	I wonder how Firefox and Chromium handle onvisibility then... in Wayland, at least

Company	X has VisibilityNotify events, but I removed support for those, because they don't work

ebassi	mcatanzaro: Key focus/pointer crossing is how the compositors have been able to tell the app "you have the user's attention"

mcatanzaro	I guess Chromium is still an XWayland client, so only Firefox in experimental Wayland mode is a relevant comparison

Company	mcatanzaro: theres also (at least) 2 meanings of what visibility means

ebassi	But we live in a world where you can leave your web browser in the background playing music, these days

Company	mcatanzaro: because if an app is on another workspace but you open the shell overlay, is that app now visible?
mcatanzaro: or if it's overlayed by a semi-transparent terminal, is it still visible?

mcatanzaro	I'd say "yes" because otherwise the app could black out its window trusting that it is not visible, and it would be a compositor bug to show that
Visible should mean visible
I guess that proves that visibility is for sure different from focus

Company	mcatanzaro: so whenever i press alt-tab you emit a visibility event - and another one when i release the tab key?

mcatanzaro	I would say yes
Maybe that's dumb, dunno

Company	mcatanzaro: so if i have an opaque app using an RGBA visual on top of your app, is your app still visible?

mcatanzaro	No?

ebassi	If you black out your contents, and then Super+tab around, the app may need to redraw, which may take a while
So it's still not going to look super nice

Company	mcatanzaro: but if I make the app only partially opaque and your app still shines through, it's visible?

mcatanzaro	Yes

Company	mcatanzaro: do i need to track that per pixel? is 1 transparent pixel shining through enough?

mcatanzaro	Company: I would say yes, that is visible
Again, might be dumb...

Company	that means my compositor has to download each frame from my app, inspect every pixel and if one of them is not opaque, it sends an event to your app?
that seems a tiny bit slow?
luckily, the relevant pixel is often the top left one, because we all use rounded corners for our decorations and they shine through!
what i'm trying to say is: this concept makes no sense in practice

Company	it sounds like a really useful thing in theory, but with our focus on translucency and rounded corners and shadows and whatnot it's pretty much impossible to define or implement meaningfully and fast
Comment 4 Michael Catanzaro 2018-06-17 11:00:10 PDT
I also tested Chromium (another obsolete XWayland client). It had the same behavior as Firefox under XWayland. In short, I haven't found any browser that is able to detect workspace changes.

We could do better than other browsers under X11 using libwnck to detect if the window is visible on the current workspace, but that doesn't seem useful since it won't work for Wayland.
Comment 5 Daniel 2018-06-17 17:39:15 PDT
Some usage details: 80 000 of the top 1 million websites (Alexa rank) use visibilityState for "something". Some random sampling of the two first pages shows [adult] video sites use it to not auto-play videos until the document is visible.
https://publicwww.com/websites/visibilityState/
Comment 6 Michael Catanzaro 2018-06-18 05:59:33 PDT
It still works just fine if the current tab is not visible in the application. My point is that it's impossible for any Wayland application to know whether its window is visible on the user's monitor, so you just can't expect WebKit to handle that.

If this functionality were added to xdg-shell and GTK+, then we could make use of it, but those developers are rarely interested in the needs of web browsers, and they raised a number of questions about how it would work.