Wed, 31 Dec 2014 07:16:47 +0100
Revert simplistic fix pending revisit of Mozilla integration attempt.
michael@0 | 1 | /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
michael@0 | 2 | /* vim: set ts=2 et sw=2 tw=80: */ |
michael@0 | 3 | /* This Source Code Form is subject to the terms of the Mozilla Public |
michael@0 | 4 | * License, v. 2.0. If a copy of the MPL was not distributed with this |
michael@0 | 5 | * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ |
michael@0 | 6 | |
michael@0 | 7 | /* representation of simple property values within CSS declarations */ |
michael@0 | 8 | |
michael@0 | 9 | #include "nsCSSValue.h" |
michael@0 | 10 | |
michael@0 | 11 | #include "mozilla/Likely.h" |
michael@0 | 12 | #include "mozilla/MemoryReporting.h" |
michael@0 | 13 | #include "mozilla/css/ImageLoader.h" |
michael@0 | 14 | #include "CSSCalc.h" |
michael@0 | 15 | #include "gfxFontConstants.h" |
michael@0 | 16 | #include "imgIRequest.h" |
michael@0 | 17 | #include "imgRequestProxy.h" |
michael@0 | 18 | #include "nsIDocument.h" |
michael@0 | 19 | #include "nsIPrincipal.h" |
michael@0 | 20 | #include "nsCSSProps.h" |
michael@0 | 21 | #include "nsCSSStyleSheet.h" |
michael@0 | 22 | #include "nsNetUtil.h" |
michael@0 | 23 | #include "nsPresContext.h" |
michael@0 | 24 | #include "nsStyleUtil.h" |
michael@0 | 25 | #include "nsDeviceContext.h" |
michael@0 | 26 | |
michael@0 | 27 | using namespace mozilla; |
michael@0 | 28 | |
michael@0 | 29 | nsCSSValue::nsCSSValue(int32_t aValue, nsCSSUnit aUnit) |
michael@0 | 30 | : mUnit(aUnit) |
michael@0 | 31 | { |
michael@0 | 32 | NS_ABORT_IF_FALSE(aUnit == eCSSUnit_Integer || aUnit == eCSSUnit_Enumerated || |
michael@0 | 33 | aUnit == eCSSUnit_EnumColor, "not an int value"); |
michael@0 | 34 | if (aUnit == eCSSUnit_Integer || aUnit == eCSSUnit_Enumerated || |
michael@0 | 35 | aUnit == eCSSUnit_EnumColor) { |
michael@0 | 36 | mValue.mInt = aValue; |
michael@0 | 37 | } |
michael@0 | 38 | else { |
michael@0 | 39 | mUnit = eCSSUnit_Null; |
michael@0 | 40 | mValue.mInt = 0; |
michael@0 | 41 | } |
michael@0 | 42 | } |
michael@0 | 43 | |
michael@0 | 44 | nsCSSValue::nsCSSValue(float aValue, nsCSSUnit aUnit) |
michael@0 | 45 | : mUnit(aUnit) |
michael@0 | 46 | { |
michael@0 | 47 | NS_ABORT_IF_FALSE(eCSSUnit_Percent <= aUnit, "not a float value"); |
michael@0 | 48 | if (eCSSUnit_Percent <= aUnit) { |
michael@0 | 49 | mValue.mFloat = aValue; |
michael@0 | 50 | MOZ_ASSERT(!mozilla::IsNaN(mValue.mFloat)); |
michael@0 | 51 | } |
michael@0 | 52 | else { |
michael@0 | 53 | mUnit = eCSSUnit_Null; |
michael@0 | 54 | mValue.mInt = 0; |
michael@0 | 55 | } |
michael@0 | 56 | } |
michael@0 | 57 | |
michael@0 | 58 | nsCSSValue::nsCSSValue(const nsString& aValue, nsCSSUnit aUnit) |
michael@0 | 59 | : mUnit(aUnit) |
michael@0 | 60 | { |
michael@0 | 61 | NS_ABORT_IF_FALSE(UnitHasStringValue(), "not a string value"); |
michael@0 | 62 | if (UnitHasStringValue()) { |
michael@0 | 63 | mValue.mString = BufferFromString(aValue).take(); |
michael@0 | 64 | } |
michael@0 | 65 | else { |
michael@0 | 66 | mUnit = eCSSUnit_Null; |
michael@0 | 67 | mValue.mInt = 0; |
michael@0 | 68 | } |
michael@0 | 69 | } |
michael@0 | 70 | |
michael@0 | 71 | nsCSSValue::nsCSSValue(nsCSSValue::Array* aValue, nsCSSUnit aUnit) |
michael@0 | 72 | : mUnit(aUnit) |
michael@0 | 73 | { |
michael@0 | 74 | NS_ABORT_IF_FALSE(UnitHasArrayValue(), "bad unit"); |
michael@0 | 75 | mValue.mArray = aValue; |
michael@0 | 76 | mValue.mArray->AddRef(); |
michael@0 | 77 | } |
michael@0 | 78 | |
michael@0 | 79 | nsCSSValue::nsCSSValue(mozilla::css::URLValue* aValue) |
michael@0 | 80 | : mUnit(eCSSUnit_URL) |
michael@0 | 81 | { |
michael@0 | 82 | mValue.mURL = aValue; |
michael@0 | 83 | mValue.mURL->AddRef(); |
michael@0 | 84 | } |
michael@0 | 85 | |
michael@0 | 86 | nsCSSValue::nsCSSValue(mozilla::css::ImageValue* aValue) |
michael@0 | 87 | : mUnit(eCSSUnit_Image) |
michael@0 | 88 | { |
michael@0 | 89 | mValue.mImage = aValue; |
michael@0 | 90 | mValue.mImage->AddRef(); |
michael@0 | 91 | } |
michael@0 | 92 | |
michael@0 | 93 | nsCSSValue::nsCSSValue(nsCSSValueGradient* aValue) |
michael@0 | 94 | : mUnit(eCSSUnit_Gradient) |
michael@0 | 95 | { |
michael@0 | 96 | mValue.mGradient = aValue; |
michael@0 | 97 | mValue.mGradient->AddRef(); |
michael@0 | 98 | } |
michael@0 | 99 | |
michael@0 | 100 | nsCSSValue::nsCSSValue(nsCSSValueTokenStream* aValue) |
michael@0 | 101 | : mUnit(eCSSUnit_TokenStream) |
michael@0 | 102 | { |
michael@0 | 103 | mValue.mTokenStream = aValue; |
michael@0 | 104 | mValue.mTokenStream->AddRef(); |
michael@0 | 105 | } |
michael@0 | 106 | |
michael@0 | 107 | nsCSSValue::nsCSSValue(mozilla::css::GridTemplateAreasValue* aValue) |
michael@0 | 108 | : mUnit(eCSSUnit_GridTemplateAreas) |
michael@0 | 109 | { |
michael@0 | 110 | mValue.mGridTemplateAreas = aValue; |
michael@0 | 111 | mValue.mGridTemplateAreas->AddRef(); |
michael@0 | 112 | } |
michael@0 | 113 | |
michael@0 | 114 | nsCSSValue::nsCSSValue(const nsCSSValue& aCopy) |
michael@0 | 115 | : mUnit(aCopy.mUnit) |
michael@0 | 116 | { |
michael@0 | 117 | if (mUnit <= eCSSUnit_DummyInherit) { |
michael@0 | 118 | // nothing to do, but put this important case first |
michael@0 | 119 | } |
michael@0 | 120 | else if (eCSSUnit_Percent <= mUnit) { |
michael@0 | 121 | mValue.mFloat = aCopy.mValue.mFloat; |
michael@0 | 122 | MOZ_ASSERT(!mozilla::IsNaN(mValue.mFloat)); |
michael@0 | 123 | } |
michael@0 | 124 | else if (UnitHasStringValue()) { |
michael@0 | 125 | mValue.mString = aCopy.mValue.mString; |
michael@0 | 126 | mValue.mString->AddRef(); |
michael@0 | 127 | } |
michael@0 | 128 | else if (eCSSUnit_Integer <= mUnit && mUnit <= eCSSUnit_EnumColor) { |
michael@0 | 129 | mValue.mInt = aCopy.mValue.mInt; |
michael@0 | 130 | } |
michael@0 | 131 | else if (IsIntegerColorUnit()) { |
michael@0 | 132 | mValue.mColor = aCopy.mValue.mColor; |
michael@0 | 133 | } |
michael@0 | 134 | else if (IsFloatColorUnit()) { |
michael@0 | 135 | mValue.mFloatColor = aCopy.mValue.mFloatColor; |
michael@0 | 136 | mValue.mFloatColor->AddRef(); |
michael@0 | 137 | } |
michael@0 | 138 | else if (UnitHasArrayValue()) { |
michael@0 | 139 | mValue.mArray = aCopy.mValue.mArray; |
michael@0 | 140 | mValue.mArray->AddRef(); |
michael@0 | 141 | } |
michael@0 | 142 | else if (eCSSUnit_URL == mUnit) { |
michael@0 | 143 | mValue.mURL = aCopy.mValue.mURL; |
michael@0 | 144 | mValue.mURL->AddRef(); |
michael@0 | 145 | } |
michael@0 | 146 | else if (eCSSUnit_Image == mUnit) { |
michael@0 | 147 | mValue.mImage = aCopy.mValue.mImage; |
michael@0 | 148 | mValue.mImage->AddRef(); |
michael@0 | 149 | } |
michael@0 | 150 | else if (eCSSUnit_Gradient == mUnit) { |
michael@0 | 151 | mValue.mGradient = aCopy.mValue.mGradient; |
michael@0 | 152 | mValue.mGradient->AddRef(); |
michael@0 | 153 | } |
michael@0 | 154 | else if (eCSSUnit_TokenStream == mUnit) { |
michael@0 | 155 | mValue.mTokenStream = aCopy.mValue.mTokenStream; |
michael@0 | 156 | mValue.mTokenStream->AddRef(); |
michael@0 | 157 | } |
michael@0 | 158 | else if (eCSSUnit_Pair == mUnit) { |
michael@0 | 159 | mValue.mPair = aCopy.mValue.mPair; |
michael@0 | 160 | mValue.mPair->AddRef(); |
michael@0 | 161 | } |
michael@0 | 162 | else if (eCSSUnit_Triplet == mUnit) { |
michael@0 | 163 | mValue.mTriplet = aCopy.mValue.mTriplet; |
michael@0 | 164 | mValue.mTriplet->AddRef(); |
michael@0 | 165 | } |
michael@0 | 166 | else if (eCSSUnit_Rect == mUnit) { |
michael@0 | 167 | mValue.mRect = aCopy.mValue.mRect; |
michael@0 | 168 | mValue.mRect->AddRef(); |
michael@0 | 169 | } |
michael@0 | 170 | else if (eCSSUnit_List == mUnit) { |
michael@0 | 171 | mValue.mList = aCopy.mValue.mList; |
michael@0 | 172 | mValue.mList->AddRef(); |
michael@0 | 173 | } |
michael@0 | 174 | else if (eCSSUnit_ListDep == mUnit) { |
michael@0 | 175 | mValue.mListDependent = aCopy.mValue.mListDependent; |
michael@0 | 176 | } |
michael@0 | 177 | else if (eCSSUnit_SharedList == mUnit) { |
michael@0 | 178 | mValue.mSharedList = aCopy.mValue.mSharedList; |
michael@0 | 179 | mValue.mSharedList->AddRef(); |
michael@0 | 180 | } |
michael@0 | 181 | else if (eCSSUnit_PairList == mUnit) { |
michael@0 | 182 | mValue.mPairList = aCopy.mValue.mPairList; |
michael@0 | 183 | mValue.mPairList->AddRef(); |
michael@0 | 184 | } |
michael@0 | 185 | else if (eCSSUnit_PairListDep == mUnit) { |
michael@0 | 186 | mValue.mPairListDependent = aCopy.mValue.mPairListDependent; |
michael@0 | 187 | } |
michael@0 | 188 | else if (eCSSUnit_GridTemplateAreas == mUnit) { |
michael@0 | 189 | mValue.mGridTemplateAreas = aCopy.mValue.mGridTemplateAreas; |
michael@0 | 190 | mValue.mGridTemplateAreas->AddRef(); |
michael@0 | 191 | } |
michael@0 | 192 | else { |
michael@0 | 193 | NS_ABORT_IF_FALSE(false, "unknown unit"); |
michael@0 | 194 | } |
michael@0 | 195 | } |
michael@0 | 196 | |
michael@0 | 197 | nsCSSValue& nsCSSValue::operator=(const nsCSSValue& aCopy) |
michael@0 | 198 | { |
michael@0 | 199 | if (this != &aCopy) { |
michael@0 | 200 | Reset(); |
michael@0 | 201 | new (this) nsCSSValue(aCopy); |
michael@0 | 202 | } |
michael@0 | 203 | return *this; |
michael@0 | 204 | } |
michael@0 | 205 | |
michael@0 | 206 | bool nsCSSValue::operator==(const nsCSSValue& aOther) const |
michael@0 | 207 | { |
michael@0 | 208 | NS_ABORT_IF_FALSE(mUnit != eCSSUnit_ListDep && |
michael@0 | 209 | aOther.mUnit != eCSSUnit_ListDep && |
michael@0 | 210 | mUnit != eCSSUnit_PairListDep && |
michael@0 | 211 | aOther.mUnit != eCSSUnit_PairListDep, |
michael@0 | 212 | "don't use operator== with dependent lists"); |
michael@0 | 213 | |
michael@0 | 214 | if (mUnit == aOther.mUnit) { |
michael@0 | 215 | if (mUnit <= eCSSUnit_DummyInherit) { |
michael@0 | 216 | return true; |
michael@0 | 217 | } |
michael@0 | 218 | else if (UnitHasStringValue()) { |
michael@0 | 219 | return (NS_strcmp(GetBufferValue(mValue.mString), |
michael@0 | 220 | GetBufferValue(aOther.mValue.mString)) == 0); |
michael@0 | 221 | } |
michael@0 | 222 | else if ((eCSSUnit_Integer <= mUnit) && (mUnit <= eCSSUnit_EnumColor)) { |
michael@0 | 223 | return mValue.mInt == aOther.mValue.mInt; |
michael@0 | 224 | } |
michael@0 | 225 | else if (IsIntegerColorUnit()) { |
michael@0 | 226 | return mValue.mColor == aOther.mValue.mColor; |
michael@0 | 227 | } |
michael@0 | 228 | else if (IsFloatColorUnit()) { |
michael@0 | 229 | return *mValue.mFloatColor == *aOther.mValue.mFloatColor; |
michael@0 | 230 | } |
michael@0 | 231 | else if (UnitHasArrayValue()) { |
michael@0 | 232 | return *mValue.mArray == *aOther.mValue.mArray; |
michael@0 | 233 | } |
michael@0 | 234 | else if (eCSSUnit_URL == mUnit) { |
michael@0 | 235 | return *mValue.mURL == *aOther.mValue.mURL; |
michael@0 | 236 | } |
michael@0 | 237 | else if (eCSSUnit_Image == mUnit) { |
michael@0 | 238 | return *mValue.mImage == *aOther.mValue.mImage; |
michael@0 | 239 | } |
michael@0 | 240 | else if (eCSSUnit_Gradient == mUnit) { |
michael@0 | 241 | return *mValue.mGradient == *aOther.mValue.mGradient; |
michael@0 | 242 | } |
michael@0 | 243 | else if (eCSSUnit_TokenStream == mUnit) { |
michael@0 | 244 | return *mValue.mTokenStream == *aOther.mValue.mTokenStream; |
michael@0 | 245 | } |
michael@0 | 246 | else if (eCSSUnit_Pair == mUnit) { |
michael@0 | 247 | return *mValue.mPair == *aOther.mValue.mPair; |
michael@0 | 248 | } |
michael@0 | 249 | else if (eCSSUnit_Triplet == mUnit) { |
michael@0 | 250 | return *mValue.mTriplet == *aOther.mValue.mTriplet; |
michael@0 | 251 | } |
michael@0 | 252 | else if (eCSSUnit_Rect == mUnit) { |
michael@0 | 253 | return *mValue.mRect == *aOther.mValue.mRect; |
michael@0 | 254 | } |
michael@0 | 255 | else if (eCSSUnit_List == mUnit) { |
michael@0 | 256 | return *mValue.mList == *aOther.mValue.mList; |
michael@0 | 257 | } |
michael@0 | 258 | else if (eCSSUnit_SharedList == mUnit) { |
michael@0 | 259 | return *mValue.mSharedList == *aOther.mValue.mSharedList; |
michael@0 | 260 | } |
michael@0 | 261 | else if (eCSSUnit_PairList == mUnit) { |
michael@0 | 262 | return *mValue.mPairList == *aOther.mValue.mPairList; |
michael@0 | 263 | } |
michael@0 | 264 | else if (eCSSUnit_GridTemplateAreas == mUnit) { |
michael@0 | 265 | return *mValue.mGridTemplateAreas == *aOther.mValue.mGridTemplateAreas; |
michael@0 | 266 | } |
michael@0 | 267 | else { |
michael@0 | 268 | return mValue.mFloat == aOther.mValue.mFloat; |
michael@0 | 269 | } |
michael@0 | 270 | } |
michael@0 | 271 | return false; |
michael@0 | 272 | } |
michael@0 | 273 | |
michael@0 | 274 | double nsCSSValue::GetAngleValueInRadians() const |
michael@0 | 275 | { |
michael@0 | 276 | double angle = GetFloatValue(); |
michael@0 | 277 | |
michael@0 | 278 | switch (GetUnit()) { |
michael@0 | 279 | case eCSSUnit_Radian: return angle; |
michael@0 | 280 | case eCSSUnit_Turn: return angle * 2 * M_PI; |
michael@0 | 281 | case eCSSUnit_Degree: return angle * M_PI / 180.0; |
michael@0 | 282 | case eCSSUnit_Grad: return angle * M_PI / 200.0; |
michael@0 | 283 | |
michael@0 | 284 | default: |
michael@0 | 285 | NS_ABORT_IF_FALSE(false, "unrecognized angular unit"); |
michael@0 | 286 | return 0.0; |
michael@0 | 287 | } |
michael@0 | 288 | } |
michael@0 | 289 | |
michael@0 | 290 | imgRequestProxy* nsCSSValue::GetImageValue(nsIDocument* aDocument) const |
michael@0 | 291 | { |
michael@0 | 292 | NS_ABORT_IF_FALSE(mUnit == eCSSUnit_Image, "not an Image value"); |
michael@0 | 293 | return mValue.mImage->mRequests.GetWeak(aDocument); |
michael@0 | 294 | } |
michael@0 | 295 | |
michael@0 | 296 | nscoord nsCSSValue::GetFixedLength(nsPresContext* aPresContext) const |
michael@0 | 297 | { |
michael@0 | 298 | NS_ABORT_IF_FALSE(mUnit == eCSSUnit_PhysicalMillimeter, |
michael@0 | 299 | "not a fixed length unit"); |
michael@0 | 300 | |
michael@0 | 301 | float inches = mValue.mFloat / MM_PER_INCH_FLOAT; |
michael@0 | 302 | return NSToCoordFloorClamped(inches * |
michael@0 | 303 | float(aPresContext->DeviceContext()->AppUnitsPerPhysicalInch())); |
michael@0 | 304 | } |
michael@0 | 305 | |
michael@0 | 306 | nscoord nsCSSValue::GetPixelLength() const |
michael@0 | 307 | { |
michael@0 | 308 | NS_ABORT_IF_FALSE(IsPixelLengthUnit(), "not a fixed length unit"); |
michael@0 | 309 | |
michael@0 | 310 | double scaleFactor; |
michael@0 | 311 | switch (mUnit) { |
michael@0 | 312 | case eCSSUnit_Pixel: return nsPresContext::CSSPixelsToAppUnits(mValue.mFloat); |
michael@0 | 313 | case eCSSUnit_Pica: scaleFactor = 16.0; break; |
michael@0 | 314 | case eCSSUnit_Point: scaleFactor = 4/3.0; break; |
michael@0 | 315 | case eCSSUnit_Inch: scaleFactor = 96.0; break; |
michael@0 | 316 | case eCSSUnit_Millimeter: scaleFactor = 96/25.4; break; |
michael@0 | 317 | case eCSSUnit_Centimeter: scaleFactor = 96/2.54; break; |
michael@0 | 318 | default: |
michael@0 | 319 | NS_ERROR("should never get here"); |
michael@0 | 320 | return 0; |
michael@0 | 321 | } |
michael@0 | 322 | return nsPresContext::CSSPixelsToAppUnits(float(mValue.mFloat*scaleFactor)); |
michael@0 | 323 | } |
michael@0 | 324 | |
michael@0 | 325 | void nsCSSValue::DoReset() |
michael@0 | 326 | { |
michael@0 | 327 | if (UnitHasStringValue()) { |
michael@0 | 328 | mValue.mString->Release(); |
michael@0 | 329 | } else if (IsFloatColorUnit()) { |
michael@0 | 330 | mValue.mFloatColor->Release(); |
michael@0 | 331 | } else if (UnitHasArrayValue()) { |
michael@0 | 332 | mValue.mArray->Release(); |
michael@0 | 333 | } else if (eCSSUnit_URL == mUnit) { |
michael@0 | 334 | mValue.mURL->Release(); |
michael@0 | 335 | } else if (eCSSUnit_Image == mUnit) { |
michael@0 | 336 | mValue.mImage->Release(); |
michael@0 | 337 | } else if (eCSSUnit_Gradient == mUnit) { |
michael@0 | 338 | mValue.mGradient->Release(); |
michael@0 | 339 | } else if (eCSSUnit_TokenStream == mUnit) { |
michael@0 | 340 | mValue.mTokenStream->Release(); |
michael@0 | 341 | } else if (eCSSUnit_Pair == mUnit) { |
michael@0 | 342 | mValue.mPair->Release(); |
michael@0 | 343 | } else if (eCSSUnit_Triplet == mUnit) { |
michael@0 | 344 | mValue.mTriplet->Release(); |
michael@0 | 345 | } else if (eCSSUnit_Rect == mUnit) { |
michael@0 | 346 | mValue.mRect->Release(); |
michael@0 | 347 | } else if (eCSSUnit_List == mUnit) { |
michael@0 | 348 | mValue.mList->Release(); |
michael@0 | 349 | } else if (eCSSUnit_SharedList == mUnit) { |
michael@0 | 350 | mValue.mSharedList->Release(); |
michael@0 | 351 | } else if (eCSSUnit_PairList == mUnit) { |
michael@0 | 352 | mValue.mPairList->Release(); |
michael@0 | 353 | } else if (eCSSUnit_GridTemplateAreas == mUnit) { |
michael@0 | 354 | mValue.mGridTemplateAreas->Release(); |
michael@0 | 355 | } |
michael@0 | 356 | mUnit = eCSSUnit_Null; |
michael@0 | 357 | } |
michael@0 | 358 | |
michael@0 | 359 | void nsCSSValue::SetIntValue(int32_t aValue, nsCSSUnit aUnit) |
michael@0 | 360 | { |
michael@0 | 361 | NS_ABORT_IF_FALSE(aUnit == eCSSUnit_Integer || aUnit == eCSSUnit_Enumerated || |
michael@0 | 362 | aUnit == eCSSUnit_EnumColor, "not an int value"); |
michael@0 | 363 | Reset(); |
michael@0 | 364 | if (aUnit == eCSSUnit_Integer || aUnit == eCSSUnit_Enumerated || |
michael@0 | 365 | aUnit == eCSSUnit_EnumColor) { |
michael@0 | 366 | mUnit = aUnit; |
michael@0 | 367 | mValue.mInt = aValue; |
michael@0 | 368 | } |
michael@0 | 369 | } |
michael@0 | 370 | |
michael@0 | 371 | void nsCSSValue::SetPercentValue(float aValue) |
michael@0 | 372 | { |
michael@0 | 373 | Reset(); |
michael@0 | 374 | mUnit = eCSSUnit_Percent; |
michael@0 | 375 | mValue.mFloat = aValue; |
michael@0 | 376 | MOZ_ASSERT(!mozilla::IsNaN(mValue.mFloat)); |
michael@0 | 377 | } |
michael@0 | 378 | |
michael@0 | 379 | void nsCSSValue::SetFloatValue(float aValue, nsCSSUnit aUnit) |
michael@0 | 380 | { |
michael@0 | 381 | NS_ABORT_IF_FALSE(eCSSUnit_Number <= aUnit, "not a float value"); |
michael@0 | 382 | Reset(); |
michael@0 | 383 | if (eCSSUnit_Number <= aUnit) { |
michael@0 | 384 | mUnit = aUnit; |
michael@0 | 385 | mValue.mFloat = aValue; |
michael@0 | 386 | MOZ_ASSERT(!mozilla::IsNaN(mValue.mFloat)); |
michael@0 | 387 | } |
michael@0 | 388 | } |
michael@0 | 389 | |
michael@0 | 390 | void nsCSSValue::SetStringValue(const nsString& aValue, |
michael@0 | 391 | nsCSSUnit aUnit) |
michael@0 | 392 | { |
michael@0 | 393 | Reset(); |
michael@0 | 394 | mUnit = aUnit; |
michael@0 | 395 | NS_ABORT_IF_FALSE(UnitHasStringValue(), "not a string unit"); |
michael@0 | 396 | if (UnitHasStringValue()) { |
michael@0 | 397 | mValue.mString = BufferFromString(aValue).take(); |
michael@0 | 398 | } else |
michael@0 | 399 | mUnit = eCSSUnit_Null; |
michael@0 | 400 | } |
michael@0 | 401 | |
michael@0 | 402 | void nsCSSValue::SetColorValue(nscolor aValue) |
michael@0 | 403 | { |
michael@0 | 404 | SetIntegerColorValue(aValue, eCSSUnit_RGBAColor); |
michael@0 | 405 | } |
michael@0 | 406 | |
michael@0 | 407 | void nsCSSValue::SetIntegerColorValue(nscolor aValue, nsCSSUnit aUnit) |
michael@0 | 408 | { |
michael@0 | 409 | Reset(); |
michael@0 | 410 | mUnit = aUnit; |
michael@0 | 411 | NS_ABORT_IF_FALSE(IsIntegerColorUnit(), "bad unit"); |
michael@0 | 412 | mValue.mColor = aValue; |
michael@0 | 413 | } |
michael@0 | 414 | |
michael@0 | 415 | void nsCSSValue::SetFloatColorValue(float aComponent1, |
michael@0 | 416 | float aComponent2, |
michael@0 | 417 | float aComponent3, |
michael@0 | 418 | float aAlpha, |
michael@0 | 419 | nsCSSUnit aUnit) |
michael@0 | 420 | { |
michael@0 | 421 | Reset(); |
michael@0 | 422 | mUnit = aUnit; |
michael@0 | 423 | NS_ABORT_IF_FALSE(IsFloatColorUnit(), "bad unit"); |
michael@0 | 424 | mValue.mFloatColor = |
michael@0 | 425 | new nsCSSValueFloatColor(aComponent1, aComponent2, aComponent3, aAlpha); |
michael@0 | 426 | mValue.mFloatColor->AddRef(); |
michael@0 | 427 | } |
michael@0 | 428 | |
michael@0 | 429 | void nsCSSValue::SetArrayValue(nsCSSValue::Array* aValue, nsCSSUnit aUnit) |
michael@0 | 430 | { |
michael@0 | 431 | Reset(); |
michael@0 | 432 | mUnit = aUnit; |
michael@0 | 433 | NS_ABORT_IF_FALSE(UnitHasArrayValue(), "bad unit"); |
michael@0 | 434 | mValue.mArray = aValue; |
michael@0 | 435 | mValue.mArray->AddRef(); |
michael@0 | 436 | } |
michael@0 | 437 | |
michael@0 | 438 | void nsCSSValue::SetURLValue(mozilla::css::URLValue* aValue) |
michael@0 | 439 | { |
michael@0 | 440 | Reset(); |
michael@0 | 441 | mUnit = eCSSUnit_URL; |
michael@0 | 442 | mValue.mURL = aValue; |
michael@0 | 443 | mValue.mURL->AddRef(); |
michael@0 | 444 | } |
michael@0 | 445 | |
michael@0 | 446 | void nsCSSValue::SetImageValue(mozilla::css::ImageValue* aValue) |
michael@0 | 447 | { |
michael@0 | 448 | Reset(); |
michael@0 | 449 | mUnit = eCSSUnit_Image; |
michael@0 | 450 | mValue.mImage = aValue; |
michael@0 | 451 | mValue.mImage->AddRef(); |
michael@0 | 452 | } |
michael@0 | 453 | |
michael@0 | 454 | void nsCSSValue::SetGradientValue(nsCSSValueGradient* aValue) |
michael@0 | 455 | { |
michael@0 | 456 | Reset(); |
michael@0 | 457 | mUnit = eCSSUnit_Gradient; |
michael@0 | 458 | mValue.mGradient = aValue; |
michael@0 | 459 | mValue.mGradient->AddRef(); |
michael@0 | 460 | } |
michael@0 | 461 | |
michael@0 | 462 | void nsCSSValue::SetTokenStreamValue(nsCSSValueTokenStream* aValue) |
michael@0 | 463 | { |
michael@0 | 464 | Reset(); |
michael@0 | 465 | mUnit = eCSSUnit_TokenStream; |
michael@0 | 466 | mValue.mTokenStream = aValue; |
michael@0 | 467 | mValue.mTokenStream->AddRef(); |
michael@0 | 468 | } |
michael@0 | 469 | |
michael@0 | 470 | void nsCSSValue::SetGridTemplateAreas(mozilla::css::GridTemplateAreasValue* aValue) |
michael@0 | 471 | { |
michael@0 | 472 | Reset(); |
michael@0 | 473 | mUnit = eCSSUnit_GridTemplateAreas; |
michael@0 | 474 | mValue.mGridTemplateAreas = aValue; |
michael@0 | 475 | mValue.mGridTemplateAreas->AddRef(); |
michael@0 | 476 | } |
michael@0 | 477 | |
michael@0 | 478 | void nsCSSValue::SetPairValue(const nsCSSValuePair* aValue) |
michael@0 | 479 | { |
michael@0 | 480 | // pairs should not be used for null/inherit/initial values |
michael@0 | 481 | NS_ABORT_IF_FALSE(aValue && |
michael@0 | 482 | aValue->mXValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 483 | aValue->mYValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 484 | aValue->mXValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 485 | aValue->mYValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 486 | aValue->mXValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 487 | aValue->mYValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 488 | aValue->mXValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 489 | aValue->mYValue.GetUnit() != eCSSUnit_Unset, |
michael@0 | 490 | "missing or inappropriate pair value"); |
michael@0 | 491 | Reset(); |
michael@0 | 492 | mUnit = eCSSUnit_Pair; |
michael@0 | 493 | mValue.mPair = new nsCSSValuePair_heap(aValue->mXValue, aValue->mYValue); |
michael@0 | 494 | mValue.mPair->AddRef(); |
michael@0 | 495 | } |
michael@0 | 496 | |
michael@0 | 497 | void nsCSSValue::SetPairValue(const nsCSSValue& xValue, |
michael@0 | 498 | const nsCSSValue& yValue) |
michael@0 | 499 | { |
michael@0 | 500 | NS_ABORT_IF_FALSE(xValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 501 | yValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 502 | xValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 503 | yValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 504 | xValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 505 | yValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 506 | xValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 507 | yValue.GetUnit() != eCSSUnit_Unset, |
michael@0 | 508 | "inappropriate pair value"); |
michael@0 | 509 | Reset(); |
michael@0 | 510 | mUnit = eCSSUnit_Pair; |
michael@0 | 511 | mValue.mPair = new nsCSSValuePair_heap(xValue, yValue); |
michael@0 | 512 | mValue.mPair->AddRef(); |
michael@0 | 513 | } |
michael@0 | 514 | |
michael@0 | 515 | void nsCSSValue::SetTripletValue(const nsCSSValueTriplet* aValue) |
michael@0 | 516 | { |
michael@0 | 517 | // triplet should not be used for null/inherit/initial values |
michael@0 | 518 | NS_ABORT_IF_FALSE(aValue && |
michael@0 | 519 | aValue->mXValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 520 | aValue->mYValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 521 | aValue->mZValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 522 | aValue->mXValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 523 | aValue->mYValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 524 | aValue->mZValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 525 | aValue->mXValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 526 | aValue->mYValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 527 | aValue->mZValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 528 | aValue->mXValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 529 | aValue->mYValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 530 | aValue->mZValue.GetUnit() != eCSSUnit_Unset, |
michael@0 | 531 | "missing or inappropriate triplet value"); |
michael@0 | 532 | Reset(); |
michael@0 | 533 | mUnit = eCSSUnit_Triplet; |
michael@0 | 534 | mValue.mTriplet = new nsCSSValueTriplet_heap(aValue->mXValue, aValue->mYValue, aValue->mZValue); |
michael@0 | 535 | mValue.mTriplet->AddRef(); |
michael@0 | 536 | } |
michael@0 | 537 | |
michael@0 | 538 | void nsCSSValue::SetTripletValue(const nsCSSValue& xValue, |
michael@0 | 539 | const nsCSSValue& yValue, |
michael@0 | 540 | const nsCSSValue& zValue) |
michael@0 | 541 | { |
michael@0 | 542 | // Only allow Null for the z component |
michael@0 | 543 | NS_ABORT_IF_FALSE(xValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 544 | yValue.GetUnit() != eCSSUnit_Null && |
michael@0 | 545 | xValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 546 | yValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 547 | zValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 548 | xValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 549 | yValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 550 | zValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 551 | xValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 552 | yValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 553 | zValue.GetUnit() != eCSSUnit_Unset, |
michael@0 | 554 | "inappropriate triplet value"); |
michael@0 | 555 | Reset(); |
michael@0 | 556 | mUnit = eCSSUnit_Triplet; |
michael@0 | 557 | mValue.mTriplet = new nsCSSValueTriplet_heap(xValue, yValue, zValue); |
michael@0 | 558 | mValue.mTriplet->AddRef(); |
michael@0 | 559 | } |
michael@0 | 560 | |
michael@0 | 561 | nsCSSRect& nsCSSValue::SetRectValue() |
michael@0 | 562 | { |
michael@0 | 563 | Reset(); |
michael@0 | 564 | mUnit = eCSSUnit_Rect; |
michael@0 | 565 | mValue.mRect = new nsCSSRect_heap; |
michael@0 | 566 | mValue.mRect->AddRef(); |
michael@0 | 567 | return *mValue.mRect; |
michael@0 | 568 | } |
michael@0 | 569 | |
michael@0 | 570 | nsCSSValueList* nsCSSValue::SetListValue() |
michael@0 | 571 | { |
michael@0 | 572 | Reset(); |
michael@0 | 573 | mUnit = eCSSUnit_List; |
michael@0 | 574 | mValue.mList = new nsCSSValueList_heap; |
michael@0 | 575 | mValue.mList->AddRef(); |
michael@0 | 576 | return mValue.mList; |
michael@0 | 577 | } |
michael@0 | 578 | |
michael@0 | 579 | void nsCSSValue::SetSharedListValue(nsCSSValueSharedList* aList) |
michael@0 | 580 | { |
michael@0 | 581 | Reset(); |
michael@0 | 582 | mUnit = eCSSUnit_SharedList; |
michael@0 | 583 | mValue.mSharedList = aList; |
michael@0 | 584 | mValue.mSharedList->AddRef(); |
michael@0 | 585 | } |
michael@0 | 586 | |
michael@0 | 587 | void nsCSSValue::SetDependentListValue(nsCSSValueList* aList) |
michael@0 | 588 | { |
michael@0 | 589 | Reset(); |
michael@0 | 590 | if (aList) { |
michael@0 | 591 | mUnit = eCSSUnit_ListDep; |
michael@0 | 592 | mValue.mListDependent = aList; |
michael@0 | 593 | } |
michael@0 | 594 | } |
michael@0 | 595 | |
michael@0 | 596 | nsCSSValuePairList* nsCSSValue::SetPairListValue() |
michael@0 | 597 | { |
michael@0 | 598 | Reset(); |
michael@0 | 599 | mUnit = eCSSUnit_PairList; |
michael@0 | 600 | mValue.mPairList = new nsCSSValuePairList_heap; |
michael@0 | 601 | mValue.mPairList->AddRef(); |
michael@0 | 602 | return mValue.mPairList; |
michael@0 | 603 | } |
michael@0 | 604 | |
michael@0 | 605 | void nsCSSValue::SetDependentPairListValue(nsCSSValuePairList* aList) |
michael@0 | 606 | { |
michael@0 | 607 | Reset(); |
michael@0 | 608 | if (aList) { |
michael@0 | 609 | mUnit = eCSSUnit_PairListDep; |
michael@0 | 610 | mValue.mPairListDependent = aList; |
michael@0 | 611 | } |
michael@0 | 612 | } |
michael@0 | 613 | |
michael@0 | 614 | void nsCSSValue::SetAutoValue() |
michael@0 | 615 | { |
michael@0 | 616 | Reset(); |
michael@0 | 617 | mUnit = eCSSUnit_Auto; |
michael@0 | 618 | } |
michael@0 | 619 | |
michael@0 | 620 | void nsCSSValue::SetInheritValue() |
michael@0 | 621 | { |
michael@0 | 622 | Reset(); |
michael@0 | 623 | mUnit = eCSSUnit_Inherit; |
michael@0 | 624 | } |
michael@0 | 625 | |
michael@0 | 626 | void nsCSSValue::SetInitialValue() |
michael@0 | 627 | { |
michael@0 | 628 | Reset(); |
michael@0 | 629 | mUnit = eCSSUnit_Initial; |
michael@0 | 630 | } |
michael@0 | 631 | |
michael@0 | 632 | void nsCSSValue::SetUnsetValue() |
michael@0 | 633 | { |
michael@0 | 634 | Reset(); |
michael@0 | 635 | mUnit = eCSSUnit_Unset; |
michael@0 | 636 | } |
michael@0 | 637 | |
michael@0 | 638 | void nsCSSValue::SetNoneValue() |
michael@0 | 639 | { |
michael@0 | 640 | Reset(); |
michael@0 | 641 | mUnit = eCSSUnit_None; |
michael@0 | 642 | } |
michael@0 | 643 | |
michael@0 | 644 | void nsCSSValue::SetAllValue() |
michael@0 | 645 | { |
michael@0 | 646 | Reset(); |
michael@0 | 647 | mUnit = eCSSUnit_All; |
michael@0 | 648 | } |
michael@0 | 649 | |
michael@0 | 650 | void nsCSSValue::SetNormalValue() |
michael@0 | 651 | { |
michael@0 | 652 | Reset(); |
michael@0 | 653 | mUnit = eCSSUnit_Normal; |
michael@0 | 654 | } |
michael@0 | 655 | |
michael@0 | 656 | void nsCSSValue::SetSystemFontValue() |
michael@0 | 657 | { |
michael@0 | 658 | Reset(); |
michael@0 | 659 | mUnit = eCSSUnit_System_Font; |
michael@0 | 660 | } |
michael@0 | 661 | |
michael@0 | 662 | void nsCSSValue::SetDummyValue() |
michael@0 | 663 | { |
michael@0 | 664 | Reset(); |
michael@0 | 665 | mUnit = eCSSUnit_Dummy; |
michael@0 | 666 | } |
michael@0 | 667 | |
michael@0 | 668 | void nsCSSValue::SetDummyInheritValue() |
michael@0 | 669 | { |
michael@0 | 670 | Reset(); |
michael@0 | 671 | mUnit = eCSSUnit_DummyInherit; |
michael@0 | 672 | } |
michael@0 | 673 | |
michael@0 | 674 | void nsCSSValue::StartImageLoad(nsIDocument* aDocument) const |
michael@0 | 675 | { |
michael@0 | 676 | NS_ABORT_IF_FALSE(eCSSUnit_URL == mUnit, "Not a URL value!"); |
michael@0 | 677 | mozilla::css::ImageValue* image = |
michael@0 | 678 | new mozilla::css::ImageValue(mValue.mURL->GetURI(), |
michael@0 | 679 | mValue.mURL->mString, |
michael@0 | 680 | mValue.mURL->mReferrer, |
michael@0 | 681 | mValue.mURL->mOriginPrincipal, |
michael@0 | 682 | aDocument); |
michael@0 | 683 | |
michael@0 | 684 | nsCSSValue* writable = const_cast<nsCSSValue*>(this); |
michael@0 | 685 | writable->SetImageValue(image); |
michael@0 | 686 | } |
michael@0 | 687 | |
michael@0 | 688 | nscolor nsCSSValue::GetColorValue() const |
michael@0 | 689 | { |
michael@0 | 690 | NS_ABORT_IF_FALSE(IsNumericColorUnit(), "not a color value"); |
michael@0 | 691 | if (IsFloatColorUnit()) { |
michael@0 | 692 | return mValue.mFloatColor->GetColorValue(mUnit); |
michael@0 | 693 | } |
michael@0 | 694 | return mValue.mColor; |
michael@0 | 695 | } |
michael@0 | 696 | |
michael@0 | 697 | bool nsCSSValue::IsNonTransparentColor() const |
michael@0 | 698 | { |
michael@0 | 699 | // We have the value in the form it was specified in at this point, so we |
michael@0 | 700 | // have to look for both the keyword 'transparent' and its equivalent in |
michael@0 | 701 | // rgba notation. |
michael@0 | 702 | nsDependentString buf; |
michael@0 | 703 | return |
michael@0 | 704 | (IsIntegerColorUnit() && NS_GET_A(GetColorValue()) > 0) || |
michael@0 | 705 | (IsFloatColorUnit() && mValue.mFloatColor->IsNonTransparentColor()) || |
michael@0 | 706 | (mUnit == eCSSUnit_Ident && |
michael@0 | 707 | !nsGkAtoms::transparent->Equals(GetStringValue(buf))) || |
michael@0 | 708 | (mUnit == eCSSUnit_EnumColor); |
michael@0 | 709 | } |
michael@0 | 710 | |
michael@0 | 711 | nsCSSValue::Array* |
michael@0 | 712 | nsCSSValue::InitFunction(nsCSSKeyword aFunctionId, uint32_t aNumArgs) |
michael@0 | 713 | { |
michael@0 | 714 | nsRefPtr<nsCSSValue::Array> func = Array::Create(aNumArgs + 1); |
michael@0 | 715 | func->Item(0).SetIntValue(aFunctionId, eCSSUnit_Enumerated); |
michael@0 | 716 | SetArrayValue(func, eCSSUnit_Function); |
michael@0 | 717 | return func; |
michael@0 | 718 | } |
michael@0 | 719 | |
michael@0 | 720 | bool |
michael@0 | 721 | nsCSSValue::EqualsFunction(nsCSSKeyword aFunctionId) const |
michael@0 | 722 | { |
michael@0 | 723 | if (mUnit != eCSSUnit_Function) { |
michael@0 | 724 | return false; |
michael@0 | 725 | } |
michael@0 | 726 | |
michael@0 | 727 | nsCSSValue::Array* func = mValue.mArray; |
michael@0 | 728 | NS_ABORT_IF_FALSE(func && func->Count() >= 1 && |
michael@0 | 729 | func->Item(0).GetUnit() == eCSSUnit_Enumerated, |
michael@0 | 730 | "illegally structured function value"); |
michael@0 | 731 | |
michael@0 | 732 | nsCSSKeyword thisFunctionId = func->Item(0).GetKeywordValue(); |
michael@0 | 733 | return thisFunctionId == aFunctionId; |
michael@0 | 734 | } |
michael@0 | 735 | |
michael@0 | 736 | // static |
michael@0 | 737 | already_AddRefed<nsStringBuffer> |
michael@0 | 738 | nsCSSValue::BufferFromString(const nsString& aValue) |
michael@0 | 739 | { |
michael@0 | 740 | nsRefPtr<nsStringBuffer> buffer = nsStringBuffer::FromString(aValue); |
michael@0 | 741 | if (buffer) { |
michael@0 | 742 | return buffer.forget(); |
michael@0 | 743 | } |
michael@0 | 744 | |
michael@0 | 745 | nsString::size_type length = aValue.Length(); |
michael@0 | 746 | |
michael@0 | 747 | // NOTE: Alloc prouduces a new, already-addref'd (refcnt = 1) buffer. |
michael@0 | 748 | // NOTE: String buffer allocation is currently fallible. |
michael@0 | 749 | buffer = nsStringBuffer::Alloc((length + 1) * sizeof(char16_t)); |
michael@0 | 750 | if (MOZ_UNLIKELY(!buffer)) { |
michael@0 | 751 | NS_RUNTIMEABORT("out of memory"); |
michael@0 | 752 | } |
michael@0 | 753 | |
michael@0 | 754 | char16_t* data = static_cast<char16_t*>(buffer->Data()); |
michael@0 | 755 | nsCharTraits<char16_t>::copy(data, aValue.get(), length); |
michael@0 | 756 | // Null-terminate. |
michael@0 | 757 | data[length] = 0; |
michael@0 | 758 | return buffer.forget(); |
michael@0 | 759 | } |
michael@0 | 760 | |
michael@0 | 761 | namespace { |
michael@0 | 762 | |
michael@0 | 763 | struct CSSValueSerializeCalcOps { |
michael@0 | 764 | CSSValueSerializeCalcOps(nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 765 | nsCSSValue::Serialization aSerialization) |
michael@0 | 766 | : mProperty(aProperty), |
michael@0 | 767 | mResult(aResult), |
michael@0 | 768 | mValueSerialization(aSerialization) |
michael@0 | 769 | { |
michael@0 | 770 | } |
michael@0 | 771 | |
michael@0 | 772 | typedef nsCSSValue input_type; |
michael@0 | 773 | typedef nsCSSValue::Array input_array_type; |
michael@0 | 774 | |
michael@0 | 775 | static nsCSSUnit GetUnit(const input_type& aValue) { |
michael@0 | 776 | return aValue.GetUnit(); |
michael@0 | 777 | } |
michael@0 | 778 | |
michael@0 | 779 | void Append(const char* aString) |
michael@0 | 780 | { |
michael@0 | 781 | mResult.AppendASCII(aString); |
michael@0 | 782 | } |
michael@0 | 783 | |
michael@0 | 784 | void AppendLeafValue(const input_type& aValue) |
michael@0 | 785 | { |
michael@0 | 786 | NS_ABORT_IF_FALSE(aValue.GetUnit() == eCSSUnit_Percent || |
michael@0 | 787 | aValue.IsLengthUnit(), "unexpected unit"); |
michael@0 | 788 | aValue.AppendToString(mProperty, mResult, mValueSerialization); |
michael@0 | 789 | } |
michael@0 | 790 | |
michael@0 | 791 | void AppendNumber(const input_type& aValue) |
michael@0 | 792 | { |
michael@0 | 793 | NS_ABORT_IF_FALSE(aValue.GetUnit() == eCSSUnit_Number, "unexpected unit"); |
michael@0 | 794 | aValue.AppendToString(mProperty, mResult, mValueSerialization); |
michael@0 | 795 | } |
michael@0 | 796 | |
michael@0 | 797 | private: |
michael@0 | 798 | nsCSSProperty mProperty; |
michael@0 | 799 | nsAString &mResult; |
michael@0 | 800 | nsCSSValue::Serialization mValueSerialization; |
michael@0 | 801 | }; |
michael@0 | 802 | |
michael@0 | 803 | } // anonymous namespace |
michael@0 | 804 | |
michael@0 | 805 | void |
michael@0 | 806 | nsCSSValue::AppendToString(nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 807 | Serialization aSerialization) const |
michael@0 | 808 | { |
michael@0 | 809 | // eCSSProperty_UNKNOWN gets used for some recursive calls below. |
michael@0 | 810 | NS_ABORT_IF_FALSE((0 <= aProperty && |
michael@0 | 811 | aProperty <= eCSSProperty_COUNT_no_shorthands) || |
michael@0 | 812 | aProperty == eCSSProperty_UNKNOWN, |
michael@0 | 813 | "property ID out of range"); |
michael@0 | 814 | |
michael@0 | 815 | nsCSSUnit unit = GetUnit(); |
michael@0 | 816 | if (unit == eCSSUnit_Null) { |
michael@0 | 817 | return; |
michael@0 | 818 | } |
michael@0 | 819 | |
michael@0 | 820 | if (eCSSUnit_String <= unit && unit <= eCSSUnit_Attr) { |
michael@0 | 821 | if (unit == eCSSUnit_Attr) { |
michael@0 | 822 | aResult.AppendLiteral("attr("); |
michael@0 | 823 | } |
michael@0 | 824 | nsAutoString buffer; |
michael@0 | 825 | GetStringValue(buffer); |
michael@0 | 826 | if (unit == eCSSUnit_String) { |
michael@0 | 827 | nsStyleUtil::AppendEscapedCSSString(buffer, aResult); |
michael@0 | 828 | } else if (unit == eCSSUnit_Families) { |
michael@0 | 829 | // XXX We really need to do *some* escaping. |
michael@0 | 830 | aResult.Append(buffer); |
michael@0 | 831 | } else { |
michael@0 | 832 | nsStyleUtil::AppendEscapedCSSIdent(buffer, aResult); |
michael@0 | 833 | } |
michael@0 | 834 | } |
michael@0 | 835 | else if (eCSSUnit_Array <= unit && unit <= eCSSUnit_Steps) { |
michael@0 | 836 | switch (unit) { |
michael@0 | 837 | case eCSSUnit_Counter: aResult.AppendLiteral("counter("); break; |
michael@0 | 838 | case eCSSUnit_Counters: aResult.AppendLiteral("counters("); break; |
michael@0 | 839 | case eCSSUnit_Cubic_Bezier: aResult.AppendLiteral("cubic-bezier("); break; |
michael@0 | 840 | case eCSSUnit_Steps: aResult.AppendLiteral("steps("); break; |
michael@0 | 841 | default: break; |
michael@0 | 842 | } |
michael@0 | 843 | |
michael@0 | 844 | nsCSSValue::Array *array = GetArrayValue(); |
michael@0 | 845 | bool mark = false; |
michael@0 | 846 | for (size_t i = 0, i_end = array->Count(); i < i_end; ++i) { |
michael@0 | 847 | if (mark && array->Item(i).GetUnit() != eCSSUnit_Null) { |
michael@0 | 848 | if (unit == eCSSUnit_Array && |
michael@0 | 849 | eCSSProperty_transition_timing_function != aProperty) |
michael@0 | 850 | aResult.AppendLiteral(" "); |
michael@0 | 851 | else |
michael@0 | 852 | aResult.AppendLiteral(", "); |
michael@0 | 853 | } |
michael@0 | 854 | if (unit == eCSSUnit_Steps && i == 1) { |
michael@0 | 855 | NS_ABORT_IF_FALSE(array->Item(i).GetUnit() == eCSSUnit_Enumerated && |
michael@0 | 856 | (array->Item(i).GetIntValue() == |
michael@0 | 857 | NS_STYLE_TRANSITION_TIMING_FUNCTION_STEP_START || |
michael@0 | 858 | array->Item(i).GetIntValue() == |
michael@0 | 859 | NS_STYLE_TRANSITION_TIMING_FUNCTION_STEP_END), |
michael@0 | 860 | "unexpected value"); |
michael@0 | 861 | if (array->Item(i).GetIntValue() == |
michael@0 | 862 | NS_STYLE_TRANSITION_TIMING_FUNCTION_STEP_START) { |
michael@0 | 863 | aResult.AppendLiteral("start"); |
michael@0 | 864 | } else { |
michael@0 | 865 | aResult.AppendLiteral("end"); |
michael@0 | 866 | } |
michael@0 | 867 | continue; |
michael@0 | 868 | } |
michael@0 | 869 | nsCSSProperty prop = |
michael@0 | 870 | ((eCSSUnit_Counter <= unit && unit <= eCSSUnit_Counters) && |
michael@0 | 871 | i == array->Count() - 1) |
michael@0 | 872 | ? eCSSProperty_list_style_type : aProperty; |
michael@0 | 873 | if (array->Item(i).GetUnit() != eCSSUnit_Null) { |
michael@0 | 874 | array->Item(i).AppendToString(prop, aResult, aSerialization); |
michael@0 | 875 | mark = true; |
michael@0 | 876 | } |
michael@0 | 877 | } |
michael@0 | 878 | if (eCSSUnit_Array == unit && |
michael@0 | 879 | aProperty == eCSSProperty_transition_timing_function) { |
michael@0 | 880 | aResult.AppendLiteral(")"); |
michael@0 | 881 | } |
michael@0 | 882 | } |
michael@0 | 883 | /* Although Function is backed by an Array, we'll handle it separately |
michael@0 | 884 | * because it's a bit quirky. |
michael@0 | 885 | */ |
michael@0 | 886 | else if (eCSSUnit_Function == unit) { |
michael@0 | 887 | const nsCSSValue::Array* array = GetArrayValue(); |
michael@0 | 888 | NS_ABORT_IF_FALSE(array->Count() >= 1, |
michael@0 | 889 | "Functions must have at least one element for the name."); |
michael@0 | 890 | |
michael@0 | 891 | /* Append the function name. */ |
michael@0 | 892 | const nsCSSValue& functionName = array->Item(0); |
michael@0 | 893 | if (functionName.GetUnit() == eCSSUnit_Enumerated) { |
michael@0 | 894 | // We assume that the first argument is always of nsCSSKeyword type. |
michael@0 | 895 | const nsCSSKeyword functionId = functionName.GetKeywordValue(); |
michael@0 | 896 | NS_ConvertASCIItoUTF16 ident(nsCSSKeywords::GetStringValue(functionId)); |
michael@0 | 897 | // Bug 721136: Normalize the identifier to lowercase, except that things |
michael@0 | 898 | // like scaleX should have the last character capitalized. This matches |
michael@0 | 899 | // what other browsers do. |
michael@0 | 900 | switch (functionId) { |
michael@0 | 901 | case eCSSKeyword_rotatex: |
michael@0 | 902 | case eCSSKeyword_scalex: |
michael@0 | 903 | case eCSSKeyword_skewx: |
michael@0 | 904 | case eCSSKeyword_translatex: |
michael@0 | 905 | ident.Replace(ident.Length() - 1, 1, char16_t('X')); |
michael@0 | 906 | break; |
michael@0 | 907 | |
michael@0 | 908 | case eCSSKeyword_rotatey: |
michael@0 | 909 | case eCSSKeyword_scaley: |
michael@0 | 910 | case eCSSKeyword_skewy: |
michael@0 | 911 | case eCSSKeyword_translatey: |
michael@0 | 912 | ident.Replace(ident.Length() - 1, 1, char16_t('Y')); |
michael@0 | 913 | break; |
michael@0 | 914 | |
michael@0 | 915 | case eCSSKeyword_rotatez: |
michael@0 | 916 | case eCSSKeyword_scalez: |
michael@0 | 917 | case eCSSKeyword_translatez: |
michael@0 | 918 | ident.Replace(ident.Length() - 1, 1, char16_t('Z')); |
michael@0 | 919 | break; |
michael@0 | 920 | |
michael@0 | 921 | default: |
michael@0 | 922 | break; |
michael@0 | 923 | } |
michael@0 | 924 | nsStyleUtil::AppendEscapedCSSIdent(ident, aResult); |
michael@0 | 925 | } else { |
michael@0 | 926 | MOZ_ASSERT(false, "should no longer have non-enumerated functions"); |
michael@0 | 927 | } |
michael@0 | 928 | aResult.AppendLiteral("("); |
michael@0 | 929 | |
michael@0 | 930 | /* Now, step through the function contents, writing each of them as we go. */ |
michael@0 | 931 | for (size_t index = 1; index < array->Count(); ++index) { |
michael@0 | 932 | array->Item(index).AppendToString(aProperty, aResult, |
michael@0 | 933 | aSerialization); |
michael@0 | 934 | |
michael@0 | 935 | /* If we're not at the final element, append a comma. */ |
michael@0 | 936 | if (index + 1 != array->Count()) |
michael@0 | 937 | aResult.AppendLiteral(", "); |
michael@0 | 938 | } |
michael@0 | 939 | |
michael@0 | 940 | /* Finally, append the closing parenthesis. */ |
michael@0 | 941 | aResult.AppendLiteral(")"); |
michael@0 | 942 | } |
michael@0 | 943 | else if (IsCalcUnit()) { |
michael@0 | 944 | NS_ABORT_IF_FALSE(GetUnit() == eCSSUnit_Calc, "unexpected unit"); |
michael@0 | 945 | CSSValueSerializeCalcOps ops(aProperty, aResult, aSerialization); |
michael@0 | 946 | css::SerializeCalc(*this, ops); |
michael@0 | 947 | } |
michael@0 | 948 | else if (eCSSUnit_Integer == unit) { |
michael@0 | 949 | aResult.AppendInt(GetIntValue(), 10); |
michael@0 | 950 | } |
michael@0 | 951 | else if (eCSSUnit_Enumerated == unit) { |
michael@0 | 952 | int32_t intValue = GetIntValue(); |
michael@0 | 953 | switch(aProperty) { |
michael@0 | 954 | |
michael@0 | 955 | |
michael@0 | 956 | case eCSSProperty_text_combine_upright: |
michael@0 | 957 | if (intValue <= NS_STYLE_TEXT_COMBINE_UPRIGHT_ALL) { |
michael@0 | 958 | AppendASCIItoUTF16(nsCSSProps::LookupPropertyValue(aProperty, intValue), |
michael@0 | 959 | aResult); |
michael@0 | 960 | } else if (intValue == NS_STYLE_TEXT_COMBINE_UPRIGHT_DIGITS_2) { |
michael@0 | 961 | aResult.AppendLiteral("digits 2"); |
michael@0 | 962 | } else if (intValue == NS_STYLE_TEXT_COMBINE_UPRIGHT_DIGITS_3) { |
michael@0 | 963 | aResult.AppendLiteral("digits 3"); |
michael@0 | 964 | } else { |
michael@0 | 965 | aResult.AppendLiteral("digits 4"); |
michael@0 | 966 | } |
michael@0 | 967 | break; |
michael@0 | 968 | |
michael@0 | 969 | case eCSSProperty_text_decoration_line: |
michael@0 | 970 | if (NS_STYLE_TEXT_DECORATION_LINE_NONE == intValue) { |
michael@0 | 971 | AppendASCIItoUTF16(nsCSSProps::LookupPropertyValue(aProperty, intValue), |
michael@0 | 972 | aResult); |
michael@0 | 973 | } else { |
michael@0 | 974 | // Ignore the "override all" internal value. |
michael@0 | 975 | // (It doesn't have a string representation.) |
michael@0 | 976 | intValue &= ~NS_STYLE_TEXT_DECORATION_LINE_OVERRIDE_ALL; |
michael@0 | 977 | nsStyleUtil::AppendBitmaskCSSValue( |
michael@0 | 978 | aProperty, intValue, |
michael@0 | 979 | NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE, |
michael@0 | 980 | NS_STYLE_TEXT_DECORATION_LINE_PREF_ANCHORS, |
michael@0 | 981 | aResult); |
michael@0 | 982 | } |
michael@0 | 983 | break; |
michael@0 | 984 | |
michael@0 | 985 | case eCSSProperty_marks: |
michael@0 | 986 | if (intValue == NS_STYLE_PAGE_MARKS_NONE) { |
michael@0 | 987 | AppendASCIItoUTF16(nsCSSProps::LookupPropertyValue(aProperty, intValue), |
michael@0 | 988 | aResult); |
michael@0 | 989 | } else { |
michael@0 | 990 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 991 | NS_STYLE_PAGE_MARKS_CROP, |
michael@0 | 992 | NS_STYLE_PAGE_MARKS_REGISTER, |
michael@0 | 993 | aResult); |
michael@0 | 994 | } |
michael@0 | 995 | break; |
michael@0 | 996 | |
michael@0 | 997 | case eCSSProperty_paint_order: |
michael@0 | 998 | static_assert |
michael@0 | 999 | (NS_STYLE_PAINT_ORDER_BITWIDTH * NS_STYLE_PAINT_ORDER_LAST_VALUE <= 8, |
michael@0 | 1000 | "SVGStyleStruct::mPaintOrder and the following cast not big enough"); |
michael@0 | 1001 | nsStyleUtil::AppendPaintOrderValue(static_cast<uint8_t>(GetIntValue()), |
michael@0 | 1002 | aResult); |
michael@0 | 1003 | break; |
michael@0 | 1004 | |
michael@0 | 1005 | case eCSSProperty_font_synthesis: |
michael@0 | 1006 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 1007 | NS_FONT_SYNTHESIS_WEIGHT, |
michael@0 | 1008 | NS_FONT_SYNTHESIS_STYLE, |
michael@0 | 1009 | aResult); |
michael@0 | 1010 | break; |
michael@0 | 1011 | |
michael@0 | 1012 | case eCSSProperty_font_variant_east_asian: |
michael@0 | 1013 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 1014 | NS_FONT_VARIANT_EAST_ASIAN_JIS78, |
michael@0 | 1015 | NS_FONT_VARIANT_EAST_ASIAN_RUBY, |
michael@0 | 1016 | aResult); |
michael@0 | 1017 | break; |
michael@0 | 1018 | |
michael@0 | 1019 | case eCSSProperty_font_variant_ligatures: |
michael@0 | 1020 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 1021 | NS_FONT_VARIANT_LIGATURES_NONE, |
michael@0 | 1022 | NS_FONT_VARIANT_LIGATURES_NO_CONTEXTUAL, |
michael@0 | 1023 | aResult); |
michael@0 | 1024 | break; |
michael@0 | 1025 | |
michael@0 | 1026 | case eCSSProperty_font_variant_numeric: |
michael@0 | 1027 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 1028 | NS_FONT_VARIANT_NUMERIC_LINING, |
michael@0 | 1029 | NS_FONT_VARIANT_NUMERIC_ORDINAL, |
michael@0 | 1030 | aResult); |
michael@0 | 1031 | break; |
michael@0 | 1032 | |
michael@0 | 1033 | case eCSSProperty_grid_auto_flow: |
michael@0 | 1034 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 1035 | NS_STYLE_GRID_AUTO_FLOW_NONE, |
michael@0 | 1036 | NS_STYLE_GRID_AUTO_FLOW_DENSE, |
michael@0 | 1037 | aResult); |
michael@0 | 1038 | break; |
michael@0 | 1039 | |
michael@0 | 1040 | case eCSSProperty_grid_auto_position: |
michael@0 | 1041 | case eCSSProperty_grid_column_start: |
michael@0 | 1042 | case eCSSProperty_grid_column_end: |
michael@0 | 1043 | case eCSSProperty_grid_row_start: |
michael@0 | 1044 | case eCSSProperty_grid_row_end: |
michael@0 | 1045 | // "span" is the only enumerated-unit value for these properties |
michael@0 | 1046 | aResult.AppendLiteral("span"); |
michael@0 | 1047 | break; |
michael@0 | 1048 | |
michael@0 | 1049 | case eCSSProperty_touch_action: |
michael@0 | 1050 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, intValue, |
michael@0 | 1051 | NS_STYLE_TOUCH_ACTION_NONE, |
michael@0 | 1052 | NS_STYLE_TOUCH_ACTION_MANIPULATION, |
michael@0 | 1053 | aResult); |
michael@0 | 1054 | break; |
michael@0 | 1055 | |
michael@0 | 1056 | default: |
michael@0 | 1057 | const nsAFlatCString& name = nsCSSProps::LookupPropertyValue(aProperty, intValue); |
michael@0 | 1058 | AppendASCIItoUTF16(name, aResult); |
michael@0 | 1059 | break; |
michael@0 | 1060 | } |
michael@0 | 1061 | } |
michael@0 | 1062 | else if (eCSSUnit_EnumColor == unit) { |
michael@0 | 1063 | // we can lookup the property in the ColorTable and then |
michael@0 | 1064 | // get a string mapping the name |
michael@0 | 1065 | nsAutoCString str; |
michael@0 | 1066 | if (nsCSSProps::GetColorName(GetIntValue(), str)){ |
michael@0 | 1067 | AppendASCIItoUTF16(str, aResult); |
michael@0 | 1068 | } else { |
michael@0 | 1069 | NS_ABORT_IF_FALSE(false, "bad color value"); |
michael@0 | 1070 | } |
michael@0 | 1071 | } |
michael@0 | 1072 | else if (IsNumericColorUnit(unit)) { |
michael@0 | 1073 | if (aSerialization == eNormalized || |
michael@0 | 1074 | unit == eCSSUnit_RGBColor || |
michael@0 | 1075 | unit == eCSSUnit_RGBAColor) { |
michael@0 | 1076 | nscolor color = GetColorValue(); |
michael@0 | 1077 | if (aSerialization == eNormalized && |
michael@0 | 1078 | color == NS_RGBA(0, 0, 0, 0)) { |
michael@0 | 1079 | // Use the strictest match for 'transparent' so we do correct |
michael@0 | 1080 | // round-tripping of all other rgba() values. |
michael@0 | 1081 | aResult.AppendLiteral("transparent"); |
michael@0 | 1082 | } else { |
michael@0 | 1083 | uint8_t a = NS_GET_A(color); |
michael@0 | 1084 | bool showAlpha = |
michael@0 | 1085 | (aSerialization == eNormalized && a < 255) || |
michael@0 | 1086 | (aSerialization == eAuthorSpecified && |
michael@0 | 1087 | unit == eCSSUnit_RGBAColor); |
michael@0 | 1088 | if (showAlpha) { |
michael@0 | 1089 | aResult.AppendLiteral("rgba("); |
michael@0 | 1090 | } else { |
michael@0 | 1091 | aResult.AppendLiteral("rgb("); |
michael@0 | 1092 | } |
michael@0 | 1093 | |
michael@0 | 1094 | NS_NAMED_LITERAL_STRING(comma, ", "); |
michael@0 | 1095 | |
michael@0 | 1096 | aResult.AppendInt(NS_GET_R(color), 10); |
michael@0 | 1097 | aResult.Append(comma); |
michael@0 | 1098 | aResult.AppendInt(NS_GET_G(color), 10); |
michael@0 | 1099 | aResult.Append(comma); |
michael@0 | 1100 | aResult.AppendInt(NS_GET_B(color), 10); |
michael@0 | 1101 | if (showAlpha) { |
michael@0 | 1102 | aResult.Append(comma); |
michael@0 | 1103 | aResult.AppendFloat(nsStyleUtil::ColorComponentToFloat(a)); |
michael@0 | 1104 | } |
michael@0 | 1105 | aResult.Append(char16_t(')')); |
michael@0 | 1106 | } |
michael@0 | 1107 | } else if (eCSSUnit_HexColor == unit) { |
michael@0 | 1108 | nscolor color = GetColorValue(); |
michael@0 | 1109 | aResult.Append('#'); |
michael@0 | 1110 | aResult.AppendPrintf("%02x", NS_GET_R(color)); |
michael@0 | 1111 | aResult.AppendPrintf("%02x", NS_GET_G(color)); |
michael@0 | 1112 | aResult.AppendPrintf("%02x", NS_GET_B(color)); |
michael@0 | 1113 | } else if (eCSSUnit_ShortHexColor == unit) { |
michael@0 | 1114 | nscolor color = GetColorValue(); |
michael@0 | 1115 | aResult.Append('#'); |
michael@0 | 1116 | aResult.AppendInt(NS_GET_R(color) / 0x11, 16); |
michael@0 | 1117 | aResult.AppendInt(NS_GET_G(color) / 0x11, 16); |
michael@0 | 1118 | aResult.AppendInt(NS_GET_B(color) / 0x11, 16); |
michael@0 | 1119 | } else { |
michael@0 | 1120 | MOZ_ASSERT(IsFloatColorUnit()); |
michael@0 | 1121 | mValue.mFloatColor->AppendToString(unit, aResult); |
michael@0 | 1122 | } |
michael@0 | 1123 | } |
michael@0 | 1124 | else if (eCSSUnit_URL == unit || eCSSUnit_Image == unit) { |
michael@0 | 1125 | aResult.Append(NS_LITERAL_STRING("url(")); |
michael@0 | 1126 | nsStyleUtil::AppendEscapedCSSString( |
michael@0 | 1127 | nsDependentString(GetOriginalURLValue()), aResult); |
michael@0 | 1128 | aResult.Append(NS_LITERAL_STRING(")")); |
michael@0 | 1129 | } |
michael@0 | 1130 | else if (eCSSUnit_Element == unit) { |
michael@0 | 1131 | aResult.Append(NS_LITERAL_STRING("-moz-element(#")); |
michael@0 | 1132 | nsAutoString tmpStr; |
michael@0 | 1133 | GetStringValue(tmpStr); |
michael@0 | 1134 | nsStyleUtil::AppendEscapedCSSIdent(tmpStr, aResult); |
michael@0 | 1135 | aResult.Append(NS_LITERAL_STRING(")")); |
michael@0 | 1136 | } |
michael@0 | 1137 | else if (eCSSUnit_Percent == unit) { |
michael@0 | 1138 | aResult.AppendFloat(GetPercentValue() * 100.0f); |
michael@0 | 1139 | } |
michael@0 | 1140 | else if (eCSSUnit_Percent < unit) { // length unit |
michael@0 | 1141 | aResult.AppendFloat(GetFloatValue()); |
michael@0 | 1142 | } |
michael@0 | 1143 | else if (eCSSUnit_Gradient == unit) { |
michael@0 | 1144 | nsCSSValueGradient* gradient = GetGradientValue(); |
michael@0 | 1145 | |
michael@0 | 1146 | if (gradient->mIsLegacySyntax) { |
michael@0 | 1147 | aResult.AppendLiteral("-moz-"); |
michael@0 | 1148 | } |
michael@0 | 1149 | if (gradient->mIsRepeating) { |
michael@0 | 1150 | aResult.AppendLiteral("repeating-"); |
michael@0 | 1151 | } |
michael@0 | 1152 | if (gradient->mIsRadial) { |
michael@0 | 1153 | aResult.AppendLiteral("radial-gradient("); |
michael@0 | 1154 | } else { |
michael@0 | 1155 | aResult.AppendLiteral("linear-gradient("); |
michael@0 | 1156 | } |
michael@0 | 1157 | |
michael@0 | 1158 | bool needSep = false; |
michael@0 | 1159 | if (gradient->mIsRadial && !gradient->mIsLegacySyntax) { |
michael@0 | 1160 | if (!gradient->mIsExplicitSize) { |
michael@0 | 1161 | if (gradient->GetRadialShape().GetUnit() != eCSSUnit_None) { |
michael@0 | 1162 | NS_ABORT_IF_FALSE(gradient->GetRadialShape().GetUnit() == |
michael@0 | 1163 | eCSSUnit_Enumerated, |
michael@0 | 1164 | "bad unit for radial gradient shape"); |
michael@0 | 1165 | int32_t intValue = gradient->GetRadialShape().GetIntValue(); |
michael@0 | 1166 | NS_ABORT_IF_FALSE(intValue != NS_STYLE_GRADIENT_SHAPE_LINEAR, |
michael@0 | 1167 | "radial gradient with linear shape?!"); |
michael@0 | 1168 | AppendASCIItoUTF16(nsCSSProps::ValueToKeyword(intValue, |
michael@0 | 1169 | nsCSSProps::kRadialGradientShapeKTable), |
michael@0 | 1170 | aResult); |
michael@0 | 1171 | needSep = true; |
michael@0 | 1172 | } |
michael@0 | 1173 | |
michael@0 | 1174 | if (gradient->GetRadialSize().GetUnit() != eCSSUnit_None) { |
michael@0 | 1175 | if (needSep) { |
michael@0 | 1176 | aResult.AppendLiteral(" "); |
michael@0 | 1177 | } |
michael@0 | 1178 | NS_ABORT_IF_FALSE(gradient->GetRadialSize().GetUnit() == |
michael@0 | 1179 | eCSSUnit_Enumerated, |
michael@0 | 1180 | "bad unit for radial gradient size"); |
michael@0 | 1181 | int32_t intValue = gradient->GetRadialSize().GetIntValue(); |
michael@0 | 1182 | AppendASCIItoUTF16(nsCSSProps::ValueToKeyword(intValue, |
michael@0 | 1183 | nsCSSProps::kRadialGradientSizeKTable), |
michael@0 | 1184 | aResult); |
michael@0 | 1185 | needSep = true; |
michael@0 | 1186 | } |
michael@0 | 1187 | } else { |
michael@0 | 1188 | NS_ABORT_IF_FALSE(gradient->GetRadiusX().GetUnit() != eCSSUnit_None, |
michael@0 | 1189 | "bad unit for radial gradient explicit size"); |
michael@0 | 1190 | gradient->GetRadiusX().AppendToString(aProperty, aResult, |
michael@0 | 1191 | aSerialization); |
michael@0 | 1192 | if (gradient->GetRadiusY().GetUnit() != eCSSUnit_None) { |
michael@0 | 1193 | aResult.AppendLiteral(" "); |
michael@0 | 1194 | gradient->GetRadiusY().AppendToString(aProperty, aResult, |
michael@0 | 1195 | aSerialization); |
michael@0 | 1196 | } |
michael@0 | 1197 | needSep = true; |
michael@0 | 1198 | } |
michael@0 | 1199 | } |
michael@0 | 1200 | if (!gradient->mIsRadial && !gradient->mIsLegacySyntax) { |
michael@0 | 1201 | if (gradient->mBgPos.mXValue.GetUnit() != eCSSUnit_None || |
michael@0 | 1202 | gradient->mBgPos.mYValue.GetUnit() != eCSSUnit_None) { |
michael@0 | 1203 | MOZ_ASSERT(gradient->mAngle.GetUnit() == eCSSUnit_None); |
michael@0 | 1204 | NS_ABORT_IF_FALSE(gradient->mBgPos.mXValue.GetUnit() == eCSSUnit_Enumerated && |
michael@0 | 1205 | gradient->mBgPos.mYValue.GetUnit() == eCSSUnit_Enumerated, |
michael@0 | 1206 | "unexpected unit"); |
michael@0 | 1207 | aResult.AppendLiteral("to"); |
michael@0 | 1208 | if (!(gradient->mBgPos.mXValue.GetIntValue() & NS_STYLE_BG_POSITION_CENTER)) { |
michael@0 | 1209 | aResult.AppendLiteral(" "); |
michael@0 | 1210 | gradient->mBgPos.mXValue.AppendToString(eCSSProperty_background_position, |
michael@0 | 1211 | aResult, aSerialization); |
michael@0 | 1212 | } |
michael@0 | 1213 | if (!(gradient->mBgPos.mYValue.GetIntValue() & NS_STYLE_BG_POSITION_CENTER)) { |
michael@0 | 1214 | aResult.AppendLiteral(" "); |
michael@0 | 1215 | gradient->mBgPos.mYValue.AppendToString(eCSSProperty_background_position, |
michael@0 | 1216 | aResult, aSerialization); |
michael@0 | 1217 | } |
michael@0 | 1218 | needSep = true; |
michael@0 | 1219 | } else if (gradient->mAngle.GetUnit() != eCSSUnit_None) { |
michael@0 | 1220 | gradient->mAngle.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1221 | needSep = true; |
michael@0 | 1222 | } |
michael@0 | 1223 | } else if (gradient->mBgPos.mXValue.GetUnit() != eCSSUnit_None || |
michael@0 | 1224 | gradient->mBgPos.mYValue.GetUnit() != eCSSUnit_None || |
michael@0 | 1225 | gradient->mAngle.GetUnit() != eCSSUnit_None) { |
michael@0 | 1226 | if (needSep) { |
michael@0 | 1227 | aResult.AppendLiteral(" "); |
michael@0 | 1228 | } |
michael@0 | 1229 | if (gradient->mIsRadial && !gradient->mIsLegacySyntax) { |
michael@0 | 1230 | aResult.AppendLiteral("at "); |
michael@0 | 1231 | } |
michael@0 | 1232 | if (gradient->mBgPos.mXValue.GetUnit() != eCSSUnit_None) { |
michael@0 | 1233 | gradient->mBgPos.mXValue.AppendToString(eCSSProperty_background_position, |
michael@0 | 1234 | aResult, aSerialization); |
michael@0 | 1235 | aResult.AppendLiteral(" "); |
michael@0 | 1236 | } |
michael@0 | 1237 | if (gradient->mBgPos.mXValue.GetUnit() != eCSSUnit_None) { |
michael@0 | 1238 | gradient->mBgPos.mYValue.AppendToString(eCSSProperty_background_position, |
michael@0 | 1239 | aResult, aSerialization); |
michael@0 | 1240 | aResult.AppendLiteral(" "); |
michael@0 | 1241 | } |
michael@0 | 1242 | if (gradient->mAngle.GetUnit() != eCSSUnit_None) { |
michael@0 | 1243 | NS_ABORT_IF_FALSE(gradient->mIsLegacySyntax, |
michael@0 | 1244 | "angle is allowed only for legacy syntax"); |
michael@0 | 1245 | gradient->mAngle.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1246 | } |
michael@0 | 1247 | needSep = true; |
michael@0 | 1248 | } |
michael@0 | 1249 | |
michael@0 | 1250 | if (gradient->mIsRadial && gradient->mIsLegacySyntax && |
michael@0 | 1251 | (gradient->GetRadialShape().GetUnit() != eCSSUnit_None || |
michael@0 | 1252 | gradient->GetRadialSize().GetUnit() != eCSSUnit_None)) { |
michael@0 | 1253 | MOZ_ASSERT(!gradient->mIsExplicitSize); |
michael@0 | 1254 | if (needSep) { |
michael@0 | 1255 | aResult.AppendLiteral(", "); |
michael@0 | 1256 | } |
michael@0 | 1257 | if (gradient->GetRadialShape().GetUnit() != eCSSUnit_None) { |
michael@0 | 1258 | NS_ABORT_IF_FALSE(gradient->GetRadialShape().GetUnit() == |
michael@0 | 1259 | eCSSUnit_Enumerated, |
michael@0 | 1260 | "bad unit for radial gradient shape"); |
michael@0 | 1261 | int32_t intValue = gradient->GetRadialShape().GetIntValue(); |
michael@0 | 1262 | NS_ABORT_IF_FALSE(intValue != NS_STYLE_GRADIENT_SHAPE_LINEAR, |
michael@0 | 1263 | "radial gradient with linear shape?!"); |
michael@0 | 1264 | AppendASCIItoUTF16(nsCSSProps::ValueToKeyword(intValue, |
michael@0 | 1265 | nsCSSProps::kRadialGradientShapeKTable), |
michael@0 | 1266 | aResult); |
michael@0 | 1267 | aResult.AppendLiteral(" "); |
michael@0 | 1268 | } |
michael@0 | 1269 | |
michael@0 | 1270 | if (gradient->GetRadialSize().GetUnit() != eCSSUnit_None) { |
michael@0 | 1271 | NS_ABORT_IF_FALSE(gradient->GetRadialSize().GetUnit() == |
michael@0 | 1272 | eCSSUnit_Enumerated, |
michael@0 | 1273 | "bad unit for radial gradient size"); |
michael@0 | 1274 | int32_t intValue = gradient->GetRadialSize().GetIntValue(); |
michael@0 | 1275 | AppendASCIItoUTF16(nsCSSProps::ValueToKeyword(intValue, |
michael@0 | 1276 | nsCSSProps::kRadialGradientSizeKTable), |
michael@0 | 1277 | aResult); |
michael@0 | 1278 | } |
michael@0 | 1279 | needSep = true; |
michael@0 | 1280 | } |
michael@0 | 1281 | if (needSep) { |
michael@0 | 1282 | aResult.AppendLiteral(", "); |
michael@0 | 1283 | } |
michael@0 | 1284 | |
michael@0 | 1285 | for (uint32_t i = 0 ;;) { |
michael@0 | 1286 | gradient->mStops[i].mColor.AppendToString(aProperty, aResult, |
michael@0 | 1287 | aSerialization); |
michael@0 | 1288 | if (gradient->mStops[i].mLocation.GetUnit() != eCSSUnit_None) { |
michael@0 | 1289 | aResult.AppendLiteral(" "); |
michael@0 | 1290 | gradient->mStops[i].mLocation.AppendToString(aProperty, aResult, |
michael@0 | 1291 | aSerialization); |
michael@0 | 1292 | } |
michael@0 | 1293 | if (++i == gradient->mStops.Length()) { |
michael@0 | 1294 | break; |
michael@0 | 1295 | } |
michael@0 | 1296 | aResult.AppendLiteral(", "); |
michael@0 | 1297 | } |
michael@0 | 1298 | |
michael@0 | 1299 | aResult.AppendLiteral(")"); |
michael@0 | 1300 | } else if (eCSSUnit_TokenStream == unit) { |
michael@0 | 1301 | nsCSSProperty shorthand = mValue.mTokenStream->mShorthandPropertyID; |
michael@0 | 1302 | if (shorthand == eCSSProperty_UNKNOWN || |
michael@0 | 1303 | nsCSSProps::PropHasFlags(shorthand, CSS_PROPERTY_IS_ALIAS) || |
michael@0 | 1304 | aProperty == eCSSProperty__x_system_font) { |
michael@0 | 1305 | // We treat serialization of aliases like '-moz-transform' as a special |
michael@0 | 1306 | // case, since it really wants to be serialized as if it were a longhand |
michael@0 | 1307 | // even though it is implemented as a shorthand. |
michael@0 | 1308 | aResult.Append(mValue.mTokenStream->mTokenStream); |
michael@0 | 1309 | } |
michael@0 | 1310 | } else if (eCSSUnit_Pair == unit) { |
michael@0 | 1311 | if (eCSSProperty_font_variant_alternates == aProperty) { |
michael@0 | 1312 | int32_t intValue = GetPairValue().mXValue.GetIntValue(); |
michael@0 | 1313 | nsAutoString out; |
michael@0 | 1314 | |
michael@0 | 1315 | // simple, enumerated values |
michael@0 | 1316 | nsStyleUtil::AppendBitmaskCSSValue(aProperty, |
michael@0 | 1317 | intValue & NS_FONT_VARIANT_ALTERNATES_ENUMERATED_MASK, |
michael@0 | 1318 | NS_FONT_VARIANT_ALTERNATES_HISTORICAL, |
michael@0 | 1319 | NS_FONT_VARIANT_ALTERNATES_HISTORICAL, |
michael@0 | 1320 | out); |
michael@0 | 1321 | |
michael@0 | 1322 | // functional values |
michael@0 | 1323 | const nsCSSValueList *list = GetPairValue().mYValue.GetListValue(); |
michael@0 | 1324 | nsAutoTArray<gfxAlternateValue,8> altValues; |
michael@0 | 1325 | |
michael@0 | 1326 | nsStyleUtil::ComputeFunctionalAlternates(list, altValues); |
michael@0 | 1327 | nsStyleUtil::SerializeFunctionalAlternates(altValues, out); |
michael@0 | 1328 | aResult.Append(out); |
michael@0 | 1329 | } else if (eCSSProperty_grid_auto_position == aProperty) { |
michael@0 | 1330 | GetPairValue().mXValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1331 | aResult.AppendLiteral(" / "); |
michael@0 | 1332 | GetPairValue().mYValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1333 | } else { |
michael@0 | 1334 | GetPairValue().AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1335 | } |
michael@0 | 1336 | } else if (eCSSUnit_Triplet == unit) { |
michael@0 | 1337 | GetTripletValue().AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1338 | } else if (eCSSUnit_Rect == unit) { |
michael@0 | 1339 | GetRectValue().AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1340 | } else if (eCSSUnit_List == unit || eCSSUnit_ListDep == unit) { |
michael@0 | 1341 | GetListValue()->AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1342 | } else if (eCSSUnit_SharedList == unit) { |
michael@0 | 1343 | GetSharedListValue()->AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1344 | } else if (eCSSUnit_PairList == unit || eCSSUnit_PairListDep == unit) { |
michael@0 | 1345 | switch (aProperty) { |
michael@0 | 1346 | case eCSSProperty_font_feature_settings: |
michael@0 | 1347 | nsStyleUtil::AppendFontFeatureSettings(*this, aResult); |
michael@0 | 1348 | break; |
michael@0 | 1349 | default: |
michael@0 | 1350 | GetPairListValue()->AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1351 | break; |
michael@0 | 1352 | } |
michael@0 | 1353 | } else if (eCSSUnit_GridTemplateAreas == unit) { |
michael@0 | 1354 | const mozilla::css::GridTemplateAreasValue* areas = GetGridTemplateAreas(); |
michael@0 | 1355 | MOZ_ASSERT(!areas->mTemplates.IsEmpty(), |
michael@0 | 1356 | "Unexpected empty array in GridTemplateAreasValue"); |
michael@0 | 1357 | nsStyleUtil::AppendEscapedCSSString(areas->mTemplates[0], aResult); |
michael@0 | 1358 | for (uint32_t i = 1; i < areas->mTemplates.Length(); i++) { |
michael@0 | 1359 | aResult.Append(char16_t(' ')); |
michael@0 | 1360 | nsStyleUtil::AppendEscapedCSSString(areas->mTemplates[i], aResult); |
michael@0 | 1361 | } |
michael@0 | 1362 | } |
michael@0 | 1363 | |
michael@0 | 1364 | switch (unit) { |
michael@0 | 1365 | case eCSSUnit_Null: break; |
michael@0 | 1366 | case eCSSUnit_Auto: aResult.AppendLiteral("auto"); break; |
michael@0 | 1367 | case eCSSUnit_Inherit: aResult.AppendLiteral("inherit"); break; |
michael@0 | 1368 | case eCSSUnit_Initial: aResult.AppendLiteral("initial"); break; |
michael@0 | 1369 | case eCSSUnit_Unset: aResult.AppendLiteral("unset"); break; |
michael@0 | 1370 | case eCSSUnit_None: aResult.AppendLiteral("none"); break; |
michael@0 | 1371 | case eCSSUnit_Normal: aResult.AppendLiteral("normal"); break; |
michael@0 | 1372 | case eCSSUnit_System_Font: aResult.AppendLiteral("-moz-use-system-font"); break; |
michael@0 | 1373 | case eCSSUnit_All: aResult.AppendLiteral("all"); break; |
michael@0 | 1374 | case eCSSUnit_Dummy: |
michael@0 | 1375 | case eCSSUnit_DummyInherit: |
michael@0 | 1376 | NS_ABORT_IF_FALSE(false, "should never serialize"); |
michael@0 | 1377 | break; |
michael@0 | 1378 | |
michael@0 | 1379 | case eCSSUnit_String: break; |
michael@0 | 1380 | case eCSSUnit_Ident: break; |
michael@0 | 1381 | case eCSSUnit_Families: break; |
michael@0 | 1382 | case eCSSUnit_URL: break; |
michael@0 | 1383 | case eCSSUnit_Image: break; |
michael@0 | 1384 | case eCSSUnit_Element: break; |
michael@0 | 1385 | case eCSSUnit_Array: break; |
michael@0 | 1386 | case eCSSUnit_Attr: |
michael@0 | 1387 | case eCSSUnit_Cubic_Bezier: |
michael@0 | 1388 | case eCSSUnit_Steps: |
michael@0 | 1389 | case eCSSUnit_Counter: |
michael@0 | 1390 | case eCSSUnit_Counters: aResult.Append(char16_t(')')); break; |
michael@0 | 1391 | case eCSSUnit_Local_Font: break; |
michael@0 | 1392 | case eCSSUnit_Font_Format: break; |
michael@0 | 1393 | case eCSSUnit_Function: break; |
michael@0 | 1394 | case eCSSUnit_Calc: break; |
michael@0 | 1395 | case eCSSUnit_Calc_Plus: break; |
michael@0 | 1396 | case eCSSUnit_Calc_Minus: break; |
michael@0 | 1397 | case eCSSUnit_Calc_Times_L: break; |
michael@0 | 1398 | case eCSSUnit_Calc_Times_R: break; |
michael@0 | 1399 | case eCSSUnit_Calc_Divided: break; |
michael@0 | 1400 | case eCSSUnit_Integer: break; |
michael@0 | 1401 | case eCSSUnit_Enumerated: break; |
michael@0 | 1402 | case eCSSUnit_EnumColor: break; |
michael@0 | 1403 | case eCSSUnit_RGBColor: break; |
michael@0 | 1404 | case eCSSUnit_RGBAColor: break; |
michael@0 | 1405 | case eCSSUnit_HexColor: break; |
michael@0 | 1406 | case eCSSUnit_ShortHexColor: break; |
michael@0 | 1407 | case eCSSUnit_PercentageRGBColor: break; |
michael@0 | 1408 | case eCSSUnit_PercentageRGBAColor: break; |
michael@0 | 1409 | case eCSSUnit_HSLColor: break; |
michael@0 | 1410 | case eCSSUnit_HSLAColor: break; |
michael@0 | 1411 | case eCSSUnit_Percent: aResult.Append(char16_t('%')); break; |
michael@0 | 1412 | case eCSSUnit_Number: break; |
michael@0 | 1413 | case eCSSUnit_Gradient: break; |
michael@0 | 1414 | case eCSSUnit_TokenStream: break; |
michael@0 | 1415 | case eCSSUnit_Pair: break; |
michael@0 | 1416 | case eCSSUnit_Triplet: break; |
michael@0 | 1417 | case eCSSUnit_Rect: break; |
michael@0 | 1418 | case eCSSUnit_List: break; |
michael@0 | 1419 | case eCSSUnit_ListDep: break; |
michael@0 | 1420 | case eCSSUnit_SharedList: break; |
michael@0 | 1421 | case eCSSUnit_PairList: break; |
michael@0 | 1422 | case eCSSUnit_PairListDep: break; |
michael@0 | 1423 | case eCSSUnit_GridTemplateAreas: break; |
michael@0 | 1424 | |
michael@0 | 1425 | case eCSSUnit_Inch: aResult.AppendLiteral("in"); break; |
michael@0 | 1426 | case eCSSUnit_Millimeter: aResult.AppendLiteral("mm"); break; |
michael@0 | 1427 | case eCSSUnit_PhysicalMillimeter: aResult.AppendLiteral("mozmm"); break; |
michael@0 | 1428 | case eCSSUnit_Centimeter: aResult.AppendLiteral("cm"); break; |
michael@0 | 1429 | case eCSSUnit_Point: aResult.AppendLiteral("pt"); break; |
michael@0 | 1430 | case eCSSUnit_Pica: aResult.AppendLiteral("pc"); break; |
michael@0 | 1431 | |
michael@0 | 1432 | case eCSSUnit_ViewportWidth: aResult.AppendLiteral("vw"); break; |
michael@0 | 1433 | case eCSSUnit_ViewportHeight: aResult.AppendLiteral("vh"); break; |
michael@0 | 1434 | case eCSSUnit_ViewportMin: aResult.AppendLiteral("vmin"); break; |
michael@0 | 1435 | case eCSSUnit_ViewportMax: aResult.AppendLiteral("vmax"); break; |
michael@0 | 1436 | |
michael@0 | 1437 | case eCSSUnit_EM: aResult.AppendLiteral("em"); break; |
michael@0 | 1438 | case eCSSUnit_XHeight: aResult.AppendLiteral("ex"); break; |
michael@0 | 1439 | case eCSSUnit_Char: aResult.AppendLiteral("ch"); break; |
michael@0 | 1440 | case eCSSUnit_RootEM: aResult.AppendLiteral("rem"); break; |
michael@0 | 1441 | |
michael@0 | 1442 | case eCSSUnit_Pixel: aResult.AppendLiteral("px"); break; |
michael@0 | 1443 | |
michael@0 | 1444 | case eCSSUnit_Degree: aResult.AppendLiteral("deg"); break; |
michael@0 | 1445 | case eCSSUnit_Grad: aResult.AppendLiteral("grad"); break; |
michael@0 | 1446 | case eCSSUnit_Radian: aResult.AppendLiteral("rad"); break; |
michael@0 | 1447 | case eCSSUnit_Turn: aResult.AppendLiteral("turn"); break; |
michael@0 | 1448 | |
michael@0 | 1449 | case eCSSUnit_Hertz: aResult.AppendLiteral("Hz"); break; |
michael@0 | 1450 | case eCSSUnit_Kilohertz: aResult.AppendLiteral("kHz"); break; |
michael@0 | 1451 | |
michael@0 | 1452 | case eCSSUnit_Seconds: aResult.Append(char16_t('s')); break; |
michael@0 | 1453 | case eCSSUnit_Milliseconds: aResult.AppendLiteral("ms"); break; |
michael@0 | 1454 | |
michael@0 | 1455 | case eCSSUnit_FlexFraction: aResult.AppendLiteral("fr"); break; |
michael@0 | 1456 | } |
michael@0 | 1457 | } |
michael@0 | 1458 | |
michael@0 | 1459 | size_t |
michael@0 | 1460 | nsCSSValue::SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1461 | { |
michael@0 | 1462 | size_t n = 0; |
michael@0 | 1463 | |
michael@0 | 1464 | switch (GetUnit()) { |
michael@0 | 1465 | // No value: nothing extra to measure. |
michael@0 | 1466 | case eCSSUnit_Null: |
michael@0 | 1467 | case eCSSUnit_Auto: |
michael@0 | 1468 | case eCSSUnit_Inherit: |
michael@0 | 1469 | case eCSSUnit_Initial: |
michael@0 | 1470 | case eCSSUnit_Unset: |
michael@0 | 1471 | case eCSSUnit_None: |
michael@0 | 1472 | case eCSSUnit_Normal: |
michael@0 | 1473 | case eCSSUnit_System_Font: |
michael@0 | 1474 | case eCSSUnit_All: |
michael@0 | 1475 | case eCSSUnit_Dummy: |
michael@0 | 1476 | case eCSSUnit_DummyInherit: |
michael@0 | 1477 | break; |
michael@0 | 1478 | |
michael@0 | 1479 | // String |
michael@0 | 1480 | case eCSSUnit_String: |
michael@0 | 1481 | case eCSSUnit_Ident: |
michael@0 | 1482 | case eCSSUnit_Families: |
michael@0 | 1483 | case eCSSUnit_Attr: |
michael@0 | 1484 | case eCSSUnit_Local_Font: |
michael@0 | 1485 | case eCSSUnit_Font_Format: |
michael@0 | 1486 | case eCSSUnit_Element: |
michael@0 | 1487 | n += mValue.mString->SizeOfIncludingThisIfUnshared(aMallocSizeOf); |
michael@0 | 1488 | break; |
michael@0 | 1489 | |
michael@0 | 1490 | // Array |
michael@0 | 1491 | case eCSSUnit_Array: |
michael@0 | 1492 | case eCSSUnit_Counter: |
michael@0 | 1493 | case eCSSUnit_Counters: |
michael@0 | 1494 | case eCSSUnit_Cubic_Bezier: |
michael@0 | 1495 | case eCSSUnit_Steps: |
michael@0 | 1496 | case eCSSUnit_Function: |
michael@0 | 1497 | case eCSSUnit_Calc: |
michael@0 | 1498 | case eCSSUnit_Calc_Plus: |
michael@0 | 1499 | case eCSSUnit_Calc_Minus: |
michael@0 | 1500 | case eCSSUnit_Calc_Times_L: |
michael@0 | 1501 | case eCSSUnit_Calc_Times_R: |
michael@0 | 1502 | case eCSSUnit_Calc_Divided: |
michael@0 | 1503 | break; |
michael@0 | 1504 | |
michael@0 | 1505 | // URL |
michael@0 | 1506 | case eCSSUnit_URL: |
michael@0 | 1507 | n += mValue.mURL->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1508 | break; |
michael@0 | 1509 | |
michael@0 | 1510 | // Image |
michael@0 | 1511 | case eCSSUnit_Image: |
michael@0 | 1512 | // Not yet measured. Measurement may be added later if DMD finds it |
michael@0 | 1513 | // worthwhile. |
michael@0 | 1514 | break; |
michael@0 | 1515 | |
michael@0 | 1516 | // Gradient |
michael@0 | 1517 | case eCSSUnit_Gradient: |
michael@0 | 1518 | n += mValue.mGradient->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1519 | break; |
michael@0 | 1520 | |
michael@0 | 1521 | // TokenStream |
michael@0 | 1522 | case eCSSUnit_TokenStream: |
michael@0 | 1523 | n += mValue.mTokenStream->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1524 | break; |
michael@0 | 1525 | |
michael@0 | 1526 | // Pair |
michael@0 | 1527 | case eCSSUnit_Pair: |
michael@0 | 1528 | n += mValue.mPair->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1529 | break; |
michael@0 | 1530 | |
michael@0 | 1531 | // Triplet |
michael@0 | 1532 | case eCSSUnit_Triplet: |
michael@0 | 1533 | n += mValue.mTriplet->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1534 | break; |
michael@0 | 1535 | |
michael@0 | 1536 | // Rect |
michael@0 | 1537 | case eCSSUnit_Rect: |
michael@0 | 1538 | n += mValue.mRect->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1539 | break; |
michael@0 | 1540 | |
michael@0 | 1541 | // List |
michael@0 | 1542 | case eCSSUnit_List: |
michael@0 | 1543 | n += mValue.mList->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1544 | break; |
michael@0 | 1545 | |
michael@0 | 1546 | // ListDep: not measured because it's non-owning. |
michael@0 | 1547 | case eCSSUnit_ListDep: |
michael@0 | 1548 | break; |
michael@0 | 1549 | |
michael@0 | 1550 | // SharedList |
michael@0 | 1551 | case eCSSUnit_SharedList: |
michael@0 | 1552 | // Makes more sense not to measure, since it most cases the list |
michael@0 | 1553 | // will be shared. |
michael@0 | 1554 | break; |
michael@0 | 1555 | |
michael@0 | 1556 | // PairList |
michael@0 | 1557 | case eCSSUnit_PairList: |
michael@0 | 1558 | n += mValue.mPairList->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1559 | break; |
michael@0 | 1560 | |
michael@0 | 1561 | // PairListDep: not measured because it's non-owning. |
michael@0 | 1562 | case eCSSUnit_PairListDep: |
michael@0 | 1563 | break; |
michael@0 | 1564 | |
michael@0 | 1565 | // GridTemplateAreas |
michael@0 | 1566 | case eCSSUnit_GridTemplateAreas: |
michael@0 | 1567 | n += mValue.mGridTemplateAreas->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1568 | break; |
michael@0 | 1569 | |
michael@0 | 1570 | // Int: nothing extra to measure. |
michael@0 | 1571 | case eCSSUnit_Integer: |
michael@0 | 1572 | case eCSSUnit_Enumerated: |
michael@0 | 1573 | case eCSSUnit_EnumColor: |
michael@0 | 1574 | break; |
michael@0 | 1575 | |
michael@0 | 1576 | // Integer Color: nothing extra to measure. |
michael@0 | 1577 | case eCSSUnit_RGBColor: |
michael@0 | 1578 | case eCSSUnit_RGBAColor: |
michael@0 | 1579 | case eCSSUnit_HexColor: |
michael@0 | 1580 | case eCSSUnit_ShortHexColor: |
michael@0 | 1581 | break; |
michael@0 | 1582 | |
michael@0 | 1583 | // Float Color |
michael@0 | 1584 | case eCSSUnit_PercentageRGBColor: |
michael@0 | 1585 | case eCSSUnit_PercentageRGBAColor: |
michael@0 | 1586 | case eCSSUnit_HSLColor: |
michael@0 | 1587 | case eCSSUnit_HSLAColor: |
michael@0 | 1588 | n += mValue.mFloatColor->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1589 | break; |
michael@0 | 1590 | |
michael@0 | 1591 | // Float: nothing extra to measure. |
michael@0 | 1592 | case eCSSUnit_Percent: |
michael@0 | 1593 | case eCSSUnit_Number: |
michael@0 | 1594 | case eCSSUnit_PhysicalMillimeter: |
michael@0 | 1595 | case eCSSUnit_ViewportWidth: |
michael@0 | 1596 | case eCSSUnit_ViewportHeight: |
michael@0 | 1597 | case eCSSUnit_ViewportMin: |
michael@0 | 1598 | case eCSSUnit_ViewportMax: |
michael@0 | 1599 | case eCSSUnit_EM: |
michael@0 | 1600 | case eCSSUnit_XHeight: |
michael@0 | 1601 | case eCSSUnit_Char: |
michael@0 | 1602 | case eCSSUnit_RootEM: |
michael@0 | 1603 | case eCSSUnit_Point: |
michael@0 | 1604 | case eCSSUnit_Inch: |
michael@0 | 1605 | case eCSSUnit_Millimeter: |
michael@0 | 1606 | case eCSSUnit_Centimeter: |
michael@0 | 1607 | case eCSSUnit_Pica: |
michael@0 | 1608 | case eCSSUnit_Pixel: |
michael@0 | 1609 | case eCSSUnit_Degree: |
michael@0 | 1610 | case eCSSUnit_Grad: |
michael@0 | 1611 | case eCSSUnit_Turn: |
michael@0 | 1612 | case eCSSUnit_Radian: |
michael@0 | 1613 | case eCSSUnit_Hertz: |
michael@0 | 1614 | case eCSSUnit_Kilohertz: |
michael@0 | 1615 | case eCSSUnit_Seconds: |
michael@0 | 1616 | case eCSSUnit_Milliseconds: |
michael@0 | 1617 | case eCSSUnit_FlexFraction: |
michael@0 | 1618 | break; |
michael@0 | 1619 | |
michael@0 | 1620 | default: |
michael@0 | 1621 | NS_ABORT_IF_FALSE(false, "bad nsCSSUnit"); |
michael@0 | 1622 | break; |
michael@0 | 1623 | } |
michael@0 | 1624 | |
michael@0 | 1625 | return n; |
michael@0 | 1626 | } |
michael@0 | 1627 | |
michael@0 | 1628 | // --- nsCSSValueList ----------------- |
michael@0 | 1629 | |
michael@0 | 1630 | nsCSSValueList::~nsCSSValueList() |
michael@0 | 1631 | { |
michael@0 | 1632 | MOZ_COUNT_DTOR(nsCSSValueList); |
michael@0 | 1633 | NS_CSS_DELETE_LIST_MEMBER(nsCSSValueList, this, mNext); |
michael@0 | 1634 | } |
michael@0 | 1635 | |
michael@0 | 1636 | nsCSSValueList* |
michael@0 | 1637 | nsCSSValueList::Clone() const |
michael@0 | 1638 | { |
michael@0 | 1639 | nsCSSValueList* result = new nsCSSValueList(*this); |
michael@0 | 1640 | nsCSSValueList* dest = result; |
michael@0 | 1641 | const nsCSSValueList* src = this->mNext; |
michael@0 | 1642 | while (src) { |
michael@0 | 1643 | dest->mNext = new nsCSSValueList(*src); |
michael@0 | 1644 | dest = dest->mNext; |
michael@0 | 1645 | src = src->mNext; |
michael@0 | 1646 | } |
michael@0 | 1647 | return result; |
michael@0 | 1648 | } |
michael@0 | 1649 | |
michael@0 | 1650 | void |
michael@0 | 1651 | nsCSSValueList::CloneInto(nsCSSValueList* aList) const |
michael@0 | 1652 | { |
michael@0 | 1653 | NS_ASSERTION(!aList->mNext, "Must be an empty list!"); |
michael@0 | 1654 | aList->mValue = mValue; |
michael@0 | 1655 | aList->mNext = mNext ? mNext->Clone() : nullptr; |
michael@0 | 1656 | } |
michael@0 | 1657 | |
michael@0 | 1658 | static void |
michael@0 | 1659 | AppendValueListToString(const nsCSSValueList* val, |
michael@0 | 1660 | nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 1661 | nsCSSValue::Serialization aSerialization) |
michael@0 | 1662 | { |
michael@0 | 1663 | for (;;) { |
michael@0 | 1664 | val->mValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1665 | val = val->mNext; |
michael@0 | 1666 | if (!val) |
michael@0 | 1667 | break; |
michael@0 | 1668 | |
michael@0 | 1669 | if (nsCSSProps::PropHasFlags(aProperty, |
michael@0 | 1670 | CSS_PROPERTY_VALUE_LIST_USES_COMMAS)) |
michael@0 | 1671 | aResult.Append(char16_t(',')); |
michael@0 | 1672 | aResult.Append(char16_t(' ')); |
michael@0 | 1673 | } |
michael@0 | 1674 | } |
michael@0 | 1675 | |
michael@0 | 1676 | static void |
michael@0 | 1677 | AppendGridTemplateToString(const nsCSSValueList* val, |
michael@0 | 1678 | nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 1679 | nsCSSValue::Serialization aSerialization) |
michael@0 | 1680 | { |
michael@0 | 1681 | // This is called for the "list" that's the top-level value of the property. |
michael@0 | 1682 | bool isSubgrid = false; |
michael@0 | 1683 | for (;;) { |
michael@0 | 1684 | bool addSpaceSeparator = true; |
michael@0 | 1685 | nsCSSUnit unit = val->mValue.GetUnit(); |
michael@0 | 1686 | |
michael@0 | 1687 | if (unit == eCSSUnit_Enumerated && |
michael@0 | 1688 | val->mValue.GetIntValue() == NS_STYLE_GRID_TEMPLATE_SUBGRID) { |
michael@0 | 1689 | isSubgrid = true; |
michael@0 | 1690 | aResult.AppendLiteral("subgrid"); |
michael@0 | 1691 | |
michael@0 | 1692 | } else if (unit == eCSSUnit_Null) { |
michael@0 | 1693 | // Empty or omitted <line-names>. |
michael@0 | 1694 | if (isSubgrid) { |
michael@0 | 1695 | aResult.AppendLiteral("()"); |
michael@0 | 1696 | } else { |
michael@0 | 1697 | // Serializes to nothing. |
michael@0 | 1698 | addSpaceSeparator = false; // Avoid a double space. |
michael@0 | 1699 | } |
michael@0 | 1700 | |
michael@0 | 1701 | } else if (unit == eCSSUnit_List || unit == eCSSUnit_ListDep) { |
michael@0 | 1702 | // Non-empty <line-names> |
michael@0 | 1703 | aResult.AppendLiteral("("); |
michael@0 | 1704 | AppendValueListToString(val->mValue.GetListValue(), aProperty, |
michael@0 | 1705 | aResult, aSerialization); |
michael@0 | 1706 | aResult.AppendLiteral(")"); |
michael@0 | 1707 | |
michael@0 | 1708 | } else { |
michael@0 | 1709 | // <track-size> |
michael@0 | 1710 | val->mValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1711 | if (!isSubgrid && |
michael@0 | 1712 | val->mNext && |
michael@0 | 1713 | val->mNext->mValue.GetUnit() == eCSSUnit_Null && |
michael@0 | 1714 | !val->mNext->mNext) { |
michael@0 | 1715 | // Break out of the loop early to avoid a trailing space. |
michael@0 | 1716 | break; |
michael@0 | 1717 | } |
michael@0 | 1718 | } |
michael@0 | 1719 | |
michael@0 | 1720 | val = val->mNext; |
michael@0 | 1721 | if (!val) { |
michael@0 | 1722 | break; |
michael@0 | 1723 | } |
michael@0 | 1724 | |
michael@0 | 1725 | if (addSpaceSeparator) { |
michael@0 | 1726 | aResult.Append(char16_t(' ')); |
michael@0 | 1727 | } |
michael@0 | 1728 | } |
michael@0 | 1729 | } |
michael@0 | 1730 | |
michael@0 | 1731 | void |
michael@0 | 1732 | nsCSSValueList::AppendToString(nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 1733 | nsCSSValue::Serialization aSerialization) const |
michael@0 | 1734 | { |
michael@0 | 1735 | if (aProperty == eCSSProperty_grid_template_columns || |
michael@0 | 1736 | aProperty == eCSSProperty_grid_template_rows) { |
michael@0 | 1737 | AppendGridTemplateToString(this, aProperty, aResult, aSerialization); |
michael@0 | 1738 | } else { |
michael@0 | 1739 | AppendValueListToString(this, aProperty, aResult, aSerialization); |
michael@0 | 1740 | } |
michael@0 | 1741 | } |
michael@0 | 1742 | |
michael@0 | 1743 | bool |
michael@0 | 1744 | nsCSSValueList::operator==(const nsCSSValueList& aOther) const |
michael@0 | 1745 | { |
michael@0 | 1746 | if (this == &aOther) |
michael@0 | 1747 | return true; |
michael@0 | 1748 | |
michael@0 | 1749 | const nsCSSValueList *p1 = this, *p2 = &aOther; |
michael@0 | 1750 | for ( ; p1 && p2; p1 = p1->mNext, p2 = p2->mNext) { |
michael@0 | 1751 | if (p1->mValue != p2->mValue) |
michael@0 | 1752 | return false; |
michael@0 | 1753 | } |
michael@0 | 1754 | return !p1 && !p2; // true if same length, false otherwise |
michael@0 | 1755 | } |
michael@0 | 1756 | |
michael@0 | 1757 | size_t |
michael@0 | 1758 | nsCSSValueList::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1759 | { |
michael@0 | 1760 | size_t n = 0; |
michael@0 | 1761 | const nsCSSValueList* v = this; |
michael@0 | 1762 | while (v) { |
michael@0 | 1763 | n += aMallocSizeOf(v); |
michael@0 | 1764 | n += v->mValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1765 | v = v->mNext; |
michael@0 | 1766 | } |
michael@0 | 1767 | return n; |
michael@0 | 1768 | } |
michael@0 | 1769 | |
michael@0 | 1770 | size_t |
michael@0 | 1771 | nsCSSValueList_heap::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1772 | { |
michael@0 | 1773 | size_t n = aMallocSizeOf(this); |
michael@0 | 1774 | n += mValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1775 | n += mNext ? mNext->SizeOfIncludingThis(aMallocSizeOf) : 0; |
michael@0 | 1776 | return n; |
michael@0 | 1777 | } |
michael@0 | 1778 | |
michael@0 | 1779 | // --- nsCSSValueSharedList ----------------- |
michael@0 | 1780 | |
michael@0 | 1781 | nsCSSValueSharedList::~nsCSSValueSharedList() |
michael@0 | 1782 | { |
michael@0 | 1783 | MOZ_COUNT_DTOR(nsCSSValueSharedList); |
michael@0 | 1784 | if (mHead) { |
michael@0 | 1785 | NS_CSS_DELETE_LIST_MEMBER(nsCSSValueList, mHead, mNext); |
michael@0 | 1786 | delete mHead; |
michael@0 | 1787 | } |
michael@0 | 1788 | } |
michael@0 | 1789 | |
michael@0 | 1790 | void |
michael@0 | 1791 | nsCSSValueSharedList::AppendToString(nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 1792 | nsCSSValue::Serialization aSerialization) const |
michael@0 | 1793 | { |
michael@0 | 1794 | if (mHead) { |
michael@0 | 1795 | mHead->AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1796 | } |
michael@0 | 1797 | } |
michael@0 | 1798 | |
michael@0 | 1799 | bool |
michael@0 | 1800 | nsCSSValueSharedList::operator==(const nsCSSValueSharedList& aOther) const |
michael@0 | 1801 | { |
michael@0 | 1802 | return !mHead == !aOther.mHead && |
michael@0 | 1803 | (!mHead || *mHead == *aOther.mHead); |
michael@0 | 1804 | } |
michael@0 | 1805 | |
michael@0 | 1806 | size_t |
michael@0 | 1807 | nsCSSValueSharedList::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1808 | { |
michael@0 | 1809 | size_t n = 0; |
michael@0 | 1810 | n += aMallocSizeOf(this); |
michael@0 | 1811 | n += mHead->SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 1812 | return n; |
michael@0 | 1813 | } |
michael@0 | 1814 | |
michael@0 | 1815 | // --- nsCSSRect ----------------- |
michael@0 | 1816 | |
michael@0 | 1817 | nsCSSRect::nsCSSRect(void) |
michael@0 | 1818 | { |
michael@0 | 1819 | MOZ_COUNT_CTOR(nsCSSRect); |
michael@0 | 1820 | } |
michael@0 | 1821 | |
michael@0 | 1822 | nsCSSRect::nsCSSRect(const nsCSSRect& aCopy) |
michael@0 | 1823 | : mTop(aCopy.mTop), |
michael@0 | 1824 | mRight(aCopy.mRight), |
michael@0 | 1825 | mBottom(aCopy.mBottom), |
michael@0 | 1826 | mLeft(aCopy.mLeft) |
michael@0 | 1827 | { |
michael@0 | 1828 | MOZ_COUNT_CTOR(nsCSSRect); |
michael@0 | 1829 | } |
michael@0 | 1830 | |
michael@0 | 1831 | nsCSSRect::~nsCSSRect() |
michael@0 | 1832 | { |
michael@0 | 1833 | MOZ_COUNT_DTOR(nsCSSRect); |
michael@0 | 1834 | } |
michael@0 | 1835 | |
michael@0 | 1836 | void |
michael@0 | 1837 | nsCSSRect::AppendToString(nsCSSProperty aProperty, nsAString& aResult, |
michael@0 | 1838 | nsCSSValue::Serialization aSerialization) const |
michael@0 | 1839 | { |
michael@0 | 1840 | NS_ABORT_IF_FALSE(mTop.GetUnit() != eCSSUnit_Null && |
michael@0 | 1841 | mTop.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 1842 | mTop.GetUnit() != eCSSUnit_Initial && |
michael@0 | 1843 | mTop.GetUnit() != eCSSUnit_Unset, |
michael@0 | 1844 | "parser should have used a bare value"); |
michael@0 | 1845 | |
michael@0 | 1846 | if (eCSSProperty_border_image_slice == aProperty || |
michael@0 | 1847 | eCSSProperty_border_image_width == aProperty || |
michael@0 | 1848 | eCSSProperty_border_image_outset == aProperty) { |
michael@0 | 1849 | NS_NAMED_LITERAL_STRING(space, " "); |
michael@0 | 1850 | |
michael@0 | 1851 | mTop.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1852 | aResult.Append(space); |
michael@0 | 1853 | mRight.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1854 | aResult.Append(space); |
michael@0 | 1855 | mBottom.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1856 | aResult.Append(space); |
michael@0 | 1857 | mLeft.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1858 | } else { |
michael@0 | 1859 | NS_NAMED_LITERAL_STRING(comma, ", "); |
michael@0 | 1860 | |
michael@0 | 1861 | aResult.AppendLiteral("rect("); |
michael@0 | 1862 | mTop.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1863 | aResult.Append(comma); |
michael@0 | 1864 | mRight.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1865 | aResult.Append(comma); |
michael@0 | 1866 | mBottom.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1867 | aResult.Append(comma); |
michael@0 | 1868 | mLeft.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1869 | aResult.Append(char16_t(')')); |
michael@0 | 1870 | } |
michael@0 | 1871 | } |
michael@0 | 1872 | |
michael@0 | 1873 | void nsCSSRect::SetAllSidesTo(const nsCSSValue& aValue) |
michael@0 | 1874 | { |
michael@0 | 1875 | mTop = aValue; |
michael@0 | 1876 | mRight = aValue; |
michael@0 | 1877 | mBottom = aValue; |
michael@0 | 1878 | mLeft = aValue; |
michael@0 | 1879 | } |
michael@0 | 1880 | |
michael@0 | 1881 | size_t |
michael@0 | 1882 | nsCSSRect_heap::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1883 | { |
michael@0 | 1884 | size_t n = aMallocSizeOf(this); |
michael@0 | 1885 | n += mTop .SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1886 | n += mRight .SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1887 | n += mBottom.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1888 | n += mLeft .SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1889 | return n; |
michael@0 | 1890 | } |
michael@0 | 1891 | |
michael@0 | 1892 | static_assert(NS_SIDE_TOP == 0 && NS_SIDE_RIGHT == 1 && |
michael@0 | 1893 | NS_SIDE_BOTTOM == 2 && NS_SIDE_LEFT == 3, |
michael@0 | 1894 | "box side constants not top/right/bottom/left == 0/1/2/3"); |
michael@0 | 1895 | |
michael@0 | 1896 | /* static */ const nsCSSRect::side_type nsCSSRect::sides[4] = { |
michael@0 | 1897 | &nsCSSRect::mTop, |
michael@0 | 1898 | &nsCSSRect::mRight, |
michael@0 | 1899 | &nsCSSRect::mBottom, |
michael@0 | 1900 | &nsCSSRect::mLeft, |
michael@0 | 1901 | }; |
michael@0 | 1902 | |
michael@0 | 1903 | // --- nsCSSValuePair ----------------- |
michael@0 | 1904 | |
michael@0 | 1905 | void |
michael@0 | 1906 | nsCSSValuePair::AppendToString(nsCSSProperty aProperty, |
michael@0 | 1907 | nsAString& aResult, |
michael@0 | 1908 | nsCSSValue::Serialization aSerialization) const |
michael@0 | 1909 | { |
michael@0 | 1910 | mXValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1911 | if (mYValue.GetUnit() != eCSSUnit_Null) { |
michael@0 | 1912 | aResult.Append(char16_t(' ')); |
michael@0 | 1913 | mYValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1914 | } |
michael@0 | 1915 | } |
michael@0 | 1916 | |
michael@0 | 1917 | size_t |
michael@0 | 1918 | nsCSSValuePair::SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1919 | { |
michael@0 | 1920 | size_t n = 0; |
michael@0 | 1921 | n += mXValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1922 | n += mYValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1923 | return n; |
michael@0 | 1924 | } |
michael@0 | 1925 | |
michael@0 | 1926 | size_t |
michael@0 | 1927 | nsCSSValuePair_heap::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1928 | { |
michael@0 | 1929 | size_t n = aMallocSizeOf(this); |
michael@0 | 1930 | n += mXValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1931 | n += mYValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1932 | return n; |
michael@0 | 1933 | } |
michael@0 | 1934 | |
michael@0 | 1935 | // --- nsCSSValueTriplet ----------------- |
michael@0 | 1936 | |
michael@0 | 1937 | void |
michael@0 | 1938 | nsCSSValueTriplet::AppendToString(nsCSSProperty aProperty, |
michael@0 | 1939 | nsAString& aResult, |
michael@0 | 1940 | nsCSSValue::Serialization aSerialization) const |
michael@0 | 1941 | { |
michael@0 | 1942 | mXValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1943 | if (mYValue.GetUnit() != eCSSUnit_Null) { |
michael@0 | 1944 | aResult.Append(char16_t(' ')); |
michael@0 | 1945 | mYValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1946 | if (mZValue.GetUnit() != eCSSUnit_Null) { |
michael@0 | 1947 | aResult.Append(char16_t(' ')); |
michael@0 | 1948 | mZValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1949 | } |
michael@0 | 1950 | } |
michael@0 | 1951 | } |
michael@0 | 1952 | |
michael@0 | 1953 | size_t |
michael@0 | 1954 | nsCSSValueTriplet_heap::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 1955 | { |
michael@0 | 1956 | size_t n = aMallocSizeOf(this); |
michael@0 | 1957 | n += mXValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1958 | n += mYValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1959 | n += mZValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 1960 | return n; |
michael@0 | 1961 | } |
michael@0 | 1962 | |
michael@0 | 1963 | // --- nsCSSValuePairList ----------------- |
michael@0 | 1964 | |
michael@0 | 1965 | nsCSSValuePairList::~nsCSSValuePairList() |
michael@0 | 1966 | { |
michael@0 | 1967 | MOZ_COUNT_DTOR(nsCSSValuePairList); |
michael@0 | 1968 | NS_CSS_DELETE_LIST_MEMBER(nsCSSValuePairList, this, mNext); |
michael@0 | 1969 | } |
michael@0 | 1970 | |
michael@0 | 1971 | nsCSSValuePairList* |
michael@0 | 1972 | nsCSSValuePairList::Clone() const |
michael@0 | 1973 | { |
michael@0 | 1974 | nsCSSValuePairList* result = new nsCSSValuePairList(*this); |
michael@0 | 1975 | nsCSSValuePairList* dest = result; |
michael@0 | 1976 | const nsCSSValuePairList* src = this->mNext; |
michael@0 | 1977 | while (src) { |
michael@0 | 1978 | dest->mNext = new nsCSSValuePairList(*src); |
michael@0 | 1979 | dest = dest->mNext; |
michael@0 | 1980 | src = src->mNext; |
michael@0 | 1981 | } |
michael@0 | 1982 | return result; |
michael@0 | 1983 | } |
michael@0 | 1984 | |
michael@0 | 1985 | void |
michael@0 | 1986 | nsCSSValuePairList::AppendToString(nsCSSProperty aProperty, |
michael@0 | 1987 | nsAString& aResult, |
michael@0 | 1988 | nsCSSValue::Serialization aSerialization) const |
michael@0 | 1989 | { |
michael@0 | 1990 | const nsCSSValuePairList* item = this; |
michael@0 | 1991 | for (;;) { |
michael@0 | 1992 | NS_ABORT_IF_FALSE(item->mXValue.GetUnit() != eCSSUnit_Null, |
michael@0 | 1993 | "unexpected null unit"); |
michael@0 | 1994 | item->mXValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 1995 | if (item->mXValue.GetUnit() != eCSSUnit_Inherit && |
michael@0 | 1996 | item->mXValue.GetUnit() != eCSSUnit_Initial && |
michael@0 | 1997 | item->mXValue.GetUnit() != eCSSUnit_Unset && |
michael@0 | 1998 | item->mYValue.GetUnit() != eCSSUnit_Null) { |
michael@0 | 1999 | aResult.Append(char16_t(' ')); |
michael@0 | 2000 | item->mYValue.AppendToString(aProperty, aResult, aSerialization); |
michael@0 | 2001 | } |
michael@0 | 2002 | item = item->mNext; |
michael@0 | 2003 | if (!item) |
michael@0 | 2004 | break; |
michael@0 | 2005 | |
michael@0 | 2006 | if (nsCSSProps::PropHasFlags(aProperty, |
michael@0 | 2007 | CSS_PROPERTY_VALUE_LIST_USES_COMMAS)) |
michael@0 | 2008 | aResult.Append(char16_t(',')); |
michael@0 | 2009 | aResult.Append(char16_t(' ')); |
michael@0 | 2010 | } |
michael@0 | 2011 | } |
michael@0 | 2012 | |
michael@0 | 2013 | bool |
michael@0 | 2014 | nsCSSValuePairList::operator==(const nsCSSValuePairList& aOther) const |
michael@0 | 2015 | { |
michael@0 | 2016 | if (this == &aOther) |
michael@0 | 2017 | return true; |
michael@0 | 2018 | |
michael@0 | 2019 | const nsCSSValuePairList *p1 = this, *p2 = &aOther; |
michael@0 | 2020 | for ( ; p1 && p2; p1 = p1->mNext, p2 = p2->mNext) { |
michael@0 | 2021 | if (p1->mXValue != p2->mXValue || |
michael@0 | 2022 | p1->mYValue != p2->mYValue) |
michael@0 | 2023 | return false; |
michael@0 | 2024 | } |
michael@0 | 2025 | return !p1 && !p2; // true if same length, false otherwise |
michael@0 | 2026 | } |
michael@0 | 2027 | |
michael@0 | 2028 | size_t |
michael@0 | 2029 | nsCSSValuePairList::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2030 | { |
michael@0 | 2031 | size_t n = 0; |
michael@0 | 2032 | const nsCSSValuePairList* v = this; |
michael@0 | 2033 | while (v) { |
michael@0 | 2034 | n += aMallocSizeOf(v); |
michael@0 | 2035 | n += v->mXValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2036 | n += v->mYValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2037 | v = v->mNext; |
michael@0 | 2038 | } |
michael@0 | 2039 | return n; |
michael@0 | 2040 | } |
michael@0 | 2041 | |
michael@0 | 2042 | size_t |
michael@0 | 2043 | nsCSSValuePairList_heap::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2044 | { |
michael@0 | 2045 | size_t n = aMallocSizeOf(this); |
michael@0 | 2046 | n += mXValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2047 | n += mYValue.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2048 | n += mNext ? mNext->SizeOfIncludingThis(aMallocSizeOf) : 0; |
michael@0 | 2049 | return n; |
michael@0 | 2050 | } |
michael@0 | 2051 | |
michael@0 | 2052 | size_t |
michael@0 | 2053 | nsCSSValue::Array::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2054 | { |
michael@0 | 2055 | size_t n = aMallocSizeOf(this); |
michael@0 | 2056 | for (size_t i = 0; i < mCount; i++) { |
michael@0 | 2057 | n += mArray[i].SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2058 | } |
michael@0 | 2059 | return n; |
michael@0 | 2060 | } |
michael@0 | 2061 | |
michael@0 | 2062 | css::URLValue::URLValue(nsIURI* aURI, nsStringBuffer* aString, |
michael@0 | 2063 | nsIURI* aReferrer, nsIPrincipal* aOriginPrincipal) |
michael@0 | 2064 | : mURI(aURI), |
michael@0 | 2065 | mString(aString), |
michael@0 | 2066 | mReferrer(aReferrer), |
michael@0 | 2067 | mOriginPrincipal(aOriginPrincipal), |
michael@0 | 2068 | mURIResolved(true) |
michael@0 | 2069 | { |
michael@0 | 2070 | NS_ABORT_IF_FALSE(aOriginPrincipal, "Must have an origin principal"); |
michael@0 | 2071 | mString->AddRef(); |
michael@0 | 2072 | } |
michael@0 | 2073 | |
michael@0 | 2074 | css::URLValue::URLValue(nsStringBuffer* aString, nsIURI* aBaseURI, |
michael@0 | 2075 | nsIURI* aReferrer, nsIPrincipal* aOriginPrincipal) |
michael@0 | 2076 | : mURI(aBaseURI), |
michael@0 | 2077 | mString(aString), |
michael@0 | 2078 | mReferrer(aReferrer), |
michael@0 | 2079 | mOriginPrincipal(aOriginPrincipal), |
michael@0 | 2080 | mURIResolved(false) |
michael@0 | 2081 | { |
michael@0 | 2082 | NS_ABORT_IF_FALSE(aOriginPrincipal, "Must have an origin principal"); |
michael@0 | 2083 | mString->AddRef(); |
michael@0 | 2084 | } |
michael@0 | 2085 | |
michael@0 | 2086 | css::URLValue::~URLValue() |
michael@0 | 2087 | { |
michael@0 | 2088 | mString->Release(); |
michael@0 | 2089 | } |
michael@0 | 2090 | |
michael@0 | 2091 | bool |
michael@0 | 2092 | css::URLValue::operator==(const URLValue& aOther) const |
michael@0 | 2093 | { |
michael@0 | 2094 | bool eq; |
michael@0 | 2095 | return NS_strcmp(nsCSSValue::GetBufferValue(mString), |
michael@0 | 2096 | nsCSSValue::GetBufferValue(aOther.mString)) == 0 && |
michael@0 | 2097 | (GetURI() == aOther.GetURI() || // handles null == null |
michael@0 | 2098 | (mURI && aOther.mURI && |
michael@0 | 2099 | NS_SUCCEEDED(mURI->Equals(aOther.mURI, &eq)) && |
michael@0 | 2100 | eq)) && |
michael@0 | 2101 | (mOriginPrincipal == aOther.mOriginPrincipal || |
michael@0 | 2102 | (NS_SUCCEEDED(mOriginPrincipal->Equals(aOther.mOriginPrincipal, |
michael@0 | 2103 | &eq)) && eq)); |
michael@0 | 2104 | } |
michael@0 | 2105 | |
michael@0 | 2106 | bool |
michael@0 | 2107 | css::URLValue::URIEquals(const URLValue& aOther) const |
michael@0 | 2108 | { |
michael@0 | 2109 | NS_ABORT_IF_FALSE(mURIResolved && aOther.mURIResolved, |
michael@0 | 2110 | "How do you know the URIs aren't null?"); |
michael@0 | 2111 | bool eq; |
michael@0 | 2112 | // Worth comparing GetURI() to aOther.GetURI() and mOriginPrincipal to |
michael@0 | 2113 | // aOther.mOriginPrincipal, because in the (probably common) case when this |
michael@0 | 2114 | // value was one of the ones that in fact did not change this will be our |
michael@0 | 2115 | // fast path to equality |
michael@0 | 2116 | return (mURI == aOther.mURI || |
michael@0 | 2117 | (NS_SUCCEEDED(mURI->Equals(aOther.mURI, &eq)) && eq)) && |
michael@0 | 2118 | (mOriginPrincipal == aOther.mOriginPrincipal || |
michael@0 | 2119 | (NS_SUCCEEDED(mOriginPrincipal->Equals(aOther.mOriginPrincipal, |
michael@0 | 2120 | &eq)) && eq)); |
michael@0 | 2121 | } |
michael@0 | 2122 | |
michael@0 | 2123 | nsIURI* |
michael@0 | 2124 | css::URLValue::GetURI() const |
michael@0 | 2125 | { |
michael@0 | 2126 | if (!mURIResolved) { |
michael@0 | 2127 | mURIResolved = true; |
michael@0 | 2128 | // Be careful to not null out mURI before we've passed it as the base URI |
michael@0 | 2129 | nsCOMPtr<nsIURI> newURI; |
michael@0 | 2130 | NS_NewURI(getter_AddRefs(newURI), |
michael@0 | 2131 | NS_ConvertUTF16toUTF8(nsCSSValue::GetBufferValue(mString)), |
michael@0 | 2132 | nullptr, mURI); |
michael@0 | 2133 | newURI.swap(mURI); |
michael@0 | 2134 | } |
michael@0 | 2135 | |
michael@0 | 2136 | return mURI; |
michael@0 | 2137 | } |
michael@0 | 2138 | |
michael@0 | 2139 | size_t |
michael@0 | 2140 | css::URLValue::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2141 | { |
michael@0 | 2142 | size_t n = aMallocSizeOf(this); |
michael@0 | 2143 | |
michael@0 | 2144 | // This string is unshared. |
michael@0 | 2145 | n += mString->SizeOfIncludingThisMustBeUnshared(aMallocSizeOf); |
michael@0 | 2146 | |
michael@0 | 2147 | // Measurement of the following members may be added later if DMD finds it is |
michael@0 | 2148 | // worthwhile: |
michael@0 | 2149 | // - mURI |
michael@0 | 2150 | // - mReferrer |
michael@0 | 2151 | // - mOriginPrincipal |
michael@0 | 2152 | |
michael@0 | 2153 | return n; |
michael@0 | 2154 | } |
michael@0 | 2155 | |
michael@0 | 2156 | |
michael@0 | 2157 | css::ImageValue::ImageValue(nsIURI* aURI, nsStringBuffer* aString, |
michael@0 | 2158 | nsIURI* aReferrer, nsIPrincipal* aOriginPrincipal, |
michael@0 | 2159 | nsIDocument* aDocument) |
michael@0 | 2160 | : URLValue(aURI, aString, aReferrer, aOriginPrincipal) |
michael@0 | 2161 | { |
michael@0 | 2162 | // NB: If aDocument is not the original document, we may not be able to load |
michael@0 | 2163 | // images from aDocument. Instead we do the image load from the original doc |
michael@0 | 2164 | // and clone it to aDocument. |
michael@0 | 2165 | nsIDocument* loadingDoc = aDocument->GetOriginalDocument(); |
michael@0 | 2166 | if (!loadingDoc) { |
michael@0 | 2167 | loadingDoc = aDocument; |
michael@0 | 2168 | } |
michael@0 | 2169 | |
michael@0 | 2170 | loadingDoc->StyleImageLoader()->LoadImage(aURI, aOriginPrincipal, aReferrer, |
michael@0 | 2171 | this); |
michael@0 | 2172 | |
michael@0 | 2173 | if (loadingDoc != aDocument) { |
michael@0 | 2174 | aDocument->StyleImageLoader()->MaybeRegisterCSSImage(this); |
michael@0 | 2175 | } |
michael@0 | 2176 | } |
michael@0 | 2177 | |
michael@0 | 2178 | static PLDHashOperator |
michael@0 | 2179 | ClearRequestHashtable(nsISupports* aKey, nsRefPtr<imgRequestProxy>& aValue, |
michael@0 | 2180 | void* aClosure) |
michael@0 | 2181 | { |
michael@0 | 2182 | mozilla::css::ImageValue* image = |
michael@0 | 2183 | static_cast<mozilla::css::ImageValue*>(aClosure); |
michael@0 | 2184 | nsIDocument* doc = static_cast<nsIDocument*>(aKey); |
michael@0 | 2185 | |
michael@0 | 2186 | #ifdef DEBUG |
michael@0 | 2187 | { |
michael@0 | 2188 | nsCOMPtr<nsIDocument> slowDoc = do_QueryInterface(aKey); |
michael@0 | 2189 | MOZ_ASSERT(slowDoc == doc); |
michael@0 | 2190 | } |
michael@0 | 2191 | #endif |
michael@0 | 2192 | |
michael@0 | 2193 | if (doc) { |
michael@0 | 2194 | doc->StyleImageLoader()->DeregisterCSSImage(image); |
michael@0 | 2195 | } |
michael@0 | 2196 | |
michael@0 | 2197 | if (aValue) { |
michael@0 | 2198 | aValue->CancelAndForgetObserver(NS_BINDING_ABORTED); |
michael@0 | 2199 | } |
michael@0 | 2200 | |
michael@0 | 2201 | return PL_DHASH_REMOVE; |
michael@0 | 2202 | } |
michael@0 | 2203 | |
michael@0 | 2204 | css::ImageValue::~ImageValue() |
michael@0 | 2205 | { |
michael@0 | 2206 | mRequests.Enumerate(&ClearRequestHashtable, this); |
michael@0 | 2207 | } |
michael@0 | 2208 | |
michael@0 | 2209 | nsCSSValueGradientStop::nsCSSValueGradientStop() |
michael@0 | 2210 | : mLocation(eCSSUnit_None), |
michael@0 | 2211 | mColor(eCSSUnit_Null) |
michael@0 | 2212 | { |
michael@0 | 2213 | MOZ_COUNT_CTOR(nsCSSValueGradientStop); |
michael@0 | 2214 | } |
michael@0 | 2215 | |
michael@0 | 2216 | nsCSSValueGradientStop::nsCSSValueGradientStop(const nsCSSValueGradientStop& aOther) |
michael@0 | 2217 | : mLocation(aOther.mLocation), |
michael@0 | 2218 | mColor(aOther.mColor) |
michael@0 | 2219 | { |
michael@0 | 2220 | MOZ_COUNT_CTOR(nsCSSValueGradientStop); |
michael@0 | 2221 | } |
michael@0 | 2222 | |
michael@0 | 2223 | nsCSSValueGradientStop::~nsCSSValueGradientStop() |
michael@0 | 2224 | { |
michael@0 | 2225 | MOZ_COUNT_DTOR(nsCSSValueGradientStop); |
michael@0 | 2226 | } |
michael@0 | 2227 | |
michael@0 | 2228 | size_t |
michael@0 | 2229 | nsCSSValueGradientStop::SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2230 | { |
michael@0 | 2231 | size_t n = 0; |
michael@0 | 2232 | n += mLocation.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2233 | n += mColor .SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2234 | return n; |
michael@0 | 2235 | } |
michael@0 | 2236 | |
michael@0 | 2237 | nsCSSValueGradient::nsCSSValueGradient(bool aIsRadial, |
michael@0 | 2238 | bool aIsRepeating) |
michael@0 | 2239 | : mIsRadial(aIsRadial), |
michael@0 | 2240 | mIsRepeating(aIsRepeating), |
michael@0 | 2241 | mIsLegacySyntax(false), |
michael@0 | 2242 | mIsExplicitSize(false), |
michael@0 | 2243 | mBgPos(eCSSUnit_None), |
michael@0 | 2244 | mAngle(eCSSUnit_None) |
michael@0 | 2245 | { |
michael@0 | 2246 | mRadialValues[0].SetNoneValue(); |
michael@0 | 2247 | mRadialValues[1].SetNoneValue(); |
michael@0 | 2248 | } |
michael@0 | 2249 | |
michael@0 | 2250 | size_t |
michael@0 | 2251 | nsCSSValueGradient::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2252 | { |
michael@0 | 2253 | size_t n = aMallocSizeOf(this); |
michael@0 | 2254 | n += mBgPos.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2255 | n += mAngle.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2256 | n += mRadialValues[0].SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2257 | n += mRadialValues[1].SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2258 | n += mStops.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2259 | for (uint32_t i = 0; i < mStops.Length(); i++) { |
michael@0 | 2260 | n += mStops[i].SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2261 | } |
michael@0 | 2262 | return n; |
michael@0 | 2263 | } |
michael@0 | 2264 | |
michael@0 | 2265 | // --- nsCSSValueTokenStream ------------ |
michael@0 | 2266 | |
michael@0 | 2267 | nsCSSValueTokenStream::nsCSSValueTokenStream() |
michael@0 | 2268 | : mPropertyID(eCSSProperty_UNKNOWN) |
michael@0 | 2269 | , mShorthandPropertyID(eCSSProperty_UNKNOWN) |
michael@0 | 2270 | { |
michael@0 | 2271 | MOZ_COUNT_CTOR(nsCSSValueTokenStream); |
michael@0 | 2272 | } |
michael@0 | 2273 | |
michael@0 | 2274 | nsCSSValueTokenStream::~nsCSSValueTokenStream() |
michael@0 | 2275 | { |
michael@0 | 2276 | MOZ_COUNT_DTOR(nsCSSValueTokenStream); |
michael@0 | 2277 | } |
michael@0 | 2278 | |
michael@0 | 2279 | size_t |
michael@0 | 2280 | nsCSSValueTokenStream::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2281 | { |
michael@0 | 2282 | size_t n = aMallocSizeOf(this); |
michael@0 | 2283 | n += mTokenStream.SizeOfExcludingThisIfUnshared(aMallocSizeOf); |
michael@0 | 2284 | return n; |
michael@0 | 2285 | } |
michael@0 | 2286 | |
michael@0 | 2287 | // --- nsCSSValueFloatColor ------------- |
michael@0 | 2288 | |
michael@0 | 2289 | bool |
michael@0 | 2290 | nsCSSValueFloatColor::operator==(nsCSSValueFloatColor& aOther) const |
michael@0 | 2291 | { |
michael@0 | 2292 | return mComponent1 == aOther.mComponent1 && |
michael@0 | 2293 | mComponent2 == aOther.mComponent2 && |
michael@0 | 2294 | mComponent3 == aOther.mComponent3 && |
michael@0 | 2295 | mAlpha == aOther.mAlpha; |
michael@0 | 2296 | } |
michael@0 | 2297 | |
michael@0 | 2298 | nscolor |
michael@0 | 2299 | nsCSSValueFloatColor::GetColorValue(nsCSSUnit aUnit) const |
michael@0 | 2300 | { |
michael@0 | 2301 | MOZ_ASSERT(nsCSSValue::IsFloatColorUnit(aUnit), "unexpected unit"); |
michael@0 | 2302 | |
michael@0 | 2303 | if (aUnit == eCSSUnit_PercentageRGBColor || |
michael@0 | 2304 | aUnit == eCSSUnit_PercentageRGBAColor) { |
michael@0 | 2305 | return NS_RGBA(NSToIntRound(mComponent1 * 255.0f), |
michael@0 | 2306 | NSToIntRound(mComponent2 * 255.0f), |
michael@0 | 2307 | NSToIntRound(mComponent3 * 255.0f), |
michael@0 | 2308 | NSToIntRound(mAlpha * 255.0f)); |
michael@0 | 2309 | } |
michael@0 | 2310 | |
michael@0 | 2311 | // HSL color |
michael@0 | 2312 | MOZ_ASSERT(aUnit == eCSSUnit_HSLColor || |
michael@0 | 2313 | aUnit == eCSSUnit_HSLAColor); |
michael@0 | 2314 | nscolor hsl = NS_HSL2RGB(mComponent1, mComponent2, mComponent3); |
michael@0 | 2315 | return NS_RGBA(NS_GET_R(hsl), |
michael@0 | 2316 | NS_GET_G(hsl), |
michael@0 | 2317 | NS_GET_B(hsl), |
michael@0 | 2318 | NSToIntRound(mAlpha * 255.0f)); |
michael@0 | 2319 | } |
michael@0 | 2320 | |
michael@0 | 2321 | bool |
michael@0 | 2322 | nsCSSValueFloatColor::IsNonTransparentColor() const |
michael@0 | 2323 | { |
michael@0 | 2324 | return mAlpha > 0.0f; |
michael@0 | 2325 | } |
michael@0 | 2326 | |
michael@0 | 2327 | void |
michael@0 | 2328 | nsCSSValueFloatColor::AppendToString(nsCSSUnit aUnit, nsAString& aResult) const |
michael@0 | 2329 | { |
michael@0 | 2330 | MOZ_ASSERT(nsCSSValue::IsFloatColorUnit(aUnit), "unexpected unit"); |
michael@0 | 2331 | |
michael@0 | 2332 | bool hasAlpha = aUnit == eCSSUnit_PercentageRGBAColor || |
michael@0 | 2333 | aUnit == eCSSUnit_HSLAColor; |
michael@0 | 2334 | bool isHSL = aUnit == eCSSUnit_HSLColor || |
michael@0 | 2335 | aUnit == eCSSUnit_HSLAColor; |
michael@0 | 2336 | |
michael@0 | 2337 | if (isHSL) { |
michael@0 | 2338 | aResult.AppendLiteral("hsl"); |
michael@0 | 2339 | } else { |
michael@0 | 2340 | aResult.AppendLiteral("rgb"); |
michael@0 | 2341 | } |
michael@0 | 2342 | if (hasAlpha) { |
michael@0 | 2343 | aResult.AppendLiteral("a("); |
michael@0 | 2344 | } else { |
michael@0 | 2345 | aResult.Append('('); |
michael@0 | 2346 | } |
michael@0 | 2347 | if (isHSL) { |
michael@0 | 2348 | aResult.AppendFloat(mComponent1 * 360.0f); |
michael@0 | 2349 | aResult.AppendLiteral(", "); |
michael@0 | 2350 | } else { |
michael@0 | 2351 | aResult.AppendFloat(mComponent1 * 100.0f); |
michael@0 | 2352 | aResult.AppendLiteral("%, "); |
michael@0 | 2353 | } |
michael@0 | 2354 | aResult.AppendFloat(mComponent2 * 100.0f); |
michael@0 | 2355 | aResult.AppendLiteral("%, "); |
michael@0 | 2356 | aResult.AppendFloat(mComponent3 * 100.0f); |
michael@0 | 2357 | if (hasAlpha) { |
michael@0 | 2358 | aResult.AppendLiteral("%, "); |
michael@0 | 2359 | aResult.AppendFloat(mAlpha); |
michael@0 | 2360 | aResult.Append(')'); |
michael@0 | 2361 | } else { |
michael@0 | 2362 | aResult.AppendLiteral("%)"); |
michael@0 | 2363 | } |
michael@0 | 2364 | } |
michael@0 | 2365 | |
michael@0 | 2366 | size_t |
michael@0 | 2367 | nsCSSValueFloatColor::SizeOfIncludingThis( |
michael@0 | 2368 | mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2369 | { |
michael@0 | 2370 | size_t n = aMallocSizeOf(this); |
michael@0 | 2371 | return n; |
michael@0 | 2372 | } |
michael@0 | 2373 | |
michael@0 | 2374 | // --- nsCSSCornerSizes ----------------- |
michael@0 | 2375 | |
michael@0 | 2376 | nsCSSCornerSizes::nsCSSCornerSizes(void) |
michael@0 | 2377 | { |
michael@0 | 2378 | MOZ_COUNT_CTOR(nsCSSCornerSizes); |
michael@0 | 2379 | } |
michael@0 | 2380 | |
michael@0 | 2381 | nsCSSCornerSizes::nsCSSCornerSizes(const nsCSSCornerSizes& aCopy) |
michael@0 | 2382 | : mTopLeft(aCopy.mTopLeft), |
michael@0 | 2383 | mTopRight(aCopy.mTopRight), |
michael@0 | 2384 | mBottomRight(aCopy.mBottomRight), |
michael@0 | 2385 | mBottomLeft(aCopy.mBottomLeft) |
michael@0 | 2386 | { |
michael@0 | 2387 | MOZ_COUNT_CTOR(nsCSSCornerSizes); |
michael@0 | 2388 | } |
michael@0 | 2389 | |
michael@0 | 2390 | nsCSSCornerSizes::~nsCSSCornerSizes() |
michael@0 | 2391 | { |
michael@0 | 2392 | MOZ_COUNT_DTOR(nsCSSCornerSizes); |
michael@0 | 2393 | } |
michael@0 | 2394 | |
michael@0 | 2395 | void |
michael@0 | 2396 | nsCSSCornerSizes::Reset() |
michael@0 | 2397 | { |
michael@0 | 2398 | NS_FOR_CSS_FULL_CORNERS(corner) { |
michael@0 | 2399 | this->GetCorner(corner).Reset(); |
michael@0 | 2400 | } |
michael@0 | 2401 | } |
michael@0 | 2402 | |
michael@0 | 2403 | static_assert(NS_CORNER_TOP_LEFT == 0 && NS_CORNER_TOP_RIGHT == 1 && |
michael@0 | 2404 | NS_CORNER_BOTTOM_RIGHT == 2 && NS_CORNER_BOTTOM_LEFT == 3, |
michael@0 | 2405 | "box corner constants not tl/tr/br/bl == 0/1/2/3"); |
michael@0 | 2406 | |
michael@0 | 2407 | /* static */ const nsCSSCornerSizes::corner_type |
michael@0 | 2408 | nsCSSCornerSizes::corners[4] = { |
michael@0 | 2409 | &nsCSSCornerSizes::mTopLeft, |
michael@0 | 2410 | &nsCSSCornerSizes::mTopRight, |
michael@0 | 2411 | &nsCSSCornerSizes::mBottomRight, |
michael@0 | 2412 | &nsCSSCornerSizes::mBottomLeft, |
michael@0 | 2413 | }; |
michael@0 | 2414 | |
michael@0 | 2415 | size_t |
michael@0 | 2416 | mozilla::css::GridTemplateAreasValue::SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const |
michael@0 | 2417 | { |
michael@0 | 2418 | size_t n = mNamedAreas.SizeOfExcludingThis(aMallocSizeOf); |
michael@0 | 2419 | n += mTemplates.SizeOfIncludingThis(aMallocSizeOf); |
michael@0 | 2420 | return n; |
michael@0 | 2421 | } |