LCOV - code coverage report
Current view: directory - content/svg/content/src - nsSVGLength2.cpp (source / functions) Found Hit Coverage
Test: app.info Lines: 258 7 2.7 %
Date: 2012-06-02 Functions: 52 2 3.8 %

       1                 : /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
       2                 : /* ***** BEGIN LICENSE BLOCK *****
       3                 :  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
       4                 :  *
       5                 :  * The contents of this file are subject to the Mozilla Public License Version
       6                 :  * 1.1 (the "License"); you may not use this file except in compliance with
       7                 :  * the License. You may obtain a copy of the License at
       8                 :  * http://www.mozilla.org/MPL/
       9                 :  *
      10                 :  * Software distributed under the License is distributed on an "AS IS" basis,
      11                 :  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
      12                 :  * for the specific language governing rights and limitations under the
      13                 :  * License.
      14                 :  *
      15                 :  * The Original Code is the Mozilla SVG project.
      16                 :  *
      17                 :  * The Initial Developer of the Original Code is Crocodile Clips Ltd..
      18                 :  * Portions created by the Initial Developer are Copyright (C) 2001
      19                 :  * the Initial Developer. All Rights Reserved.
      20                 :  *
      21                 :  * Contributor(s):
      22                 :  *   Alex Fritze <alex.fritze@crocodile-clips.com> (original author)
      23                 :  *   Jonathan Watt <jonathan.watt@strath.ac.uk>
      24                 :  *
      25                 :  * Alternatively, the contents of this file may be used under the terms of
      26                 :  * either the GNU General Public License Version 2 or later (the "GPL"), or
      27                 :  * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
      28                 :  * in which case the provisions of the GPL or the LGPL are applicable instead
      29                 :  * of those above. If you wish to allow use of your version of this file only
      30                 :  * under the terms of either the GPL or the LGPL, and not to allow others to
      31                 :  * use your version of this file under the terms of the MPL, indicate your
      32                 :  * decision by deleting the provisions above and replace them with the notice
      33                 :  * and other provisions required by the GPL or the LGPL. If you do not delete
      34                 :  * the provisions above, a recipient may use your version of this file under
      35                 :  * the terms of any one of the MPL, the GPL or the LGPL.
      36                 :  *
      37                 :  * ***** END LICENSE BLOCK ***** */
      38                 : 
      39                 : #include "mozilla/Util.h"
      40                 : 
      41                 : #include "nsSVGLength2.h"
      42                 : #include "prdtoa.h"
      43                 : #include "nsTextFormatter.h"
      44                 : #include "nsSVGSVGElement.h"
      45                 : #include "nsIFrame.h"
      46                 : #include "nsSVGIntegrationUtils.h"
      47                 : #include "nsSVGAttrTearoffTable.h"
      48                 : #include "nsContentUtils.h" // NS_ENSURE_FINITE
      49                 : #include "nsSMILValue.h"
      50                 : #include "nsSMILFloatType.h"
      51                 : 
      52                 : using namespace mozilla;
      53                 : 
      54            1464 : NS_SVG_VAL_IMPL_CYCLE_COLLECTION(nsSVGLength2::DOMBaseVal, mSVGElement)
      55                 : 
      56            1464 : NS_SVG_VAL_IMPL_CYCLE_COLLECTION(nsSVGLength2::DOMAnimVal, mSVGElement)
      57                 : 
      58            1464 : NS_SVG_VAL_IMPL_CYCLE_COLLECTION(nsSVGLength2::DOMAnimatedLength, mSVGElement)
      59                 : 
      60               0 : NS_IMPL_CYCLE_COLLECTING_ADDREF(nsSVGLength2::DOMBaseVal)
      61               0 : NS_IMPL_CYCLE_COLLECTING_RELEASE(nsSVGLength2::DOMBaseVal)
      62                 : 
      63               0 : NS_IMPL_CYCLE_COLLECTING_ADDREF(nsSVGLength2::DOMAnimVal)
      64               0 : NS_IMPL_CYCLE_COLLECTING_RELEASE(nsSVGLength2::DOMAnimVal)
      65                 : 
      66               0 : NS_IMPL_CYCLE_COLLECTING_ADDREF(nsSVGLength2::DOMAnimatedLength)
      67               0 : NS_IMPL_CYCLE_COLLECTING_RELEASE(nsSVGLength2::DOMAnimatedLength)
      68                 : 
      69               0 : NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsSVGLength2::DOMBaseVal)
      70               0 :   NS_INTERFACE_MAP_ENTRY(nsIDOMSVGLength)
      71               0 :   NS_INTERFACE_MAP_ENTRY(nsISupports)
      72               0 :   NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO(SVGLength)
      73               0 : NS_INTERFACE_MAP_END
      74                 : 
      75               0 : NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsSVGLength2::DOMAnimVal)
      76               0 :   NS_INTERFACE_MAP_ENTRY(nsIDOMSVGLength)
      77               0 :   NS_INTERFACE_MAP_ENTRY(nsISupports)
      78               0 :   NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO(SVGLength)
      79               0 : NS_INTERFACE_MAP_END
      80                 : 
      81                 : DOMCI_DATA(SVGAnimatedLength, nsSVGLength2::DOMAnimatedLength)
      82                 : 
      83               0 : NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsSVGLength2::DOMAnimatedLength)
      84               0 :   NS_INTERFACE_MAP_ENTRY(nsIDOMSVGAnimatedLength)
      85               0 :   NS_INTERFACE_MAP_ENTRY(nsISupports)
      86               0 :   NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO(SVGAnimatedLength)
      87               0 : NS_INTERFACE_MAP_END
      88                 : 
      89                 : static nsIAtom** const unitMap[] =
      90                 : {
      91                 :   nsnull, /* SVG_LENGTHTYPE_UNKNOWN */
      92                 :   nsnull, /* SVG_LENGTHTYPE_NUMBER */
      93                 :   &nsGkAtoms::percentage,
      94                 :   &nsGkAtoms::em,
      95                 :   &nsGkAtoms::ex,
      96                 :   &nsGkAtoms::px,
      97                 :   &nsGkAtoms::cm,
      98                 :   &nsGkAtoms::mm,
      99                 :   &nsGkAtoms::in,
     100                 :   &nsGkAtoms::pt,
     101                 :   &nsGkAtoms::pc
     102                 : };
     103                 : 
     104                 : static nsSVGAttrTearoffTable<nsSVGLength2, nsIDOMSVGAnimatedLength>
     105            1464 :   sSVGAnimatedLengthTearoffTable;
     106                 : static nsSVGAttrTearoffTable<nsSVGLength2, nsIDOMSVGLength>
     107            1464 :   sBaseSVGLengthTearoffTable;
     108                 : static nsSVGAttrTearoffTable<nsSVGLength2, nsIDOMSVGLength>
     109            1464 :   sAnimSVGLengthTearoffTable;
     110                 : 
     111                 : /* Helper functions */
     112                 : 
     113                 : static bool
     114               0 : IsValidUnitType(PRUint16 unit)
     115                 : {
     116               0 :   if (unit > nsIDOMSVGLength::SVG_LENGTHTYPE_UNKNOWN &&
     117                 :       unit <= nsIDOMSVGLength::SVG_LENGTHTYPE_PC)
     118               0 :     return true;
     119                 : 
     120               0 :   return false;
     121                 : }
     122                 : 
     123                 : static void
     124               0 : GetUnitString(nsAString& unit, PRUint16 unitType)
     125                 : {
     126               0 :   if (IsValidUnitType(unitType)) {
     127               0 :     if (unitMap[unitType]) {
     128               0 :       (*unitMap[unitType])->ToString(unit);
     129                 :     }
     130               0 :     return;
     131                 :   }
     132                 : 
     133               0 :   NS_NOTREACHED("Unknown unit type");
     134               0 :   return;
     135                 : }
     136                 : 
     137                 : static PRUint16
     138               0 : GetUnitTypeForString(const char* unitStr)
     139                 : {
     140               0 :   if (!unitStr || *unitStr == '\0') 
     141               0 :     return nsIDOMSVGLength::SVG_LENGTHTYPE_NUMBER;
     142                 :                    
     143               0 :   nsCOMPtr<nsIAtom> unitAtom = do_GetAtom(unitStr);
     144                 : 
     145               0 :   for (PRUint32 i = 0 ; i < ArrayLength(unitMap) ; i++) {
     146               0 :     if (unitMap[i] && *unitMap[i] == unitAtom) {
     147               0 :       return i;
     148                 :     }
     149                 :   }
     150                 : 
     151               0 :   return nsIDOMSVGLength::SVG_LENGTHTYPE_UNKNOWN;
     152                 : }
     153                 : 
     154                 : static void
     155               0 : GetValueString(nsAString &aValueAsString, float aValue, PRUint16 aUnitType)
     156                 : {
     157                 :   PRUnichar buf[24];
     158                 :   nsTextFormatter::snprintf(buf, sizeof(buf)/sizeof(PRUnichar),
     159               0 :                             NS_LITERAL_STRING("%g").get(),
     160               0 :                             (double)aValue);
     161               0 :   aValueAsString.Assign(buf);
     162                 : 
     163               0 :   nsAutoString unitString;
     164               0 :   GetUnitString(unitString, aUnitType);
     165               0 :   aValueAsString.Append(unitString);
     166               0 : }
     167                 : 
     168                 : static nsresult
     169               0 : GetValueFromString(const nsAString &aValueAsString,
     170                 :                    float *aValue,
     171                 :                    PRUint16 *aUnitType)
     172                 : {
     173               0 :   NS_ConvertUTF16toUTF8 value(aValueAsString);
     174               0 :   const char *str = value.get();
     175                 : 
     176               0 :   if (NS_IsAsciiWhitespace(*str))
     177               0 :     return NS_ERROR_DOM_SYNTAX_ERR;
     178                 :   
     179                 :   char *rest;
     180               0 :   *aValue = float(PR_strtod(str, &rest));
     181               0 :   if (rest != str && NS_finite(*aValue)) {
     182               0 :     *aUnitType = GetUnitTypeForString(rest);
     183               0 :     if (IsValidUnitType(*aUnitType)) {
     184               0 :       return NS_OK;
     185                 :     }
     186                 :   }
     187                 :   
     188               0 :   return NS_ERROR_DOM_SYNTAX_ERR;
     189                 : }
     190                 : 
     191                 : static float
     192               0 : FixAxisLength(float aLength)
     193                 : {
     194               0 :   if (aLength == 0.0f) {
     195               0 :     NS_WARNING("zero axis length");
     196               0 :     return 1e-20f;
     197                 :   }
     198               0 :   return aLength;
     199                 : }
     200                 : 
     201                 : float
     202               0 : nsSVGLength2::GetAxisLength(nsSVGSVGElement *aCtx) const
     203                 : {
     204               0 :   if (!aCtx)
     205               0 :     return 1;
     206                 : 
     207               0 :   return FixAxisLength(aCtx->GetLength(mCtxType));
     208                 : }
     209                 : 
     210                 : float
     211               0 : nsSVGLength2::GetAxisLength(nsIFrame *aNonSVGFrame) const
     212                 : {
     213               0 :   gfxRect rect = nsSVGIntegrationUtils::GetSVGRectForNonSVGFrame(aNonSVGFrame);
     214                 :   float length;
     215               0 :   switch (mCtxType) {
     216               0 :   case nsSVGUtils::X: length = rect.Width(); break;
     217               0 :   case nsSVGUtils::Y: length = rect.Height(); break;
     218                 :   case nsSVGUtils::XY:
     219               0 :     length = nsSVGUtils::ComputeNormalizedHypotenuse(rect.Width(), rect.Height());
     220               0 :     break;
     221                 :   default:
     222               0 :     NS_NOTREACHED("Unknown axis type");
     223               0 :     length = 1;
     224               0 :     break;
     225                 :   }
     226               0 :   return FixAxisLength(length);
     227                 : }
     228                 : 
     229                 : float
     230               0 : nsSVGLength2::GetUnitScaleFactor(nsSVGElement *aSVGElement,
     231                 :                                  PRUint8 aUnitType) const
     232                 : {
     233               0 :   switch (aUnitType) {
     234                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_NUMBER:
     235                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PX:
     236               0 :     return 1;
     237                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_EMS:
     238               0 :     return 1 / GetEmLength(aSVGElement);
     239                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_EXS:
     240               0 :     return 1 / GetExLength(aSVGElement);
     241                 :   }
     242                 : 
     243               0 :   return GetUnitScaleFactor(aSVGElement->GetCtx(), aUnitType);
     244                 : }
     245                 : 
     246                 : float
     247               0 : nsSVGLength2::GetUnitScaleFactor(nsSVGSVGElement *aCtx, PRUint8 aUnitType) const
     248                 : {
     249               0 :   switch (aUnitType) {
     250                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_NUMBER:
     251                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PX:
     252               0 :     return 1;
     253                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_MM:
     254               0 :     return GetMMPerPixel();
     255                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_CM:
     256               0 :     return GetMMPerPixel() / 10.0f;
     257                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_IN:
     258               0 :     return GetMMPerPixel() / MM_PER_INCH_FLOAT;
     259                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PT:
     260               0 :     return GetMMPerPixel() * POINTS_PER_INCH_FLOAT / MM_PER_INCH_FLOAT;
     261                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PC:
     262               0 :     return GetMMPerPixel() * POINTS_PER_INCH_FLOAT / MM_PER_INCH_FLOAT / 12.0f;
     263                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PERCENTAGE:
     264               0 :     return 100.0f / GetAxisLength(aCtx);
     265                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_EMS:
     266               0 :     return 1 / GetEmLength(aCtx);
     267                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_EXS:
     268               0 :     return 1 / GetExLength(aCtx);
     269                 :   default:
     270               0 :     NS_NOTREACHED("Unknown unit type");
     271               0 :     return 0;
     272                 :   }
     273                 : }
     274                 : 
     275                 : float
     276               0 : nsSVGLength2::GetUnitScaleFactor(nsIFrame *aFrame, PRUint8 aUnitType) const
     277                 : {
     278               0 :   nsIContent* content = aFrame->GetContent();
     279               0 :   if (content->IsSVG())
     280               0 :     return GetUnitScaleFactor(static_cast<nsSVGElement*>(content), aUnitType);
     281                 : 
     282               0 :   switch (aUnitType) {
     283                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_NUMBER:
     284                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PX:
     285               0 :     return 1;
     286                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_MM:
     287               0 :     return GetMMPerPixel();
     288                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_CM:
     289               0 :     return GetMMPerPixel() / 10.0f;
     290                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_IN:
     291               0 :     return GetMMPerPixel() / MM_PER_INCH_FLOAT;
     292                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PT:
     293               0 :     return GetMMPerPixel() * POINTS_PER_INCH_FLOAT / MM_PER_INCH_FLOAT;
     294                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PC:
     295               0 :     return GetMMPerPixel() * POINTS_PER_INCH_FLOAT / MM_PER_INCH_FLOAT / 12.0f;
     296                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_PERCENTAGE:
     297               0 :     return 100.0f / GetAxisLength(aFrame);
     298                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_EMS:
     299               0 :     return 1 / GetEmLength(aFrame);
     300                 :   case nsIDOMSVGLength::SVG_LENGTHTYPE_EXS:
     301               0 :     return 1 / GetExLength(aFrame);
     302                 :   default:
     303               0 :     NS_NOTREACHED("Unknown unit type");
     304               0 :     return 0;
     305                 :   }
     306                 : }
     307                 : 
     308                 : void
     309               0 : nsSVGLength2::SetBaseValueInSpecifiedUnits(float aValue,
     310                 :                                            nsSVGElement *aSVGElement,
     311                 :                                            bool aDoSetAttr)
     312                 : {
     313               0 :   if (mIsBaseSet && mBaseVal == aValue) {
     314               0 :     return;
     315                 :   }
     316                 : 
     317               0 :   nsAttrValue emptyOrOldValue;
     318               0 :   if (aDoSetAttr) {
     319               0 :     emptyOrOldValue = aSVGElement->WillChangeLength(mAttrEnum);
     320                 :   }
     321               0 :   mBaseVal = aValue;
     322               0 :   mIsBaseSet = true;
     323               0 :   if (!mIsAnimated) {
     324               0 :     mAnimVal = mBaseVal;
     325                 :   }
     326                 :   else {
     327               0 :     aSVGElement->AnimationNeedsResample();
     328                 :   }
     329               0 :   if (aDoSetAttr) {
     330               0 :     aSVGElement->DidChangeLength(mAttrEnum, emptyOrOldValue);
     331                 :   }
     332                 : }
     333                 : 
     334                 : nsresult
     335               0 : nsSVGLength2::ConvertToSpecifiedUnits(PRUint16 unitType,
     336                 :                                       nsSVGElement *aSVGElement)
     337                 : {
     338               0 :   if (!IsValidUnitType(unitType))
     339               0 :     return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
     340                 : 
     341               0 :   if (mIsBaseSet && mSpecifiedUnitType == PRUint8(unitType))
     342               0 :     return NS_OK;
     343                 : 
     344                 :   // Even though we're not changing the visual effect this length will have
     345                 :   // on the document, we still need to send out notifications in case we have
     346                 :   // mutation listeners, since the actual string value of the attribute will
     347                 :   // change.
     348               0 :   nsAttrValue emptyOrOldValue = aSVGElement->WillChangeLength(mAttrEnum);
     349                 : 
     350                 :   float valueInUserUnits =
     351               0 :     mBaseVal / GetUnitScaleFactor(aSVGElement, mSpecifiedUnitType);
     352               0 :   mSpecifiedUnitType = PRUint8(unitType);
     353                 :   // Setting aDoSetAttr to false here will ensure we don't call
     354                 :   // Will/DidChangeAngle a second time (and dispatch duplicate notifications).
     355               0 :   SetBaseValue(valueInUserUnits, aSVGElement, false);
     356                 : 
     357               0 :   aSVGElement->DidChangeLength(mAttrEnum, emptyOrOldValue);
     358                 : 
     359               0 :   return NS_OK;
     360                 : }
     361                 : 
     362                 : nsresult
     363               0 : nsSVGLength2::NewValueSpecifiedUnits(PRUint16 unitType,
     364                 :                                      float valueInSpecifiedUnits,
     365                 :                                      nsSVGElement *aSVGElement)
     366                 : {
     367               0 :   NS_ENSURE_FINITE(valueInSpecifiedUnits, NS_ERROR_ILLEGAL_VALUE);
     368                 : 
     369               0 :   if (!IsValidUnitType(unitType))
     370               0 :     return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
     371                 : 
     372               0 :   if (mIsBaseSet && mBaseVal == valueInSpecifiedUnits &&
     373                 :       mSpecifiedUnitType == PRUint8(unitType)) {
     374               0 :     return NS_OK;
     375                 :   }
     376                 : 
     377               0 :   nsAttrValue emptyOrOldValue = aSVGElement->WillChangeLength(mAttrEnum);
     378               0 :   mBaseVal = valueInSpecifiedUnits;
     379               0 :   mIsBaseSet = true;
     380               0 :   mSpecifiedUnitType = PRUint8(unitType);
     381               0 :   if (!mIsAnimated) {
     382               0 :     mAnimVal = mBaseVal;
     383                 :   }
     384                 :   else {
     385               0 :     aSVGElement->AnimationNeedsResample();
     386                 :   }
     387               0 :   aSVGElement->DidChangeLength(mAttrEnum, emptyOrOldValue);
     388               0 :   return NS_OK;
     389                 : }
     390                 : 
     391                 : nsresult
     392               0 : nsSVGLength2::ToDOMBaseVal(nsIDOMSVGLength **aResult, nsSVGElement *aSVGElement)
     393                 : {
     394               0 :   *aResult = sBaseSVGLengthTearoffTable.GetTearoff(this);
     395               0 :   if (!*aResult) {
     396               0 :     *aResult = new DOMBaseVal(this, aSVGElement);
     397               0 :     if (!*aResult)
     398               0 :       return NS_ERROR_OUT_OF_MEMORY;
     399               0 :     sBaseSVGLengthTearoffTable.AddTearoff(this, *aResult);
     400                 :   }
     401                 : 
     402               0 :   NS_ADDREF(*aResult);
     403               0 :   return NS_OK;
     404                 : }
     405                 : 
     406               0 : nsSVGLength2::DOMBaseVal::~DOMBaseVal()
     407                 : {
     408               0 :   sBaseSVGLengthTearoffTable.RemoveTearoff(mVal);
     409               0 : }
     410                 : 
     411                 : nsresult
     412               0 : nsSVGLength2::ToDOMAnimVal(nsIDOMSVGLength **aResult, nsSVGElement *aSVGElement)
     413                 : {
     414               0 :   *aResult = sAnimSVGLengthTearoffTable.GetTearoff(this);
     415               0 :   if (!*aResult) {
     416               0 :     *aResult = new DOMAnimVal(this, aSVGElement);
     417               0 :     if (!*aResult)
     418               0 :       return NS_ERROR_OUT_OF_MEMORY;
     419               0 :     sAnimSVGLengthTearoffTable.AddTearoff(this, *aResult);
     420                 :   }
     421                 : 
     422               0 :   NS_ADDREF(*aResult);
     423               0 :   return NS_OK;
     424                 : }
     425                 : 
     426               0 : nsSVGLength2::DOMAnimVal::~DOMAnimVal()
     427                 : {
     428               0 :   sAnimSVGLengthTearoffTable.RemoveTearoff(mVal);
     429               0 : }
     430                 : 
     431                 : /* Implementation */
     432                 : 
     433                 : nsresult
     434               0 : nsSVGLength2::SetBaseValueString(const nsAString &aValueAsString,
     435                 :                                  nsSVGElement *aSVGElement,
     436                 :                                  bool aDoSetAttr)
     437                 : {
     438                 :   float value;
     439                 :   PRUint16 unitType;
     440                 : 
     441               0 :   nsresult rv = GetValueFromString(aValueAsString, &value, &unitType);
     442               0 :   if (NS_FAILED(rv)) {
     443               0 :     return rv;
     444                 :   }
     445                 : 
     446               0 :   if (mIsBaseSet && mBaseVal == value &&
     447                 :       mSpecifiedUnitType == PRUint8(unitType)) {
     448               0 :     return NS_OK;
     449                 :   }
     450                 : 
     451               0 :   nsAttrValue emptyOrOldValue;
     452               0 :   if (aDoSetAttr) {
     453               0 :     emptyOrOldValue = aSVGElement->WillChangeLength(mAttrEnum);
     454                 :   }
     455               0 :   mBaseVal = value;
     456               0 :   mIsBaseSet = true;
     457               0 :   mSpecifiedUnitType = PRUint8(unitType);
     458               0 :   if (!mIsAnimated) {
     459               0 :     mAnimVal = mBaseVal;
     460                 :   }
     461                 :   else {
     462               0 :     aSVGElement->AnimationNeedsResample();
     463                 :   }
     464                 : 
     465               0 :   if (aDoSetAttr) {
     466               0 :     aSVGElement->DidChangeLength(mAttrEnum, emptyOrOldValue);
     467                 :   }
     468               0 :   return NS_OK;
     469                 : }
     470                 : 
     471                 : void
     472               0 : nsSVGLength2::GetBaseValueString(nsAString & aValueAsString) const
     473                 : {
     474               0 :   GetValueString(aValueAsString, mBaseVal, mSpecifiedUnitType);
     475               0 : }
     476                 : 
     477                 : void
     478               0 : nsSVGLength2::GetAnimValueString(nsAString & aValueAsString) const
     479                 : {
     480               0 :   GetValueString(aValueAsString, mAnimVal, mSpecifiedUnitType);
     481               0 : }
     482                 : 
     483                 : void
     484               0 : nsSVGLength2::SetBaseValue(float aValue, nsSVGElement *aSVGElement,
     485                 :                            bool aDoSetAttr)
     486                 : {
     487                 :   SetBaseValueInSpecifiedUnits(aValue * GetUnitScaleFactor(aSVGElement,
     488               0 :                                                            mSpecifiedUnitType),
     489               0 :                                aSVGElement, aDoSetAttr);
     490               0 : }
     491                 : 
     492                 : void
     493               0 : nsSVGLength2::SetAnimValueInSpecifiedUnits(float aValue,
     494                 :                                            nsSVGElement* aSVGElement)
     495                 : {
     496               0 :   mAnimVal = aValue;
     497               0 :   mIsAnimated = true;
     498               0 :   aSVGElement->DidAnimateLength(mAttrEnum);
     499               0 : }
     500                 : 
     501                 : void
     502               0 : nsSVGLength2::SetAnimValue(float aValue, nsSVGElement *aSVGElement)
     503                 : {
     504                 :   SetAnimValueInSpecifiedUnits(aValue * GetUnitScaleFactor(aSVGElement,
     505               0 :                                                            mSpecifiedUnitType),
     506               0 :                                aSVGElement);
     507               0 : }
     508                 : 
     509                 : nsresult
     510               0 : nsSVGLength2::ToDOMAnimatedLength(nsIDOMSVGAnimatedLength **aResult,
     511                 :                                   nsSVGElement *aSVGElement)
     512                 : {
     513               0 :   *aResult = sSVGAnimatedLengthTearoffTable.GetTearoff(this);
     514               0 :   if (!*aResult) {
     515               0 :     *aResult = new DOMAnimatedLength(this, aSVGElement);
     516               0 :     if (!*aResult)
     517               0 :       return NS_ERROR_OUT_OF_MEMORY;
     518               0 :     sSVGAnimatedLengthTearoffTable.AddTearoff(this, *aResult);
     519                 :   }
     520                 : 
     521               0 :   NS_ADDREF(*aResult);
     522               0 :   return NS_OK;
     523                 : }
     524                 : 
     525               0 : nsSVGLength2::DOMAnimatedLength::~DOMAnimatedLength()
     526                 : {
     527               0 :   sSVGAnimatedLengthTearoffTable.RemoveTearoff(mVal);
     528               0 : }
     529                 : 
     530                 : nsISMILAttr*
     531               0 : nsSVGLength2::ToSMILAttr(nsSVGElement *aSVGElement)
     532                 : {
     533               0 :   return new SMILLength(this, aSVGElement);
     534                 : }
     535                 : 
     536                 : nsresult
     537               0 : nsSVGLength2::SMILLength::ValueFromString(const nsAString& aStr,
     538                 :                                  const nsISMILAnimationElement* /*aSrcElement*/,
     539                 :                                  nsSMILValue& aValue,
     540                 :                                  bool& aPreventCachingOfSandwich) const
     541                 : {
     542                 :   float value;
     543                 :   PRUint16 unitType;
     544                 :   
     545               0 :   nsresult rv = GetValueFromString(aStr, &value, &unitType);
     546               0 :   if (NS_FAILED(rv)) {
     547               0 :     return rv;
     548                 :   }
     549                 : 
     550               0 :   nsSMILValue val(&nsSMILFloatType::sSingleton);
     551               0 :   val.mU.mDouble = value / mVal->GetUnitScaleFactor(mSVGElement, unitType);
     552               0 :   aValue = val;
     553                 :   aPreventCachingOfSandwich =
     554                 :               (unitType == nsIDOMSVGLength::SVG_LENGTHTYPE_PERCENTAGE ||
     555                 :                unitType == nsIDOMSVGLength::SVG_LENGTHTYPE_EMS ||
     556               0 :                unitType == nsIDOMSVGLength::SVG_LENGTHTYPE_EXS);
     557                 : 
     558               0 :   return NS_OK;
     559                 : }
     560                 : 
     561                 : nsSMILValue
     562               0 : nsSVGLength2::SMILLength::GetBaseValue() const
     563                 : {
     564               0 :   nsSMILValue val(&nsSMILFloatType::sSingleton);
     565               0 :   val.mU.mDouble = mVal->GetBaseValue(mSVGElement);
     566                 :   return val;
     567                 : }
     568                 : 
     569                 : void
     570               0 : nsSVGLength2::SMILLength::ClearAnimValue()
     571                 : {
     572               0 :   if (mVal->mIsAnimated) {
     573               0 :     mVal->mIsAnimated = false;
     574               0 :     mVal->mAnimVal = mVal->mBaseVal;
     575               0 :     mSVGElement->DidAnimateLength(mVal->mAttrEnum);
     576                 :   }  
     577               0 : }
     578                 : 
     579                 : nsresult
     580               0 : nsSVGLength2::SMILLength::SetAnimValue(const nsSMILValue& aValue)
     581                 : {
     582               0 :   NS_ASSERTION(aValue.mType == &nsSMILFloatType::sSingleton,
     583                 :     "Unexpected type to assign animated value");
     584               0 :   if (aValue.mType == &nsSMILFloatType::sSingleton) {
     585               0 :     mVal->SetAnimValue(float(aValue.mU.mDouble), mSVGElement);
     586                 :   }
     587               0 :   return NS_OK;
     588            4392 : }

Generated by: LCOV version 1.7