Diff
Modified: trunk/LayoutTests/ChangeLog (160769 => 160770)
--- trunk/LayoutTests/ChangeLog 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/LayoutTests/ChangeLog 2013-12-18 17:27:58 UTC (rev 160770)
@@ -1,3 +1,19 @@
+2013-12-18 Rob Buis <[email protected]>
+
+ [CSS Shapes] Implement interpolation between keywords in basic shapes
+ https://bugs.webkit.org/show_bug.cgi?id=125108
+
+ Reviewed by Simon Fraser.
+
+ Add tests to shape-outside-animation when animating using keywords for the circle/ellipse center positions.
+ Also add tests for invalid mixing of keyword and values in the center coordinate to parsing-test-utils.js.
+
+ * fast/shapes/parsing/parsing-shape-inside-expected.txt:
+ * fast/shapes/parsing/parsing-shape-outside-expected.txt:
+ * fast/shapes/parsing/parsing-test-utils.js:
+ * fast/shapes/shape-outside-floats/shape-outside-animation-expected.txt:
+ * fast/shapes/shape-outside-floats/shape-outside-animation.html:
+
2013-12-18 Dániel Bátyai <[email protected]>
CSS: Null-pointer dereference with negative 'orphans' value.
Modified: trunk/LayoutTests/fast/shapes/parsing/parsing-shape-inside-expected.txt (160769 => 160770)
--- trunk/LayoutTests/fast/shapes/parsing/parsing-shape-inside-expected.txt 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/LayoutTests/fast/shapes/parsing/parsing-shape-inside-expected.txt 2013-12-18 17:27:58 UTC (rev 160770)
@@ -191,6 +191,8 @@
PASS getComputedStyleValue("-webkit-shape-inside", "circle(10px at 10px 10px at center)") is "auto"
PASS getCSSText("-webkit-shape-inside", "circle(10px at center center 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-inside", "circle(10px at center center 10px)") is "auto"
+PASS getCSSText("-webkit-shape-inside", "circle(10px at 10% left)") is ""
+PASS getComputedStyleValue("-webkit-shape-inside", "circle(10px at 10% left)") is "auto"
PASS getCSSText("-webkit-shape-inside", "circle(at 10px 10px 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-inside", "circle(at 10px 10px 10px)") is "auto"
PASS getCSSText("-webkit-shape-inside", "circle(at 10px 10px at center)") is ""
@@ -211,6 +213,8 @@
PASS getComputedStyleValue("-webkit-shape-inside", "ellipse(10px at 10px 10px at center)") is "auto"
PASS getCSSText("-webkit-shape-inside", "ellipse(10px at center center 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-inside", "ellipse(10px at center center 10px)") is "auto"
+PASS getCSSText("-webkit-shape-inside", "ellipse(10px 10px at 10% left)") is ""
+PASS getComputedStyleValue("-webkit-shape-inside", "ellipse(10px 10px at 10% left)") is "auto"
PASS getCSSText("-webkit-shape-inside", "ellipse(10px 20px 30px at center center 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-inside", "ellipse(10px 20px 30px at center center 10px)") is "auto"
PASS getCSSText("-webkit-shape-inside", "ellipse(at 10px 10px 10px)") is ""
Modified: trunk/LayoutTests/fast/shapes/parsing/parsing-shape-outside-expected.txt (160769 => 160770)
--- trunk/LayoutTests/fast/shapes/parsing/parsing-shape-outside-expected.txt 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/LayoutTests/fast/shapes/parsing/parsing-shape-outside-expected.txt 2013-12-18 17:27:58 UTC (rev 160770)
@@ -189,6 +189,8 @@
PASS getComputedStyleValue("-webkit-shape-outside", "circle(10px at 10px 10px at center)") is "auto"
PASS getCSSText("-webkit-shape-outside", "circle(10px at center center 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-outside", "circle(10px at center center 10px)") is "auto"
+PASS getCSSText("-webkit-shape-outside", "circle(10px at 10% left)") is ""
+PASS getComputedStyleValue("-webkit-shape-outside", "circle(10px at 10% left)") is "auto"
PASS getCSSText("-webkit-shape-outside", "circle(at 10px 10px 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-outside", "circle(at 10px 10px 10px)") is "auto"
PASS getCSSText("-webkit-shape-outside", "circle(at 10px 10px at center)") is ""
@@ -209,6 +211,8 @@
PASS getComputedStyleValue("-webkit-shape-outside", "ellipse(10px at 10px 10px at center)") is "auto"
PASS getCSSText("-webkit-shape-outside", "ellipse(10px at center center 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-outside", "ellipse(10px at center center 10px)") is "auto"
+PASS getCSSText("-webkit-shape-outside", "ellipse(10px 10px at 10% left)") is ""
+PASS getComputedStyleValue("-webkit-shape-outside", "ellipse(10px 10px at 10% left)") is "auto"
PASS getCSSText("-webkit-shape-outside", "ellipse(10px 20px 30px at center center 10px)") is ""
PASS getComputedStyleValue("-webkit-shape-outside", "ellipse(10px 20px 30px at center center 10px)") is "auto"
PASS getCSSText("-webkit-shape-outside", "ellipse(at 10px 10px 10px)") is ""
Modified: trunk/LayoutTests/fast/shapes/parsing/parsing-test-utils.js (160769 => 160770)
--- trunk/LayoutTests/fast/shapes/parsing/parsing-test-utils.js 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/LayoutTests/fast/shapes/parsing/parsing-test-utils.js 2013-12-18 17:27:58 UTC (rev 160770)
@@ -117,6 +117,7 @@
"circle(10px at 10px 10px 10px)",
"circle(10px at 10px 10px at center)",
"circle(10px at center center 10px)",
+ "circle(10px at 10% left)",
"circle(at 10px 10px 10px)",
"circle(at 10px 10px at center)",
"circle(at center center 10px)",
@@ -129,6 +130,7 @@
"ellipse(10px at 10px 10px 10px)",
"ellipse(10px at 10px 10px at center)",
"ellipse(10px at center center 10px)",
+ "ellipse(10px 10px at 10% left)",
"ellipse(10px 20px 30px at center center 10px)",
"ellipse(at 10px 10px 10px)",
"ellipse(at 10px 10px at center)",
Modified: trunk/LayoutTests/fast/shapes/shape-outside-floats/shape-outside-animation-expected.txt (160769 => 160770)
--- trunk/LayoutTests/fast/shapes/shape-outside-floats/shape-outside-animation-expected.txt 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/LayoutTests/fast/shapes/shape-outside-floats/shape-outside-animation-expected.txt 2013-12-18 17:27:58 UTC (rev 160770)
@@ -4,10 +4,24 @@
Moving Text
Moving Text
Moving Text
+Moving Text
+Moving Text
+Moving Text
+Moving Text
+Moving Text
+Moving Text
+Moving Text
PASS - "webkitShapeOutside" property for "rectangle-box" element at 1s saw something close to: rectangle(10%, 10%, 80%, 80%, 0px, 0px)
PASS - "webkitShapeOutside" property for "circle-box" element at 1s saw something close to: circle(35% at 35% 35%)
PASS - "webkitShapeOutside" property for "ellipse-box" element at 1s saw something close to: ellipse(35% 30% at 35% 35%)
PASS - "webkitShapeOutside" property for "polygon-box" element at 1s saw something close to: polygon(nonzero, 10% 10%, 90% 10%, 90% 90%, 10% 90%)
PASS - "webkitShapeOutside" property for "polygon2-box" element at 1s saw something close to: polygon(nonzero, 20% 20%, 80% 20%, 80% 80%, 20% 80%)
PASS - "webkitShapeOutside" property for "circle-auto-box" element at 1s saw something close to: circle(50% at 50% 50%)
+PASS - "webkitShapeOutside" property for "circle-to-topleft-box" element at 1s saw something close to: circle(35% at 25% 25%)
+PASS - "webkitShapeOutside" property for "circle-to-topleft-box" element at 1s saw something close to: circle(35% at 25% 25%)
+PASS - "webkitShapeOutside" property for "circle-to-bottomright-using-keyword-box" element at 1s saw something close to: circle(35% at 75% 75%)
+PASS - "webkitShapeOutside" property for "circle-to-bottomright-using-keyword-box" element at 1s saw something close to: circle(35% at 75% 75%)
+PASS - "webkitShapeOutside" property for "circle-to-bottomright-extended-box" element at 1s saw something close to: circle(35% at 75% 75%)
+PASS - "webkitShapeOutside" property for "circle-to-bottomright-extended-using-keyword-box" element at 1s saw something close to: circle(35% at 70% 70%)
+PASS - "webkitShapeOutside" property for "circle-to-bottomright-extended-using-keyword-2-box" element at 1s saw something close to: circle(35% at 70% 70%)
Modified: trunk/LayoutTests/fast/shapes/shape-outside-floats/shape-outside-animation.html (160769 => 160770)
--- trunk/LayoutTests/fast/shapes/shape-outside-floats/shape-outside-animation.html 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/LayoutTests/fast/shapes/shape-outside-floats/shape-outside-animation.html 2013-12-18 17:27:58 UTC (rev 160770)
@@ -10,7 +10,7 @@
.box {
height: 100px;
width: 100px;
- margin: 10px;
+ margin: 50px;
float: left;
}
@@ -38,6 +38,34 @@
-webkit-animation: circle-auto-anim 2s linear
}
+ #circle-to-topleft-box {
+ -webkit-animation: circle-to-topleft-anim 2s linear
+ }
+
+ #circle-to-topleft-using-keyword-box {
+ -webkit-animation: circle-to-topleft-using-keyword-anim 2s linear
+ }
+
+ #circle-to-bottomright-box {
+ -webkit-animation: circle-to-bottomright-anim 2s linear
+ }
+
+ #circle-to-bottomright-using-keyword-box {
+ -webkit-animation: circle-to-bottomright-using-keyword-anim 2s linear
+ }
+
+ #circle-to-bottomright-extended-box {
+ -webkit-animation: circle-to-bottomright-extended-anim 2s linear
+ }
+
+ #circle-to-bottomright-extended-using-keyword-box {
+ -webkit-animation: circle-to-bottomright-extended-using-keyword-anim 2s linear
+ }
+
+ #circle-to-bottomright-extended-using-keyword-2-box {
+ -webkit-animation: circle-to-bottomright-extended-using-keyword-2-anim 2s linear
+ }
+
@-webkit-keyframes rectangle-anim {
from { -webkit-shape-outside: rectangle(0%, 0%, 100%, 100%); }
to { -webkit-shape-outside: rectangle(20%, 20%, 60%, 60%); }
@@ -68,6 +96,40 @@
to { -webkit-shape-outside: circle(50% at 50% 50%); }
}
+ @-webkit-keyframes circle-to-topleft-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%); }
+ to { -webkit-shape-outside: circle(20% at 0% 0%); }
+ }
+
+ @-webkit-keyframes circle-to-topleft-using-keyword-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%); }
+ to { -webkit-shape-outside: circle(20% at left top); }
+ }
+
+ @-webkit-keyframes circle-to-bottomright-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%); }
+ to { -webkit-shape-outside: circle(20% at 100% 100%); }
+ }
+
+ @-webkit-keyframes circle-to-bottomright-using-keyword-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%); }
+ to { -webkit-shape-outside: circle(20% at right bottom); }
+ }
+
+ @-webkit-keyframes circle-to-bottomright-extended-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%); }
+ to { -webkit-shape-outside: circle(20% at 100% 100%); }
+ }
+
+ @-webkit-keyframes circle-to-bottomright-extended-using-keyword-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%); }
+ to { -webkit-shape-outside: circle(20% at right 10% bottom 20px); }
+ }
+
+ @-webkit-keyframes circle-to-bottomright-extended-using-keyword-2-anim {
+ from { -webkit-shape-outside: circle(50% at 50% 50%) border-box; }
+ to { -webkit-shape-outside: circle(20% at right 10% bottom 10px) border-box; }
+ }
</style>
<script src=""
<script type="text/_javascript_">
@@ -79,6 +141,13 @@
["polygon-anim", 1, "polygon-box", "webkitShapeOutside", "polygon(nonzero, 10% 10%, 90% 10%, 90% 90%, 10% 90%)", 0.05],
["polygon2-anim", 1, "polygon2-box", "webkitShapeOutside", "polygon(nonzero, 20% 20%, 80% 20%, 80% 80%, 20% 80%)", 0.05],
["circle-auto-anim", 1, "circle-auto-box", "webkitShapeOutside", "circle(50% at 50% 50%)", 0.05],
+ ["circle-to-topleft-anim", 1, "circle-to-topleft-box", "webkitShapeOutside", "circle(35% at 25% 25%)", 0.05],
+ ["circle-to-topleft-anim", 1, "circle-to-topleft-box", "webkitShapeOutside", "circle(35% at 25% 25%)", 0.05],
+ ["circle-to-bottomright-using-keyword-anim", 1, "circle-to-bottomright-using-keyword-box", "webkitShapeOutside", "circle(35% at 75% 75%)", 0.05],
+ ["circle-to-bottomright-using-keyword-anim", 1, "circle-to-bottomright-using-keyword-box", "webkitShapeOutside", "circle(35% at 75% 75%)", 0.05],
+ ["circle-to-bottomright-extended-anim", 1, "circle-to-bottomright-extended-box", "webkitShapeOutside", "circle(35% at 75% 75%)", 0.05],
+ ["circle-to-bottomright-extended-using-keyword-anim", 1, "circle-to-bottomright-extended-using-keyword-box", "webkitShapeOutside", "circle(35% at 70% 70%)", 0.01],
+ ["circle-to-bottomright-extended-using-keyword-2-anim", 1, "circle-to-bottomright-extended-using-keyword-2-box", "webkitShapeOutside", "circle(35% at 70% 70%)", 0.01],
];
runAnimationTest(expectedValues);
@@ -110,6 +179,34 @@
<div class="box" id="circle-auto-box"></div>
Moving Text
</div>
+<div class='container'>
+ <div class="box" id="circle-to-topleft-box"></div>
+ Moving Text
+</div>
+<div class='container'>
+ <div class="box" id="circle-to-topleft-using-keyword-box"></div>
+ Moving Text
+</div>
+<div class='container'>
+ <div class="box" id="circle-to-bottomright-box"></div>
+ Moving Text
+</div>
+<div class='container'>
+ <div class="box" id="circle-to-bottomright-using-keyword-box"></div>
+ Moving Text
+</div>
+<div class='container'>
+ <div class="box" id="circle-to-bottomright-extended-box"></div>
+ Moving Text
+</div>
+<div class='container'>
+ <div class="box" id="circle-to-bottomright-extended-using-keyword-box"></div>
+ Moving Text
+</div>
+<div class='container'>
+ <div class="box" id="circle-to-bottomright-extended-using-keyword-2-box"></div>
+ Moving Text
+</div>
<div id="result">
</div>
Modified: trunk/Source/WebCore/ChangeLog (160769 => 160770)
--- trunk/Source/WebCore/ChangeLog 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/Source/WebCore/ChangeLog 2013-12-18 17:27:58 UTC (rev 160770)
@@ -1,3 +1,33 @@
+2013-12-18 Rob Buis <[email protected]>
+
+ [CSS Shapes] Implement interpolation between keywords in basic shapes
+ https://bugs.webkit.org/show_bug.cgi?id=125108
+
+ Reviewed by Simon Fraser.
+
+ Allow blending for all center coordinates since top/left and bottom/right default to correct
+ Length values of 0% and 100%. For mixed keyword and value positions compute the length's used
+ for blending to percentages. This is possible since we compute the reference box bounds given the
+ renderer.
+
+ * page/animation/CSSPropertyAnimation.cpp:
+ (WebCore::blendFunc): Pass additional RenderBox parameter.
+ * rendering/style/BasicShapes.cpp:
+ (WebCore::BasicShape::canBlend): Don't check circle/ellipse center anymore, but do check that both
+ shapes use the same reference box.
+ (WebCore::BasicShape::referenceBoxSize): Compute box dimension depending on reference box.
+ (WebCore::BasicShapeCenterCoordinate::lengthForBlending): Convert to percentage for Bottom/Right.
+ (WebCore::BasicShapeRectangle::blend):
+ (WebCore::DeprecatedBasicShapeCircle::blend):
+ (WebCore::BasicShapeCircle::blend):
+ (WebCore::DeprecatedBasicShapeEllipse::blend):
+ (WebCore::BasicShapeEllipse::blend):
+ (WebCore::BasicShapePolygon::blend):
+ (WebCore::BasicShapeInsetRectangle::blend):
+ (WebCore::BasicShapeInset::blend):
+ * rendering/style/BasicShapes.h:
+ (WebCore::BasicShapeCenterCoordinate::blend): Use new lengthForBlending.
+
2013-12-18 Dániel Bátyai <[email protected]>
CSS: Null-pointer dereference with negative 'orphans' value.
Modified: trunk/Source/WebCore/page/animation/CSSPropertyAnimation.cpp (160769 => 160770)
--- trunk/Source/WebCore/page/animation/CSSPropertyAnimation.cpp 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/Source/WebCore/page/animation/CSSPropertyAnimation.cpp 2013-12-18 17:27:58 UTC (rev 160770)
@@ -125,7 +125,7 @@
return to.blendByUsingMatrixInterpolation(from, progress, anim->renderer()->isBox() ? toRenderBox(anim->renderer())->borderBoxRect().size() : LayoutSize());
}
-static inline PassRefPtr<ClipPathOperation> blendFunc(const AnimationBase*, ClipPathOperation* from, ClipPathOperation* to, double progress)
+static inline PassRefPtr<ClipPathOperation> blendFunc(const AnimationBase* anim, ClipPathOperation* from, ClipPathOperation* to, double progress)
{
if (!from || !to)
return to;
@@ -140,11 +140,12 @@
if (!fromShape->canBlend(toShape))
return to;
- return ShapeClipPathOperation::create(toShape->blend(fromShape, progress));
+ ASSERT(anim->renderer()->isBox());
+ return ShapeClipPathOperation::create(toShape->blend(fromShape, progress, *toRenderBox(anim->renderer())));
}
#if ENABLE(CSS_SHAPES)
-static inline PassRefPtr<ShapeValue> blendFunc(const AnimationBase*, ShapeValue* from, ShapeValue* to, double progress)
+static inline PassRefPtr<ShapeValue> blendFunc(const AnimationBase* anim, ShapeValue* from, ShapeValue* to, double progress)
{
if (!from || !to)
return to;
@@ -159,7 +160,8 @@
if (!fromShape->canBlend(toShape))
return to;
- return ShapeValue::createShapeValue(toShape->blend(fromShape, progress));
+ ASSERT(anim->renderer()->isBox());
+ return ShapeValue::createShapeValue(toShape->blend(fromShape, progress, *toRenderBox(anim->renderer())));
}
#endif
Modified: trunk/Source/WebCore/rendering/style/BasicShapes.cpp (160769 => 160770)
--- trunk/Source/WebCore/rendering/style/BasicShapes.cpp 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/Source/WebCore/rendering/style/BasicShapes.cpp 2013-12-18 17:27:58 UTC (rev 160770)
@@ -35,6 +35,7 @@
#include "FloatRect.h"
#include "LengthFunctions.h"
#include "Path.h"
+#include "RenderBox.h"
namespace WebCore {
@@ -44,34 +45,63 @@
if (type() != other->type())
return false;
+ // Both shapes must use the same reference box.
+ if (box() != other->box())
+ return false;
+
// Just polygons with same number of vertices can be animated.
if (type() == BasicShape::BasicShapePolygonType
&& (static_cast<const BasicShapePolygon*>(this)->values().size() != static_cast<const BasicShapePolygon*>(other)->values().size()
|| static_cast<const BasicShapePolygon*>(this)->windRule() != static_cast<const BasicShapePolygon*>(other)->windRule()))
return false;
- // Circles with keywords for radii or center coordinates cannot be animated.
+ // Circles with keywords for radii coordinates cannot be animated.
if (type() == BasicShape::BasicShapeCircleType) {
const BasicShapeCircle* thisCircle = static_cast<const BasicShapeCircle*>(this);
const BasicShapeCircle* otherCircle = static_cast<const BasicShapeCircle*>(other);
- if (!thisCircle->radius().canBlend(otherCircle->radius())
- || !thisCircle->centerX().canBlend(otherCircle->centerX())
- || !thisCircle->centerY().canBlend(otherCircle->centerY()))
+ if (!thisCircle->radius().canBlend(otherCircle->radius()))
return false;
}
- // Ellipses with keywords for radii or center coordinates cannot be animated.
+ // Ellipses with keywords for radii coordinates cannot be animated.
if (type() != BasicShape::BasicShapeEllipseType)
return true;
const BasicShapeEllipse* thisEllipse = static_cast<const BasicShapeEllipse*>(this);
const BasicShapeEllipse* otherEllipse = static_cast<const BasicShapeEllipse*>(other);
return (thisEllipse->radiusX().canBlend(otherEllipse->radiusX())
- && thisEllipse->radiusY().canBlend(otherEllipse->radiusY())
- && thisEllipse->centerX().canBlend(otherEllipse->centerX())
- && thisEllipse->centerY().canBlend(otherEllipse->centerY()));
+ && thisEllipse->radiusY().canBlend(otherEllipse->radiusY()));
}
+FloatSize BasicShape::referenceBoxSize(const RenderBox& renderer) const
+{
+ switch (box()) {
+ case ContentBox:
+ return renderer.contentBoxRect().size();
+ case PaddingBox:
+ return renderer.paddingBoxRect().size();
+ case BorderBox:
+ return renderer.size();
+ case None: // If <box> is not supplied, then the reference box defaults to margin-box.
+ case MarginBox:
+ return FloatSize(renderer.marginLeft() + renderer.width() + renderer.marginRight(),
+ renderer.marginTop() + renderer.height() + renderer.marginBottom());
+ }
+
+ ASSERT_NOT_REACHED();
+ return FloatSize();
+}
+
+Length BasicShapeCenterCoordinate::lengthForBlending(const FloatSize& boxSize) const
+{
+ Length length = this->length();
+ if (keyword() == Right)
+ return Length(100 - (length.isPercent() ? length.percent() : 100.f * (length.value() / boxSize.width())), Percent);
+ if (keyword() == Bottom)
+ return Length(100 - (length.isPercent() ? length.percent() : 100.f * (length.value() / boxSize.height())), Percent);
+ return length;
+}
+
void BasicShapeRectangle::path(Path& path, const FloatRect& boundingBox)
{
ASSERT(path.isEmpty());
@@ -89,7 +119,7 @@
);
}
-PassRefPtr<BasicShape> BasicShapeRectangle::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> BasicShapeRectangle::blend(const BasicShape* other, double progress, const RenderBox&) const
{
ASSERT(type() == other->type());
@@ -119,7 +149,7 @@
));
}
-PassRefPtr<BasicShape> DeprecatedBasicShapeCircle::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> DeprecatedBasicShapeCircle::blend(const BasicShape* other, double progress, const RenderBox&) const
{
ASSERT(type() == other->type());
@@ -161,14 +191,15 @@
));
}
-PassRefPtr<BasicShape> BasicShapeCircle::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> BasicShapeCircle::blend(const BasicShape* other, double progress, const RenderBox& renderer) const
{
ASSERT(type() == other->type());
const BasicShapeCircle* o = static_cast<const BasicShapeCircle*>(other);
RefPtr<BasicShapeCircle> result = BasicShapeCircle::create();
- result->setCenterX(m_centerX.blend(o->centerX(), progress));
- result->setCenterY(m_centerY.blend(o->centerY(), progress));
+ FloatSize boxSize = referenceBoxSize(renderer);
+ result->setCenterX(m_centerX.blend(o->centerX(), progress, boxSize));
+ result->setCenterY(m_centerY.blend(o->centerY(), progress, boxSize));
result->setRadius(m_radius.blend(o->radius(), progress));
return result.release();
}
@@ -188,7 +219,7 @@
));
}
-PassRefPtr<BasicShape> DeprecatedBasicShapeEllipse::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> DeprecatedBasicShapeEllipse::blend(const BasicShape* other, double progress, const RenderBox&) const
{
ASSERT(type() == other->type());
@@ -228,7 +259,7 @@
radiusY * 2));
}
-PassRefPtr<BasicShape> BasicShapeEllipse::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> BasicShapeEllipse::blend(const BasicShape* other, double progress, const RenderBox& renderer) const
{
ASSERT(type() == other->type());
const BasicShapeEllipse* o = static_cast<const BasicShapeEllipse*>(other);
@@ -243,8 +274,9 @@
return result;
}
- result->setCenterX(m_centerX.blend(o->centerX(), progress));
- result->setCenterY(m_centerY.blend(o->centerY(), progress));
+ FloatSize boxSize = referenceBoxSize(renderer);
+ result->setCenterX(m_centerX.blend(o->centerX(), progress, boxSize));
+ result->setCenterY(m_centerY.blend(o->centerY(), progress, boxSize));
result->setRadiusX(m_radiusX.blend(o->radiusX(), progress));
result->setRadiusY(m_radiusY.blend(o->radiusY(), progress));
return result.release();
@@ -268,7 +300,7 @@
path.closeSubpath();
}
-PassRefPtr<BasicShape> BasicShapePolygon::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> BasicShapePolygon::blend(const BasicShape* other, double progress, const RenderBox&) const
{
ASSERT(type() == other->type());
@@ -310,7 +342,7 @@
);
}
-PassRefPtr<BasicShape> BasicShapeInsetRectangle::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> BasicShapeInsetRectangle::blend(const BasicShape* other, double progress, const RenderBox&) const
{
ASSERT(type() == other->type());
@@ -356,7 +388,7 @@
);
}
-PassRefPtr<BasicShape> BasicShapeInset::blend(const BasicShape* other, double progress) const
+PassRefPtr<BasicShape> BasicShapeInset::blend(const BasicShape* other, double progress, const RenderBox&) const
{
ASSERT(type() == other->type());
Modified: trunk/Source/WebCore/rendering/style/BasicShapes.h (160769 => 160770)
--- trunk/Source/WebCore/rendering/style/BasicShapes.h 2013-12-18 17:26:21 UTC (rev 160769)
+++ trunk/Source/WebCore/rendering/style/BasicShapes.h 2013-12-18 17:27:58 UTC (rev 160770)
@@ -41,6 +41,7 @@
class FloatRect;
class Path;
+class RenderBox;
class BasicShape : public RefCounted<BasicShape> {
public:
@@ -69,7 +70,7 @@
virtual void path(Path&, const FloatRect&) = 0;
virtual WindRule windRule() const { return RULE_NONZERO; }
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const = 0;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const = 0;
virtual Type type() const = 0;
@@ -82,6 +83,8 @@
{
}
+ FloatSize referenceBoxSize(const RenderBox&) const;
+
private:
ReferenceBox m_box;
};
@@ -113,7 +116,7 @@
}
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return BasicShapeRectangleType; }
private:
@@ -143,21 +146,13 @@
Keyword keyword() const { return m_keyword; }
const Length& length() const { return m_length; }
+ Length lengthForBlending(const FloatSize&) const;
- bool canBlend(const BasicShapeCenterCoordinate& other) const
+ BasicShapeCenterCoordinate blend(const BasicShapeCenterCoordinate& other, double progress, const FloatSize& boxSize) const
{
- // FIXME determine how to interpolate between keywords. See bug 125108.
- return m_keyword == None && other.keyword() == None;
+ return BasicShapeCenterCoordinate(lengthForBlending(boxSize).blend(other.lengthForBlending(boxSize), progress));
}
- BasicShapeCenterCoordinate blend(const BasicShapeCenterCoordinate& other, double progress) const
- {
- if (m_keyword != None || other.keyword() != None)
- return BasicShapeCenterCoordinate(other);
-
- return BasicShapeCenterCoordinate(m_length.blend(other.length(), progress));
- }
-
private:
Keyword m_keyword;
Length m_length;
@@ -212,7 +207,7 @@
void setRadius(BasicShapeRadius radius) { m_radius = std::move(radius); }
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return BasicShapeCircleType; }
private:
@@ -236,7 +231,7 @@
void setRadius(Length radius) { m_radius = std::move(radius); }
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return DeprecatedBasicShapeCircleType; }
private:
@@ -263,7 +258,7 @@
void setRadiusY(BasicShapeRadius radiusY) { m_radiusY = std::move(radiusY); }
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return BasicShapeEllipseType; }
private:
@@ -290,7 +285,7 @@
void setRadiusY(Length radiusY) { m_radiusY = std::move(radiusY); }
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return DeprecatedBasicShapeEllipseType; }
private:
@@ -314,7 +309,7 @@
void appendPoint(Length x, Length y) { m_values.append(std::move(x)); m_values.append(std::move(y)); }
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual WindRule windRule() const OVERRIDE { return m_windRule; }
@@ -355,7 +350,7 @@
}
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return BasicShapeInsetRectangleType; }
private:
@@ -394,7 +389,7 @@
void setBottomLeftRadius(LengthSize radius) { m_bottomLeftRadius = std::move(radius); }
virtual void path(Path&, const FloatRect&) OVERRIDE;
- virtual PassRefPtr<BasicShape> blend(const BasicShape*, double) const OVERRIDE;
+ virtual PassRefPtr<BasicShape> blend(const BasicShape*, double, const RenderBox&) const OVERRIDE;
virtual Type type() const OVERRIDE { return BasicShapeInsetType; }
private: