Bug 655877 - Part 34: Implement SVG DOM text methods in terms of the new SVG text frame. r=longsonr
authorCameron McCormack <cam@mcc.id.au>
Mon, 11 Feb 2013 17:22:17 +1100
changeset 121494 37efcc78e70e5dacee7ab9c31a02c7acba2d8462
parent 121493 9bc717b46687dec44940b912c56b757eb2a5d11e
child 121495 22b95038354b962b212bd40888d5ecae6f54de3a
push id24291
push userryanvm@gmail.com
push dateMon, 11 Feb 2013 19:12:51 +0000
treeherdermozilla-central@93ba23f414ff [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerslongsonr
bugs655877
milestone21.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 655877 - Part 34: Implement SVG DOM text methods in terms of the new SVG text frame. r=longsonr
content/svg/content/src/SVGTextContentElement.cpp
content/svg/content/src/SVGTextContentElement.h
--- a/content/svg/content/src/SVGTextContentElement.cpp
+++ b/content/svg/content/src/SVGTextContentElement.cpp
@@ -1,125 +1,214 @@
 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "mozilla/dom/SVGTextContentElement.h"
 #include "nsISVGPoint.h"
 #include "nsSVGTextContainerFrame.h"
+#include "nsSVGTextFrame2.h"
 #include "nsIDOMSVGAnimatedLength.h"
 #include "nsIDOMSVGRect.h"
 #include "nsIDOMSVGAnimatedEnum.h"
 
 namespace mozilla {
 namespace dom {
 
 nsSVGTextContainerFrame*
 SVGTextContentElement::GetTextContainerFrame()
 {
   return do_QueryFrame(GetPrimaryFrame(Flush_Layout));
 }
 
+nsSVGTextFrame2*
+SVGTextContentElement::GetSVGTextFrame()
+{
+  nsIFrame* frame = GetPrimaryFrame(Flush_Layout);
+  while (frame) {
+    nsSVGTextFrame2* textFrame = do_QueryFrame(frame);
+    if (textFrame) {
+      return textFrame;
+    }
+    frame = frame->GetParent();
+  }
+  return nullptr;
+}
+
 //----------------------------------------------------------------------
 
 int32_t
 SVGTextContentElement::GetNumberOfChars()
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
-  return metrics ? metrics->GetNumberOfChars() : 0;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+    return textFrame ? textFrame->GetNumberOfChars(this) : 0;
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+    return metrics ? metrics->GetNumberOfChars() : 0;
+  }
 }
 
 float
 SVGTextContentElement::GetComputedTextLength()
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
-  return metrics ? metrics->GetComputedTextLength() : 0.0f;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+    return textFrame ? textFrame->GetComputedTextLength(this) : 0.0f;
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+    return metrics ? metrics->GetComputedTextLength() : 0.0f;
+  }
 }
 
 float
 SVGTextContentElement::GetSubStringLength(uint32_t charnum, uint32_t nchars, ErrorResult& rv)
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
-  if (!metrics)
-    return 0.0f;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+    if (!textFrame)
+      return 0.0f;
+
+    uint32_t charcount = textFrame->GetNumberOfChars(this);
+    if (charcount <= charnum || nchars > charcount - charnum) {
+      rv.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
+      return 0.0f;
+    }
+
+    if (nchars == 0)
+      return 0.0f;
 
-  uint32_t charcount = metrics->GetNumberOfChars();
-  if (charcount <= charnum || nchars > charcount - charnum) {
-    rv.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
-    return 0.0f;
+    return textFrame->GetSubStringLength(this, charnum, nchars);
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+    if (!metrics)
+      return 0.0f;
+
+    uint32_t charcount = metrics->GetNumberOfChars();
+    if (charcount <= charnum || nchars > charcount - charnum) {
+      rv.Throw(NS_ERROR_DOM_INDEX_SIZE_ERR);
+      return 0.0f;
+    }
+
+    if (nchars == 0)
+      return 0.0f;
+
+    return metrics->GetSubStringLength(charnum, nchars);
   }
-
-  if (nchars == 0)
-    return 0.0f;
-
-  return metrics->GetSubStringLength(charnum, nchars);
 }
 
 already_AddRefed<nsISVGPoint>
 SVGTextContentElement::GetStartPositionOfChar(uint32_t charnum, ErrorResult& rv)
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+  nsCOMPtr<nsISVGPoint> point;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+    if (!textFrame) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return nullptr;
+    }
 
-  if (!metrics) {
-    rv.Throw(NS_ERROR_FAILURE);
-    return nullptr;
+    rv = textFrame->GetStartPositionOfChar(this, charnum, getter_AddRefs(point));
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+
+    if (!metrics) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return nullptr;
+    }
+
+    rv = metrics->GetStartPositionOfChar(charnum, getter_AddRefs(point));
   }
