Bug 1245751 - Part 10: Allow href without xlink on SVG Gradient elements. draft
authorBoris Chiou <boris.chiou@gmail.com>
Thu, 07 Jul 2016 14:26:57 +0800
changeset 407861 6b2613479084dd04277569a7055f70a747eb4973
parent 407860 b8a2a9dc7b0b38e8ddcc0c2ecc1d791d2a170103
child 407862 bc5c68ea10fb547099dd973e9799e7868f20a429
push id28064
push userbmo:boris.chiou@gmail.com
push dateWed, 31 Aug 2016 04:26:14 +0000
bugs1245751
milestone51.0a1
Bug 1245751 - Part 10: Allow href without xlink on SVG Gradient elements. MozReview-Commit-ID: IjLtYNb7bZp
dom/svg/SVGGradientElement.cpp
dom/svg/SVGGradientElement.h
layout/svg/nsSVGGradientFrame.cpp
--- a/dom/svg/SVGGradientElement.cpp
+++ b/dom/svg/SVGGradientElement.cpp
@@ -36,18 +36,19 @@ nsSVGElement::EnumInfo SVGGradientElemen
     SVG_UNIT_TYPE_OBJECTBOUNDINGBOX
   },
   { &nsGkAtoms::spreadMethod,
     sSpreadMethodMap,
     SVG_SPREADMETHOD_PAD
   }
 };
 
-nsSVGElement::StringInfo SVGGradientElement::sStringInfo[1] =
+nsSVGElement::StringInfo SVGGradientElement::sStringInfo[2] =
 {
+  { &nsGkAtoms::href, kNameSpaceID_None, true },
   { &nsGkAtoms::href, kNameSpaceID_XLink, true }
 };
 
 //----------------------------------------------------------------------
 // Implementation
 
 SVGGradientElement::SVGGradientElement(already_AddRefed<mozilla::dom::NodeInfo>& aNodeInfo)
   : SVGGradientElementBase(aNodeInfo)
@@ -90,17 +91,19 @@ already_AddRefed<SVGAnimatedEnumeration>
 SVGGradientElement::SpreadMethod()
 {
   return mEnumAttributes[SPREADMETHOD].ToDOMAnimatedEnum(this);
 }
 
 already_AddRefed<SVGAnimatedString>
 SVGGradientElement::Href()
 {
-  return mStringAttributes[HREF].ToDOMAnimatedString(this);
+  return mStringAttributes[HREF].IsExplicitlySet()
+         ? mStringAttributes[HREF].ToDOMAnimatedString(this)
+         : mStringAttributes[XLINK_HREF].ToDOMAnimatedString(this);
 }
 
 //----------------------------------------------------------------------
 // nsIContent methods
 
 NS_IMETHODIMP_(bool)
 SVGGradientElement::IsAttributeMapped(const nsIAtom* name) const
 {
--- a/dom/svg/SVGGradientElement.h
+++ b/dom/svg/SVGGradientElement.h
@@ -69,19 +69,19 @@ protected:
   virtual EnumAttributesInfo GetEnumInfo() override;
   virtual StringAttributesInfo GetStringInfo() override;
 
   enum { GRADIENTUNITS, SPREADMETHOD };
   nsSVGEnum mEnumAttributes[2];
   static nsSVGEnumMapping sSpreadMethodMap[];
   static EnumInfo sEnumInfo[2];
 
-  enum { HREF };
-  nsSVGString mStringAttributes[1];
-  static StringInfo sStringInfo[1];
+  enum { HREF, XLINK_HREF };
+  nsSVGString mStringAttributes[2];
+  static StringInfo sStringInfo[2];
 
   // SVGGradientElement values
   nsAutoPtr<nsSVGAnimatedTransformList> mGradientTransform;
 };
 
 //---------------------Linear Gradients------------------------
 
 typedef SVGGradientElement SVGLinearGradientElementBase;
--- a/layout/svg/nsSVGGradientFrame.cpp
+++ b/layout/svg/nsSVGGradientFrame.cpp
@@ -63,17 +63,18 @@ nsSVGGradientFrame::AttributeChanged(int
                                      nsIAtom*        aAttribute,
                                      int32_t         aModType)
 {
   if (aNameSpaceID == kNameSpaceID_None &&
       (aAttribute == nsGkAtoms::gradientUnits ||
        aAttribute == nsGkAtoms::gradientTransform ||
        aAttribute == nsGkAtoms::spreadMethod)) {
     nsSVGEffects::InvalidateDirectRenderingObservers(this);
-  } else if (aNameSpaceID == kNameSpaceID_XLink &&
+  } else if ((aNameSpaceID == kNameSpaceID_XLink ||
+              aNameSpaceID == kNameSpaceID_None) &&
              aAttribute == nsGkAtoms::href) {
     // Blow away our reference, if any
     Properties().Delete(nsSVGEffects::HrefAsPaintingProperty());
     mNoHRefURI = false;
     // And update whoever references us
     nsSVGEffects::InvalidateDirectRenderingObservers(this);
   }
 
@@ -313,20 +314,29 @@ nsSVGGradientFrame::GetReferencedGradien
 {
   if (mNoHRefURI)
     return nullptr;
 
   nsSVGPaintingProperty *property =
     Properties().Get(nsSVGEffects::HrefAsPaintingProperty());
 
   if (!property) {
-    // Fetch our gradient element's xlink:href attribute
-    dom::SVGGradientElement*grad = static_cast<dom::SVGGradientElement*>(mContent);
+    // Fetch our gradient element's href or xlink:href attribute
+    dom::SVGGradientElement* grad =
+      static_cast<dom::SVGGradientElement*>(mContent);
     nsAutoString href;
-    grad->mStringAttributes[dom::SVGGradientElement::HREF].GetAnimValue(href, grad);
+    if (grad->mStringAttributes[dom::SVGGradientElement::HREF]
+          .IsExplicitlySet()) {
+      grad->mStringAttributes[dom::SVGGradientElement::HREF]
+        .GetAnimValue(href, grad);
+    } else {
+      grad->mStringAttributes[dom::SVGGradientElement::XLINK_HREF]
+        .GetAnimValue(href, grad);
+    }
+
     if (href.IsEmpty()) {
       mNoHRefURI = true;
       return nullptr; // no URL
     }
 
     // Convert href to an nsIURI
     nsCOMPtr<nsIURI> targetURI;
     nsCOMPtr<nsIURI> base = mContent->GetBaseURI();