Skip to content

Commit

Permalink
Change behavior of window.open w.r.t. windowPreferences and popups
Browse files Browse the repository at this point in the history
See [1] for more context, but this CL implements new behavior for
how window.open() interprets the windowPreferences argument when
deciding whether to open the window as a new tab or as a "popup",
which is a separate window with minimal UI (toolbars, onmibox,
etc.).

Before this CL, a popup will be opened instead of tab if:
 1. the windowFeatures parameter is *not* empty, and
 2. one of the following conditions is true:
  * both `location` and `toolbar` are false or missing
  * `menubar` is false or missing
  * `resizable is false or missing
  * `scrollbar` is false or missing
  * `status` is false or missing

After this CL, a popup will be opened if:
 1. the windowFeatures parameter contains a `width` parameter

[1] whatwg/html#5872

Fixed: 1192701
Change-Id: I50e745b1000d460c49085edd57d13f420b875ff3
  • Loading branch information
mfreed7 authored and chromium-wpt-export-bot committed Jun 15, 2021
1 parent b3d034d commit cecc883
Show file tree
Hide file tree
Showing 2 changed files with 73 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<!DOCTYPE html>
<script>
var channelName = window.name;
var channel = new BroadcastChannel(channelName);
const allBarProps = [
window.locationbar.visible,
window.menubar.visible,
window.personalbar.visible,
window.scrollbars.visible,
window.statusbar.visible,
window.toolbar.visible
];
const allTrue = allBarProps.every(x=>x);
const allFalse = allBarProps.every(x=>!x);
channel.postMessage({isPopup: allFalse, mixedState: !allTrue && !allFalse});

// Because messages are not delivered synchronously and because closing a
// browsing context prompts the eventual clearing of all task sources, this
// document should not be closed until the opener document has confirmed
// receipt.
channel.onmessage = function() {
window.close();
};
</script>
49 changes: 49 additions & 0 deletions html/browsers/the-window-object/window-open-popup-behavior.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
<!DOCTYPE html>
<meta charset=utf-8>
<meta name="timeout" content="long">
<title>Window.open popup behavior</title>
<link rel="author" href="[email protected]">
<link rel="help" href="https://html.spec.whatwg.org/multipage/window-object.html#window-open-steps">
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>

<script>
function testOne(windowFeatures, expectPopup) {
const windowName = Math.round(Math.random()*1e12);
const channel = new BroadcastChannel(windowName);
var w;
promise_test(() => {
return new Promise(resolve => {
w = window.open("support/window-open-popup-target.html", windowName, windowFeatures);
channel.addEventListener('message', resolve);
}).then(e => {
// Send message first so if asserts throw the popup is still closed
channel.postMessage(null);
assert_false(e.data.mixedState, "No mixed state");
assert_equals(e.data.isPopup, expectPopup, "Popup state");
});
},`${windowFeatures} (expect ${expectPopup ? "popup" : "tab"})`);
}

// No windowpreferences at all - tab.
testOne(undefined, /*expectPopup=*/false);

// Test all permutations of these properties:
const features = ["noopener","noreferrer","toolbar","location","menubar","resizable","scrollbars","status"];
const nProps = features.length;
const skip = 7; // To speed up the test, don't test all values. Skip 7 to pseudo-randomize.
for(let i=0;i<2**nProps;i+=skip) {
const enableVec = Number(i).toString(2).padStart(nProps,'0').split('').map(s => (s==="1"));
let windowFeatures = [];
for(let i=0;i<nProps;++i) {
if (enableVec[i])
windowFeatures.push(features[i] + "=yes");
}
windowFeatures = windowFeatures.join(',');
// Either noopener or noreferrer will force a new tab.
const allowPopup = !enableVec[0] && !enableVec[1];
// Width should be the only property that influences popup vs. tab.
testOne(windowFeatures, /*expectPopup=*/false); // No "width" feature = no popup
testOne(windowFeatures + ",width=123", /*expectPopup=*/allowPopup); // "width" feature = popup
}
</script>

0 comments on commit cecc883

Please sign in to comment.