internal bool ParseSize() { nsCSSValue width = new nsCSSValue(), height = new nsCSSValue(); if (!ParseVariant(ref width, VARIANT_AHKL, nsCSSProps.kPageSizeKTable)) { return false; } if (width.IsLengthUnit()) { ParseVariant(ref height, VARIANT_LENGTH, null); } if (!ExpectEndProperty()) { return false; } if (width == height || height.GetUnit() == nsCSSUnit.Null) { AppendValue(nsCSSProperty.Size, width); } else { var pair = new nsCSSValue(); pair.SetPairValue(width, height); AppendValue(nsCSSProperty.Size, pair); } return true; }
// Note that this does include VARIANT_CALC, which is numeric. This is // because calc() parsing, as proposed, drops range restrictions inside // the calc() expression and clamps the result of the calculation to the // range. // Note that callers passing VARIANT_CALC in aVariantMask will get // full-range parsing inside the calc() expression, and the code that // computes the calc will be required to clamp the resulting value to an // appropriate range. internal bool ParseNonNegativeVariant(ref nsCSSValue aValue, int32_t aVariantMask, int32_t[] aKeywordTable) { // The variant mask must only contain non-numeric variants or the ones // that we specifically handle. Debug.Assert((aVariantMask & ~(VARIANT_ALL_NONNUMERIC | VARIANT_NUMBER | VARIANT_LENGTH | VARIANT_PERCENT | VARIANT_INTEGER)) == 0, "need to update code below to handle additional variants"); if (ParseVariant(ref aValue, aVariantMask, aKeywordTable)) { if (nsCSSUnit.Number == aValue.GetUnit() || aValue.IsLengthUnit()){ if (aValue.GetFloatValue() < 0) { UngetToken(); return false; } } else if (aValue.GetUnit() == nsCSSUnit.Percent) { if (aValue.GetPercentValue() < 0) { UngetToken(); return false; } } else if (aValue.GetUnit() == nsCSSUnit.Integer) { if (aValue.GetIntValue() < 0) { UngetToken(); return false; } } return true; } return false; }
internal bool ParseShadowItem(ref nsCSSValue aValue, bool aIsBoxShadow) { // A shadow list item is an array, with entries in this sequence: const int IndexX = 0; const int IndexY = 1; const int IndexRadius = 2; const int IndexSpread = 3; const int IndexColor = 4; const int IndexInset = 5; nsCSSValue[] val = new nsCSSValue[6]; if (aIsBoxShadow) { // Optional inset keyword (ignore errors) ParseVariant(ref val[IndexInset], VARIANT_KEYWORD, nsCSSProps.kBoxShadowTypeKTable); } var xOrColor = new nsCSSValue(); bool haveColor = false; if (!ParseVariant(ref xOrColor, VARIANT_COLOR | VARIANT_LENGTH | VARIANT_CALC, null)) { return false; } if (xOrColor.IsLengthUnit() || xOrColor.IsCalcUnit()) { val[IndexX] = xOrColor; } else { // Must be a color (as string or color value) Debug.Assert(xOrColor.GetUnit() == nsCSSUnit.Ident || xOrColor.GetUnit() == nsCSSUnit.Color || xOrColor.GetUnit() == nsCSSUnit.EnumColor, "Must be a color value"); val[IndexColor] = xOrColor; haveColor = true; // X coordinate mandatory after color if (!ParseVariant(ref val[IndexX], VARIANT_LENGTH | VARIANT_CALC, null)) { return false; } } // Y coordinate; mandatory if (!ParseVariant(ref val[IndexY], VARIANT_LENGTH | VARIANT_CALC, null)) { return false; } // Optional radius. Ignore errors except if they pass a negative // value which we must reject. If we use ParseNonNegativeVariant // we can't tell the difference between an unspecified radius // and a negative radius. if (ParseVariant(ref val[IndexRadius], VARIANT_LENGTH | VARIANT_CALC, null) && val[IndexRadius].IsLengthUnit() && val[IndexRadius].GetFloatValue() < 0) { return false; } if (aIsBoxShadow) { // Optional spread ParseVariant(ref val[IndexSpread], VARIANT_LENGTH | VARIANT_CALC, null); } if (!haveColor) { // Optional color ParseVariant(ref val[IndexColor], VARIANT_COLOR, null); } if (aIsBoxShadow && val[IndexInset].GetUnit() == nsCSSUnit.Null) { // Optional inset keyword ParseVariant(ref val[IndexInset], VARIANT_KEYWORD, nsCSSProps.kBoxShadowTypeKTable); } aValue.SetArrayValue(val, nsCSSUnit.Array); return true; }
internal bool ParseBorderSpacing() { nsCSSValue xValue = new nsCSSValue(), yValue = new nsCSSValue(); if (!ParseNonNegativeVariant(ref xValue, VARIANT_HL | VARIANT_CALC, null)) { return false; } // If we have one length, get the optional second length. // set the second value equal to the first. if (xValue.IsLengthUnit() || xValue.IsCalcUnit()) { ParseNonNegativeVariant(ref yValue, VARIANT_LENGTH | VARIANT_CALC, null); } if (!ExpectEndProperty()) { return false; } if (yValue == xValue || yValue.GetUnit() == nsCSSUnit.Null) { AppendValue(nsCSSProperty.BorderSpacing, xValue); } else { var pair = new nsCSSValue(); pair.SetPairValue(xValue, yValue); AppendValue(nsCSSProperty.BorderSpacing, pair); } return true; }