Bug 1288812 - Part 1. Serialize just the fragment for local urls. draft
authorcku <cku@mozilla.com>
Sat, 06 Aug 2016 06:51:44 +0800
changeset 397806 1b464c8408b904aa677413736770096037d85202
parent 397720 ae849fc20f4e380a311c423cb1fc56313a442b39
child 397807 a1955f9a4b484696ba562123757b647242064f17
push id25408
push userbmo:cku@mozilla.com
push dateMon, 08 Aug 2016 11:18:40 +0000
bugs1288812
milestone51.0a1
Bug 1288812 - Part 1. Serialize just the fragment for local urls. MozReview-Commit-ID: 7FQ5hXgG3gg
layout/style/nsComputedDOMStyle.cpp
layout/style/nsComputedDOMStyle.h
--- a/layout/style/nsComputedDOMStyle.cpp
+++ b/layout/style/nsComputedDOMStyle.cpp
@@ -2143,17 +2143,17 @@ nsComputedDOMStyle::DoGetImageLayerImage
     //    For local references, there is no need to download any external
     //    resource, so Layer::mImage is not used.
     //    Instead, we store the local URI in one place -- on Layer::mSourceURI.
     //    Hence, we must serialize using mSourceURI (instead of
     //    SetValueToStyleImage()/mImage) in this case.
     if (aLayers.mLayers[i].mSourceURI.IsLocalRef()) {
       // This is how we represent a 'mask-image' reference for a local URI,
       // such as 'mask-image:url(#mymask)' or 'mask:url(#mymask)'
-      val->SetURI(aLayers.mLayers[i].mSourceURI.GetSourceURL());
+      SetValueToFragmentOrURL(&aLayers.mLayers[i].mSourceURI, val);
     } else {
       SetValueToStyleImage(image, val);
     }
 
     valueList->AppendCSSValue(val.forget());
   }
 
   return valueList.forget();
@@ -2382,16 +2382,38 @@ nsComputedDOMStyle::SetValueToPosition(
   SetValueToPositionCoord(aPosition.mXPosition, valX);
   aValueList->AppendCSSValue(valX.forget());
 
   RefPtr<nsROCSSPrimitiveValue> valY = new nsROCSSPrimitiveValue;
   SetValueToPositionCoord(aPosition.mYPosition, valY);
   aValueList->AppendCSSValue(valY.forget());
 }
 
+
+void
+nsComputedDOMStyle::SetValueToFragmentOrURL(
+    const FragmentOrURL* aFragmentOrURL,
+    nsROCSSPrimitiveValue* aValue)
+{
+  if (aFragmentOrURL->IsLocalRef()) {
+    nsString fragment;
+    aFragmentOrURL->GetSourceString(fragment);
+    fragment.Insert(u"url(\"", 0);
+    fragment.Append(u"\")");
+    aValue->SetString(fragment);
+  } else {
+    nsCOMPtr<nsIURI> url = aFragmentOrURL->GetSourceURL();
+    if (url) {
+      aValue->SetURI(url);
+    } else {
+      aValue->SetIdent(eCSSKeyword_none);
+    }
+  }
+}
+
 already_AddRefed<CSSValue>
 nsComputedDOMStyle::DoGetBackgroundPosition()
 {
   const nsStyleImageLayers& layers = StyleBackground()->mImage;
   return DoGetImageLayerPosition(layers);
 }
 
 already_AddRefed<CSSValue>
