Reviewed by Oliver.
Make renderers pull localTransform instead of depending on DOM elements to push
This allows for cleaner invalidation code, and makes writing animation easier.
Also fixed a tiny bug in SVGRenderImage focus ring calculations while there
Updated test results for svg/custom/focus-ring.svg
* WebCore.xcodeproj/project.pbxproj:
* ksvg2/svg/SVGAElement.cpp:
(WebCore::SVGAElement::createRenderer):
* ksvg2/svg/SVGAnimateMotionElement.cpp:
(WebCore::SVGAnimateMotionElement::applyAnimatedValueToElement):
* ksvg2/svg/SVGAnimateTransformElement.cpp:
(WebCore::SVGAnimateTransformElement::applyAnimatedValueToElement):
* ksvg2/svg/SVGClipPathElement.cpp:
(WebCore::SVGClipPathElement::canvasResource):
* ksvg2/svg/SVGElement.h:
* ksvg2/svg/SVGGElement.cpp:
(WebCore::SVGGElement::createRenderer):
* ksvg2/svg/SVGImageElement.cpp:
* ksvg2/svg/SVGLocatable.cpp:
(WebCore::SVGLocatable::getCTM):
(WebCore::SVGLocatable::getScreenCTM):
* ksvg2/svg/SVGMarkerElement.cpp:
(WebCore::SVGMarkerElement::canvasResource):
(WebCore::SVGMarkerElement::notifyAttributeChange):
* ksvg2/svg/SVGSVGElement.h:
* ksvg2/svg/SVGStyledElement.cpp:
(WebCore::SVGStyledElement::rendererIsNeeded):
(WebCore::SVGStyledElement::notifyResourceParentIfExistant):
* ksvg2/svg/SVGStyledElement.h:
(WebCore::SVGStyledElement::style):
* ksvg2/svg/SVGStyledTransformableElement.cpp:
(WebCore::SVGStyledTransformableElement::animatedLocalTransform):
(WebCore::SVGStyledTransformableElement::parseMappedAttribute):
(WebCore::SVGStyledTransformableElement::notifyAttributeChange):
(WebCore::SVGStyledTransformableElement::createRenderer):
* ksvg2/svg/SVGStyledTransformableElement.h:
(WebCore::SVGStyledTransformableElement::toPathData):
* ksvg2/svg/SVGSwitchElement.cpp:
(WebCore::SVGSwitchElement::createRenderer):
* ksvg2/svg/SVGTRefElement.cpp:
(WebCore::SVGTRefElement::updateReferencedText):
* ksvg2/svg/SVGTextElement.cpp:
(WebCore::SVGTextElement::parseMappedAttribute):
(WebCore::SVGTextElement::animatedLocalTransform):
* ksvg2/svg/SVGTextElement.h:
* ksvg2/svg/SVGTextPathElement.cpp:
* ksvg2/svg/SVGTextPathElement.h:
* ksvg2/svg/SVGTransformable.cpp:
(WebCore::SVGTransformable::getCTM):
(WebCore::SVGTransformable::getScreenCTM):
* ksvg2/svg/SVGTransformable.h:
* ksvg2/svg/SVGUseElement.cpp:
(WebCore::SVGUseElement::createRenderer):
(WebCore::SVGUseElement::attachShadowTree):
* platform/graphics/AffineTransform.h:
(WebCore::AffineTransform::operator!=):
* platform/graphics/svg/SVGResourceMarker.cpp:
(WebCore::SVGResourceMarker::setMarker):
* platform/graphics/svg/SVGResourceMarker.h:
* rendering/RenderForeignObject.cpp:
(WebCore::RenderForeignObject::calculateLocalTransform):
(WebCore::RenderForeignObject::layout):
* rendering/RenderForeignObject.h:
(WebCore::RenderForeignObject::localTransform):
* rendering/RenderObject.cpp:
* rendering/RenderObject.h:
* rendering/RenderPath.cpp:
(WebCore::RenderPath::RenderPath):
(WebCore::RenderPath::localTransform):
(WebCore::RenderPath::calculateLocalTransform):
(WebCore::RenderPath::layout):
* rendering/RenderPath.h:
* rendering/RenderSVGContainer.cpp:
(WebCore::RenderSVGContainer::localTransform):
(WebCore::RenderSVGContainer::calculateLocalTransform):
(WebCore::RenderSVGContainer::layout):
* rendering/RenderSVGContainer.h:
* rendering/RenderSVGImage.h:
(WebCore::RenderSVGImage::localTransform):
* rendering/RenderSVGText.cpp:
(WebCore::RenderSVGText::calculateLocalTransform):
(WebCore::RenderSVGText::layout):
* rendering/RenderSVGText.h:
(WebCore::RenderSVGText::isSVGText):
(WebCore::RenderSVGText::localTransform):
* rendering/RenderSVGTextPath.cpp:
(WebCore::RenderSVGTextPath::layoutPath):
(WebCore::RenderSVGTextPath::startOffset):
(WebCore::RenderSVGTextPath::exactAlignment):
(WebCore::RenderSVGTextPath::stretchMethod):
* rendering/RenderSVGTextPath.h:
* rendering/RenderSVGTransformableContainer.cpp: Added.
(WebCore::RenderSVGTransformableContainer::RenderSVGTransformableContainer):
(WebCore::RenderSVGTransformableContainer::calculateLocalTransform):
* rendering/RenderSVGTransformableContainer.h: Added.
* rendering/RenderSVGViewportContainer.h:
git-svn-id: https://svn.webkit.org/repository/webkit/trunk@26534
268f45cc-cd09-0410-ab3c-
d52691b4dbfc
+2007-10-10 Eric Seidel <eric@webkit.org>
+
+ Reviewed by Oliver.
+
+ Updated results for:
+ http://bugs.webkit.org/show_bug.cgi?id=15458
+
+ * platform/mac/svg/custom/focus-ring-expected.checksum: Added.
+ * platform/mac/svg/custom/focus-ring-expected.png: Added.
+ * platform/mac/svg/custom/focus-ring-expected.txt: Added.
+
2007-10-09 Alexey Proskuryakov <ap@webkit.org>
Reviewed by Anders.
--- /dev/null
+37b8faf5bf39caf573762517d6ebcaa1
\ No newline at end of file
--- /dev/null
+KCanvasResource {id="clip" [type=CLIPPER] [clip data=[[winding=NON-ZERO] [path=M0.00,0.00L100.00,0.00L100.00,100.00L0.00,100.00]]]}
+layer at (0,0) size 800x1000
+ RenderView at (0,0) size 800x600
+layer at (0,0) size 800x1000
+ RenderSVGRoot {svg} at (-5,10) size 823.99x1010.07
+ RenderPath {circle} at (15,10) size 100x100 [fill={[type=SOLID] [color=#FFA500]}] [data="M115.00,60.00L114.90,63.14L114.61,66.27L114.11,69.37L113.43,72.43L112.55,75.45L111.49,78.41L110.24,81.29L108.82,84.09L107.22,86.79L105.45,89.39L103.53,91.87L101.45,94.23L99.23,96.45L96.87,98.53L94.39,100.45L91.79,102.22L89.09,103.82L86.29,105.24L83.41,106.49L80.45,107.55L77.43,108.43L74.37,109.11L71.27,109.61L68.14,109.90L65.00,110.00L61.86,109.90L58.73,109.61L55.63,109.11L52.57,108.43L49.55,107.55L46.59,106.49L43.71,105.24L40.91,103.82L38.21,102.22L35.61,100.45L33.13,98.53L30.77,96.45L28.55,94.23L26.47,91.87L24.55,89.39L22.78,86.79L21.18,84.09L19.76,81.29L18.51,78.41L17.45,75.45L16.57,72.43L15.89,69.37L15.39,66.27L15.10,63.14L15.00,60.00L15.10,56.86L15.39,53.73L15.89,50.63L16.57,47.57L17.45,44.55L18.51,41.59L19.76,38.71L21.18,35.91L22.78,33.21L24.55,30.61L26.47,28.13L28.55,25.77L30.77,23.55L33.13,21.47L35.61,19.55L38.21,17.78L40.91,16.18L43.71,14.76L46.59,13.51L49.55,12.45L52.57,11.57L55.63,10.89L58.73,10.39L61.86,10.10L65.00,10.00L68.14,10.10L71.27,10.39L74.37,10.89L77.43,11.57L80.45,12.45L83.41,13.51L86.29,14.76L89.09,16.18L91.79,17.78L94.39,19.55L96.87,21.47L99.23,23.55L101.45,25.77L103.53,28.13L105.45,30.61L107.22,33.21L108.82,35.91L110.24,38.71L111.49,41.59L112.55,44.55L113.43,47.57L114.11,50.63L114.61,53.73L114.90,56.86"]
+ RenderPath {path} at (140,10) size 100x100 [fill={[type=SOLID] [color=#FFA500]}] [data="M140.00,10.00L190.00,110.00L240.00,60.00L220.00,60.00L200.00,30.00"]
+ RenderSVGContainer {g} at (270,10) size 100x100
+ RenderPath {rect} at (270,10) size 100x100 [fill={[type=SOLID] [color=#FFA500]}] [data="M270.00,10.00L370.00,10.00L370.00,110.00L270.00,110.00"]
+ RenderSVGContainer {g} at (10,140) size 136.60x136.60 [transform={m=((0.87,0.50)(-0.50,0.87)) t=(60.00,140.00)}]
+ RenderPath {rect} at (10,140) size 136.60x136.60 [fill={[type=SOLID] [color=#FFA500]}] [data="M0.00,0.00L100.00,0.00L100.00,100.00L0.00,100.00"]
+ RenderPath {rect} at (150,140) size 136.60x136.60 [transform={m=((0.87,0.50)(-0.50,0.87)) t=(200.00,140.00)}] [fill={[type=SOLID] [color=#FFA500]}] [data="M0.00,0.00L100.00,0.00L100.00,100.00L0.00,100.00"]
+ RenderSVGContainer {g} at (310,140) size 136.60x136.60
+ RenderPath {rect} at (310,140) size 136.60x136.60 [transform={m=((0.87,0.50)(-0.50,0.87)) t=(360.00,140.00)}] [fill={[type=SOLID] [color=#FFA500]}] [data="M0.00,0.00L100.00,0.00L100.00,100.00L0.00,100.00"]
+ RenderSVGText {text} at (10,320) size 76x18 contains 1 chunk(s)
+ RenderSVGInlineText {#text} at (0,-14) size 76x18
+ chunk 1 text run 1 at (10.00,320.00) startOffset 0 endOffset 12 width 76.00: "focused text"
+ RenderSVGText {text} at (0,0) size 76x18 contains 1 chunk(s)
+ RenderSVGInlineText {#text} at (0,-14) size 76x18
+ chunk 1 text run 1 at (0.00,0.00) startOffset 0 endOffset 12 width 76.00: "focused text"
+ RenderSVGContainer {g} at (198,307.88) size 74.82x53.59
+ RenderSVGText {text} at (0,0) size 76x18 contains 1 chunk(s)
+ RenderSVGInlineText {#text} at (0,-14) size 76x18
+ chunk 1 text run 1 at (0.00,0.00) startOffset 0 endOffset 12 width 76.00: "focused text"
+ RenderImage {image} at (0,0) size 530x410
+ RenderImage {image} at (0,0) size 530x410
+ RenderSVGContainer {g} at (155,400) size 663.99x620.07 [transform={m=((0.87,0.50)(-0.50,0.87)) t=(360.00,400.00)}]
+ RenderImage {image} at (0,0) size 530x410
+2007-10-10 Eric Seidel <eric@webkit.org>
+
+ Reviewed by Oliver.
+
+ Make renderers pull localTransform instead of depending on DOM elements to push
+ This allows for cleaner invalidation code, and makes writing animation easier.
+ Also fixed a tiny bug in SVGRenderImage focus ring calculations while there
+
+ Updated test results for svg/custom/focus-ring.svg
+
+ * WebCore.xcodeproj/project.pbxproj:
+ * ksvg2/svg/SVGAElement.cpp:
+ (WebCore::SVGAElement::createRenderer):
+ * ksvg2/svg/SVGAnimateMotionElement.cpp:
+ (WebCore::SVGAnimateMotionElement::applyAnimatedValueToElement):
+ * ksvg2/svg/SVGAnimateTransformElement.cpp:
+ (WebCore::SVGAnimateTransformElement::applyAnimatedValueToElement):
+ * ksvg2/svg/SVGClipPathElement.cpp:
+ (WebCore::SVGClipPathElement::canvasResource):
+ * ksvg2/svg/SVGElement.h:
+ * ksvg2/svg/SVGGElement.cpp:
+ (WebCore::SVGGElement::createRenderer):
+ * ksvg2/svg/SVGImageElement.cpp:
+ * ksvg2/svg/SVGLocatable.cpp:
+ (WebCore::SVGLocatable::getCTM):
+ (WebCore::SVGLocatable::getScreenCTM):
+ * ksvg2/svg/SVGMarkerElement.cpp:
+ (WebCore::SVGMarkerElement::canvasResource):
+ (WebCore::SVGMarkerElement::notifyAttributeChange):
+ * ksvg2/svg/SVGSVGElement.h:
+ * ksvg2/svg/SVGStyledElement.cpp:
+ (WebCore::SVGStyledElement::rendererIsNeeded):
+ (WebCore::SVGStyledElement::notifyResourceParentIfExistant):
+ * ksvg2/svg/SVGStyledElement.h:
+ (WebCore::SVGStyledElement::style):
+ * ksvg2/svg/SVGStyledTransformableElement.cpp:
+ (WebCore::SVGStyledTransformableElement::animatedLocalTransform):
+ (WebCore::SVGStyledTransformableElement::parseMappedAttribute):
+ (WebCore::SVGStyledTransformableElement::notifyAttributeChange):
+ (WebCore::SVGStyledTransformableElement::createRenderer):
+ * ksvg2/svg/SVGStyledTransformableElement.h:
+ (WebCore::SVGStyledTransformableElement::toPathData):
+ * ksvg2/svg/SVGSwitchElement.cpp:
+ (WebCore::SVGSwitchElement::createRenderer):
+ * ksvg2/svg/SVGTRefElement.cpp:
+ (WebCore::SVGTRefElement::updateReferencedText):
+ * ksvg2/svg/SVGTextElement.cpp:
+ (WebCore::SVGTextElement::parseMappedAttribute):
+ (WebCore::SVGTextElement::animatedLocalTransform):
+ * ksvg2/svg/SVGTextElement.h:
+ * ksvg2/svg/SVGTextPathElement.cpp:
+ * ksvg2/svg/SVGTextPathElement.h:
+ * ksvg2/svg/SVGTransformable.cpp:
+ (WebCore::SVGTransformable::getCTM):
+ (WebCore::SVGTransformable::getScreenCTM):
+ * ksvg2/svg/SVGTransformable.h:
+ * ksvg2/svg/SVGUseElement.cpp:
+ (WebCore::SVGUseElement::createRenderer):
+ (WebCore::SVGUseElement::attachShadowTree):
+ * platform/graphics/AffineTransform.h:
+ (WebCore::AffineTransform::operator!=):
+ * platform/graphics/svg/SVGResourceMarker.cpp:
+ (WebCore::SVGResourceMarker::setMarker):
+ * platform/graphics/svg/SVGResourceMarker.h:
+ * rendering/RenderForeignObject.cpp:
+ (WebCore::RenderForeignObject::calculateLocalTransform):
+ (WebCore::RenderForeignObject::layout):
+ * rendering/RenderForeignObject.h:
+ (WebCore::RenderForeignObject::localTransform):
+ * rendering/RenderObject.cpp:
+ * rendering/RenderObject.h:
+ * rendering/RenderPath.cpp:
+ (WebCore::RenderPath::RenderPath):
+ (WebCore::RenderPath::localTransform):
+ (WebCore::RenderPath::calculateLocalTransform):
+ (WebCore::RenderPath::layout):
+ * rendering/RenderPath.h:
+ * rendering/RenderSVGContainer.cpp:
+ (WebCore::RenderSVGContainer::localTransform):
+ (WebCore::RenderSVGContainer::calculateLocalTransform):
+ (WebCore::RenderSVGContainer::layout):
+ * rendering/RenderSVGContainer.h:
+ * rendering/RenderSVGImage.h:
+ (WebCore::RenderSVGImage::localTransform):
+ * rendering/RenderSVGText.cpp:
+ (WebCore::RenderSVGText::calculateLocalTransform):
+ (WebCore::RenderSVGText::layout):
+ * rendering/RenderSVGText.h:
+ (WebCore::RenderSVGText::isSVGText):
+ (WebCore::RenderSVGText::localTransform):
+ * rendering/RenderSVGTextPath.cpp:
+ (WebCore::RenderSVGTextPath::layoutPath):
+ (WebCore::RenderSVGTextPath::startOffset):
+ (WebCore::RenderSVGTextPath::exactAlignment):
+ (WebCore::RenderSVGTextPath::stretchMethod):
+ * rendering/RenderSVGTextPath.h:
+ * rendering/RenderSVGTransformableContainer.cpp: Added.
+ (WebCore::RenderSVGTransformableContainer::RenderSVGTransformableContainer):
+ (WebCore::RenderSVGTransformableContainer::calculateLocalTransform):
+ * rendering/RenderSVGTransformableContainer.h: Added.
+ * rendering/RenderSVGViewportContainer.h:
+
2007-10-10 Oliver Hunt <oliver@apple.com>
Reviewed by Eric.
A88DD4890B4629B000C02990 /* PathTraversalState.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A88DD4880B4629B000C02990 /* PathTraversalState.cpp */; };
A89943280B42338800D7C802 /* BitmapImage.h in Headers */ = {isa = PBXBuildFile; fileRef = A89943260B42338700D7C802 /* BitmapImage.h */; };
A89943290B42338800D7C802 /* BitmapImage.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A89943270B42338700D7C802 /* BitmapImage.cpp */; };
+ A8A909AC0CBCD6B50029B807 /* RenderSVGTransformableContainer.h in Headers */ = {isa = PBXBuildFile; fileRef = A8A909AA0CBCD6B50029B807 /* RenderSVGTransformableContainer.h */; };
+ A8A909AD0CBCD6B50029B807 /* RenderSVGTransformableContainer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A8A909AB0CBCD6B50029B807 /* RenderSVGTransformableContainer.cpp */; };
A8C4A7FD09D563270003AC8D /* StyledElement.h in Headers */ = {isa = PBXBuildFile; fileRef = A8C4A7EB09D563270003AC8D /* StyledElement.h */; settings = {ATTRIBUTES = (Private, ); }; };
A8C4A7FE09D563270003AC8D /* StyledElement.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A8C4A7EC09D563270003AC8D /* StyledElement.cpp */; };
A8C4A80009D563270003AC8D /* Node.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A8C4A7EE09D563270003AC8D /* Node.cpp */; };
A890DF1E0930974800513F88 /* SVGStyledLocatableElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; indentWidth = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SVGStyledLocatableElement.cpp; sourceTree = "<group>"; tabWidth = 8; usesTabs = 0; };
A89943260B42338700D7C802 /* BitmapImage.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = BitmapImage.h; sourceTree = "<group>"; };
A89943270B42338700D7C802 /* BitmapImage.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = BitmapImage.cpp; sourceTree = "<group>"; };
+ A8A909AA0CBCD6B50029B807 /* RenderSVGTransformableContainer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RenderSVGTransformableContainer.h; sourceTree = "<group>"; };
+ A8A909AB0CBCD6B50029B807 /* RenderSVGTransformableContainer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = RenderSVGTransformableContainer.cpp; sourceTree = "<group>"; };
A8C0F6EF089701F100BA5114 /* TimeScheduler.cpp */ = {isa = PBXFileReference; fileEncoding = 4; indentWidth = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TimeScheduler.cpp; sourceTree = "<group>"; tabWidth = 8; usesTabs = 0; };
A8C0F6F0089701F100BA5114 /* TimeScheduler.h */ = {isa = PBXFileReference; fileEncoding = 4; indentWidth = 4; lastKnownFileType = sourcecode.c.h; path = TimeScheduler.h; sourceTree = "<group>"; tabWidth = 8; usesTabs = 0; };
A8C0F6F4089701F100BA5114 /* SVGCSSPropertyNames.in */ = {isa = PBXFileReference; fileEncoding = 4; indentWidth = 4; lastKnownFileType = text; path = SVGCSSPropertyNames.in; sourceTree = "<group>"; tabWidth = 8; usesTabs = 0; };
853CA9E40AEEC608002372DC /* SVGRootInlineBox.cpp */,
853CA9E50AEEC608002372DC /* SVGRootInlineBox.h */,
A8CFF04C0A154F09000A4234 /* TableLayout.h */,
+ A8A909AA0CBCD6B50029B807 /* RenderSVGTransformableContainer.h */,
+ A8A909AB0CBCD6B50029B807 /* RenderSVGTransformableContainer.cpp */,
);
path = rendering;
sourceTree = "<group>";
BC64B4DA0CB4298A005F2B62 /* CSSFontFaceSrcValue.h in Headers */,
BC64B4DC0CB4298A005F2B62 /* CSSFontSelector.h in Headers */,
A84EBD830CB8C97700079609 /* JSStyleSheetList.h in Headers */,
+ A8A909AC0CBCD6B50029B807 /* RenderSVGTransformableContainer.h in Headers */,
);
runOnlyForDeploymentPostprocessing = 0;
};
A84EBD780CB8C89200079609 /* JSStyleSheetListCustom.cpp in Sources */,
A84EBD840CB8C97700079609 /* JSStyleSheetList.cpp in Sources */,
A84EC1390CB9FDBC00079609 /* SVGCSSComputedStyleDeclaration.cpp in Sources */,
+ A8A909AD0CBCD6B50029B807 /* RenderSVGTransformableContainer.cpp in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
#include "KeyboardEvent.h"
#include "MouseEvent.h"
#include "PlatformMouseEvent.h"
-#include "RenderSVGContainer.h"
+#include "RenderSVGTransformableContainer.h"
#include "RenderSVGInline.h"
#include "ResourceRequest.h"
#include "SVGNames.h"
if (static_cast<SVGElement*>(parent())->isTextContent())
return new (arena) RenderSVGInline(this);
- return new (arena) RenderSVGContainer(this);
+ return new (arena) RenderSVGTransformableContainer(this);
}
void SVGAElement::defaultEventHandler(Event* evt)
#if ENABLE(SVG) && ENABLE(SVG_EXPERIMENTAL_FEATURES)
#include "SVGAnimateMotionElement.h"
+#include "RenderObject.h"
#include "SVGMPathElement.h"
#include "SVGParserUtilities.h"
#include "SVGPathElement.h"
transform.translate(m_animatedTranslation.width(), m_animatedTranslation.height());
if (!transform.isIdentity()) {
transformList->appendItem(SVGTransform(transform), ec);
- transformableElement->updateLocalTransform(transformList.get());
+ transformableElement->setTransform(transformList.get());
+ if (transformableElement->renderer())
+ transformableElement->renderer()->setNeedsLayout(true); // should be part of setTransform
}
}
#if ENABLE(SVG) && ENABLE(SVG_EXPERIMENTAL_FEATURES)
#include "SVGAnimateTransformElement.h"
-#include "TimeScheduler.h"
-#include "SVGAngle.h"
#include "AffineTransform.h"
+#include "RenderObject.h"
+#include "SVGAngle.h"
+#include "SVGParserUtilities.h"
#include "SVGSVGElement.h"
#include "SVGStyledTransformableElement.h"
#include "SVGTransform.h"
#include "SVGTransformList.h"
-#include "SVGParserUtilities.h"
+#include "TimeScheduler.h"
+
#include <math.h>
#include <wtf/MathExtras.h>
transformList->clear(ec);
transformList->appendItem(m_animatedTransform, ec);
- transform->updateLocalTransform(transformList.get());
+ transform->setTransform(transformList.get());
+ if (transform->renderer())
+ transform->renderer()->setNeedsLayout(true); // should really be in setTransform
}
bool SVGAnimateTransformElement::calculateFromAndToValues(EAnimationMode animationMode, unsigned valueIndex)
#include "CSSStyleSelector.h"
#include "Document.h"
#include "SVGNames.h"
+#include "SVGTransformList.h"
#include "SVGUnitTypes.h"
namespace WebCore {
RenderStyle* clipPathStyle = styleForRenderer(parent()->renderer()); // FIXME: Manual style resolution is a hack
for (Node* n = firstChild(); n; n = n->nextSibling()) {
- SVGElement* e = svg_dynamic_cast(n);
- if (e && e->isStyled()) {
- SVGStyledElement* styled = static_cast<SVGStyledElement*>(e);
+ if (n->isSVGElement() && static_cast<SVGElement*>(n)->isStyledTransformable()) {
+ SVGStyledTransformableElement* styled = static_cast<SVGStyledTransformableElement*>(n);
RenderStyle* pathStyle = document()->styleSelector()->styleForElement(styled, clipPathStyle);
Path pathData = styled->toPathData();
- if (e->isStyledTransformable())
- pathData.transform(static_cast<SVGStyledTransformableElement*>(e)->localMatrix());
+ // FIXME: How do we know the element has done a layout?
+ pathData.transform(styled->animatedLocalTransform());
if (!pathData.isEmpty())
m_clipper->addClipData(pathData, pathStyle->svgStyle()->clipRule(), bbox);
pathStyle->deref(document()->renderArena());
{ \
const SVGElement* context = contextElement(); \
ASSERT(context); \
- return RefPtr<ClassName::SVGAnimatedTemplate##UpperProperty>(new ClassName::SVGAnimatedTemplate##UpperProperty(context)); \
+ return new ClassName::SVGAnimatedTemplate##UpperProperty(context); \
}
#define ANIMATED_PROPERTY_DEFINITIONS(ClassName, BareType, UpperClassName, LowerClassName, UpperProperty, LowerProperty, AttrName, StorageGetter) \
ANIMATED_PROPERTY_DEFINITIONS_INTERNAL(ClassName, ClassName, BareType, UpperClassName, LowerClassName, UpperProperty, LowerProperty, AttrName, StorageGetter, this) \
PassRefPtr<ClassName::SVGAnimatedTemplate##UpperProperty> ClassName::LowerProperty##Animated() const \
{ \
- return RefPtr<ClassName::SVGAnimatedTemplate##UpperProperty>(new ClassName::SVGAnimatedTemplate##UpperProperty(this)); \
+ return new ClassName::SVGAnimatedTemplate##UpperProperty(this); \
}
namespace WebCore {
#if ENABLE(SVG)
#include "SVGGElement.h"
-#include "RenderSVGContainer.h"
+#include "RenderSVGTransformableContainer.h"
namespace WebCore {
RenderObject* SVGGElement::createRenderer(RenderArena* arena, RenderStyle* style)
{
- return new (arena) RenderSVGContainer(this);
-}
-
-AffineTransform SVGGElement::localMatrix() const
-{
- return m_localMatrix;
+ return new (arena) RenderSVGTransformableContainer(this);
}
}
#include "SVGImageElement.h"
#include "CSSPropertyNames.h"
-#include "RenderSVGContainer.h"
#include "RenderSVGImage.h"
#include "SVGDocument.h"
#include "SVGLength.h"
AffineTransform ctm;
Node* parent = element->parentNode();
- if (parent && parent->isElementNode()) {
- SVGElement* parentElement = svg_dynamic_cast(parent);
+ if (parent && parent->isSVGElement()) {
+ SVGElement* parentElement = static_cast<SVGElement*>(parent);
if (parentElement && parentElement->isStyledLocatable()) {
AffineTransform parentCTM = static_cast<SVGStyledLocatableElement*>(parentElement)->getCTM();
ctm = parentCTM * ctm;
AffineTransform ctm;
Node* parent = element->parentNode();
- if (parent && parent->isElementNode()) {
- SVGElement* parentElement = svg_dynamic_cast(parent);
+ if (parent && parent->isSVGElement()) {
+ SVGElement* parentElement = static_cast<SVGElement*>(parent);
if (parentElement && parentElement->isStyledLocatable()) {
AffineTransform parentCTM = static_cast<SVGStyledLocatableElement*>(parentElement)->getScreenCTM();
ctm = parentCTM * ctm;
if (!m_marker)
m_marker = new SVGResourceMarker();
- m_marker->setMarker(static_cast<RenderSVGContainer*>(renderer()));
+ m_marker->setMarker(static_cast<RenderSVGViewportContainer*>(renderer()));
// Spec: If the attribute is not specified, the effect is as if a
// value of "0" were specified.
if (!m_marker || !attached() || document()->parsing())
return;
- RenderSVGContainer* markerContainer = static_cast<RenderSVGContainer*>(renderer());
+ RenderSVGViewportContainer* markerContainer = static_cast<RenderSVGViewportContainer*>(renderer());
// NOTE: This is a typical case, where proper "attributeChanged" usage would reduce the number of updates needed.
if (markerContainer)
void SVGSVGElement::setCurrentTranslate(const FloatPoint &translation)
{
m_translation = translation;
- if (parentNode() == document())
+ if (parentNode() == document() && document()->renderer())
document()->renderer()->repaint();
}
protected:
virtual const SVGElement* contextElement() const { return this; }
- friend class RenderSVGContainer;
friend class RenderSVGRoot;
friend class RenderSVGViewportContainer;
#include "Document.h"
#include "HTMLNames.h"
#include "PlatformString.h"
-#include "RenderPath.h"
#include "SVGElement.h"
#include "SVGElementInstance.h"
#include "SVGNames.h"
+#include "RenderObject.h"
#include "SVGRenderStyle.h"
#include "SVGResource.h"
#include "SVGSVGElement.h"
bool SVGStyledElement::rendererIsNeeded(RenderStyle* style)
{
+ // http://www.w3.org/TR/SVG/extend.html#PrivateData
+ // Prevent anything other than SVG renderers from appearing in our render tree
+ // Spec: SVG allows inclusion of elements from foreign namespaces anywhere
+ // with the SVG content. In general, the SVG user agent will include the unknown
+ // elements in the DOM but will otherwise ignore unknown elements.
if (!parentNode() || parentNode()->isSVGElement())
return StyledElement::rendererIsNeeded(style);
return false;
}
-RenderObject* SVGStyledElement::createRenderer(RenderArena* arena, RenderStyle* style)
-{
- // The path data is set upon the first layout() call.
- return new (arena) RenderPath(style, this);
-}
-
static inline void mapAttributeToCSSProperty(HashMap<AtomicStringImpl*, int>* propertyNameToIdMap, const QualifiedName& attrName, const char* cssPropertyName = 0)
{
int propertyId = 0;
if (node->hasTagName(SVGNames::linearGradientTag) || node->hasTagName(SVGNames::radialGradientTag) ||
node->hasTagName(SVGNames::patternTag) || node->hasTagName(SVGNames::clipPathTag) ||
node->hasTagName(SVGNames::markerTag) || node->hasTagName(SVGNames::maskTag)) {
- SVGElement* element = svg_dynamic_cast(node);
- ASSERT(element);
-
- element->notifyAttributeChange();
+ static_cast<SVGElement*>(node)->notifyAttributeChange();
}
node = node->parentNode();
class RenderPath;
- class SVGStyledElement : public SVGElement {
+ class SVGStyledElement : public SVGElement, public SVGStylable {
public:
SVGStyledElement(const QualifiedName&, Document*);
virtual ~SVGStyledElement();
// 'SVGStylable' functions
virtual PassRefPtr<CSSValue> getPresentationAttribute(const String& name);
+ virtual CSSStyleDeclaration* style() { return StyledElement::style(); }
- // These need to be implemented.
virtual bool rendererIsNeeded(RenderStyle*);
- virtual Path toPathData() const { return Path(); }
- virtual RenderObject* createRenderer(RenderArena*, RenderStyle*);
virtual SVGResource* canvasResource() { return 0; }
virtual bool mapToEntry(const QualifiedName&, MappedAttributeEntry&) const;
ANIMATED_PROPERTY_DEFINITIONS(SVGStyledTransformableElement, SVGTransformList*, TransformList, transformList, Transform, transform, SVGNames::transformAttr.localName(), m_transform.get())
-AffineTransform SVGStyledTransformableElement::localMatrix() const
-{
- return m_localMatrix;
-}
-
AffineTransform SVGStyledTransformableElement::getCTM() const
{
return SVGTransformable::getCTM(this);
return SVGTransformable::getScreenCTM(this);
}
-void SVGStyledTransformableElement::updateLocalTransform(SVGTransformList* localTransforms)
+AffineTransform SVGStyledTransformableElement::animatedLocalTransform() const
{
- SVGTransform localTransform = localTransforms->concatenate();
- if (localTransform.matrix() == m_localMatrix)
- return;
-
- m_localMatrix = localTransform.matrix();
- if (renderer()) {
- renderer()->setLocalTransform(m_localMatrix);
- renderer()->setNeedsLayout(true);
- }
+ return transform()->concatenate().matrix();
}
void SVGStyledTransformableElement::parseMappedAttribute(MappedAttribute* attr)
if (!SVGTransformable::parseTransformAttribute(localTransforms, attr->value()))
localTransforms->clear(ec);
- else
- updateLocalTransform(localTransforms);
+ else {
+ setTransformBaseValue(localTransforms);
+ if (renderer())
+ renderer()->setNeedsLayout(true); // should really be in setTransform
+ }
} else
SVGStyledLocatableElement::parseMappedAttribute(attr);
}
return SVGTransformable::getBBox(this);
}
-void SVGStyledTransformableElement::attach()
+void SVGStyledTransformableElement::notifyAttributeChange() const
{
- SVGStyledElement::attach();
-
- if (renderer() && !m_localMatrix.isIdentity())
- renderer()->setLocalTransform(m_localMatrix);
+ if (renderer())
+ renderer()->setNeedsLayout(true);
+ SVGStyledLocatableElement::notifyAttributeChange();
}
-void SVGStyledTransformableElement::notifyAttributeChange() const
+RenderObject* SVGStyledTransformableElement::createRenderer(RenderArena* arena, RenderStyle* style)
{
- // FIXME: We should cache this, and only update if needed. The whole nAC() concept, should be
- // switched to something similar like attributeChanged(), but specific to SVG DOM. (Niko)
- const_cast<SVGStyledTransformableElement*>(this)->updateLocalTransform(transform());
- SVGStyledLocatableElement::notifyAttributeChange();
+ // By default, any subclass is expected to do path-based drawing
+ return new (arena) RenderPath(style, this);
}
}
virtual bool isStyledTransformable() const { return true; }
- // 'SVGTransformable' functions
- virtual AffineTransform localMatrix() const;
-
// Derived from: 'SVGLocatable'
virtual AffineTransform getCTM() const;
virtual AffineTransform getScreenCTM() const;
virtual SVGElement* nearestViewportElement() const;
virtual SVGElement* farthestViewportElement() const;
+
+ virtual AffineTransform animatedLocalTransform() const;
virtual FloatRect getBBox() const;
virtual void parseMappedAttribute(MappedAttribute*);
-
- void updateLocalTransform(SVGTransformList*);
- virtual void attach();
+ // "base class" methods for all the elements which render as paths
+ virtual Path toPathData() const { return Path(); }
+ virtual RenderObject* createRenderer(RenderArena*, RenderStyle*);
+
virtual void notifyAttributeChange() const;
protected:
- mutable AffineTransform m_localMatrix;
ANIMATED_PROPERTY_DECLARATIONS(SVGStyledTransformableElement, SVGTransformList*, RefPtr<SVGTransformList>, Transform, transform)
};
#if ENABLE(SVG)
#include "SVGSwitchElement.h"
-#include "RenderSVGContainer.h"
+#include "RenderSVGTransformableContainer.h"
#include "SVGNames.h"
namespace WebCore {
RenderObject* SVGSwitchElement::createRenderer(RenderArena* arena, RenderStyle*)
{
- return new (arena) RenderSVGContainer(this);
+ return new (arena) RenderSVGTransformableContainer(this);
}
}
void SVGTRefElement::updateReferencedText()
{
- Element* targetElement = ownerDocument()->getElementById(SVGURIReference::getTarget(href()));
- SVGElement* target = svg_dynamic_cast(targetElement);
- if (target) {
- ExceptionCode ignore = 0;
- setTextContent(target->textContent(), ignore);
- }
-}
-
-void SVGTRefElement::attributeChanged(Attribute* attr, bool preserveDecls)
-{
- if (attr->name().matches(XLinkNames::hrefAttr))
- updateReferencedText();
-
- SVGTextPositioningElement::attributeChanged(attr, preserveDecls);
+ Element* target = document()->getElementById(SVGURIReference::getTarget(href()));
+ String textContent;
+ if (target && target->isSVGElement())
+ textContent = static_cast<SVGElement*>(target)->textContent();
+ ExceptionCode ignore = 0;
+ setTextContent(textContent, ignore);
}
void SVGTRefElement::parseMappedAttribute(MappedAttribute* attr)
SVGTRefElement(const QualifiedName&, Document*);
virtual ~SVGTRefElement();
- virtual void attributeChanged(Attribute* attr, bool preserveDecls);
virtual void parseMappedAttribute(MappedAttribute*);
virtual RenderObject* createRenderer(RenderArena*, RenderStyle*);
ANIMATED_PROPERTY_DEFINITIONS(SVGTextElement, SVGTransformList*, TransformList, transformList, Transform, transform, SVGNames::transformAttr.localName(), m_transform.get())
-AffineTransform SVGTextElement::localMatrix() const
-{
- return m_localMatrix;
-}
-
void SVGTextElement::parseMappedAttribute(MappedAttribute* attr)
{
if (attr->name() == SVGNames::transformAttr) {
if (!SVGTransformable::parseTransformAttribute(localTransforms, attr->value()))
localTransforms->clear(ec);
- else
- updateLocalTransform(localTransforms);
+ else {
+ setTransformBaseValue(localTransforms);
+ if (renderer())
+ renderer()->setNeedsLayout(true); // should be in setTransformBaseValue
+ }
} else
SVGTextPositioningElement::parseMappedAttribute(attr);
}
-void SVGTextElement::updateLocalTransform(SVGTransformList* localTransforms)
-{
- // Update cached local matrix
- SVGTransform localTransform = localTransforms->concatenate();
- if (localTransform.isValid()) {
- m_localMatrix = localTransform.matrix();
- if (renderer()) {
- renderer()->setLocalTransform(m_localMatrix);
- renderer()->setNeedsLayout(true);
- }
- }
-}
-
-void SVGTextElement::attach()
-{
- SVGStyledElement::attach();
-
- if (renderer() && !m_localMatrix.isIdentity())
- renderer()->setLocalTransform(m_localMatrix);
-}
-
SVGElement* SVGTextElement::nearestViewportElement() const
{
return SVGTransformable::nearestViewportElement(this);
return SVGTransformable::getCTM(this);
}
+AffineTransform SVGTextElement::animatedLocalTransform() const
+{
+ return transform()->concatenate().matrix();
+}
+
RenderObject* SVGTextElement::createRenderer(RenderArena* arena, RenderStyle* style)
{
return new (arena) RenderSVGText(this);
virtual FloatRect getBBox() const;
virtual AffineTransform getCTM() const;
virtual AffineTransform getScreenCTM() const;
+ virtual AffineTransform animatedLocalTransform() const;
virtual RenderObject* createRenderer(RenderArena*, RenderStyle*);
virtual bool childShouldCreateRenderer(Node*) const;
- virtual void attach();
- virtual AffineTransform localMatrix() const;
-
- virtual void updateLocalTransform(SVGTransformList*);
-
+
protected:
virtual const SVGElement* contextElement() const { return this; }
attach();
}
-void SVGTextPathElement::attach()
-{
- SVGStyledElement::attach();
-
- if (!renderer())
- return;
-
- String id = SVGURIReference::getTarget(href());
- Element* targetElement = ownerDocument()->getElementById(id);
- ASSERT(targetElement);
-
- if (!targetElement->hasTagName(SVGNames::pathTag))
- return;
-
- SVGPathElement* pathElement = static_cast<SVGPathElement*>(targetElement);
-
- RenderSVGTextPath* textPath = static_cast<RenderSVGTextPath*>(renderer());
- ASSERT(textPath);
-
- textPath->setStartOffset(m_startOffset.valueAsPercentage());
- textPath->setExactAlignment(m_method == SVG_TEXTPATH_SPACINGTYPE_EXACT);
- textPath->setStretchMethod(m_spacing == SVG_TEXTPATH_METHODTYPE_STRETCH);
-
- // TODO: Catch transform updates :-)
- Path pathData = pathElement->toPathData();
- pathData.transform(pathElement->localMatrix());
- textPath->setLayoutPath(pathData);
-}
-
}
#endif // ENABLE(SVG)
virtual void insertedIntoDocument();
virtual void buildPendingResource();
- virtual void attach();
-
virtual void parseMappedAttribute(MappedAttribute* attr);
virtual bool rendererIsNeeded(RenderStyle* style) { return StyledElement::rendererIsNeeded(style); }
virtual RenderObject* createRenderer(RenderArena*, RenderStyle*);
AffineTransform SVGTransformable::getCTM(const SVGElement* element) const
{
AffineTransform ctm = SVGLocatable::getCTM(element);
- return localMatrix() * ctm;
+ return animatedLocalTransform() * ctm;
}
AffineTransform SVGTransformable::getScreenCTM(const SVGElement* element) const
{
AffineTransform ctm = SVGLocatable::getScreenCTM(element);
- return localMatrix() * ctm;
+ return animatedLocalTransform() * ctm;
}
int parseTransformParamList(const UChar*& ptr, const UChar* end, double* values, int required, int optional)
SVGTransformable();
virtual ~SVGTransformable();
- // 'SVGTransformable' functions
- virtual AffineTransform localMatrix() const = 0;
-
- virtual void updateLocalTransform(SVGTransformList*) = 0;
-
static bool parseTransformAttribute(SVGTransformList*, const AtomicString& transform);
static bool parseTransformAttribute(SVGTransformList*, const UChar*& ptr, const UChar* end);
static bool parseTransformValue(unsigned type, const UChar*& ptr, const UChar* end, SVGTransform&);
+
AffineTransform getCTM(const SVGElement*) const;
AffineTransform getScreenCTM(const SVGElement*) const;
+
+ virtual AffineTransform animatedLocalTransform() const = 0;
};
} // namespace WebCore
#include "Document.h"
#include "Event.h"
#include "HTMLNames.h"
-#include "RenderSVGContainer.h"
+#include "RenderSVGTransformableContainer.h"
#include "SVGElementInstance.h"
#include "SVGElementInstanceList.h"
#include "SVGGElement.h"
RenderObject* SVGUseElement::createRenderer(RenderArena* arena, RenderStyle*)
{
- return new (arena) RenderSVGContainer(this);
+ return new (arena) RenderSVGTransformableContainer(this);
}
void SVGUseElement::attach()
if (RenderObject* shadowRenderer = m_shadowTreeRootElement->renderer()) {
shadowRenderer->setStyle(style);
renderer()->addChild(shadowRenderer, m_shadowTreeRootElement->nextRenderer());
-
- // Mimic SVGStyledTransformableElement::attach() functionality
- SVGGElement* gElement = static_cast<SVGGElement*>(m_shadowTreeRootElement.get());
- shadowRenderer->setLocalTransform(gElement->localMatrix());
-
m_shadowTreeRootElement->setAttached();
}
}
#endif
bool operator==(const AffineTransform&) const;
+ bool operator!=(const AffineTransform& other) const { return !(*this == other); }
AffineTransform& operator*=(const AffineTransform&);
AffineTransform operator*(const AffineTransform&);
#include "AffineTransform.h"
#include "GraphicsContext.h"
-#include "RenderSVGContainer.h"
+#include "RenderSVGViewportContainer.h"
#include "TextStream.h"
namespace WebCore {
{
}
-void SVGResourceMarker::setMarker(RenderSVGContainer* marker)
+void SVGResourceMarker::setMarker(RenderSVGViewportContainer* marker)
{
m_marker = marker;
}
namespace WebCore {
class GraphicsContext;
- class RenderSVGContainer;
+ class RenderSVGViewportContainer;
class SVGResourceMarker : public SVGResource {
public:
SVGResourceMarker();
virtual ~SVGResourceMarker();
- void setMarker(RenderSVGContainer*);
+ void setMarker(RenderSVGViewportContainer*);
void setRef(double refX, double refY);
double refX() const { return m_refX; }
double m_refX, m_refY;
FloatRect m_cachedBounds;
float m_angle;
- RenderSVGContainer* m_marker;
+ RenderSVGViewportContainer* m_marker;
bool m_useStrokeWidth;
};
#include "RenderView.h"
#include "SVGForeignObjectElement.h"
#include "SVGLength.h"
+#include "SVGTransformList.h"
namespace WebCore {
return false;
}
+bool RenderForeignObject::calculateLocalTransform()
+{
+ AffineTransform oldTransform = m_localTransform;
+ m_localTransform = static_cast<SVGForeignObjectElement*>(element())->animatedLocalTransform();
+ return (oldTransform != m_localTransform);
+}
+
void RenderForeignObject::layout()
{
ASSERT(needsLayout());
oldBounds = m_absoluteBounds;
oldOutlineBox = absoluteOutlineBox();
}
-
+
+ calculateLocalTransform();
+
RenderBlock::layout();
m_absoluteBounds = absoluteClippedOverflowRect();
virtual void paint(PaintInfo&, int parentX, int parentY);
- virtual AffineTransform localTransform() const { return m_transform; }
- virtual void setLocalTransform(const AffineTransform& transform) { m_transform = transform; }
+ virtual AffineTransform localTransform() const { return m_localTransform; }
+ virtual bool calculateLocalTransform();
virtual void computeAbsoluteRepaintRect(IntRect&, bool fixed);
virtual bool requiresLayer();
private:
AffineTransform translationForAttributes();
- AffineTransform m_transform;
+ AffineTransform m_localTransform;
IntRect m_absoluteBounds;
};
}
// minimum height
- m_height = m_cachedImage && m_cachedImage->errorOccurred() ? intrinsicSize().height() : 0;
+ m_height = errorOccurred() ? intrinsicSize().height() : 0;
calcWidth();
calcHeight();
protected:
Image* image() { return m_cachedImage ? m_cachedImage->image() : nullImage(); }
+
+ bool errorOccurred() const { return m_cachedImage && m_cachedImage->errorOccurred(); }
private:
int calcAspectRatioWidth() const;
bool isWidthSpecified() const;
bool isHeightSpecified() const;
- bool errorOccurred() const { return m_cachedImage && m_cachedImage->errorOccurred(); }
-
// The image we are rendering.
CachedImage* m_cachedImage;
return AffineTransform(1, 0, 0, 1, xPos(), yPos());
}
-void RenderObject::setLocalTransform(const AffineTransform&)
-{
- ASSERT(false);
-}
-
AffineTransform RenderObject::absoluteTransform() const
{
if (parent())
virtual FloatRect relativeBBox(bool includeStroke = true) const;
virtual AffineTransform localTransform() const;
- virtual void setLocalTransform(const AffineTransform&);
virtual AffineTransform absoluteTransform() const;
#endif
#include "SVGResourceFilter.h"
#include "SVGResourceMarker.h"
#include "SVGResourceMasker.h"
-#include "SVGStyledElement.h"
+#include "SVGStyledTransformableElement.h"
+#include "SVGTransformList.h"
#include "SVGURIReference.h"
#include <wtf/MathExtras.h>
namespace WebCore {
// RenderPath
-RenderPath::RenderPath(RenderStyle* style, SVGStyledElement* node)
+RenderPath::RenderPath(RenderStyle* style, SVGStyledTransformableElement* node)
: RenderObject(node)
{
ASSERT(style != 0);
+ ASSERT(static_cast<SVGElement*>(node)->isStyledTransformable());
}
RenderPath::~RenderPath()
AffineTransform RenderPath::localTransform() const
{
- return m_matrix;
-}
-
-void RenderPath::setLocalTransform(const AffineTransform& matrix)
-{
- m_matrix = matrix;
+ return m_localTransform;
}
FloatPoint RenderPath::mapAbsolutePointToLocal(const FloatPoint& point) const
return m_path;
}
+bool RenderPath::calculateLocalTransform()
+{
+ AffineTransform oldTransform = m_localTransform;
+ m_localTransform = static_cast<SVGStyledTransformableElement*>(element())->animatedLocalTransform();
+ return (m_localTransform != oldTransform);
+}
+
void RenderPath::layout()
{
IntRect oldBounds;
oldBounds = m_absoluteBounds;
oldOutlineBox = absoluteOutlineBox();
}
+
+ calculateLocalTransform();
- setPath(static_cast<SVGStyledElement*>(element())->toPathData());
+ setPath(static_cast<SVGStyledTransformableElement*>(element())->toPathData());
m_absoluteBounds = absoluteClippedOverflowRect();
if ((paintInfo.phase == PaintPhaseOutline || paintInfo.phase == PaintPhaseSelfOutline) && style()->outlineWidth())
paintOutline(paintInfo.context, boundingBox.x(), boundingBox.y(), boundingBox.width(), boundingBox.height(), style());
-
+
paintInfo.context->restore();
}
class FloatPoint;
class Path;
class RenderSVGContainer;
-class SVGStyledElement;
+class SVGStyledTransformableElement;
class RenderPath : public RenderObject
{
public:
- RenderPath(RenderStyle* style, SVGStyledElement *node);
+ RenderPath(RenderStyle*, SVGStyledTransformableElement*);
virtual ~RenderPath();
// Hit-detection seperated for the fill and the stroke
virtual bool isRenderPath() const { return true; }
virtual const char* renderName() const { return "RenderPath"; }
+ bool calculateLocalTransform();
virtual AffineTransform localTransform() const;
- virtual void setLocalTransform(const AffineTransform& matrix);
virtual void layout();
virtual IntRect absoluteClippedOverflowRect();
mutable FloatRect m_fillBBox;
mutable FloatRect m_strokeBbox;
FloatRect m_markerBounds;
- AffineTransform m_matrix;
+ AffineTransform m_localTransform;
IntRect m_absoluteBounds;
};
AffineTransform RenderSVGContainer::localTransform() const
{
- return m_matrix;
-}
-
-void RenderSVGContainer::setLocalTransform(const AffineTransform& matrix)
-{
- m_matrix = matrix;
+ return m_localTransform;
}
bool RenderSVGContainer::requiresLayer()
return height() + marginTop() + marginBottom();
}
+bool RenderSVGContainer::calculateLocalTransform()
+{
+ // subclasses can override this to add transform support
+ return false;
+}
+
void RenderSVGContainer::layout()
{
ASSERT(needsLayout());
oldBounds = m_absoluteBounds;
oldOutlineBox = absoluteOutlineBox();
}
+
+ calculateLocalTransform();
for (RenderObject* child = firstChild(); child; child = child->nextSibling()) {
// Only force our kids to layout if we're being asked to relayout as a result of a parent changing
- // FIXME: We should be able to skip relayout of non-relative kids when only bounds have changed
- // however, we can't tell the difference between bounds changing and transform changing.
+ // FIXME: We should be able to skip relayout of non-relative kids when only bounds size has changed
+ // that's a possible future optimization using LayoutState
// http://bugs.webkit.org/show_bug.cgi?id=15391
if (selfNeedsLayout())
child->setNeedsLayout(true);
FloatRect relativeBBox(bool includeStroke = true) const;
+ virtual bool calculateLocalTransform();
virtual AffineTransform localTransform() const;
- void setLocalTransform(const AffineTransform&);
-
virtual AffineTransform viewportTransform() const;
virtual bool nodeAtPoint(const HitTestRequest&, HitTestResult&, int x, int y, int tx, int ty, HitTestAction);
bool selfWillPaint() const;
bool m_drawsContents : 1;
-
+
+protected:
IntRect m_absoluteBounds;
-
- AffineTransform m_matrix;
+ AffineTransform m_localTransform;
};
} // namespace WebCore
}
}
+bool RenderSVGImage::calculateLocalTransform()
+{
+ AffineTransform oldTransform = m_localTransform;
+ m_localTransform = static_cast<SVGStyledTransformableElement*>(element())->animatedLocalTransform();
+ return (m_localTransform != oldTransform);
+}
+
+void RenderSVGImage::layout()
+{
+ ASSERT(needsLayout());
+
+ IntRect oldBounds;
+ IntRect oldOutlineBox;
+ bool checkForRepaint = checkForRepaintDuringLayout();
+ if (checkForRepaint) {
+ oldBounds = absoluteClippedOverflowRect();
+ oldOutlineBox = absoluteOutlineBox();
+ }
+
+ calculateLocalTransform();
+
+ // minimum height
+ m_height = errorOccurred() ? intrinsicSize().height() : 0;
+
+ calcWidth();
+ calcHeight();
+
+ if (checkForRepaint)
+ repaintAfterLayoutIfNeeded(oldBounds, oldOutlineBox);
+
+ setNeedsLayout(false);
+}
+
void RenderSVGImage::paint(PaintInfo& paintInfo, int, int)
{
if (paintInfo.context->paintingDisabled() || style()->visibility() == HIDDEN)
void RenderSVGImage::addFocusRingRects(GraphicsContext* graphicsContext, int tx, int ty)
{
- graphicsContext->addFocusRingRect(m_absoluteBounds);
+ // this is called from paint() after the localTransform has already been applied
+ IntRect contentRect = enclosingIntRect(relativeBBox());
+ graphicsContext->addFocusRingRect(contentRect);
}
void RenderSVGImage::absoluteRects(Vector<IntRect>& rects, int, int, bool)
RenderSVGImage(SVGImageElement*);
virtual ~RenderSVGImage();
- virtual AffineTransform localTransform() const { return m_transform; }
- virtual void setLocalTransform(const AffineTransform& transform) { m_transform = transform; }
+ virtual AffineTransform localTransform() const { return m_localTransform; }
virtual FloatRect relativeBBox(bool includeStroke = true) const;
virtual IntRect absoluteClippedOverflowRect();
virtual void imageChanged(CachedImage*);
void adjustRectsForAspectRatio(FloatRect& destRect, FloatRect& srcRect, SVGPreserveAspectRatio*);
+
+ virtual void layout();
virtual void paint(PaintInfo&, int parentX, int parentY);
bool requiresLayer();
virtual void calcWidth();
virtual void calcHeight();
+ bool calculateLocalTransform();
private:
AffineTransform translationForAttributes();
- AffineTransform m_transform;
- IntRect m_absoluteBounds;
+ AffineTransform m_localTransform;
float m_imageWidth;
float m_imageHeight;
};
#include "SVGResourceFilter.h"
#include "SVGRootInlineBox.h"
#include "SVGTextElement.h"
+#include "SVGTransformList.h"
#include "SVGURIReference.h"
namespace WebCore {
return false;
}
+bool RenderSVGText::calculateLocalTransform()
+{
+ AffineTransform oldTransform = m_localTransform;
+ m_localTransform = static_cast<SVGTextElement*>(element())->animatedLocalTransform();
+ return (oldTransform != m_localTransform);
+}
+
void RenderSVGText::layout()
{
ASSERT(needsLayout());
int xOffset = (int)(text->x()->getFirst().value());
int yOffset = (int)(text->y()->getFirst().value());
setPos(xOffset, yOffset);
+
+ calculateLocalTransform();
RenderBlock::layout();
virtual const char* renderName() const { return "RenderSVGText"; }
- virtual AffineTransform localTransform() const { return m_transform; }
- virtual void setLocalTransform(const AffineTransform& transform) { m_transform = transform; }
+ virtual bool isSVGText() const { return true; }
+
+ bool calculateLocalTransform();
+ virtual AffineTransform localTransform() const { return m_localTransform; }
+
virtual void paint(PaintInfo&, int tx, int ty);
virtual bool nodeAtPoint(const HitTestRequest&, HitTestResult&, int x, int y, int tx, int ty, HitTestAction);
- virtual void absoluteRects(Vector<IntRect>&, int tx, int ty, bool topLevel = true);
- virtual IntRect absoluteClippedOverflowRect();
+
virtual bool requiresLayer();
virtual void layout();
+
+ virtual void absoluteRects(Vector<IntRect>&, int tx, int ty, bool topLevel = true);
+ virtual IntRect absoluteClippedOverflowRect();
virtual FloatRect relativeBBox(bool includeStroke = true) const;
+
virtual InlineBox* createInlineBox(bool makePlaceHolderBox, bool isRootLineBox, bool isOnlyRun = false);
- virtual bool isSVGText() const { return true; }
private:
- AffineTransform m_transform;
+ AffineTransform m_localTransform;
IntRect m_absoluteBounds;
};
#include "FloatRect.h"
#include "SVGInlineTextBox.h"
+#include "SVGPathElement.h"
#include "SVGRootInlineBox.h"
+#include "SVGTextPathElement.h"
+#include "SVGTransformList.h"
namespace WebCore {
Path RenderSVGTextPath::layoutPath() const
{
- return m_layoutPath;
-}
-
-void RenderSVGTextPath::setLayoutPath(const Path& path)
-{
- m_layoutPath = path;
+ SVGTextPathElement* textPathElement = static_cast<SVGTextPathElement*>(element());
+ String pathId = SVGURIReference::getTarget(textPathElement->href());
+ Element* targetElement = textPathElement->document()->getElementById(pathId);
+ if (!targetElement || !targetElement->hasTagName(SVGNames::pathTag))
+ return Path();
+
+ SVGPathElement* pathElement = static_cast<SVGPathElement*>(targetElement);
+
+ Path pathData = pathElement->toPathData();
+ // Spec: The transform attribute on the referenced 'path' element represents a
+ // supplemental transformation relative to the current user coordinate system for
+ // the current 'text' element, including any adjustments to the current user coordinate
+ // system due to a possible transform attribute on the current 'text' element.
+ // http://www.w3.org/TR/SVG/text.html#TextPathElement
+ pathData.transform(pathElement->animatedLocalTransform());
+ return pathData;
}
float RenderSVGTextPath::startOffset() const
{
- return m_startOffset;
-}
-
-void RenderSVGTextPath::setStartOffset(float offset)
-{
- m_startOffset = offset;
+ return static_cast<SVGTextPathElement*>(element())->startOffset().valueAsPercentage();
}
bool RenderSVGTextPath::exactAlignment() const
{
- return m_exactAlignment;
-}
-
-void RenderSVGTextPath::setExactAlignment(bool value)
-{
- m_exactAlignment = value;
+ return static_cast<SVGTextPathElement*>(element())->spacing() == SVG_TEXTPATH_SPACINGTYPE_EXACT;
}
bool RenderSVGTextPath::stretchMethod() const
{
- return m_stretchMethod;
-}
-
-void RenderSVGTextPath::setStretchMethod(bool value)
-{
- m_stretchMethod = value;
+ return static_cast<SVGTextPathElement*>(element())->method() == SVG_TEXTPATH_METHODTYPE_STRETCH;
}
void RenderSVGTextPath::absoluteRects(Vector<IntRect>& rects, int, int)
RenderSVGTextPath(Node*);
Path layoutPath() const;
- void setLayoutPath(const Path&);
-
float startOffset() const;
- void setStartOffset(float);
-
bool exactAlignment() const;
- void setExactAlignment(bool);
-
bool stretchMethod() const;
- void setStretchMethod(bool);
virtual const char* renderName() const { return "RenderSVGTextPath"; }
virtual void absoluteRects(Vector<IntRect>& rects, int tx, int ty);
--- /dev/null
+/*
+ Copyright (C) 2004, 2005 Nikolas Zimmermann <wildfox@kde.org>
+ 2004, 2005, 2006 Rob Buis <buis@kde.org>
+
+ This file is part of the KDE project
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Library General Public
+ License as published by the Free Software Foundation; either
+ version 2 of the License, or (at your option) any later version.
+
+ This library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Library General Public License for more details.
+
+ You should have received a copy of the GNU Library General Public License
+ along with this library; see the file COPYING.LIB. If not, write to
+ the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ Boston, MA 02110-1301, USA.
+ */
+
+#include "config.h"
+#if ENABLE(SVG)
+
+#include "RenderSVGTransformableContainer.h"
+
+#include "SVGStyledTransformableElement.h"
+#include "SVGTransformList.h"
+
+namespace WebCore {
+
+RenderSVGTransformableContainer::RenderSVGTransformableContainer(SVGStyledTransformableElement* node)
+ : RenderSVGContainer(node)
+{
+}
+
+bool RenderSVGTransformableContainer::calculateLocalTransform()
+{
+ AffineTransform oldTransform = m_localTransform;
+ m_localTransform = static_cast<SVGStyledTransformableElement*>(element())->animatedLocalTransform();
+ return (m_localTransform != oldTransform);
+}
+
+}
+
+#endif // ENABLE(SVG)
--- /dev/null
+/*
+ Copyright (C) 2007 Eric Seidel <eric@webkit.org
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Library General Public
+ License as published by the Free Software Foundation; either
+ version 2 of the License, or (at your option) any later version.
+
+ This library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Library General Public License for more details.
+
+ You should have received a copy of the GNU Library General Public License
+ aint with this library; see the file COPYING.LIB. If not, write to
+ the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ Boston, MA 02111-1307, USA.
+ */
+
+
+#ifndef RenderSVGTransformableContainer_h
+#define RenderSVGTransformableContainer_h
+
+#if ENABLE(SVG)
+#include "RenderSVGContainer.h"
+
+namespace WebCore {
+
+ class SVGStyledTransformableElement;
+ class RenderSVGTransformableContainer : public RenderSVGContainer {
+ public:
+ RenderSVGTransformableContainer(SVGStyledTransformableElement*);
+
+ virtual bool calculateLocalTransform();
+ };
+}
+
+#endif // ENABLE(SVG)
+#endif // RenderSVGTransformableContainer_h
virtual void applyContentTransforms(PaintInfo&);
virtual void applyAdditionalTransforms(PaintInfo&);
-
- AffineTransform m_matrix;
FloatRect m_viewport;
- IntRect m_absoluteBounds;
};
} // namespace WebCore