/** * Tries to call |nsCSSValue::StartImageLoad()| on an image source. * Image sources are specified by |url()| or |-moz-image-rect()| function. */ static void TryToStartImageLoadOnValue(const nsCSSValue& aValue, nsIDocument* aDocument, nsCSSValueTokenStream* aTokenStream) { MOZ_ASSERT(aDocument); if (aValue.GetUnit() == eCSSUnit_URL) { aValue.StartImageLoad(aDocument); if (aTokenStream) { aTokenStream->mImageValues.PutEntry(aValue.GetImageStructValue()); } } else if (aValue.GetUnit() == eCSSUnit_Image) { // If we already have a request, see if this document needs to clone it. imgIRequest* request = aValue.GetImageValue(nullptr); if (request) { mozilla::css::ImageValue* imageValue = aValue.GetImageStructValue(); aDocument->StyleImageLoader()->MaybeRegisterCSSImage(imageValue); if (aTokenStream) { aTokenStream->mImageValues.PutEntry(imageValue); } } } else if (aValue.EqualsFunction(eCSSKeyword__moz_image_rect)) { nsCSSValue::Array* arguments = aValue.GetArrayValue(); MOZ_ASSERT(arguments->Count() == 6, "unexpected num of arguments"); const nsCSSValue& image = arguments->Item(1); TryToStartImageLoadOnValue(image, aDocument, aTokenStream); } }
/** * Tries to call |nsCSSValue::StartImageLoad()| on an image source. * Image sources are specified by |url()| or |-moz-image-rect()| function. */ static void TryToStartImageLoadOnValue(const nsCSSValue& aValue, nsIDocument* aDocument, nsStyleContext* aContext, nsCSSProperty aProperty, bool aForTokenStream) { MOZ_ASSERT(aDocument); if (aValue.GetUnit() == eCSSUnit_URL) { aValue.StartImageLoad(aDocument); if (aForTokenStream && aContext) { CSSVariableImageTable::Add(aContext, aProperty, aValue.GetImageStructValue()); } } else if (aValue.GetUnit() == eCSSUnit_Image) { // If we already have a request, see if this document needs to clone it. imgIRequest* request = aValue.GetImageValue(nullptr); if (request) { ImageValue* imageValue = aValue.GetImageStructValue(); aDocument->StyleImageLoader()->MaybeRegisterCSSImage(imageValue); if (aForTokenStream && aContext) { CSSVariableImageTable::Add(aContext, aProperty, imageValue); } } } else if (aValue.EqualsFunction(eCSSKeyword__moz_image_rect)) { nsCSSValue::Array* arguments = aValue.GetArrayValue(); MOZ_ASSERT(arguments->Count() == 6, "unexpected num of arguments"); const nsCSSValue& image = arguments->Item(1); TryToStartImageLoadOnValue(image, aDocument, aContext, aProperty, aForTokenStream); } }
/* static */ nscoord nsMathMLFrame::CalcLength(nsPresContext* aPresContext, nsStyleContext* aStyleContext, const nsCSSValue& aCSSValue, float aFontSizeInflation) { NS_ASSERTION(aCSSValue.IsLengthUnit(), "not a length unit"); if (aCSSValue.IsFixedLengthUnit()) { return aCSSValue.GetFixedLength(aPresContext); } if (aCSSValue.IsPixelLengthUnit()) { return aCSSValue.GetPixelLength(); } nsCSSUnit unit = aCSSValue.GetUnit(); if (eCSSUnit_EM == unit) { const nsStyleFont* font = aStyleContext->StyleFont(); return NSToCoordRound(aCSSValue.GetFloatValue() * (float)font->mFont.size); } else if (eCSSUnit_XHeight == unit) { aPresContext->SetUsesExChUnits(true); RefPtr<nsFontMetrics> fm = nsLayoutUtils:: GetFontMetricsForStyleContext(aStyleContext, aFontSizeInflation); nscoord xHeight = fm->XHeight(); return NSToCoordRound(aCSSValue.GetFloatValue() * (float)xHeight); } // MathML doesn't specify other CSS units such as rem or ch NS_ERROR("Unsupported unit"); return 0; }
static void ProcessTranslatePart(float& aResult, const nsCSSValue& aValue, nsStyleContext* aContext, nsPresContext* aPresContext, PRBool& aCanStoreInRuleTree, nscoord aSize, float aAppUnitsPerMatrixUnit) { nscoord offset = 0; float percent = 0.0f; if (aValue.GetUnit() == eCSSUnit_Percent) { percent = aValue.GetPercentValue(); } else if (aValue.IsCalcUnit()) { nsRuleNode::ComputedCalc result = nsRuleNode::SpecifiedCalcToComputedCalc(aValue, aContext, aPresContext, aCanStoreInRuleTree); percent = result.mPercent; offset = result.mLength; } else { offset = CalcLength(aValue, aContext, aPresContext, aCanStoreInRuleTree); } aResult = (percent * NSAppUnitsToFloatPixels(aSize, aAppUnitsPerMatrixUnit)) + NSAppUnitsToFloatPixels(offset, aAppUnitsPerMatrixUnit); }
/* static */ nscoord nsMathMLFrame::CalcLength(nsPresContext* aPresContext, nsStyleContext* aStyleContext, const nsCSSValue& aCSSValue) { NS_ASSERTION(aCSSValue.IsLengthUnit(), "not a length unit"); if (aCSSValue.IsFixedLengthUnit()) { return aCSSValue.GetLengthTwips(); } nsCSSUnit unit = aCSSValue.GetUnit(); if (eCSSUnit_Pixel == unit) { return NSFloatPixelsToTwips(aCSSValue.GetFloatValue(), aPresContext->ScaledPixelsToTwips()); } else if (eCSSUnit_EM == unit) { const nsStyleFont* font = aStyleContext->GetStyleFont(); return NSToCoordRound(aCSSValue.GetFloatValue() * (float)font->mFont.size); } else if (eCSSUnit_XHeight == unit) { nscoord xHeight; const nsStyleFont* font = aStyleContext->GetStyleFont(); nsCOMPtr<nsIFontMetrics> fm = aPresContext->GetMetricsFor(font->mFont); fm->GetXHeight(xHeight); return NSToCoordRound(aCSSValue.GetFloatValue() * (float)xHeight); } return 0; }
float ProcessTranslatePart(const nsCSSValue& aValue, nsStyleContext* aContext, nsPresContext* aPresContext, RuleNodeCacheConditions& aConditions, TransformReferenceBox* aRefBox, TransformReferenceBox::DimensionGetter aDimensionGetter) { nscoord offset = 0; float percent = 0.0f; if (aValue.GetUnit() == eCSSUnit_Percent) { percent = aValue.GetPercentValue(); } else if (aValue.GetUnit() == eCSSUnit_Pixel || aValue.GetUnit() == eCSSUnit_Number) { // Handle this here (even though nsRuleNode::CalcLength handles it // fine) so that callers are allowed to pass a null style context // and pres context to SetToTransformFunction if they know (as // StyleAnimationValue does) that all lengths within the transform // function have already been computed to pixels and percents. // // Raw numbers are treated as being pixels. // // Don't convert to aValue to AppUnits here to avoid precision issues. return aValue.GetFloatValue(); } else if (aValue.IsCalcUnit()) { nsRuleNode::ComputedCalc result = nsRuleNode::SpecifiedCalcToComputedCalc(aValue, aContext, aPresContext, aConditions); percent = result.mPercent; offset = result.mLength; } else { offset = nsRuleNode::CalcLength(aValue, aContext, aPresContext, aConditions); } float translation = NSAppUnitsToFloatPixels(offset, nsPresContext::AppUnitsPerCSSPixel()); // We want to avoid calling aDimensionGetter if there's no percentage to be // resolved (for performance reasons - see TransformReferenceBox). if (percent != 0.0f && aRefBox) { translation += percent * NSAppUnitsToFloatPixels((aRefBox->*aDimensionGetter)(), nsPresContext::AppUnitsPerCSSPixel()); } return translation; }
static void TryToStartImageLoad(const nsCSSValue& aValue, nsIDocument* aDocument, nsCSSProperty aProperty) { if (aValue.GetUnit() == eCSSUnit_List) { for (const nsCSSValueList* l = aValue.GetListValue(); l; l = l->mNext) { TryToStartImageLoad(l->mValue, aDocument, aProperty); } } else if (nsCSSProps::PropHasFlags(aProperty, CSS_PROPERTY_IMAGE_IS_IN_ARRAY_0)) { if (aValue.GetUnit() == eCSSUnit_Array) { TryToStartImageLoadOnValue(aValue.GetArrayValue()->Item(0), aDocument); } } else { TryToStartImageLoadOnValue(aValue, aDocument); } }
float ProcessTranslatePart(const nsCSSValue& aValue, nsStyleContext* aContext, nsPresContext* aPresContext, bool& aCanStoreInRuleTree, nscoord aSize) { nscoord offset = 0; float percent = 0.0f; if (aValue.GetUnit() == eCSSUnit_Percent) { percent = aValue.GetPercentValue(); } else if (aValue.GetUnit() == eCSSUnit_Pixel || aValue.GetUnit() == eCSSUnit_Number) { // Handle this here (even though nsRuleNode::CalcLength handles it // fine) so that callers are allowed to pass a null style context // and pres context to SetToTransformFunction if they know (as // StyleAnimationValue does) that all lengths within the transform // function have already been computed to pixels and percents. // // Raw numbers are treated as being pixels. // // Don't convert to aValue to AppUnits here to avoid precision issues. return aValue.GetFloatValue(); } else if (aValue.IsCalcUnit()) { nsRuleNode::ComputedCalc result = nsRuleNode::SpecifiedCalcToComputedCalc(aValue, aContext, aPresContext, aCanStoreInRuleTree); percent = result.mPercent; offset = result.mLength; } else { offset = nsRuleNode::CalcLength(aValue, aContext, aPresContext, aCanStoreInRuleTree); } return (percent * NSAppUnitsToFloatPixels(aSize, nsPresContext::AppUnitsPerCSSPixel())) + NSAppUnitsToFloatPixels(offset, nsPresContext::AppUnitsPerCSSPixel()); }
void nsMathMLmpaddedFrame::UpdateValue(int32_t aSign, int32_t aPseudoUnit, const nsCSSValue& aCSSValue, const ReflowOutput& aDesiredSize, nscoord& aValueToUpdate, float aFontSizeInflation) const { nsCSSUnit unit = aCSSValue.GetUnit(); if (NS_MATHML_SIGN_INVALID != aSign && eCSSUnit_Null != unit) { nscoord scaler = 0, amount = 0; if (eCSSUnit_Percent == unit || eCSSUnit_Number == unit) { switch(aPseudoUnit) { case NS_MATHML_PSEUDO_UNIT_WIDTH: scaler = aDesiredSize.Width(); break; case NS_MATHML_PSEUDO_UNIT_HEIGHT: scaler = aDesiredSize.BlockStartAscent(); break; case NS_MATHML_PSEUDO_UNIT_DEPTH: scaler = aDesiredSize.Height() - aDesiredSize.BlockStartAscent(); break; default: // if we ever reach here, it would mean something is wrong // somewhere with the setup and/or the caller NS_ERROR("Unexpected Pseudo Unit"); return; } } if (eCSSUnit_Number == unit) amount = NSToCoordRound(float(scaler) * aCSSValue.GetFloatValue()); else if (eCSSUnit_Percent == unit) amount = NSToCoordRound(float(scaler) * aCSSValue.GetPercentValue()); else amount = CalcLength(PresContext(), mStyleContext, aCSSValue, aFontSizeInflation); if (NS_MATHML_SIGN_PLUS == aSign) aValueToUpdate += amount; else if (NS_MATHML_SIGN_MINUS == aSign) aValueToUpdate -= amount; else aValueToUpdate = amount; } }
void nsMathMLmpaddedFrame::UpdateValue(PRInt32 aSign, PRInt32 aPseudoUnit, const nsCSSValue& aCSSValue, const nsBoundingMetrics& aBoundingMetrics, nscoord& aValueToUpdate) const { nsCSSUnit unit = aCSSValue.GetUnit(); if (NS_MATHML_SIGN_INVALID != aSign && eCSSUnit_Null != unit) { nscoord scaler = 0, amount = 0; if (eCSSUnit_Percent == unit || eCSSUnit_Number == unit) { switch(aPseudoUnit) { case NS_MATHML_PSEUDO_UNIT_WIDTH: scaler = aBoundingMetrics.width; break; case NS_MATHML_PSEUDO_UNIT_HEIGHT: scaler = aBoundingMetrics.ascent; break; case NS_MATHML_PSEUDO_UNIT_DEPTH: scaler = aBoundingMetrics.descent; break; default: // if we ever reach here, it would mean something is wrong // somewhere with the setup and/or the caller NS_ERROR("Unexpected Pseudo Unit"); return; } } if (eCSSUnit_Number == unit) amount = NSToCoordRound(float(scaler) * aCSSValue.GetFloatValue()); else if (eCSSUnit_Percent == unit) amount = NSToCoordRound(float(scaler) * aCSSValue.GetPercentValue()); else amount = CalcLength(PresContext(), mStyleContext, aCSSValue); nscoord oldValue = aValueToUpdate; if (NS_MATHML_SIGN_PLUS == aSign) aValueToUpdate += amount; else if (NS_MATHML_SIGN_MINUS == aSign) aValueToUpdate -= amount; else aValueToUpdate = amount; } }
/** * Tries to call |nsCSSValue::StartImageLoad()| on an image source. * Image sources are specified by |url()| or |-moz-image-rect()| function. */ static void TryToStartImageLoadOnValue(const nsCSSValue& aValue, nsIDocument* aDocument) { if (aValue.GetUnit() == eCSSUnit_URL) { aValue.StartImageLoad(aDocument); } else if (aValue.EqualsFunction(eCSSKeyword__moz_image_rect)) { nsCSSValue::Array* arguments = aValue.GetArrayValue(); NS_ABORT_IF_FALSE(arguments->Count() == 6, "unexpected num of arguments"); const nsCSSValue& image = arguments->Item(1); if (image.GetUnit() == eCSSUnit_URL) image.StartImageLoad(aDocument); } }
/* Helper function to fill in an nscoord with the specified nsCSSValue. */ static nscoord CalcLength(const nsCSSValue &aValue, nsStyleContext* aContext, nsPresContext* aPresContext, PRBool &aCanStoreInRuleTree) { if (aValue.GetUnit() == eCSSUnit_Pixel) { // Handle this here (even though nsRuleNode::CalcLength handles it // fine) so that callers are allowed to pass a null style context // and pres context to SetToTransformFunction if they know (as // nsStyleAnimation does) that all lengths within the transform // function have already been computed to pixels and percents. return nsPresContext::CSSPixelsToAppUnits(aValue.GetFloatValue()); } return nsRuleNode::CalcLength(aValue, aContext, aPresContext, aCanStoreInRuleTree); }
void nsCSSValue::SetTripletValue(const nsCSSValue& xValue, const nsCSSValue& yValue, const nsCSSValue& zValue) { // Only allow Null for the z component NS_ABORT_IF_FALSE(xValue.GetUnit() != eCSSUnit_Null && yValue.GetUnit() != eCSSUnit_Null && xValue.GetUnit() != eCSSUnit_Inherit && yValue.GetUnit() != eCSSUnit_Inherit && zValue.GetUnit() != eCSSUnit_Inherit && xValue.GetUnit() != eCSSUnit_Initial && yValue.GetUnit() != eCSSUnit_Initial && zValue.GetUnit() != eCSSUnit_Initial, "inappropriate triplet value"); Reset(); mUnit = eCSSUnit_Triplet; mValue.mTriplet = new nsCSSValueTriplet_heap(xValue, yValue, zValue); mValue.mTriplet->AddRef(); }
void nsCSSValue::SetPairValue(const nsCSSValue& xValue, const nsCSSValue& yValue) { NS_ABORT_IF_FALSE(xValue.GetUnit() != eCSSUnit_Null && yValue.GetUnit() != eCSSUnit_Null && xValue.GetUnit() != eCSSUnit_Inherit && yValue.GetUnit() != eCSSUnit_Inherit && xValue.GetUnit() != eCSSUnit_Initial && yValue.GetUnit() != eCSSUnit_Initial, "inappropriate pair value"); Reset(); mUnit = eCSSUnit_Pair; mValue.mPair = new nsCSSValuePair_heap(xValue, yValue); mValue.mPair->AddRef(); }
void nsMathMLmpaddedFrame::UpdateValue(PRInt32 aSign, PRInt32 aPseudoUnit, const nsCSSValue& aCSSValue, nscoord aLeftSpace, const nsBoundingMetrics& aBoundingMetrics, nscoord& aValueToUpdate) const { nsCSSUnit unit = aCSSValue.GetUnit(); if (NS_MATHML_SIGN_INVALID != aSign && eCSSUnit_Null != unit) { nscoord scaler = 0, amount = 0; if (eCSSUnit_Percent == unit || eCSSUnit_Number == unit) { switch(aPseudoUnit) { case NS_MATHML_PSEUDO_UNIT_WIDTH: scaler = aBoundingMetrics.width; break; case NS_MATHML_PSEUDO_UNIT_HEIGHT: scaler = aBoundingMetrics.ascent; break; case NS_MATHML_PSEUDO_UNIT_DEPTH: scaler = aBoundingMetrics.descent; break; case NS_MATHML_PSEUDO_UNIT_LSPACE: scaler = aLeftSpace; break; default: // if we ever reach here, it would mean something is wrong // somewhere with the setup and/or the caller NS_ASSERTION(0, "Unexpected Pseudo Unit"); return; } } if (eCSSUnit_Number == unit) amount = NSToCoordRound(float(scaler) * aCSSValue.GetFloatValue()); else if (eCSSUnit_Percent == unit) amount = NSToCoordRound(float(scaler) * aCSSValue.GetPercentValue()); else amount = CalcLength(PresContext(), mStyleContext, aCSSValue); nscoord oldValue = aValueToUpdate; if (NS_MATHML_SIGN_PLUS == aSign) aValueToUpdate += amount; else if (NS_MATHML_SIGN_MINUS == aSign) aValueToUpdate -= amount; else aValueToUpdate = amount; /* The REC says: Dimensions that would be positive if the content was rendered normally cannot be made negative using <mpadded>; a positive dimension is set to 0 if it would otherwise become negative. Dimensions which are initially 0 can be made negative */ if (0 < oldValue && 0 > aValueToUpdate) aValueToUpdate = 0; } }
/** * Tries to call |nsCSSValue::StartImageLoad()| on an image source. * Image sources are specified by |url()| or |-moz-image-rect()| function. */ static void TryToStartImageLoadOnValue(const nsCSSValue& aValue, nsIDocument* aDocument, nsStyleContext* aContext, nsCSSPropertyID aProperty, bool aForTokenStream) { MOZ_ASSERT(aDocument); if (aValue.GetUnit() == eCSSUnit_URL) { #ifdef MOZ_ENABLE_MASK_AS_SHORTHAND // The 'mask-image' property accepts local reference URIs. // For example, // mask-image: url(#mask_id); // refer to a SVG mask element, whose id is // // "mask_id", in the current document. // For such 'mask-image' values (pointing to an in-document element), // there is no need to trigger image download. if (aProperty == eCSSProperty_mask_image) { // Filter out all fragment URLs. // Since nsCSSValue::GetURLStructValue runs much faster than // nsIURI::EqualsExceptRef bellow, we get performance gain by this // early return. URLValue* urlValue = aValue.GetURLStructValue(); if (urlValue->GetLocalURLFlag()) { return; } // Even though urlValue is not a fragment URL, it might still refer to // an internal resource. // For example, aDocument base URL is "http://foo/index.html" and // intentionally references a mask-image at // url(http://foo/index.html#mask) which still refers to a resource in // aDocument. nsIURI* imageURI = aValue.GetURLValue(); if (imageURI) { nsIURI* docURI = aDocument->GetDocumentURI(); bool isEqualExceptRef = false; nsresult rv = imageURI->EqualsExceptRef(docURI, &isEqualExceptRef); if (NS_SUCCEEDED(rv) && isEqualExceptRef) { return; } } } #endif aValue.StartImageLoad(aDocument); if (aForTokenStream && aContext) { CSSVariableImageTable::Add(aContext, aProperty, aValue.GetImageStructValue()); } } else if (aValue.GetUnit() == eCSSUnit_Image) { // If we already have a request, see if this document needs to clone it. imgIRequest* request = aValue.GetImageValue(nullptr); if (request) { ImageValue* imageValue = aValue.GetImageStructValue(); aDocument->StyleImageLoader()->MaybeRegisterCSSImage(imageValue); if (aForTokenStream && aContext) { CSSVariableImageTable::Add(aContext, aProperty, imageValue); } } } else if (aValue.EqualsFunction(eCSSKeyword__moz_image_rect)) { nsCSSValue::Array* arguments = aValue.GetArrayValue(); MOZ_ASSERT(arguments->Count() == 6, "unexpected num of arguments"); const nsCSSValue& image = arguments->Item(1); TryToStartImageLoadOnValue(image, aDocument, aContext, aProperty, aForTokenStream); } }