@@ -5555,22 +5577,19 @@ nsComputedDOMStyle::GetSVGPaintFor(bool 
     }
     case eStyleSVGPaintType_Color:
     {
       SetToRGBAColor(val, paint->mPaint.mColor);
       break;
     }
     case eStyleSVGPaintType_Server:
     {
-      // Bug 1288812 - we should only serialize fragment for local-ref URL.
       RefPtr<nsDOMCSSValueList> valueList = GetROCSSValueList(false);
       RefPtr<nsROCSSPrimitiveValue> fallback = new nsROCSSPrimitiveValue;
-      nsCOMPtr<nsIURI> paintServerURI =
-        paint->mPaint.mPaintServer->GetSourceURL();
-      val->SetURI(paintServerURI);
+      SetValueToFragmentOrURL(paint->mPaint.mPaintServer, val);
       SetToRGBAColor(fallback, paint->mFallbackColor);
 
       valueList->AppendCSSValue(val.forget());
       valueList->AppendCSSValue(fallback.forget());
       return valueList.forget();
     }
     case eStyleSVGPaintType_ContextFill:
     {
@@ -5598,53 +5617,35 @@ nsComputedDOMStyle::DoGetStroke()
 {
   return GetSVGPaintFor(false);
 }
 
 already_AddRefed<CSSValue>
 nsComputedDOMStyle::DoGetMarkerEnd()
 {
   RefPtr<nsROCSSPrimitiveValue> val = new nsROCSSPrimitiveValue;
-  // Bug 1288812 - we should only serialize fragment for local-ref URL.
-  nsCOMPtr<nsIURI> markerURI = StyleSVG()->mMarkerEnd.GetSourceURL();
-
-  if (markerURI)
-    val->SetURI(markerURI);
-  else
-    val->SetIdent(eCSSKeyword_none);
+  SetValueToFragmentOrURL(&StyleSVG()->mMarkerEnd, val);
 
   return val.forget();
 }
 
 already_AddRefed<CSSValue>
 nsComputedDOMStyle::DoGetMarkerMid()
 {
   RefPtr<nsROCSSPrimitiveValue> val = new nsROCSSPrimitiveValue;
-  // Bug 1288812 - we should only serialize fragment for local-ref URL.
-  nsCOMPtr<nsIURI> markerURI = StyleSVG()->mMarkerMid.GetSourceURL();
-
-  if (markerURI)
-    val->SetURI(markerURI);
-  else
-    val->SetIdent(eCSSKeyword_none);
+  SetValueToFragmentOrURL(&StyleSVG()->mMarkerMid, val);
 
   return val.forget();
 }
 
 already_AddRefed<CSSValue>
 nsComputedDOMStyle::DoGetMarkerStart()
 {
   RefPtr<nsROCSSPrimitiveValue> val = new nsROCSSPrimitiveValue;
-  // Bug 1288812 - we should only serialize fragment for local-ref URL.
-  nsCOMPtr<nsIURI> markerURI = StyleSVG()->mMarkerStart.GetSourceURL();
-
-  if (markerURI)
-    val->SetURI(markerURI);
-  else
-    val->SetIdent(eCSSKeyword_none);
+  SetValueToFragmentOrURL(&StyleSVG()->mMarkerStart, val);
 
   return val.forget();
 }
 
 already_AddRefed<CSSValue>
 nsComputedDOMStyle::DoGetStrokeDasharray()
 {
   const nsStyleSVG* svg = StyleSVG();
@@ -6027,20 +6028,18 @@ nsComputedDOMStyle::DoGetClipPath()
   switch (svg->mClipPath.GetType()) {
     case StyleClipPathType::Shape:
       return CreatePrimitiveValueForClipPath(svg->mClipPath.GetBasicShape(),
                                              svg->mClipPath.GetSizingBox());
     case StyleClipPathType::Box:
       return CreatePrimitiveValueForClipPath(nullptr,
                                              svg->mClipPath.GetSizingBox());
     case StyleClipPathType::URL: {
-      // Bug 1288812 - we should only serialize fragment for local-ref URL.
-      nsCOMPtr<nsIURI> pathURI = svg->mClipPath.GetURL()->GetSourceURL();
       RefPtr<nsROCSSPrimitiveValue> val = new nsROCSSPrimitiveValue;
-      val->SetURI(pathURI);
+      SetValueToFragmentOrURL(svg->mClipPath.GetURL(), val);
       return val.forget();
     }
     case StyleClipPathType::None_: {
       RefPtr<nsROCSSPrimitiveValue> val = new nsROCSSPrimitiveValue;
       val->SetIdent(eCSSKeyword_none);
       return val.forget();
     }
     default:
@@ -6061,19 +6060,18 @@ nsComputedDOMStyle::SetCssTextToCoord(ns
 
 already_AddRefed<CSSValue>
 nsComputedDOMStyle::CreatePrimitiveValueForStyleFilter(
   const nsStyleFilter& aStyleFilter)
 {
   RefPtr<nsROCSSPrimitiveValue> value = new nsROCSSPrimitiveValue;
   // Handle url().
   if (aStyleFilter.GetType() == NS_STYLE_FILTER_URL) {
-    // Bug 1288812 - we should only serialize fragment for local-ref URL.
-    nsCOMPtr<nsIURI> filterURI = aStyleFilter.GetURL()->GetSourceURL();
-    value->SetURI(filterURI);
+    MOZ_ASSERT(aStyleFilter.GetURL()->GetSourceURL());
+    SetValueToFragmentOrURL(aStyleFilter.GetURL(), value);
     return value.forget();
   }
 
   // Filter function name and opening parenthesis.
   nsAutoString filterFunctionString;
   AppendASCIItoUTF16(
     nsCSSProps::ValueToKeyword(aStyleFilter.GetType(),
                                nsCSSProps::kFilterFunctionKTable),
@@ -6141,17 +6139,17 @@ nsComputedDOMStyle::DoGetMask()
       !(firstLayer.mImage.GetType() == eStyleImageType_Null ||
         firstLayer.mImage.GetType() == eStyleImageType_Image)) {
     return nullptr;
   }
 
   RefPtr<nsROCSSPrimitiveValue> val = new nsROCSSPrimitiveValue;
 
   if (firstLayer.mSourceURI.GetSourceURL()) {
-    val->SetURI(firstLayer.mSourceURI.GetSourceURL());
+    SetValueToFragmentOrURL(&firstLayer.mSourceURI, val);
   } else {
     val->SetIdent(eCSSKeyword_none);
   }
 
   return val.forget();
 }
 
 #ifdef MOZ_ENABLE_MASK_AS_SHORTHAND
--- a/layout/style/nsComputedDOMStyle.h
+++ b/layout/style/nsComputedDOMStyle.h
@@ -584,16 +584,18 @@ private:
   void SetToRGBAColor(nsROCSSPrimitiveValue* aValue, nscolor aColor);
   void SetValueToStyleImage(const nsStyleImage& aStyleImage,
                             nsROCSSPrimitiveValue* aValue);
   void SetValueToPositionCoord(
     const nsStyleImageLayers::Position::PositionCoord& aCoord,
     nsROCSSPrimitiveValue* aValue);
   void SetValueToPosition(const nsStyleImageLayers::Position& aPosition,
                           nsDOMCSSValueList* aValueList);
+  void SetValueToFragmentOrURL(const FragmentOrURL* aFragmentOrURL,
+                               nsROCSSPrimitiveValue* aValue);
 
   /**
    * A method to get a percentage base for a percentage value.  Returns true
    * if a percentage base value was determined, false otherwise.
    */
   typedef bool (nsComputedDOMStyle::*PercentageBaseGetter)(nscoord&);
 
   /**