1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
|
Services.scriptloader.loadSubScript(
"chrome://mochitests/content/browser/gfx/layers/apz/test/mochitest/apz_test_native_event_utils.js",
this
);
Services.scriptloader.loadSubScript(
"chrome://mochitests/content/browser/browser/base/content/test/forms/head.js",
this
);
const PAGECONTENT_TRANSLATED =
"<html><body>" +
"<div id='div'>" +
"<iframe id='frame' width='320' height='295' style='margin: 100px;'" +
" src='https://example.com/document-builder.sjs?html=<html><select id=select><option>he he he</option><option>boo boo</option><option>baz baz</option></select></html>'" +
"</iframe>" +
"</div></body></html>";
function openSelectPopup(x, y, win) {
const popupShownPromise = BrowserTestUtils.waitForSelectPopupShown(win);
EventUtils.synthesizeNativeMouseEvent({
type: "click",
target: win.document.documentElement,
screenX: x,
screenY: y,
});
return popupShownPromise;
}
add_task(async function () {
const pageUrl = "data:text/html," + escape(PAGECONTENT_TRANSLATED);
const newWin = await BrowserTestUtils.openNewBrowserWindow({ fission: true });
const browserLoadedPromise = BrowserTestUtils.browserLoaded(
newWin.gBrowser.selectedBrowser,
true /* includeSubFrames */
);
BrowserTestUtils.startLoadingURIString(
newWin.gBrowser.selectedBrowser,
pageUrl
);
await browserLoadedPromise;
newWin.gBrowser.selectedBrowser.focus();
const tab = newWin.gBrowser.selectedTab;
// We need to explicitly call Element.focus() since dataURL is treated as
// cross-origin, thus autofocus doesn't work there.
const iframeBC = await SpecialPowers.spawn(tab.linkedBrowser, [], () => {
return content.document.querySelector("iframe").browsingContext;
});
const [iframeBorderLeft, iframeBorderTop, iframeX, iframeY] =
await SpecialPowers.spawn(tab.linkedBrowser, [], async function () {
await SpecialPowers.contentTransformsReceived(content);
const iframe = content.document.querySelector("iframe");
const rect = iframe.getBoundingClientRect();
const x = content.window.mozInnerScreenX + rect.left;
const y = content.window.mozInnerScreenY + rect.top;
const cs = content.window.getComputedStyle(iframe);
return [parseInt(cs.borderLeftWidth), parseInt(cs.borderTopWidth), x, y];
});
const selectRect = await SpecialPowers.spawn(iframeBC, [], async function () {
await SpecialPowers.contentTransformsReceived(content);
const input = content.document.getElementById("select");
const focusPromise = new Promise(resolve => {
input.addEventListener("focus", resolve, { once: true });
});
input.focus();
await focusPromise;
return input.getBoundingClientRect();
});
// Open the select popup.
const selectPopup = await openSelectPopup(
iframeX + selectRect.x + selectRect.width / 2,
iframeY + selectRect.y + selectRect.height / 2,
newWin
);
// Check the coordinates of 'selectPopup'.
let popupRect = selectPopup.getBoundingClientRect();
is(
popupRect.x,
iframeX +
iframeBorderLeft +
selectRect.x -
newWin.mozInnerScreenX +
parseFloat(getComputedStyle(selectPopup).marginLeft),
"x position of the popup"
);
let expectedYPosition =
iframeY +
selectRect.y +
iframeBorderTop -
newWin.mozInnerScreenY +
parseFloat(getComputedStyle(selectPopup).marginTop);
// On platforms other than macOS the popup menu is positioned below the
// option element. On macOS the top is aligned to the selected item (so the
// first label).
if (navigator.platform.includes("Mac")) {
const offsetToSelectedItem =
selectPopup.querySelector("menuitem[selected]").getBoundingClientRect()
.top - popupRect.top;
expectedYPosition -= offsetToSelectedItem;
} else {
expectedYPosition += selectRect.height;
}
isfuzzy(
popupRect.y,
expectedYPosition,
window.devicePixelRatio,
"y position of the popup"
);
await hideSelectPopup("enter", newWin);
await BrowserTestUtils.closeWindow(newWin);
});
|