Bug 1406217 - Fix computation of scrollframe's offset to the reference frame. r?mstange
We need to get the offset across documents boundaries, since the scrollframe
might be inside a subdocument. In such cases we were previously computing
a (incorrect) zero offset for the scrollframe, which was throwing off the
margin for the sticky items inside the scrollframe.
MozReview-Commit-ID: AWeQ9ay2cmp
--- a/layout/painting/nsDisplayList.cpp
+++ b/layout/painting/nsDisplayList.cpp
@@ -7330,17 +7330,17 @@ nsDisplayStickyPosition::CreateWebRender
Maybe<wr::StickySideConstraint> bottom;
Maybe<wr::StickySideConstraint> left;
nsRect outer;
nsRect inner;
stickyScrollContainer->GetScrollRanges(mFrame, &outer, &inner);
nsIFrame* scrollFrame = do_QueryFrame(stickyScrollContainer->ScrollFrame());
- nsPoint offset = scrollFrame->GetOffsetTo(ReferenceFrame());
+ nsPoint offset = scrollFrame->GetOffsetToCrossDoc(ReferenceFrame());
// Adjust the scrollPort coordinates to be relative to the reference frame,
// so that it is in the same space as everything else.
nsRect scrollPort = stickyScrollContainer->ScrollFrame()->GetScrollPortRect();
scrollPort += offset;
// The following computations make more sense upon understanding the
// semantics of "inner" and "outer", which is explained in the comment on
new file mode 100644
--- /dev/null
+++ b/layout/reftests/position-sticky/iframe-1-helper.html
@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html>
+ <head>
+ <style>
+ html, body {
+ margin: 0;
+ padding: 0;
+ }
+ </style>
+ </head>
+ <body>
+ <div style="overflow: auto; width: 150px; height: 200px">
+ <div style="position: sticky; top: 0; width: 100px; height: 100px; background-color: green"></div>
+ <div style="height: 300px; width: 100px"></div>
+ </div>
+ </body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/position-sticky/iframe-1-ref.html
@@ -0,0 +1,20 @@
+<!DOCTYPE html>
+<html>
+ <head>
+ <title>Sticky-positioned item inside a scrollframe inside an iframe</title>
+ <style>
+ html, body {
+ margin: 0;
+ padding: 0;
+ }
+ </style>
+ </head>
+ <body>
+ <div style="overflow: auto; margin-top: 100px; width: 150px; height: 200px">
+ <div style="width: 100px; height: 100px; background-color: green"></div>
+ <div style="height: 300px; width: 100px"></div>
+ </div>
+ </body>
+</html>
+ </body>
+</html>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/position-sticky/iframe-1.html
@@ -0,0 +1,15 @@
+<!DOCTYPE html>
+<html>
+ <head>
+ <title>Sticky-positioned item inside a scrollframe inside an iframe</title>
+ <style>
+ html, body {
+ margin: 0;
+ padding: 0;
+ }
+ </style>
+ </head>
+ <body>
+ <iframe src="iframe-1-helper.html" style="margin-top: 100px; border: none; height: 300px"></iframe>
+ </body>
+</html>
--- a/layout/reftests/position-sticky/reftest.list
+++ b/layout/reftests/position-sticky/reftest.list
@@ -44,8 +44,9 @@ skip-if(!asyncPan) == inline-4.html inli
fails == column-contain-1a.html column-contain-1-ref.html
== column-contain-1b.html column-contain-1-ref.html
== column-contain-2.html column-contain-2-ref.html
== block-in-inline-1.html block-in-inline-1-ref.html
fuzzy-if(skiaContent,1,22) fuzzy-if(winWidget&&!layersGPUAccelerated,116,1320) fuzzy-if(Android,8,1533) == block-in-inline-2.html block-in-inline-2-ref.html
fuzzy-if(Android,8,630) fuzzy-if(OSX,1,11) fuzzy-if(skiaContent,1,220) fuzzy-if(winWidget&&!layersGPUAccelerated,116,1320) == block-in-inline-3.html block-in-inline-3-ref.html
== block-in-inline-continuations.html block-in-inline-continuations-ref.html
fuzzy-if(winWidget&&!layersGPUAccelerated,140,140) == inner-table-1.html inner-table-1-ref.html
+== iframe-1.html iframe-1-ref.html