-
-  nsCOMPtr<nsISVGPoint> point;
-  rv = metrics->GetStartPositionOfChar(charnum, getter_AddRefs(point));
   return point.forget();
 }
 
 already_AddRefed<nsISVGPoint>
 SVGTextContentElement::GetEndPositionOfChar(uint32_t charnum, ErrorResult& rv)
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+  nsCOMPtr<nsISVGPoint> point;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+    if (!textFrame) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return nullptr;
+    }
 
-  if (!metrics) {
-    rv.Throw(NS_ERROR_FAILURE);
-    return nullptr;
+    rv = textFrame->GetEndPositionOfChar(this, charnum, getter_AddRefs(point));
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+
+    if (!metrics) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return nullptr;
+    }
+
+    rv = metrics->GetEndPositionOfChar(charnum, getter_AddRefs(point));
   }
-
-  nsCOMPtr<nsISVGPoint> point;
-  rv = metrics->GetEndPositionOfChar(charnum, getter_AddRefs(point));
   return point.forget();
 }
 
 already_AddRefed<nsIDOMSVGRect>
 SVGTextContentElement::GetExtentOfChar(uint32_t charnum, ErrorResult& rv)
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+  nsCOMPtr<nsIDOMSVGRect> rect;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+
+    if (!textFrame) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return nullptr;
+    }
 
-  if (!metrics) {
-    rv.Throw(NS_ERROR_FAILURE);
-    return nullptr;
+    rv = textFrame->GetExtentOfChar(this, charnum, getter_AddRefs(rect));
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+
+    if (!metrics) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return nullptr;
+    }
+
+    rv = metrics->GetExtentOfChar(charnum, getter_AddRefs(rect));
   }
-
-  nsCOMPtr<nsIDOMSVGRect> rect;
-  rv = metrics->GetExtentOfChar(charnum, getter_AddRefs(rect));
   return rect.forget();
 }
 
 float
 SVGTextContentElement::GetRotationOfChar(uint32_t charnum, ErrorResult& rv)
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+  float rotation;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+
+    if (!textFrame) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return 0.0f;
+    }
 
-  if (!metrics) {
-    rv.Throw(NS_ERROR_FAILURE);
-    return 0.0f;
+    rv = textFrame->GetRotationOfChar(this, charnum, &rotation);
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+
+    if (!metrics) {
+      rv.Throw(NS_ERROR_FAILURE);
+      return 0.0f;
+    }
+
+    rv = metrics->GetRotationOfChar(charnum, &rotation);
   }
-
-  float _retval;
-  rv = metrics->GetRotationOfChar(charnum, &_retval);
-  return _retval;
+  return rotation;
 }
 
 int32_t
 SVGTextContentElement::GetCharNumAtPosition(nsISVGPoint& aPoint)
 {
-  nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
-  return metrics ? metrics->GetCharNumAtPosition(&aPoint) : -1;
+  if (NS_SVGTextCSSFramesEnabled()) {
+    nsSVGTextFrame2* textFrame = GetSVGTextFrame();
+    return textFrame ? textFrame->GetCharNumAtPosition(this, &aPoint) : -1;
+  } else {
+    nsSVGTextContainerFrame* metrics = GetTextContainerFrame();
+    return metrics ? metrics->GetCharNumAtPosition(&aPoint) : -1;
+  }
 }
 
 } // namespace dom
 } // namespace mozilla
--- a/content/svg/content/src/SVGTextContentElement.h
+++ b/content/svg/content/src/SVGTextContentElement.h
@@ -4,16 +4,17 @@
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #ifndef mozilla_dom_SVGTextContentElement_h
 #define mozilla_dom_SVGTextContentElement_h
 
 #include "mozilla/dom/SVGGraphicsElement.h"
 
 class nsSVGTextContainerFrame;
+class nsSVGTextFrame2;
 
 namespace mozilla {
 class nsISVGPoint;
 
 namespace dom {
 
 typedef SVGGraphicsElement SVGTextContentElementBase;
 
@@ -34,14 +35,15 @@ public:
 
 protected:
 
   SVGTextContentElement(already_AddRefed<nsINodeInfo> aNodeInfo)
     : SVGTextContentElementBase(aNodeInfo)
   {}
 
   nsSVGTextContainerFrame* GetTextContainerFrame();
+  nsSVGTextFrame2* GetSVGTextFrame();
 };
 
 } // namespace dom
 } // namespace mozilla
 
 #endif // mozilla_dom_SVGTextContentElement_h