Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / third_party / WebKit / Source / core / rendering / svg / RenderSVGResourceContainer.cpp
index 5d04e5a..53dcdfc 100644 (file)
  */
 
 #include "config.h"
-
 #include "core/rendering/svg/RenderSVGResourceContainer.h"
 
 #include "core/rendering/RenderLayer.h"
-#include "core/rendering/RenderView.h"
-#include "core/rendering/svg/SVGRenderingContext.h"
+#include "core/rendering/svg/RenderSVGResourceClipper.h"
+#include "core/rendering/svg/RenderSVGResourceFilter.h"
+#include "core/rendering/svg/RenderSVGResourceMasker.h"
+#include "core/rendering/svg/SVGResources.h"
 #include "core/rendering/svg/SVGResourcesCache.h"
-#include "core/svg/SVGGraphicsElement.h"
 
 #include "wtf/TemporaryChange.h"
 
@@ -121,7 +121,7 @@ void RenderSVGResourceContainer::markAllClientsForInvalidation(InvalidationMode
         if (markForInvalidation)
             markClientForInvalidation(client, mode);
 
-        RenderSVGResource::markForLayoutAndParentResourceInvalidation(client, needsLayout);
+        RenderSVGResourceContainer::markForLayoutAndParentResourceInvalidation(client, needsLayout);
     }
 
     markAllClientLayersForInvalidation();
@@ -147,7 +147,7 @@ void RenderSVGResourceContainer::markClientForInvalidation(RenderObject* client,
         client->setNeedsBoundariesUpdate();
         break;
     case PaintInvalidation:
-        client->setShouldDoFullPaintInvalidation(true);
+        client->setShouldDoFullPaintInvalidation();
         break;
     case ParentOnlyInvalidation:
         break;
@@ -230,53 +230,70 @@ void RenderSVGResourceContainer::registerResource()
     }
 }
 
-static bool shouldTransformOnTextPainting(RenderObject* object, AffineTransform& resourceTransform)
+static inline void removeFromCacheAndInvalidateDependencies(RenderObject* object, bool needsLayout)
 {
     ASSERT(object);
+    if (SVGResources* resources = SVGResourcesCache::cachedResourcesForRenderObject(object)) {
+        if (RenderSVGResourceFilter* filter = resources->filter())
+            filter->removeClientFromCache(object);
 
-    // This method should only be called for RenderObjects that deal with text rendering. Cmp. RenderObject.h's is*() methods.
-    ASSERT(object->isSVGText() || object->isSVGTextPath() || object->isSVGInline());
-
-    // In text drawing, the scaling part of the graphics context CTM is removed, compare SVGInlineTextBox::paintTextWithShadows.
-    // So, we use that scaling factor here, too, and then push it down to pattern or gradient space
-    // in order to keep the pattern or gradient correctly scaled.
-    float scalingFactor = SVGRenderingContext::calculateScreenFontSizeScalingFactor(object);
-    if (scalingFactor == 1)
-        return false;
-    resourceTransform.scale(scalingFactor);
-    return true;
-}
+        if (RenderSVGResourceMasker* masker = resources->masker())
+            masker->removeClientFromCache(object);
 
-AffineTransform RenderSVGResourceContainer::computeResourceSpaceTransform(RenderObject* object, const AffineTransform& baseTransform, const SVGRenderStyle& svgStyle, unsigned short resourceMode)
-{
-    AffineTransform computedSpaceTransform = baseTransform;
-    if (resourceMode & ApplyToTextMode) {
-        // Depending on the font scaling factor, we may need to apply an
-        // additional transform (scale-factor) the paintserver, since text
-        // painting removes the scale factor from the context. (See
-        // SVGInlineTextBox::paintTextWithShadows.)
-        AffineTransform additionalTextTransformation;
-        if (shouldTransformOnTextPainting(object, additionalTextTransformation))
-            computedSpaceTransform = additionalTextTransformation * computedSpaceTransform;
+        if (RenderSVGResourceClipper* clipper = resources->clipper())
+            clipper->removeClientFromCache(object);
     }
-    if (resourceMode & ApplyToStrokeMode) {
-        // Non-scaling stroke needs to reset the transform back to the host transform.
-        if (svgStyle.vectorEffect() == VE_NON_SCALING_STROKE)
-            computedSpaceTransform = transformOnNonScalingStroke(object, computedSpaceTransform);
+
+    if (!object->node() || !object->node()->isSVGElement())
+        return;
+    SVGElementSet* dependencies = toSVGElement(object->node())->setOfIncomingReferences();
+    if (!dependencies)
+        return;
+
+    // We allow cycles in SVGDocumentExtensions reference sets in order to avoid expensive
+    // reference graph adjustments on changes, so we need to break possible cycles here.
+    // This strong reference is safe, as it is guaranteed that this set will be emptied
+    // at the end of recursion.
+    typedef WillBeHeapHashSet<RawPtrWillBeMember<SVGElement> > SVGElementSet;
+    DEFINE_STATIC_LOCAL(OwnPtrWillBePersistent<SVGElementSet>, invalidatingDependencies, (adoptPtrWillBeNoop(new SVGElementSet)));
+
+    SVGElementSet::iterator end = dependencies->end();
+    for (SVGElementSet::iterator it = dependencies->begin(); it != end; ++it) {
+        if (RenderObject* renderer = (*it)->renderer()) {
+            if (UNLIKELY(!invalidatingDependencies->add(*it).isNewEntry)) {
+                // Reference cycle: we are in process of invalidating this dependant.
+                continue;
+            }
+
+            RenderSVGResourceContainer::markForLayoutAndParentResourceInvalidation(renderer, needsLayout);
+            invalidatingDependencies->remove(*it);
+        }
     }
-    return computedSpaceTransform;
 }
 
-// FIXME: This does not belong here.
-AffineTransform RenderSVGResourceContainer::transformOnNonScalingStroke(RenderObject* object, const AffineTransform& resourceTransform)
+void RenderSVGResourceContainer::markForLayoutAndParentResourceInvalidation(RenderObject* object, bool needsLayout)
 {
-    if (!object->isSVGShape())
-        return resourceTransform;
+    ASSERT(object);
+    ASSERT(object->node());
+
+    if (needsLayout && !object->documentBeingDestroyed())
+        object->setNeedsLayoutAndFullPaintInvalidation();
+
+    removeFromCacheAndInvalidateDependencies(object, needsLayout);
+
+    // Invalidate resources in ancestor chain, if needed.
+    RenderObject* current = object->parent();
+    while (current) {
+        removeFromCacheAndInvalidateDependencies(current, needsLayout);
 
-    SVGGraphicsElement* element = toSVGGraphicsElement(object->node());
-    AffineTransform transform = element->getScreenCTM(SVGGraphicsElement::DisallowStyleUpdate);
-    transform *= resourceTransform;
-    return transform;
+        if (current->isSVGResourceContainer()) {
+            // This will process the rest of the ancestors.
+            toRenderSVGResourceContainer(current)->removeAllClientsFromCache();
+            break;
+        }
+
+        current = current->parent();
+    }
 }
 
 }