2009-09-18 Simon Fraser <simon.fraser@apple.com>

        Reviewed by Dave Hyatt.

        Transformed elements inside position:fixed container are clipped incorrectly
        https://bugs.webkit.org/show_bug.cgi?id=29346

        Fix clipping and hit testing on transformed elements inside a position:fixed element.
        Previously, the code used the overflowClipRect of the parent clip rects, but
        this is not correct for fixed postion elements. Instead, share code that is
        already present in calculateRects() to get the correct rect.

        Test: fast/overflow/position-fixed-transform-clipping.html

        * rendering/RenderLayer.h:
        * rendering/RenderLayer.cpp:
        (WebCore::RenderLayer::paintLayer):
        (WebCore::RenderLayer::hitTestLayer):
        Call the new backgroundClipRect() to get the correct clipRect.

        (WebCore::RenderLayer::backgroundClipRect):
        New method, factored out of calculateRects(), that computes the clip rect,
        doing the right thing for fixed position elements.

        (WebCore::RenderLayer::calculateRects):
        Call the new backgroundClipRect() method.

git-svn-id: http://svn.webkit.org/repository/webkit/trunk@48524 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent 87a5f65c
2009-09-18 Simon Fraser <simon.fraser@apple.com>
Reviewed by Dave Hyatt.
Transformed elements inside position:fixed container are clipped incorrectly
https://bugs.webkit.org/show_bug.cgi?id=29346
Testcase for clipping a transformed element inside a position:fixed parent.
* fast/overflow/position-fixed-transform-clipping.html: Added.
* platform/mac/fast/overflow/position-fixed-transform-clipping-expected.checksum: Added.
* platform/mac/fast/overflow/position-fixed-transform-clipping-expected.png: Added.
* platform/mac/fast/overflow/position-fixed-transform-clipping-expected.txt: Added.
2009-09-18 Dan Bernstein <mitz@apple.com>
Updated test result for <rdar://problem/7050773>
......
<!DOCTYPE>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>Position fixed with transform clipping</title>
<style type="text/css" media="screen">
body {
height: 2000px;
margin: 0;
}
.container {
position: fixed;
width: 400px;
height: 50px;
border: 2px solid black;
overflow: hidden;
}
.box {
width: 100%;
height: 100%;
background-color: green;
-webkit-transform: translate(0, 0);
}
p {
position: absolute;
top: 100px;
}
</style>
<script type="text/javascript" charset="utf-8">
window.addEventListener('load', function() {
window.scrollBy(0, 25);
}, false);
</script>
</head>
<body>
<p><a href="https://bugs.webkit.org/show_bug.cgi?id=29346">https://bugs.webkit.org/show_bug.cgi?id=29346</a><br>
Green box should fill the black border.</p>
<div class="container">
<div class="box">
</div>
</div>
</body>
</html>
layer at (0,0) size 785x2000
RenderView at (0,0) size 785x600
layer at (0,0) size 785x2000
RenderBlock {HTML} at (0,0) size 785x2000
RenderBody {BODY} at (0,0) size 785x2000
layer at (0,116) size 305x36
RenderBlock (positioned) {P} at (0,116) size 305x36
RenderInline {A} at (0,0) size 305x18 [color=#0000EE]
RenderText {#text} at (0,0) size 305x18
text run at (0,0) width 305: "https://bugs.webkit.org/show_bug.cgi?id=29346"
RenderBR {BR} at (305,14) size 0x0
RenderText {#text} at (0,18) size 244x18
text run at (0,18) width 244: "Green box should fill the black border."
layer at (0,25) size 404x54 clip at (2,27) size 400x50
RenderBlock (positioned) {DIV} at (0,0) size 404x54 [border: (2px solid #000000)]
layer at (2,27) size 400x50
RenderBlock {DIV} at (2,2) size 400x50 [bgcolor=#008000]
scrolled to 0,25
2009-09-18 Simon Fraser <simon.fraser@apple.com>
Reviewed by Dave Hyatt.
Transformed elements inside position:fixed container are clipped incorrectly
https://bugs.webkit.org/show_bug.cgi?id=29346
Fix clipping and hit testing on transformed elements inside a position:fixed element.
Previously, the code used the overflowClipRect of the parent clip rects, but
this is not correct for fixed postion elements. Instead, share code that is
already present in calculateRects() to get the correct rect.
Test: fast/overflow/position-fixed-transform-clipping.html
* rendering/RenderLayer.h:
* rendering/RenderLayer.cpp:
(WebCore::RenderLayer::paintLayer):
(WebCore::RenderLayer::hitTestLayer):
Call the new backgroundClipRect() to get the correct clipRect.
(WebCore::RenderLayer::backgroundClipRect):
New method, factored out of calculateRects(), that computes the clip rect,
doing the right thing for fixed position elements.
(WebCore::RenderLayer::calculateRects):
Call the new backgroundClipRect() method.
2009-09-18 Dan Bernstein <mitz@apple.com>
Reviewed by Darin Adler.
......@@ -2127,9 +2127,7 @@ void RenderLayer::paintLayer(RenderLayer* rootLayer, GraphicsContext* p,
// Make sure the parent's clip rects have been calculated.
IntRect clipRect = paintDirtyRect;
if (parent()) {
ClipRects parentRects;
parentClipRects(rootLayer, parentRects, paintFlags & PaintLayerTemporaryClipRects);
clipRect = parentRects.overflowClipRect();
clipRect = backgroundClipRect(rootLayer, paintFlags & PaintLayerTemporaryClipRects);
clipRect.intersect(paintDirtyRect);
}
......@@ -2434,9 +2432,7 @@ RenderLayer* RenderLayer::hitTestLayer(RenderLayer* rootLayer, RenderLayer* cont
if (transform() && !appliedTransform) {
// Make sure the parent's clip rects have been calculated.
if (parent()) {
ClipRects parentRects;
parentClipRects(rootLayer, parentRects, useTemporaryClipRects);
IntRect clipRect = parentRects.overflowClipRect();
IntRect clipRect = backgroundClipRect(rootLayer, useTemporaryClipRects);
// Go ahead and test the enclosing clip now.
if (!clipRect.contains(hitTestPoint))
return 0;
......@@ -2734,10 +2730,10 @@ void RenderLayer::parentClipRects(const RenderLayer* rootLayer, ClipRects& clipR
clipRects = *parent()->clipRects();
}
void RenderLayer::calculateRects(const RenderLayer* rootLayer, const IntRect& paintDirtyRect, IntRect& layerBounds,
IntRect& backgroundRect, IntRect& foregroundRect, IntRect& outlineRect, bool temporaryClipRects) const
IntRect RenderLayer::backgroundClipRect(const RenderLayer* rootLayer, bool temporaryClipRects) const
{
if (rootLayer != this && parent()) {
IntRect backgroundRect;
if (parent()) {
ClipRects parentRects;
parentClipRects(rootLayer, parentRects, temporaryClipRects);
backgroundRect = renderer()->style()->position() == FixedPosition ? parentRects.fixedClipRect() :
......@@ -2747,7 +2743,15 @@ void RenderLayer::calculateRects(const RenderLayer* rootLayer, const IntRect& pa
ASSERT(view);
if (view && parentRects.fixed() && rootLayer->renderer() == view)
backgroundRect.move(view->frameView()->scrollX(), view->frameView()->scrollY());
}
return backgroundRect;
}
void RenderLayer::calculateRects(const RenderLayer* rootLayer, const IntRect& paintDirtyRect, IntRect& layerBounds,
IntRect& backgroundRect, IntRect& foregroundRect, IntRect& outlineRect, bool temporaryClipRects) const
{
if (rootLayer != this && parent()) {
backgroundRect = backgroundClipRect(rootLayer, temporaryClipRects);
backgroundRect.intersect(paintDirtyRect);
} else
backgroundRect = paintDirtyRect;
......
......@@ -516,6 +516,7 @@ private:
void setPaintingInsideReflection(bool b) { m_paintingInsideReflection = b; }
void parentClipRects(const RenderLayer* rootLayer, ClipRects&, bool temporaryClipRects = false) const;
IntRect backgroundClipRect(const RenderLayer* rootLayer, bool temporaryClipRects) const;
RenderLayer* enclosingTransformedAncestor() const;
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment