Skip to content

[Bug]: document.visibilityState broken in window opened from <webview> with nativeWindowOpen #31959

@miniak

Description

@miniak

Preflight Checklist

Electron Version

16.0.1

What operating system are you using?

macOS

Operating System Version

macOS Catalina 10.15.7

What arch are you using?

x64

Last Known Working Electron version

N/A

Expected Behavior

I open a scriptable popup window from a webview, which has nativeWindowOpen enabled (explicitly or via sandbox). I expect document.visibilityState to work correctly.

Actual Behavior

document.visibilityState always returns visible even when the window is occluded or minimized.

Testcase Gist URL

No response

Additional Information

window-open-document-visibility.zip

The problem is that the window is incorrectly identified as being a webview, which has customized document.visibilityState handling:

if (isWebView) {
// Webview `document.visibilityState` tracks window visibility (and ignores
// the actual <webview> element visibility) for backwards compatibility.
// See discussion in #9178.
//
// Note that this results in duplicate visibilitychange events (since
// Chromium also fires them) and potentially incorrect visibility change.
// We should reconsider this decision for Electron 2.0.
let cachedVisibilityState = isHiddenPage ? 'hidden' : 'visible';
// Subscribe to visibilityState changes.
ipcRendererInternal.on(IPC_MESSAGES.GUEST_INSTANCE_VISIBILITY_CHANGE, function (_event, visibilityState: VisibilityState) {
if (cachedVisibilityState !== visibilityState) {
cachedVisibilityState = visibilityState;
document.dispatchEvent(new Event('visibilitychange'));
}
});
// Make document.hidden and document.visibilityState return the correct value.
const getDocumentHidden = () => cachedVisibilityState !== 'visible';
Object.defineProperty(document, 'hidden', {
get: getDocumentHidden
});
if (contextIsolationEnabled) internalContextBridge.overrideGlobalPropertyFromIsolatedWorld(['document', 'hidden'], getDocumentHidden);
const getDocumentVisibilityState = () => cachedVisibilityState;
Object.defineProperty(document, 'visibilityState', {
get: getDocumentVisibilityState
});
if (contextIsolationEnabled) internalContextBridge.overrideGlobalPropertyFromIsolatedWorld(['document', 'visibilityState'], getDocumentVisibilityState);
}
};

I think the root cause is the same as in #31949.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions