Convert background-position to use nsCSSValuePair rather than acting like a shorthand property. b=258080 r+sr=bzbarsky

This commit is contained in:
dbaron@dbaron.org 2007-04-15 15:25:20 -07:00
Родитель 8b24cb8ae7
Коммит 8deaea57d2
12 изменённых файлов: 322 добавлений и 389 удалений

Просмотреть файл

@ -223,8 +223,13 @@ PRBool nsCSSDeclaration::AppendValueToString(nsCSSProperty aProperty, nsAString&
case eCSSType_ValuePair: {
const nsCSSValuePair *pair = NS_STATIC_CAST(const nsCSSValuePair*, storage);
AppendCSSValueToString(aProperty, pair->mXValue, aResult);
if (pair->mYValue != pair->mXValue) {
if (pair->mYValue != pair->mXValue ||
(aProperty == eCSSProperty_background_position &&
pair->mXValue.GetUnit() != eCSSUnit_Inherit &&
pair->mXValue.GetUnit() != eCSSUnit_Initial)) {
// Only output a Y value if it's different from the X value
// or if it's a background-position value other than 'initial'
// or 'inherit'.
aResult.Append(PRUnichar(' '));
AppendCSSValueToString(aProperty, pair->mYValue, aResult);
}
@ -614,14 +619,8 @@ nsCSSDeclaration::GetValue(nsCSSProperty aProperty,
aValue.Append(PRUnichar(' '));
appendedSomething = PR_TRUE;
}
if (AppendValueToString(eCSSProperty_background_x_position, aValue)) {
aValue.Append(PRUnichar(' '));
#ifdef DEBUG
PRBool check =
#endif
AppendValueToString(eCSSProperty_background_y_position, aValue);
NS_ASSERTION(check, "we parsed half of background-position");
} else if (appendedSomething) {
if (!AppendValueToString(eCSSProperty_background_position, aValue) &&
appendedSomething) {
NS_ASSERTION(!aValue.IsEmpty() && aValue.Last() == PRUnichar(' '),
"We appended a space before!");
// We appended an extra space. Let's get rid of it
@ -681,17 +680,6 @@ nsCSSDeclaration::GetValue(nsCSSProperty aProperty,
}
break;
}
case eCSSProperty_background_position: {
if (AppendValueToString(eCSSProperty_background_x_position, aValue)) {
aValue.Append(PRUnichar(' '));
#ifdef DEBUG
PRBool check =
#endif
AppendValueToString(eCSSProperty_background_y_position, aValue);
NS_ASSERTION(check, "we parsed half of background-position");
}
break;
}
#ifdef MOZ_SVG
case eCSSProperty_marker: {
nsCSSValue endValue, midValue, startValue;
@ -727,18 +715,20 @@ nsCSSDeclaration::GetValueIsImportant(nsCSSProperty aProperty) const
return mImportantData->StorageFor(aProperty) != nsnull;
}
// XXXldb Bug 376075 All callers of AllPropertiesSameImportance also
// need to check for 'inherit' and 'initial' values, since you can't
// output a mix of either mixed with other values in the same shorthand!
PRBool
nsCSSDeclaration::AllPropertiesSameImportance(PRInt32 aFirst, PRInt32 aSecond,
PRInt32 aThird, PRInt32 aFourth,
PRInt32 aFifth, PRInt32 aSixth,
PRInt32 aFifth,
PRBool & aImportance) const
{
aImportance = GetValueIsImportant(OrderValueAt(aFirst-1));
if ((aSecond && aImportance != GetValueIsImportant(OrderValueAt(aSecond-1))) ||
(aThird && aImportance != GetValueIsImportant(OrderValueAt(aThird-1))) ||
(aFourth && aImportance != GetValueIsImportant(OrderValueAt(aFourth-1))) ||
(aFifth && aImportance != GetValueIsImportant(OrderValueAt(aFifth-1))) ||
(aSixth && aImportance != GetValueIsImportant(OrderValueAt(aSixth-1)))) {
(aFifth && aImportance != GetValueIsImportant(OrderValueAt(aFifth-1)))) {
return PR_FALSE;
}
return PR_TRUE;
@ -824,15 +814,15 @@ nsCSSDeclaration::TryBorderShorthand(nsAString & aString, PRUint32 aPropertiesSe
PRBool isWidthImportant, isStyleImportant, isColorImportant;
if (AllPropertiesSameImportance(aBorderTopWidth, aBorderBottomWidth,
aBorderLeftWidth, aBorderRightWidth,
0, 0,
0,
isWidthImportant) &&
AllPropertiesSameImportance(aBorderTopStyle, aBorderBottomStyle,
aBorderLeftStyle, aBorderRightStyle,
0, 0,
0,
isStyleImportant) &&
AllPropertiesSameImportance(aBorderTopColor, aBorderBottomColor,
aBorderLeftColor, aBorderRightColor,
0, 0,
0,
isColorImportant)) {
if (isWidthImportant == isStyleImportant && isWidthImportant == isColorImportant) {
border = PR_TRUE;
@ -874,7 +864,7 @@ nsCSSDeclaration::TryBorderSideShorthand(nsAString & aString,
{
PRBool isImportant;
if (AllPropertiesSameImportance(aBorderWidth, aBorderStyle, aBorderColor,
0, 0, 0,
0, 0,
isImportant)) {
AppendASCIItoUTF16(nsCSSProps::GetStringValue(aShorthand), aString);
aString.AppendLiteral(": ");
@ -910,7 +900,7 @@ nsCSSDeclaration::TryFourSidesShorthand(nsAString & aString,
PRBool isImportant;
if (aTop && aBottom && aLeft && aRight &&
AllPropertiesSameImportance(aTop, aBottom, aLeft, aRight,
0, 0,
0,
isImportant)) {
// all 4 properties are set, we can output a shorthand
AppendASCIItoUTF16(nsCSSProps::GetStringValue(aShorthand), aString);
@ -953,16 +943,15 @@ nsCSSDeclaration::TryBackgroundShorthand(nsAString & aString,
PRInt32 & aBgImage,
PRInt32 & aBgRepeat,
PRInt32 & aBgAttachment,
PRInt32 & aBgPositionX,
PRInt32 & aBgPositionY) const
PRInt32 & aBgPosition) const
{
// 0 means not in the mOrder array; otherwise it's index+1
// check if we have at least two properties set; otherwise, no need to
// use a shorthand
PRBool isImportant;
if (aBgColor && aBgImage && aBgRepeat && aBgAttachment && aBgPositionX && aBgPositionY &&
if (aBgColor && aBgImage && aBgRepeat && aBgAttachment && aBgPosition &&
AllPropertiesSameImportance(aBgColor, aBgImage, aBgRepeat, aBgAttachment,
aBgPositionX, aBgPositionY, isImportant)) {
aBgPosition, isImportant)) {
AppendASCIItoUTF16(nsCSSProps::GetStringValue(eCSSProperty_background), aString);
aString.AppendLiteral(": ");
@ -982,30 +971,14 @@ nsCSSDeclaration::TryBackgroundShorthand(nsAString & aString,
aBgAttachment = 0;
aString.Append(PRUnichar(' '));
UseBackgroundPosition(aString, aBgPositionX, aBgPositionY);
AppendValueToString(eCSSProperty_background_position, aString);
aBgPosition = 0;
AppendImportanceToString(isImportant, aString);
aString.AppendLiteral("; ");
}
}
void
nsCSSDeclaration::UseBackgroundPosition(nsAString & aString,
PRInt32 & aBgPositionX,
PRInt32 & aBgPositionY) const
{
nsAutoString backgroundXValue, backgroundYValue;
AppendValueToString(eCSSProperty_background_x_position, backgroundXValue);
AppendValueToString(eCSSProperty_background_y_position, backgroundYValue);
aString.Append(backgroundXValue);
if (!backgroundXValue.Equals(backgroundYValue, nsCaseInsensitiveStringComparator())) {
// the two values are different
aString.Append(PRUnichar(' '));
aString.Append(backgroundYValue);
}
aBgPositionX = 0;
aBgPositionY = 0;
}
void
nsCSSDeclaration::TryOverflowShorthand(nsAString & aString,
PRInt32 & aOverflowX,
@ -1014,7 +987,7 @@ nsCSSDeclaration::TryOverflowShorthand(nsAString & aString,
PRBool isImportant;
if (aOverflowX && aOverflowY &&
AllPropertiesSameImportance(aOverflowX, aOverflowY,
0, 0, 0, 0, isImportant)) {
0, 0, 0, isImportant)) {
nsCSSValue xValue, yValue;
GetValueOrImportantValue(eCSSProperty_overflow_x, xValue);
GetValueOrImportantValue(eCSSProperty_overflow_y, yValue);
@ -1041,7 +1014,7 @@ nsCSSDeclaration::TryMarkerShorthand(nsAString & aString,
PRBool isImportant;
if (aMarkerEnd && aMarkerMid && aMarkerEnd &&
AllPropertiesSameImportance(aMarkerEnd, aMarkerMid, aMarkerStart,
0, 0, 0, isImportant)) {
0, 0, isImportant)) {
nsCSSValue endValue, midValue, startValue;
GetValueOrImportantValue(eCSSProperty_marker_end, endValue);
GetValueOrImportantValue(eCSSProperty_marker_mid, midValue);
@ -1103,7 +1076,7 @@ nsCSSDeclaration::ToString(nsAString& aString) const
PRInt32 marginTop = 0, marginBottom = 0, marginLeft = 0, marginRight = 0;
PRInt32 paddingTop = 0, paddingBottom = 0, paddingLeft = 0, paddingRight = 0;
PRInt32 bgColor = 0, bgImage = 0, bgRepeat = 0, bgAttachment = 0;
PRInt32 bgPositionX = 0, bgPositionY = 0;
PRInt32 bgPosition = 0;
PRInt32 overflowX = 0, overflowY = 0;
PRUint32 borderPropertiesSet = 0, finalBorderPropertiesToSet = 0;
#ifdef MOZ_SVG
@ -1166,8 +1139,7 @@ nsCSSDeclaration::ToString(nsAString& aString) const
case eCSSProperty_background_image: bgImage = index+1; break;
case eCSSProperty_background_repeat: bgRepeat = index+1; break;
case eCSSProperty_background_attachment: bgAttachment = index+1; break;
case eCSSProperty_background_x_position: bgPositionX = index+1; break;
case eCSSProperty_background_y_position: bgPositionY = index+1; break;
case eCSSProperty_background_position: bgPosition = index+1; break;
case eCSSProperty_overflow_x: overflowX = index+1; break;
case eCSSProperty_overflow_y: overflowY = index+1; break;
@ -1245,7 +1217,7 @@ nsCSSDeclaration::ToString(nsAString& aString) const
PR_TRUE);
TryBackgroundShorthand(aString,
bgColor, bgImage, bgRepeat, bgAttachment,
bgPositionX, bgPositionY);
bgPosition);
TryOverflowShorthand(aString, overflowX, overflowY);
#ifdef MOZ_SVG
TryMarkerShorthand(aString, markerEnd, markerMid, markerStart);
@ -1300,30 +1272,7 @@ nsCSSDeclaration::ToString(nsAString& aString) const
NS_CASE_OUTPUT_PROPERTY_VALUE(eCSSProperty_background_image, bgImage)
NS_CASE_OUTPUT_PROPERTY_VALUE(eCSSProperty_background_repeat, bgRepeat)
NS_CASE_OUTPUT_PROPERTY_VALUE(eCSSProperty_background_attachment, bgAttachment)
case eCSSProperty_background_x_position:
case eCSSProperty_background_y_position: {
// 0 means not in the mOrder array; otherwise it's index+1
PRBool isImportant;
if (bgPositionX && bgPositionY &&
AllPropertiesSameImportance(bgPositionX, bgPositionY,
0, 0, 0, 0, isImportant)) {
AppendASCIItoUTF16(nsCSSProps::GetStringValue(eCSSProperty_background_position), aString);
aString.AppendLiteral(": ");
UseBackgroundPosition(aString, bgPositionX, bgPositionY);
AppendImportanceToString(isImportant, aString);
aString.AppendLiteral("; ");
}
else if (eCSSProperty_background_x_position == property && bgPositionX) {
AppendPropertyAndValueToString(eCSSProperty_background_x_position, aString);
bgPositionX = 0;
}
else if (eCSSProperty_background_y_position == property && bgPositionY) {
AppendPropertyAndValueToString(eCSSProperty_background_y_position, aString);
bgPositionY = 0;
}
break;
}
NS_CASE_OUTPUT_PROPERTY_VALUE(eCSSProperty_background_position, bgPosition)
NS_CASE_OUTPUT_PROPERTY_VALUE(eCSSProperty_overflow_x, overflowX)
NS_CASE_OUTPUT_PROPERTY_VALUE(eCSSProperty_overflow_y, overflowY)

Просмотреть файл

@ -193,11 +193,7 @@ private:
void TryBackgroundShorthand(nsAString & aString,
PRInt32 & aBgColor, PRInt32 & aBgImage,
PRInt32 & aBgRepeat, PRInt32 & aBgAttachment,
PRInt32 & aBgPositionX,
PRInt32 & aBgPositionY) const;
void UseBackgroundPosition(nsAString & aString,
PRInt32 & aBgPositionX,
PRInt32 & aBgPositionY) const;
PRInt32 & aBgPosition) const;
void TryOverflowShorthand(nsAString & aString,
PRInt32 & aOverflowX, PRInt32 & aOverflowY) const;
#ifdef MOZ_SVG
@ -209,7 +205,7 @@ private:
PRBool AllPropertiesSameImportance(PRInt32 aFirst, PRInt32 aSecond,
PRInt32 aThird, PRInt32 aFourth,
PRInt32 aFifth, PRInt32 aSixth,
PRInt32 aFifth,
PRBool & aImportance) const;
PRBool AllPropertiesSameValue(PRInt32 aFirst, PRInt32 aSecond,
PRInt32 aThird, PRInt32 aFourth) const;

Просмотреть файл

@ -306,6 +306,7 @@ protected:
PRBool ParseAzimuth(nsresult& aErrorCode, nsCSSValue& aValue);
PRBool ParseBackground(nsresult& aErrorCode);
PRBool ParseBackgroundPosition(nsresult& aErrorCode);
PRBool ParseBackgroundPositionValues(nsresult& aErrorCode);
PRBool ParseBorderColor(nsresult& aErrorCode);
PRBool ParseBorderColors(nsresult& aErrorCode,
nsCSSValueList** aResult,
@ -4185,6 +4186,8 @@ PRBool CSSParserImpl::ParseDirectionalBoxProperty(nsresult& aErrorCode,
PRBool CSSParserImpl::ParseProperty(nsresult& aErrorCode,
nsCSSProperty aPropID)
{
NS_ASSERTION(aPropID < eCSSProperty_COUNT, "index out of range");
switch (aPropID) { // handle shorthand or multiple properties
case eCSSProperty_background:
return ParseBackground(aErrorCode);
@ -4302,10 +4305,7 @@ PRBool CSSParserImpl::ParseProperty(nsresult& aErrorCode,
return ParseMarker(aErrorCode);
#endif
// Strip out properties we use internally. These properties are used
// by compound property parsing routines (e.g. "background-position").
case eCSSProperty_background_x_position:
case eCSSProperty_background_y_position:
// Strip out properties we use internally.
case eCSSProperty_margin_end_value:
case eCSSProperty_margin_left_value:
case eCSSProperty_margin_right_value:
@ -4458,10 +4458,6 @@ PRBool CSSParserImpl::ParseSingleValueProperty(nsresult& aErrorCode,
case eCSSProperty_background_repeat:
return ParseVariant(aErrorCode, aValue, VARIANT_HK,
nsCSSProps::kBackgroundRepeatKTable);
case eCSSProperty_background_x_position: // for internal use
case eCSSProperty_background_y_position: // for internal use
return ParseVariant(aErrorCode, aValue, VARIANT_HKLP,
kBackgroundXYPositionKTable);
case eCSSProperty_binding:
return ParseVariant(aErrorCode, aValue, VARIANT_HUO, nsnull);
case eCSSProperty_border_collapse:
@ -4855,144 +4851,183 @@ BackgroundPositionMaskToCSSValue(PRInt32 aMask, PRBool isX)
PRBool CSSParserImpl::ParseBackground(nsresult& aErrorCode)
{
const PRInt32 numProps = 6;
static const nsCSSProperty kBackgroundIDs[numProps] = {
eCSSProperty_background_color,
eCSSProperty_background_image,
eCSSProperty_background_repeat,
eCSSProperty_background_attachment,
eCSSProperty_background_x_position,
eCSSProperty_background_y_position
};
nsAutoParseCompoundProperty compound(this);
nsCSSValue values[numProps];
PRInt32 found = ParseChoice(aErrorCode, values, kBackgroundIDs, numProps);
if ((found < 1) || (PR_FALSE == ExpectEndProperty(aErrorCode, PR_TRUE))) {
return PR_FALSE;
}
// Fill in the values that the shorthand will set if we don't find
// other values.
mTempData.mColor.mBackColor.SetIntValue(NS_STYLE_BG_COLOR_TRANSPARENT,
eCSSUnit_Enumerated);
mTempData.SetPropertyBit(eCSSProperty_background_color);
mTempData.mColor.mBackImage.SetNoneValue();
mTempData.SetPropertyBit(eCSSProperty_background_image);
mTempData.mColor.mBackRepeat.SetIntValue(NS_STYLE_BG_REPEAT_XY,
eCSSUnit_Enumerated);
mTempData.SetPropertyBit(eCSSProperty_background_repeat);
mTempData.mColor.mBackAttachment.SetIntValue(NS_STYLE_BG_ATTACHMENT_SCROLL,
eCSSUnit_Enumerated);
mTempData.SetPropertyBit(eCSSProperty_background_attachment);
mTempData.mColor.mBackPosition.mXValue.SetPercentValue(0.0f);
mTempData.mColor.mBackPosition.mYValue.SetPercentValue(0.0f);
mTempData.SetPropertyBit(eCSSProperty_background_position);
// including the ones that we can't set from the shorthand.
mTempData.mColor.mBackClip.SetInitialValue();
mTempData.SetPropertyBit(eCSSProperty__moz_background_clip);
mTempData.mColor.mBackOrigin.SetInitialValue();
mTempData.SetPropertyBit(eCSSProperty__moz_background_origin);
mTempData.mColor.mBackInlinePolicy.SetInitialValue();
mTempData.SetPropertyBit(eCSSProperty__moz_background_inline_policy);
if (0 != (found & 0x30)) { // found one or more position values, validate them
if (0 == (found & 0x20)) {
if (eCSSUnit_Enumerated == values[4].GetUnit()) {
PRInt32 mask = values[4].GetIntValue();
values[4] = BackgroundPositionMaskToCSSValue(mask, PR_TRUE);
values[5] = BackgroundPositionMaskToCSSValue(mask, PR_FALSE);
}
else {
values[5].SetPercentValue(0.5f);
}
// XXX If ParseSingleValueProperty were table-driven (bug 376079) and
// automatically filled in the right field of mTempData, we could move
// ParseBackgroundPosition to it (as a special case) and switch back
// to using ParseChoice here.
PRBool haveColor = PR_FALSE,
haveImage = PR_FALSE,
haveRepeat = PR_FALSE,
haveAttach = PR_FALSE,
havePosition = PR_FALSE;
while (GetToken(aErrorCode, PR_TRUE)) {
nsCSSTokenType tt = mToken.mType;
UngetToken(); // ...but we'll still cheat and use mToken
if (tt == eCSSToken_Symbol) {
// ExpectEndProperty only looks for symbols, and nothing else will
// show up as one.
break;
}
else { // both x & y values
nsCSSUnit xUnit = values[4].GetUnit();
nsCSSUnit yUnit = values[5].GetUnit();
if (eCSSUnit_Enumerated == xUnit) {
PRInt32 xValue = values[4].GetIntValue();
if (eCSSUnit_Enumerated == yUnit) {
PRInt32 yValue = values[5].GetIntValue();
if (0 != (xValue & (BG_LEFT | BG_RIGHT)) && // x is really an x value
0 != (yValue & (BG_LEFT | BG_RIGHT))) { // y is also an x value
return PR_FALSE;
}
if (0 != (xValue & (BG_TOP | BG_BOTTOM)) && // x is really an y value
0 != (yValue & (BG_TOP | BG_BOTTOM))) { // y is also an y value
return PR_FALSE;
}
if (0 != (xValue & (BG_TOP | BG_BOTTOM)) || // x is really a y value
0 != (yValue & (BG_LEFT | BG_RIGHT))) { // or y is really an x value
PRInt32 holdXValue = xValue;
xValue = yValue;
yValue = holdXValue;
}
NS_ASSERTION(xValue & BG_CLR, "bad x value");
NS_ASSERTION(yValue & BG_CTB, "bad y value");
values[4] = BackgroundPositionMaskToCSSValue(xValue, PR_TRUE);
values[5] = BackgroundPositionMaskToCSSValue(yValue, PR_FALSE);
if (tt == eCSSToken_Ident) {
nsCSSKeyword keyword = nsCSSKeywords::LookupKeyword(mToken.mIdent);
PRInt32 dummy;
if (keyword == eCSSKeyword_inherit ||
keyword == eCSSKeyword__moz_initial) {
if (haveColor || haveImage || haveRepeat || haveAttach || havePosition)
return PR_FALSE;
haveColor = haveImage = haveRepeat = haveAttach = havePosition =
PR_TRUE;
GetToken(aErrorCode, PR_TRUE); // undo the UngetToken above
nsCSSValue val;
if (keyword == eCSSKeyword_inherit) {
val.SetInheritValue();
} else {
val.SetInitialValue();
}
else {
if (!(xValue & BG_CLR)) {
// The first keyword can only be 'center', 'left', or 'right'
return PR_FALSE;
}
values[4] = BackgroundPositionMaskToCSSValue(xValue, PR_TRUE);
mTempData.mColor.mBackColor = val;
mTempData.mColor.mBackImage = val;
mTempData.mColor.mBackRepeat = val;
mTempData.mColor.mBackAttachment = val;
mTempData.mColor.mBackPosition.mXValue = val;
mTempData.mColor.mBackPosition.mYValue = val;
// Reset (for 'inherit') the 3 properties that can't be
// specified, although it's not entirely clear in the spec:
// http://lists.w3.org/Archives/Public/www-style/2007Mar/0110
mTempData.mColor.mBackClip = val;
mTempData.mColor.mBackOrigin = val;
mTempData.mColor.mBackInlinePolicy = val;
break;
} else if (keyword == eCSSKeyword_none) {
if (haveImage)
return PR_FALSE;
haveImage = PR_TRUE;
if (!ParseSingleValueProperty(aErrorCode, mTempData.mColor.mBackImage,
eCSSProperty_background_image)) {
NS_NOTREACHED("should be able to parse");
return PR_FALSE;
}
} else if (nsCSSProps::FindKeyword(keyword,
nsCSSProps::kBackgroundAttachmentKTable, dummy)) {
if (haveAttach)
return PR_FALSE;
haveAttach = PR_TRUE;
if (!ParseSingleValueProperty(aErrorCode,
mTempData.mColor.mBackAttachment,
eCSSProperty_background_attachment)) {
NS_NOTREACHED("should be able to parse");
return PR_FALSE;
}
} else if (nsCSSProps::FindKeyword(keyword,
nsCSSProps::kBackgroundRepeatKTable, dummy)) {
if (haveRepeat)
return PR_FALSE;
haveRepeat = PR_TRUE;
if (!ParseSingleValueProperty(aErrorCode, mTempData.mColor.mBackRepeat,
eCSSProperty_background_repeat)) {
NS_NOTREACHED("should be able to parse");
return PR_FALSE;
}
} else if (nsCSSProps::FindKeyword(keyword,
kBackgroundXYPositionKTable, dummy)) {
if (havePosition)
return PR_FALSE;
havePosition = PR_TRUE;
if (!ParseBackgroundPositionValues(aErrorCode)) {
return PR_FALSE;
}
} else {
if (haveColor)
return PR_FALSE;
haveColor = PR_TRUE;
if (!ParseSingleValueProperty(aErrorCode, mTempData.mColor.mBackColor,
eCSSProperty_background_color)) {
return PR_FALSE;
}
}
else {
if (eCSSUnit_Enumerated == yUnit) {
PRInt32 yValue = values[5].GetIntValue();
if (!(yValue & BG_CTB)) {
// The second keyword can only be 'center', 'top', or 'bottom'
return PR_FALSE;
}
values[5] = BackgroundPositionMaskToCSSValue(yValue, PR_FALSE);
}
} else if (eCSSToken_Function == tt &&
mToken.mIdent.LowerCaseEqualsLiteral("url")) {
if (haveImage)
return PR_FALSE;
haveImage = PR_TRUE;
if (!ParseSingleValueProperty(aErrorCode, mTempData.mColor.mBackImage,
eCSSProperty_background_image)) {
return PR_FALSE;
}
} else if (mToken.IsDimension() || tt == eCSSToken_Percentage) {
if (havePosition)
return PR_FALSE;
havePosition = PR_TRUE;
if (!ParseBackgroundPositionValues(aErrorCode)) {
return PR_FALSE;
}
} else {
if (haveColor)
return PR_FALSE;
haveColor = PR_TRUE;
if (!ParseSingleValueProperty(aErrorCode, mTempData.mColor.mBackColor,
eCSSProperty_background_color)) {
return PR_FALSE;
}
}
}
// Provide missing values
if ((found & 0x01) == 0) {
values[0].SetIntValue(NS_STYLE_BG_COLOR_TRANSPARENT, eCSSUnit_Enumerated);
}
if ((found & 0x02) == 0) {
values[1].SetNoneValue();
}
if ((found & 0x04) == 0) {
values[2].SetIntValue(NS_STYLE_BG_REPEAT_XY, eCSSUnit_Enumerated);
}
if ((found & 0x08) == 0) {
values[3].SetIntValue(NS_STYLE_BG_ATTACHMENT_SCROLL, eCSSUnit_Enumerated);
}
if ((found & 0x30) == 0) {
values[4].SetPercentValue(0.0f);
values[5].SetPercentValue(0.0f);
}
PRInt32 index;
for (index = 0; index < numProps; ++index) {
AppendValue(kBackgroundIDs[index], values[index]);
}
// Background properties not settable from the shorthand get reset to their initial value
static const PRInt32 numResetProps = 3;
static const nsCSSProperty kBackgroundResetIDs[numResetProps] = {
eCSSProperty__moz_background_clip,
eCSSProperty__moz_background_inline_policy,
eCSSProperty__moz_background_origin
};
nsCSSValue initial;
initial.SetInitialValue();
for (index = 0; index < numResetProps; ++index) {
AppendValue(kBackgroundResetIDs[index], initial);
}
return PR_TRUE;
return ExpectEndProperty(aErrorCode, PR_TRUE) &&
(haveColor || haveImage || haveRepeat || haveAttach || havePosition);
}
PRBool CSSParserImpl::ParseBackgroundPosition(nsresult& aErrorCode)
{
if (!ParseBackgroundPositionValues(aErrorCode) ||
!ExpectEndProperty(aErrorCode, PR_TRUE))
return PR_FALSE;
mTempData.SetPropertyBit(eCSSProperty_background_position);
return PR_TRUE;
}
PRBool CSSParserImpl::ParseBackgroundPositionValues(nsresult& aErrorCode)
{
// First try a percentage or a length value
nsCSSValue xValue, yValue;
nsCSSValue &xValue = mTempData.mColor.mBackPosition.mXValue,
&yValue = mTempData.mColor.mBackPosition.mYValue;
if (ParseVariant(aErrorCode, xValue, VARIANT_HLP, nsnull)) {
if (eCSSUnit_Inherit == xValue.GetUnit() ||
eCSSUnit_Initial == xValue.GetUnit()) { // both are inherited or both are set to initial
if (ExpectEndProperty(aErrorCode, PR_TRUE)) {
AppendValue(eCSSProperty_background_x_position, xValue);
AppendValue(eCSSProperty_background_y_position, xValue);
return PR_TRUE;
}
return PR_FALSE;
yValue = xValue;
return PR_TRUE;
}
// We have one percentage/length. Get the optional second
// percentage/length/keyword.
if (ParseVariant(aErrorCode, yValue, VARIANT_LP, nsnull)) {
// We have two numbers
if (ExpectEndProperty(aErrorCode, PR_TRUE)) {
AppendValue(eCSSProperty_background_x_position, xValue);
AppendValue(eCSSProperty_background_y_position, yValue);
return PR_TRUE;
}
return PR_FALSE;
return PR_TRUE;
}
if (ParseEnum(aErrorCode, yValue, kBackgroundXYPositionKTable)) {
@ -5001,23 +5036,14 @@ PRBool CSSParserImpl::ParseBackgroundPosition(nsresult& aErrorCode)
// The second keyword can only be 'center', 'top', or 'bottom'
return PR_FALSE;
}
if (ExpectEndProperty(aErrorCode, PR_TRUE)) {
yValue = BackgroundPositionMaskToCSSValue(yVal, PR_FALSE);
AppendValue(eCSSProperty_background_x_position, xValue);
AppendValue(eCSSProperty_background_y_position, yValue);
return PR_TRUE;
}
return PR_FALSE;
yValue = BackgroundPositionMaskToCSSValue(yVal, PR_FALSE);
return PR_TRUE;
}
// If only one percentage or length value is given, it sets the
// horizontal position only, and the vertical position will be 50%.
if (ExpectEndProperty(aErrorCode, PR_TRUE)) {
AppendValue(eCSSProperty_background_x_position, xValue);
AppendValue(eCSSProperty_background_y_position, nsCSSValue(0.5f, eCSSUnit_Percent));
return PR_TRUE;
}
return PR_FALSE;
yValue.SetPercentValue(0.5f);
return PR_TRUE;
}
// Now try keywords. We do this manually to allow for the first
@ -5046,13 +5072,8 @@ PRBool CSSParserImpl::ParseBackgroundPosition(nsresult& aErrorCode)
return PR_FALSE;
}
if (ExpectEndProperty(aErrorCode, PR_TRUE)) {
xValue = BackgroundPositionMaskToCSSValue(mask, PR_TRUE);
AppendValue(eCSSProperty_background_x_position, xValue);
AppendValue(eCSSProperty_background_y_position, yValue);
return PR_TRUE;
}
return PR_FALSE;
xValue = BackgroundPositionMaskToCSSValue(mask, PR_TRUE);
return PR_TRUE;
}
}
}
@ -5064,15 +5085,10 @@ PRBool CSSParserImpl::ParseBackgroundPosition(nsresult& aErrorCode)
return PR_FALSE;
}
if (ExpectEndProperty(aErrorCode, PR_TRUE)) {
// Create style values
xValue = BackgroundPositionMaskToCSSValue(mask, PR_TRUE);
yValue = BackgroundPositionMaskToCSSValue(mask, PR_FALSE);
AppendValue(eCSSProperty_background_x_position, xValue);
AppendValue(eCSSProperty_background_y_position, yValue);
return PR_TRUE;
}
return PR_FALSE;
// Create style values
xValue = BackgroundPositionMaskToCSSValue(mask, PR_TRUE);
yValue = BackgroundPositionMaskToCSSValue(mask, PR_FALSE);
return PR_TRUE;
}
// These must be in CSS order (top,right,bottom,left) for indexing to work

Просмотреть файл

@ -83,10 +83,6 @@
/*************************************************************************/
// XXX Should we really be using CSS_PROP_SHORTHAND for 'border-spacing',
// 'background-position', and 'size'?
// All includers must explicitly define CSS_PROP_NOTIMPLEMENTED if they
// want this. (Only the DOM cares.)
#ifndef CSS_PROP_NOTIMPLEMENTED
@ -281,12 +277,8 @@ CSS_PROP_BACKGROUND(background-color, background_color, BackgroundColor, Color,
CSS_PROP_BACKGROUND(background-image, background_image, BackgroundImage, Color, mBackImage, eCSSType_Value, nsnull)
CSS_PROP_BACKGROUND(-moz-background-inline-policy, _moz_background_inline_policy, MozBackgroundInlinePolicy, Color, mBackInlinePolicy, eCSSType_Value, kBackgroundInlinePolicyKTable)
CSS_PROP_BACKGROUND(-moz-background-origin, _moz_background_origin, MozBackgroundOrigin, Color, mBackOrigin, eCSSType_Value, kBackgroundOriginKTable)
CSS_PROP_SHORTHAND(background-position, background_position, BackgroundPosition)
CSS_PROP_BACKGROUND(background-position, background_position, BackgroundPosition, Color, mBackPosition, eCSSType_ValuePair, nsnull)
CSS_PROP_BACKGROUND(background-repeat, background_repeat, BackgroundRepeat, Color, mBackRepeat, eCSSType_Value, kBackgroundRepeatKTable)
#ifndef CSS_PROP_LIST_EXCLUDE_INTERNAL
CSS_PROP_BACKGROUND(-x-background-x-position, background_x_position, BackgroundXPosition, Color, mBackPositionX, eCSSType_Value, kBackgroundXPositionKTable) // XXX bug 3935
CSS_PROP_BACKGROUND(-x-background-y-position, background_y_position, BackgroundYPosition, Color, mBackPositionY, eCSSType_Value, kBackgroundYPositionKTable) // XXX bug 3935
#endif /* !defined (CSS_PROP_LIST_EXCLUDE_INTERNAL) */
CSS_PROP_DISPLAY(-moz-binding, binding, MozBinding, Display, mBinding, eCSSType_Value, nsnull) // XXX bug 3935
CSS_PROP_SHORTHAND(border, border, Border)
CSS_PROP_SHORTHAND(border-bottom, border_bottom, BorderBottom)

Просмотреть файл

@ -1223,20 +1223,13 @@ static const nsCSSProperty gBackgroundSubpropTable[] = {
eCSSProperty_background_image,
eCSSProperty_background_repeat,
eCSSProperty_background_attachment,
eCSSProperty_background_x_position,
eCSSProperty_background_y_position,
eCSSProperty_background_position,
eCSSProperty__moz_background_clip, // XXX Added LDB.
eCSSProperty__moz_background_origin, // XXX Added LDB.
eCSSProperty__moz_background_inline_policy, // XXX Added LDB.
eCSSProperty_UNKNOWN
};
static const nsCSSProperty gBackgroundPositionSubpropTable[] = {
eCSSProperty_background_x_position,
eCSSProperty_background_y_position,
eCSSProperty_UNKNOWN
};
static const nsCSSProperty gBorderSubpropTable[] = {
eCSSProperty_border_top_width,
eCSSProperty_border_right_width,

Просмотреть файл

@ -138,8 +138,7 @@ nsCSSColor::nsCSSColor(const nsCSSColor& aCopy)
mBackImage(aCopy.mBackImage),
mBackRepeat(aCopy.mBackRepeat),
mBackAttachment(aCopy.mBackAttachment),
mBackPositionX(aCopy.mBackPositionX),
mBackPositionY(aCopy.mBackPositionY),
mBackPosition(aCopy.mBackPosition),
mBackClip(aCopy.mBackClip),
mBackOrigin(aCopy.mBackOrigin),
mBackInlinePolicy(aCopy.mBackInlinePolicy)

Просмотреть файл

@ -48,39 +48,6 @@
#include "nsCSSValue.h"
#include <stdio.h>
struct nsCSSStruct {
// EMPTY on purpose. ABSTRACT with no virtuals (typedef void nsCSSStruct?)
};
// We use the nsCSS* structures for storing nsCSSDeclaration's
// *temporary* data during parsing and modification. (They are too big
// for permanent storage.) We also use them for nsRuleData, with some
// additions of things that the style system must cascade, but that
// aren't CSS properties. Thus we use typedefs and inheritance
// (forwards, when the rule data needs extra data) to make the rule data
// structs from the declaration structs.
// NOTE: For compilation speed, this typedef also appears in nsRuleNode.h
typedef nsCSSStruct nsRuleDataStruct;
struct nsCSSFont : public nsCSSStruct {
nsCSSFont(void);
nsCSSFont(const nsCSSFont& aCopy);
~nsCSSFont(void);
nsCSSValue mFamily;
nsCSSValue mStyle;
nsCSSValue mVariant;
nsCSSValue mWeight;
nsCSSValue mSize;
nsCSSValue mSizeAdjust; // NEW
nsCSSValue mStretch; // NEW
};
struct nsRuleDataFont : public nsCSSFont {
PRBool mFamilyFromHTML; // Is the family from an HTML FONT element
};
// Prefer nsCSSValue::Array for lists of fixed size.
struct nsCSSValueList {
nsCSSValueList(void);
@ -93,47 +60,6 @@ struct nsCSSValueList {
nsCSSValueList* mNext;
};
struct nsCSSColor : public nsCSSStruct {
nsCSSColor(void);
nsCSSColor(const nsCSSColor& aCopy);
~nsCSSColor(void);
nsCSSValue mColor;
nsCSSValue mBackColor;
nsCSSValue mBackImage;
nsCSSValue mBackRepeat;
nsCSSValue mBackAttachment;
nsCSSValue mBackPositionX;
nsCSSValue mBackPositionY;
nsCSSValue mBackClip;
nsCSSValue mBackOrigin;
nsCSSValue mBackInlinePolicy;
};
struct nsRuleDataColor : public nsCSSColor {
};
struct nsCSSText : public nsCSSStruct {
nsCSSText(void);
nsCSSText(const nsCSSText& aCopy);
~nsCSSText(void);
nsCSSValue mWordSpacing;
nsCSSValue mLetterSpacing;
nsCSSValue mVerticalAlign;
nsCSSValue mTextTransform;
nsCSSValue mTextAlign;
nsCSSValue mTextIndent;
nsCSSValue mDecoration;
nsCSSValueList* mTextShadow; // NEW
nsCSSValue mUnicodeBidi; // NEW
nsCSSValue mLineHeight;
nsCSSValue mWhiteSpace;
};
struct nsRuleDataText : public nsCSSText {
};
struct nsCSSRect {
nsCSSRect(void);
nsCSSRect(const nsCSSRect& aCopy);
@ -228,6 +154,107 @@ struct nsCSSValueListRect {
static const side_type sides[4];
};
// Should be replaced with nsCSSValueList and nsCSSValue::Array.
struct nsCSSCounterData {
nsCSSCounterData(void);
nsCSSCounterData(const nsCSSCounterData& aCopy);
~nsCSSCounterData(void);
static PRBool Equal(nsCSSCounterData* aList1, nsCSSCounterData* aList2);
nsCSSValue mCounter;
nsCSSValue mValue;
nsCSSCounterData* mNext;
};
// Should be replaced with nsCSSValueList and nsCSSValue::Array.
struct nsCSSQuotes {
nsCSSQuotes(void);
nsCSSQuotes(const nsCSSQuotes& aCopy);
~nsCSSQuotes(void);
static PRBool Equal(nsCSSQuotes* aList1, nsCSSQuotes* aList2);
nsCSSValue mOpen;
nsCSSValue mClose;
nsCSSQuotes* mNext;
};
/****************************************************************************/
struct nsCSSStruct {
// EMPTY on purpose. ABSTRACT with no virtuals (typedef void nsCSSStruct?)
};
// We use the nsCSS* structures for storing nsCSSDeclaration's
// *temporary* data during parsing and modification. (They are too big
// for permanent storage.) We also use them for nsRuleData, with some
// additions of things that the style system must cascade, but that
// aren't CSS properties. Thus we use typedefs and inheritance
// (forwards, when the rule data needs extra data) to make the rule data
// structs from the declaration structs.
// NOTE: For compilation speed, this typedef also appears in nsRuleNode.h
typedef nsCSSStruct nsRuleDataStruct;
struct nsCSSFont : public nsCSSStruct {
nsCSSFont(void);
nsCSSFont(const nsCSSFont& aCopy);
~nsCSSFont(void);
nsCSSValue mFamily;
nsCSSValue mStyle;
nsCSSValue mVariant;
nsCSSValue mWeight;
nsCSSValue mSize;
nsCSSValue mSizeAdjust; // NEW
nsCSSValue mStretch; // NEW
};
struct nsRuleDataFont : public nsCSSFont {
PRBool mFamilyFromHTML; // Is the family from an HTML FONT element
};
struct nsCSSColor : public nsCSSStruct {
nsCSSColor(void);
nsCSSColor(const nsCSSColor& aCopy);
~nsCSSColor(void);
nsCSSValue mColor;
nsCSSValue mBackColor;
nsCSSValue mBackImage;
nsCSSValue mBackRepeat;
nsCSSValue mBackAttachment;
nsCSSValuePair mBackPosition;
nsCSSValue mBackClip;
nsCSSValue mBackOrigin;
nsCSSValue mBackInlinePolicy;
};
struct nsRuleDataColor : public nsCSSColor {
};
struct nsCSSText : public nsCSSStruct {
nsCSSText(void);
nsCSSText(const nsCSSText& aCopy);
~nsCSSText(void);
nsCSSValue mWordSpacing;
nsCSSValue mLetterSpacing;
nsCSSValue mVerticalAlign;
nsCSSValue mTextTransform;
nsCSSValue mTextAlign;
nsCSSValue mTextIndent;
nsCSSValue mDecoration;
nsCSSValueList* mTextShadow; // NEW
nsCSSValue mUnicodeBidi; // NEW
nsCSSValue mLineHeight;
nsCSSValue mWhiteSpace;
};
struct nsRuleDataText : public nsCSSText {
};
struct nsCSSDisplay : public nsCSSStruct {
nsCSSDisplay(void);
nsCSSDisplay(const nsCSSDisplay& aCopy);
@ -373,32 +400,6 @@ struct nsCSSPage : public nsCSSStruct { // NEW
struct nsRuleDataPage : public nsCSSPage {
};
// Should be replaced with nsCSSValueList and nsCSSValue::Array.
struct nsCSSCounterData {
nsCSSCounterData(void);
nsCSSCounterData(const nsCSSCounterData& aCopy);
~nsCSSCounterData(void);
static PRBool Equal(nsCSSCounterData* aList1, nsCSSCounterData* aList2);
nsCSSValue mCounter;
nsCSSValue mValue;
nsCSSCounterData* mNext;
};
// Should be replaced with nsCSSValueList and nsCSSValue::Array.
struct nsCSSQuotes {
nsCSSQuotes(void);
nsCSSQuotes(const nsCSSQuotes& aCopy);
~nsCSSQuotes(void);
static PRBool Equal(nsCSSQuotes* aList1, nsCSSQuotes* aList2);
nsCSSValue mOpen;
nsCSSValue mClose;
nsCSSQuotes* mNext;
};
struct nsCSSContent : public nsCSSStruct {
nsCSSContent(void);
nsCSSContent(const nsCSSContent& aCopy);

Просмотреть файл

@ -3089,46 +3089,46 @@ nsRuleNode::ComputeBackgroundData(nsStyleStruct* aStartStruct,
}
// background-position: enum, length, percent (flags), inherit
if (eCSSUnit_Percent == colorData.mBackPositionX.GetUnit()) {
bg->mBackgroundXPosition.mFloat = colorData.mBackPositionX.GetPercentValue();
if (eCSSUnit_Percent == colorData.mBackPosition.mXValue.GetUnit()) {
bg->mBackgroundXPosition.mFloat = colorData.mBackPosition.mXValue.GetPercentValue();
bg->mBackgroundFlags |= NS_STYLE_BG_X_POSITION_PERCENT;
bg->mBackgroundFlags &= ~NS_STYLE_BG_X_POSITION_LENGTH;
}
else if (colorData.mBackPositionX.IsLengthUnit()) {
bg->mBackgroundXPosition.mCoord = CalcLength(colorData.mBackPositionX, nsnull,
else if (colorData.mBackPosition.mXValue.IsLengthUnit()) {
bg->mBackgroundXPosition.mCoord = CalcLength(colorData.mBackPosition.mXValue, nsnull,
aContext, mPresContext, inherited);
bg->mBackgroundFlags |= NS_STYLE_BG_X_POSITION_LENGTH;
bg->mBackgroundFlags &= ~NS_STYLE_BG_X_POSITION_PERCENT;
}
else if (eCSSUnit_Enumerated == colorData.mBackPositionX.GetUnit()) {
bg->mBackgroundXPosition.mFloat = (float)colorData.mBackPositionX.GetIntValue() / 100.0f;
else if (eCSSUnit_Enumerated == colorData.mBackPosition.mXValue.GetUnit()) {
bg->mBackgroundXPosition.mFloat = (float)colorData.mBackPosition.mXValue.GetIntValue() / 100.0f;
bg->mBackgroundFlags |= NS_STYLE_BG_X_POSITION_PERCENT;
bg->mBackgroundFlags &= ~NS_STYLE_BG_X_POSITION_LENGTH;
}
else if (eCSSUnit_Inherit == colorData.mBackPositionX.GetUnit()) {
else if (eCSSUnit_Inherit == colorData.mBackPosition.mXValue.GetUnit()) {
inherited = PR_TRUE;
bg->mBackgroundXPosition = parentBG->mBackgroundXPosition;
bg->mBackgroundFlags &= ~(NS_STYLE_BG_X_POSITION_LENGTH | NS_STYLE_BG_X_POSITION_PERCENT);
bg->mBackgroundFlags |= (parentFlags & (NS_STYLE_BG_X_POSITION_LENGTH | NS_STYLE_BG_X_POSITION_PERCENT));
}
if (eCSSUnit_Percent == colorData.mBackPositionY.GetUnit()) {
bg->mBackgroundYPosition.mFloat = colorData.mBackPositionY.GetPercentValue();
if (eCSSUnit_Percent == colorData.mBackPosition.mYValue.GetUnit()) {
bg->mBackgroundYPosition.mFloat = colorData.mBackPosition.mYValue.GetPercentValue();
bg->mBackgroundFlags |= NS_STYLE_BG_Y_POSITION_PERCENT;
bg->mBackgroundFlags &= ~NS_STYLE_BG_Y_POSITION_LENGTH;
}
else if (colorData.mBackPositionY.IsLengthUnit()) {
bg->mBackgroundYPosition.mCoord = CalcLength(colorData.mBackPositionY, nsnull,
else if (colorData.mBackPosition.mYValue.IsLengthUnit()) {
bg->mBackgroundYPosition.mCoord = CalcLength(colorData.mBackPosition.mYValue, nsnull,
aContext, mPresContext, inherited);
bg->mBackgroundFlags |= NS_STYLE_BG_Y_POSITION_LENGTH;
bg->mBackgroundFlags &= ~NS_STYLE_BG_Y_POSITION_PERCENT;
}
else if (eCSSUnit_Enumerated == colorData.mBackPositionY.GetUnit()) {
bg->mBackgroundYPosition.mFloat = (float)colorData.mBackPositionY.GetIntValue() / 100.0f;
else if (eCSSUnit_Enumerated == colorData.mBackPosition.mYValue.GetUnit()) {
bg->mBackgroundYPosition.mFloat = (float)colorData.mBackPosition.mYValue.GetIntValue() / 100.0f;
bg->mBackgroundFlags |= NS_STYLE_BG_Y_POSITION_PERCENT;
bg->mBackgroundFlags &= ~NS_STYLE_BG_Y_POSITION_LENGTH;
}
else if (eCSSUnit_Inherit == colorData.mBackPositionY.GetUnit()) {
else if (eCSSUnit_Inherit == colorData.mBackPosition.mYValue.GetUnit()) {
inherited = PR_TRUE;
bg->mBackgroundYPosition = parentBG->mBackgroundYPosition;
bg->mBackgroundFlags &= ~(NS_STYLE_BG_Y_POSITION_LENGTH | NS_STYLE_BG_Y_POSITION_PERCENT);

Просмотреть файл

@ -112,8 +112,6 @@ const char* gShorthandPropertiesWithDOMProp[] = {
const char *gInaccessibleProperties[] = {
// Don't print the properties that aren't accepted by the parser, per
// CSSParserImpl::ParseProperty
"-x-background-x-position",
"-x-background-y-position",
"margin-end-value",
"margin-left-value",
"margin-right-value",

Просмотреть файл

@ -1,5 +1,4 @@
var gShorthandPropertiesLikeLonghand = [
{ name: "background-position", prop: "backgroundPosition"},
{ name: "-moz-margin-end", prop: "MozMarginEnd"},
{ name: "margin-left", prop: "marginLeft"},
{ name: "margin-right", prop: "marginRight"},

Просмотреть файл

@ -25,11 +25,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=375363
var gDeclaration = document.getElementById("testnode").style;
/* all failures covered by bug 375363 */
var gKnownFails = {
"background-position": true
};
function test_property(property)
{
var pass = true;
@ -54,9 +49,9 @@ function test_property(property)
if (property.prop)
match = match && gDeclaration[property.prop] == val;
(property.name in gKnownFails ? todo : ok)(pass && match, "inherit parsed, stored, and serialized for CSS '" + property.name + "'");
ok(pass && match, "inherit parsed, stored, and serialized for CSS '" + property.name + "'");
if (!match) {
/* already included in above todo/ok, but exceptional in itself */
/* already included in above ok, but exceptional in itself */
ok(match, "getPropertyValue matches nsICSSProperties for CSS '" + property.name + "'");
}
}

Просмотреть файл

@ -25,11 +25,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=375363
var gDeclaration = document.getElementById("testnode").style;
/* all failures covered by bug 375363 */
var gKnownFails = {
"background-position": true
};
function test_property(property)
{
var pass = true;
@ -54,9 +49,9 @@ function test_property(property)
if (property.prop)
match = match && gDeclaration[property.prop] == val;
(property.name in gKnownFails ? todo : ok)(pass && match, "-moz-initial parsed, stored, and serialized for CSS '" + property.name + "'");
ok(pass && match, "-moz-initial parsed, stored, and serialized for CSS '" + property.name + "'");
if (!match) {
/* already included in above todo/ok, but exceptional in itself */
/* already included in above ok, but exceptional in itself */
ok(match, "getPropertyValue matches nsICSSProperties for CSS '" + property.name + "'");
}
}