--- a/dom/base/nsGlobalWindowOuter.cpp
+++ b/dom/base/nsGlobalWindowOuter.cpp
@@ -3243,52 +3243,65 @@ void nsGlobalWindowOuter::GetNameOuter(n
void nsGlobalWindowOuter::SetNameOuter(const nsAString& aName,
mozilla::ErrorResult& aError) {
if (mDocShell) {
aError = mDocShell->SetName(aName);
}
}
// Helper functions used by many methods below.
-int32_t nsGlobalWindowOuter::DevToCSSIntPixels(int32_t px) {
- if (!mDocShell) return px; // assume 1:1
-
- RefPtr<nsPresContext> presContext = mDocShell->GetPresContext();
- if (!presContext) return px;
-
- return presContext->DevPixelsToIntCSSPixels(px);
-}
-
-int32_t nsGlobalWindowOuter::CSSToDevIntPixels(int32_t px) {
- if (!mDocShell) return px; // assume 1:1
-
- RefPtr<nsPresContext> presContext = mDocShell->GetPresContext();
- if (!presContext) return px;
-
- return presContext->CSSPixelsToDevPixels(px);
-}
-
-nsIntSize nsGlobalWindowOuter::DevToCSSIntPixels(nsIntSize px) {
- if (!mDocShell) return px; // assume 1:1
-
- RefPtr<nsPresContext> presContext = mDocShell->GetPresContext();
- if (!presContext) return px;
-
- return nsIntSize(presContext->DevPixelsToIntCSSPixels(px.width),
- presContext->DevPixelsToIntCSSPixels(px.height));
-}
-
-nsIntSize nsGlobalWindowOuter::CSSToDevIntPixels(nsIntSize px) {
- if (!mDocShell) return px; // assume 1:1
-
- RefPtr<nsPresContext> presContext = mDocShell->GetPresContext();
- if (!presContext) return px;
-
- return nsIntSize(presContext->CSSPixelsToDevPixels(px.width),
- presContext->CSSPixelsToDevPixels(px.height));
+int32_t nsGlobalWindowOuter::DevToCSSIntPixelsForBaseWindow(
+ int32_t aDevicePixels, nsIBaseWindow* aWindow) {
+ MOZ_ASSERT(aWindow);
+ double scale;
+ aWindow->GetUnscaledDevicePixelsPerCSSPixel(&scale);
+ double zoom = 1.0;
+ if (mDocShell && mDocShell->GetPresContext()) {
+ zoom = mDocShell->GetPresContext()->GetFullZoom();
+ }
+ return std::floor(aDevicePixels / scale / zoom + 0.5);
+}
+
+nsIntSize nsGlobalWindowOuter::DevToCSSIntPixelsForBaseWindow(
+ nsIntSize aDeviceSize, nsIBaseWindow* aWindow) {
+ MOZ_ASSERT(aWindow);
+ double scale;
+ aWindow->GetUnscaledDevicePixelsPerCSSPixel(&scale);
+ double zoom = 1.0;
+ if (mDocShell && mDocShell->GetPresContext()) {
+ zoom = mDocShell->GetPresContext()->GetFullZoom();
+ }
+ return nsIntSize::Round(
+ static_cast<float>(aDeviceSize.width / scale / zoom),
+ static_cast<float>(aDeviceSize.height / scale / zoom));
+}
+
+int32_t nsGlobalWindowOuter::CSSToDevIntPixelsForBaseWindow(
+ int32_t aCSSPixels, nsIBaseWindow* aWindow) {
+ MOZ_ASSERT(aWindow);
+ double scale;
+ aWindow->GetUnscaledDevicePixelsPerCSSPixel(&scale);
+ double zoom = 1.0;
+ if (mDocShell && mDocShell->GetPresContext()) {
+ zoom = mDocShell->GetPresContext()->GetFullZoom();
+ }
+ return std::floor(aCSSPixels * scale * zoom + 0.5);
+}
+
+nsIntSize nsGlobalWindowOuter::CSSToDevIntPixelsForBaseWindow(
+ nsIntSize aCSSSize, nsIBaseWindow* aWindow) {
+ MOZ_ASSERT(aWindow);
+ double scale;
+ aWindow->GetUnscaledDevicePixelsPerCSSPixel(&scale);
+ double zoom = 1.0;
+ if (mDocShell && mDocShell->GetPresContext()) {
+ zoom = mDocShell->GetPresContext()->GetFullZoom();
+ }
+ return nsIntSize::Round(static_cast<float>(aCSSSize.width * scale * zoom),
+ static_cast<float>(aCSSSize.height * scale * zoom));
}
nsresult nsGlobalWindowOuter::GetInnerSize(CSSIntSize& aSize) {
EnsureSizeAndPositionUpToDate();
NS_ENSURE_STATE(mDocShell);
RefPtr<nsPresContext> presContext = mDocShell->GetPresContext();
@@ -3355,17 +3368,18 @@ void nsGlobalWindowOuter::SetInnerWidthO
}
// Nothing has been overriden, so change the docshell itself.
int32_t height = 0;
int32_t unused = 0;
nsCOMPtr<nsIBaseWindow> docShellAsWin(do_QueryInterface(mDocShell));
docShellAsWin->GetSize(&unused, &height);
- aError = SetDocShellWidthAndHeight(CSSToDevIntPixels(aInnerWidth), height);
+ aError = SetDocShellWidthAndHeight(
+ CSSToDevIntPixelsForBaseWindow(aInnerWidth, docShellAsWin), height);
}
int32_t nsGlobalWindowOuter::GetInnerHeightOuter(ErrorResult& aError) {
CSSIntSize size;
aError = GetInnerSize(size);
return size.height;
}
@@ -3400,17 +3414,18 @@ void nsGlobalWindowOuter::SetInnerHeight
}
// Nothing has been overriden, so change the docshell itself.
int32_t height = 0;
int32_t width = 0;
nsCOMPtr<nsIBaseWindow> docShellAsWin(do_QueryInterface(mDocShell));
docShellAsWin->GetSize(&width, &height);
- aError = SetDocShellWidthAndHeight(width, CSSToDevIntPixels(aInnerHeight));
+ aError = SetDocShellWidthAndHeight(
+ width, CSSToDevIntPixelsForBaseWindow(aInnerHeight, docShellAsWin));
}
nsIntSize nsGlobalWindowOuter::GetOuterSize(CallerType aCallerType,
ErrorResult& aError) {
if (nsContentUtils::ResistFingerprinting(aCallerType)) {
CSSIntSize size;
aError = GetInnerSize(size);
return nsIntSize(size.width, size.height);
@@ -3433,17 +3448,17 @@ nsIntSize nsGlobalWindowOuter::GetOuterS
}
nsIntSize sizeDevPixels;
aError = treeOwnerAsWin->GetSize(&sizeDevPixels.width, &sizeDevPixels.height);
if (aError.Failed()) {
return nsIntSize();
}
- return DevToCSSIntPixels(sizeDevPixels);
+ return DevToCSSIntPixelsForBaseWindow(sizeDevPixels, treeOwnerAsWin);
}
int32_t nsGlobalWindowOuter::GetOuterWidthOuter(CallerType aCallerType,
ErrorResult& aError) {
return GetOuterSize(aCallerType, aError).width;
}
int32_t nsGlobalWindowOuter::GetOuterHeightOuter(CallerType aCallerType,
@@ -3465,17 +3480,18 @@ void nsGlobalWindowOuter::SetOuterSize(i
aCallerType);
int32_t width, height;
aError = treeOwnerAsWin->GetSize(&width, &height);
if (aError.Failed()) {
return;
}
- int32_t lengthDevPixels = CSSToDevIntPixels(aLengthCSSPixels);
+ int32_t lengthDevPixels =
+ CSSToDevIntPixelsForBaseWindow(aLengthCSSPixels, treeOwnerAsWin);
if (aIsWidth) {
width = lengthDevPixels;
} else {
height = lengthDevPixels;
}
aError = treeOwnerAsWin->SetSize(width, height, true);
CheckForDPIChange();
@@ -3690,17 +3706,17 @@ void nsGlobalWindowOuter::SetScreenXOute
int32_t x, y;
aError = treeOwnerAsWin->GetPosition(&x, &y);
if (aError.Failed()) {
return;
}
CheckSecurityLeftAndTop(&aScreenX, nullptr, aCallerType);
- x = CSSToDevIntPixels(aScreenX);
+ x = CSSToDevIntPixelsForBaseWindow(aScreenX, treeOwnerAsWin);
aError = treeOwnerAsWin->SetPosition(x, y);
CheckForDPIChange();
}
int32_t nsGlobalWindowOuter::GetScreenYOuter(CallerType aCallerType,
ErrorResult& aError) {
@@ -3718,17 +3734,17 @@ void nsGlobalWindowOuter::SetScreenYOute
int32_t x, y;
aError = treeOwnerAsWin->GetPosition(&x, &y);
if (aError.Failed()) {
return;
}
CheckSecurityLeftAndTop(nullptr, &aScreenY, aCallerType);
- y = CSSToDevIntPixels(aScreenY);
+ y = CSSToDevIntPixelsForBaseWindow(aScreenY, treeOwnerAsWin);
aError = treeOwnerAsWin->SetPosition(x, y);
CheckForDPIChange();
}
// NOTE: Arguments to this function should have values scaled to
// CSS pixels, not device pixels.
@@ -3805,32 +3821,33 @@ void nsGlobalWindowOuter::CheckSecurityL
nsContentUtils::HidePopupsInDocument(mDoc);
#endif
if (nsGlobalWindowOuter* rootWindow =
nsGlobalWindowOuter::Cast(GetPrivateRoot())) {
rootWindow->FlushPendingNotifications(FlushType::Layout);
}
- nsCOMPtr<nsIBaseWindow> treeOwner = GetTreeOwnerWindow();
+ nsCOMPtr<nsIBaseWindow> treeOwnerAsWin = GetTreeOwnerWindow();
RefPtr<nsScreen> screen = GetScreen();
- if (treeOwner && screen) {
+ if (treeOwnerAsWin && screen) {
int32_t winLeft, winTop, winWidth, winHeight;
// Get the window size
- treeOwner->GetPositionAndSize(&winLeft, &winTop, &winWidth, &winHeight);
+ treeOwnerAsWin->GetPositionAndSize(&winLeft, &winTop, &winWidth,
+ &winHeight);
// convert those values to CSS pixels
// XXX four separate retrievals of the prescontext
- winLeft = DevToCSSIntPixels(winLeft);
- winTop = DevToCSSIntPixels(winTop);
- winWidth = DevToCSSIntPixels(winWidth);
- winHeight = DevToCSSIntPixels(winHeight);
+ winLeft = DevToCSSIntPixelsForBaseWindow(winLeft, treeOwnerAsWin);
+ winTop = DevToCSSIntPixelsForBaseWindow(winTop, treeOwnerAsWin);
+ winWidth = DevToCSSIntPixelsForBaseWindow(winWidth, treeOwnerAsWin);
+ winHeight = DevToCSSIntPixelsForBaseWindow(winHeight, treeOwnerAsWin);
// Get the screen dimensions
// XXX This should use nsIScreenManager once it's fully fleshed out.
int32_t screenLeft = screen->GetAvailLeft(IgnoreErrors());
int32_t screenWidth = screen->GetAvailWidth(IgnoreErrors());
int32_t screenHeight = screen->GetAvailHeight(IgnoreErrors());
#if defined(XP_MACOSX)
/* The mac's coordinate system is different from the assumed Windows'
@@ -5097,24 +5114,25 @@ void nsGlobalWindowOuter::MoveByOuter(in
int32_t x, y;
aError = treeOwnerAsWin->GetPosition(&x, &y);
if (aError.Failed()) {
return;
}
// mild abuse of a "size" object so we don't need more helper functions
- nsIntSize cssPos(DevToCSSIntPixels(nsIntSize(x, y)));
+ nsIntSize cssPos(
+ DevToCSSIntPixelsForBaseWindow(nsIntSize(x, y), treeOwnerAsWin));
cssPos.width += aXDif;
cssPos.height += aYDif;
CheckSecurityLeftAndTop(&cssPos.width, &cssPos.height, aCallerType);
- nsIntSize newDevPos(CSSToDevIntPixels(cssPos));
+ nsIntSize newDevPos(CSSToDevIntPixelsForBaseWindow(cssPos, treeOwnerAsWin));
aError = treeOwnerAsWin->SetPosition(newDevPos.width, newDevPos.height);
CheckForDPIChange();
}
nsresult nsGlobalWindowOuter::MoveBy(int32_t aXDif, int32_t aYDif) {
ErrorResult rv;
@@ -5152,17 +5170,17 @@ void nsGlobalWindowOuter::ResizeToOuter(
if (!treeOwnerAsWin) {
aError.Throw(NS_ERROR_FAILURE);
return;
}
nsIntSize cssSize(aWidth, aHeight);
CheckSecurityWidthAndHeight(&cssSize.width, &cssSize.height, aCallerType);
- nsIntSize devSz(CSSToDevIntPixels(cssSize));
+ nsIntSize devSz(CSSToDevIntPixelsForBaseWindow(cssSize, treeOwnerAsWin));
aError = treeOwnerAsWin->SetSize(devSz.width, devSz.height, true);
CheckForDPIChange();
}
void nsGlobalWindowOuter::ResizeByOuter(int32_t aWidthDif, int32_t aHeightDif,
CallerType aCallerType,
@@ -5207,24 +5225,25 @@ void nsGlobalWindowOuter::ResizeByOuter(
if (aError.Failed()) {
return;
}
// To do this correctly we have to convert what we got from GetSize
// into CSS pixels, add the arguments, do the security check, and
// then convert back to device pixels for the call to SetSize.
- nsIntSize cssSize(DevToCSSIntPixels(nsIntSize(width, height)));
+ nsIntSize cssSize(
+ DevToCSSIntPixelsForBaseWindow(nsIntSize(width, height), treeOwnerAsWin));
cssSize.width += aWidthDif;
cssSize.height += aHeightDif;
CheckSecurityWidthAndHeight(&cssSize.width, &cssSize.height, aCallerType);
- nsIntSize newDevSize(CSSToDevIntPixels(cssSize));
+ nsIntSize newDevSize(CSSToDevIntPixelsForBaseWindow(cssSize, treeOwnerAsWin));
aError = treeOwnerAsWin->SetSize(newDevSize.width, newDevSize.height, true);
CheckForDPIChange();
}
void nsGlobalWindowOuter::SizeToContentOuter(CallerType aCallerType,
ErrorResult& aError) {
@@ -5245,34 +5264,45 @@ void nsGlobalWindowOuter::SizeToContentO
// viewer for a toplevel docshell.
nsCOMPtr<nsIContentViewer> cv;
mDocShell->GetContentViewer(getter_AddRefs(cv));
if (!cv) {
aError.Throw(NS_ERROR_FAILURE);
return;
}
- int32_t width, height;
- aError = cv->GetContentSize(&width, &height);
+ nsIntSize contentSize;
+ aError = cv->GetContentSize(&contentSize.width, &contentSize.height);
if (aError.Failed()) {
return;
}
// Make sure the new size is following the CheckSecurityWidthAndHeight
// rules.
nsCOMPtr<nsIDocShellTreeOwner> treeOwner = GetTreeOwner();
if (!treeOwner) {
aError.Throw(NS_ERROR_FAILURE);
return;
}
- nsIntSize cssSize(DevToCSSIntPixels(nsIntSize(width, height)));
+ // Don't use DevToCSSIntPixelsForBaseWindow() nor
+ // CSSToDevIntPixelsForBaseWindow() here because contentSize is comes from
+ // nsIContentViewer::GetContentSize() and it's computed with nsPresContext so
+ // that we need to work with nsPresContext here too.
+ RefPtr<nsPresContext> presContext = cv->GetPresContext();
+ MOZ_ASSERT(
+ presContext,
+ "Should be non-nullptr if nsIContentViewer::GetContentSize() succeeded");
+ nsIntSize cssSize(presContext->DevPixelsToIntCSSPixels(contentSize.width),
+ presContext->DevPixelsToIntCSSPixels(contentSize.height));
+
CheckSecurityWidthAndHeight(&cssSize.width, &cssSize.height, aCallerType);
- nsIntSize newDevSize(CSSToDevIntPixels(cssSize));
+ nsIntSize newDevSize(presContext->CSSPixelsToDevPixels(cssSize.width),
+ presContext->CSSPixelsToDevPixels(cssSize.height));
nsCOMPtr<nsIDocShell> docShell = mDocShell;
aError =
treeOwner->SizeShellTo(docShell, newDevSize.width, newDevSize.height);
}
already_AddRefed<nsPIWindowRoot> nsGlobalWindowOuter::GetTopWindowRoot() {
nsPIDOMWindowOuter* piWin = GetPrivateRoot();