Changeset 107516 in webkit
- Timestamp:
- Feb 12, 2012, 4:43:27 PM (13 years ago)
- Location:
- trunk
- Files:
-
- 2 added
- 2 deleted
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/LayoutTests/ChangeLog
r107511 r107516 1 2012-02-12 Kenichi Ishibashi <bashi@chromium.org> 2 3 If @font-face does not provide an explicit italic/bold variant, regular is used. 4 https://bugs.webkit.org/show_bug.cgi?id=34147 5 6 Reviewed by Dan Bernstein. 7 8 Added two tests to make sure font matching algorithm matches the current draft of CSS Fonts Module Level 3, and removed a test which uses obsoleted 'all' value for font-weight and font-style. 9 10 * fast/css/font-face-descriptor-multiple-values-parsing-expected.txt: Removed. 11 * fast/css/font-face-descriptor-multiple-values-parsing.html: Removed. 12 * fast/css/font-face-synthetic-bold-italic.html: Added. 13 * fast/css/font-face-weight-matching.html: Added. 14 * platform/chromium/test_expectations.txt: Needs rebaselines. 15 1 16 2012-02-12 Csaba Osztrogonác <ossy@webkit.org> 2 17 -
trunk/LayoutTests/platform/chromium/test_expectations.txt
r107469 r107516 3979 3979 BUGWK78367 : media/video-zoom-controls.html = IMAGE 3980 3980 BUGWK78367 : media/video-zoom.html = IMAGE 3981 3982 BUGWK34147 : fast/css/font-face-synthetic-bold-italic.html = MISSING FAIL 3983 BUGWK34147 : fast/css/font-face-weight-matching.html = MISSING FAIL -
trunk/Source/WebCore/ChangeLog
r107515 r107516 1 2012-02-12 Kenichi Ishibashi <bashi@chromium.org> 2 3 If @font-face does not provide an explicit italic/bold variant, regular is used. 4 https://bugs.webkit.org/show_bug.cgi?id=34147 5 6 Reviewed by Dan Bernstein. 7 8 Update @font-face handling code so that it matches @font-face behavior to the current draft of CSS3 Font spec. The original patch was written by yusukes@chromium.org. 9 - Drops support for "bolder", "lighter", and "all" value. These are no longer allowed. 10 - Only allows one value for font-style and font-weight. 11 12 Tests: fast/css/font-face-synthetic-bold-italic.html 13 fast/css/font-face-weight-matching.html 14 15 * css/CSSFontSelector.cpp: 16 (WebCore::CSSFontSelector::addFontFaceRule): Removed "all", "lighter", "bolder" handling code. 17 (WebCore::compareFontFaces):Updated the weight matching algortihm. 18 * css/CSSParser.cpp: 19 (WebCore::CSSParser::parseValue): Replaced parseFontStyle() call with checking primitive values. 20 (WebCore::CSSParser::parseFontWeight): Changed to allow only primitive values. 21 (WebCore::CSSParser::createFontFaceRule): Removed checks for font-weight and font-style. 22 (WebCore::CSSParser::deleteFontFaceOnlyValues): Ditto. 23 * css/CSSParser.h: Removed parseFontStyle(). 24 1 25 2012-02-12 David Reveman <reveman@chromium.org> 2 26 -
trunk/Source/WebCore/css/CSSFontSelector.cpp
r106695 r107516 107 107 108 108 if (RefPtr<CSSValue> fontStyle = style->getPropertyCSSValue(CSSPropertyFontStyle)) { 109 if (fontStyle->isPrimitiveValue()) { 110 RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated(); 111 list->append(fontStyle); 112 fontStyle = list; 113 } else if (!fontStyle->isValueList()) 109 if (!fontStyle->isPrimitiveValue()) 114 110 return; 115 111 116 CSSValueList* styleList = static_cast<CSSValueList*>(fontStyle.get()); 117 unsigned numStyles = styleList->length(); 118 if (!numStyles) 112 switch (static_cast<CSSPrimitiveValue*>(fontStyle.get())->getIdent()) { 113 case CSSValueNormal: 114 traitsMask |= FontStyleNormalMask; 115 break; 116 case CSSValueItalic: 117 case CSSValueOblique: 118 traitsMask |= FontStyleItalicMask; 119 break; 120 default: 121 break; 122 } 123 } else 124 traitsMask |= FontStyleNormalMask; 125 126 if (RefPtr<CSSValue> fontWeight = style->getPropertyCSSValue(CSSPropertyFontWeight)) { 127 if (!fontWeight->isPrimitiveValue()) 119 128 return; 120 129 121 for (unsigned i = 0; i < numStyles; ++i) { 122 switch (static_cast<CSSPrimitiveValue*>(styleList->itemWithoutBoundsCheck(i))->getIdent()) { 123 case CSSValueAll: 124 traitsMask |= FontStyleMask; 125 break; 126 case CSSValueNormal: 127 traitsMask |= FontStyleNormalMask; 128 break; 129 case CSSValueItalic: 130 case CSSValueOblique: 131 traitsMask |= FontStyleItalicMask; 132 break; 133 default: 134 break; 135 } 130 switch (static_cast<CSSPrimitiveValue*>(fontWeight.get())->getIdent()) { 131 case CSSValueBold: 132 case CSSValue700: 133 traitsMask |= FontWeight700Mask; 134 break; 135 case CSSValueNormal: 136 case CSSValue400: 137 traitsMask |= FontWeight400Mask; 138 break; 139 case CSSValue900: 140 traitsMask |= FontWeight900Mask; 141 break; 142 case CSSValue800: 143 traitsMask |= FontWeight800Mask; 144 break; 145 case CSSValue600: 146 traitsMask |= FontWeight600Mask; 147 break; 148 case CSSValue500: 149 traitsMask |= FontWeight500Mask; 150 break; 151 case CSSValue300: 152 traitsMask |= FontWeight300Mask; 153 break; 154 case CSSValue200: 155 traitsMask |= FontWeight200Mask; 156 break; 157 case CSSValue100: 158 traitsMask |= FontWeight100Mask; 159 break; 160 default: 161 break; 136 162 } 137 163 } else 138 traitsMask |= FontStyleMask; 139 140 if (RefPtr<CSSValue> fontWeight = style->getPropertyCSSValue(CSSPropertyFontWeight)) { 141 if (fontWeight->isPrimitiveValue()) { 142 RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated(); 143 list->append(fontWeight); 144 fontWeight = list; 145 } else if (!fontWeight->isValueList()) 146 return; 147 148 CSSValueList* weightList = static_cast<CSSValueList*>(fontWeight.get()); 149 unsigned numWeights = weightList->length(); 150 if (!numWeights) 151 return; 152 153 for (unsigned i = 0; i < numWeights; ++i) { 154 switch (static_cast<CSSPrimitiveValue*>(weightList->itemWithoutBoundsCheck(i))->getIdent()) { 155 case CSSValueAll: 156 traitsMask |= FontWeightMask; 157 break; 158 case CSSValueBolder: 159 case CSSValueBold: 160 case CSSValue700: 161 traitsMask |= FontWeight700Mask; 162 break; 163 case CSSValueNormal: 164 case CSSValue400: 165 traitsMask |= FontWeight400Mask; 166 break; 167 case CSSValue900: 168 traitsMask |= FontWeight900Mask; 169 break; 170 case CSSValue800: 171 traitsMask |= FontWeight800Mask; 172 break; 173 case CSSValue600: 174 traitsMask |= FontWeight600Mask; 175 break; 176 case CSSValue500: 177 traitsMask |= FontWeight500Mask; 178 break; 179 case CSSValue300: 180 traitsMask |= FontWeight300Mask; 181 break; 182 case CSSValueLighter: 183 case CSSValue200: 184 traitsMask |= FontWeight200Mask; 185 break; 186 case CSSValue100: 187 traitsMask |= FontWeight100Mask; 188 break; 189 default: 190 break; 191 } 192 } 193 } else 194 traitsMask |= FontWeightMask; 164 traitsMask |= FontWeight400Mask; 195 165 196 166 if (RefPtr<CSSValue> fontVariant = style->getPropertyCSSValue(CSSPropertyFontVariant)) { 167 // font-variant descriptor can be a value list. 197 168 if (fontVariant->isPrimitiveValue()) { 198 169 RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated(); … … 209 180 for (unsigned i = 0; i < numVariants; ++i) { 210 181 switch (static_cast<CSSPrimitiveValue*>(variantList->itemWithoutBoundsCheck(i))->getIdent()) { 211 case CSSValueAll:212 traitsMask |= FontVariantMask;213 break;214 182 case CSSValueNormal: 215 183 traitsMask |= FontVariantNormalMask; … … 428 396 return firstHasDesiredVariant; 429 397 398 // We need to check font-variant css property for CSS2.1 compatibility. 430 399 if ((desiredTraitsMaskForComparison & FontVariantSmallCapsMask) && !first->isLocalFallback() && !second->isLocalFallback()) { 431 400 // Prefer a font that has indicated that it can only support small-caps to a font that claims to support … … 457 426 return true; 458 427 459 // http://www.w3.org/TR/2002/WD-css3-webfonts-20020802/#q46 says: "If there are fewer then 9 weights in the family, the default algorithm 460 // for filling the "holes" is as follows. If '500' is unassigned, it will be assigned the same font as '400'. If any of the values '600', 461 // '700', '800', or '900' remains unassigned, they are assigned to the same face as the next darker assigned keyword, if any, or the next 462 // lighter one otherwise. If any of '300', '200', or '100' remains unassigned, it is assigned to the next lighter assigned keyword, if any, 463 // or the next darker otherwise." 464 // For '400', we made up our own rule (which then '500' follows). 428 // http://www.w3.org/TR/2011/WD-css3-fonts-20111004/#font-matching-algorithm says : 429 // - If the desired weight is less than 400, weights below the desired weight are checked in descending order followed by weights above the desired weight in ascending order until a match is found. 430 // - If the desired weight is greater than 500, weights above the desired weight are checked in ascending order followed by weights below the desired weight in descending order until a match is found. 431 // - If the desired weight is 400, 500 is checked first and then the rule for desired weights less than 400 is used. 432 // - If the desired weight is 500, 400 is checked first and then the rule for desired weights less than 400 is used. 465 433 466 434 static const unsigned fallbackRuleSets = 9; … … 470 438 { FontWeight100Mask, FontWeight300Mask, FontWeight400Mask, FontWeight500Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask }, 471 439 { FontWeight200Mask, FontWeight100Mask, FontWeight400Mask, FontWeight500Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask }, 472 { FontWeight500Mask, FontWeight300Mask, FontWeight 600Mask, FontWeight200Mask, FontWeight700Mask, FontWeight100Mask, FontWeight800Mask, FontWeight900Mask },473 { FontWeight400Mask, FontWeight300Mask, FontWeight 600Mask, FontWeight200Mask, FontWeight700Mask, FontWeight100Mask, FontWeight800Mask, FontWeight900Mask },440 { FontWeight500Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask }, 441 { FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask }, 474 442 { FontWeight700Mask, FontWeight800Mask, FontWeight900Mask, FontWeight500Mask, FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask }, 475 443 { FontWeight800Mask, FontWeight900Mask, FontWeight600Mask, FontWeight500Mask, FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask }, -
trunk/Source/WebCore/css/CSSParser.cpp
r107369 r107516 1412 1412 1413 1413 case CSSPropertyFontStyle: // normal | italic | oblique | inherit 1414 return parseFontStyle(important); 1414 if (id == CSSValueNormal || id == CSSValueItalic || id == CSSValueOblique) 1415 validPrimitive = true; 1416 break; 1415 1417 1416 1418 case CSSPropertyFontVariant: // normal | small-caps | inherit … … 4339 4341 } 4340 4342 4341 bool CSSParser::parseFontStyle(bool important)4342 {4343 RefPtr<CSSValueList> values;4344 if (m_valueList->size() > 1)4345 values = CSSValueList::createCommaSeparated();4346 CSSParserValue* val;4347 bool expectComma = false;4348 while ((val = m_valueList->current())) {4349 RefPtr<CSSPrimitiveValue> parsedValue;4350 if (!expectComma) {4351 expectComma = true;4352 if (val->id == CSSValueNormal || val->id == CSSValueItalic || val->id == CSSValueOblique)4353 parsedValue = cssValuePool()->createIdentifierValue(val->id);4354 else if (val->id == CSSValueAll && !values) {4355 // 'all' is only allowed in @font-face and with no other values. Make a value list to4356 // indicate that we are in the @font-face case.4357 values = CSSValueList::createCommaSeparated();4358 parsedValue = cssValuePool()->createIdentifierValue(val->id);4359 }4360 } else if (val->unit == CSSParserValue::Operator && val->iValue == ',') {4361 expectComma = false;4362 m_valueList->next();4363 continue;4364 }4365 4366 if (!parsedValue)4367 return false;4368 4369 m_valueList->next();4370 4371 if (values)4372 values->append(parsedValue.release());4373 else {4374 addProperty(CSSPropertyFontStyle, parsedValue.release(), important);4375 return true;4376 }4377 }4378 4379 if (values && values->length()) {4380 m_hasFontFaceOnlyValues = true;4381 addProperty(CSSPropertyFontStyle, values.release(), important);4382 return true;4383 }4384 4385 return false;4386 }4387 4388 4343 bool CSSParser::parseFontVariant(bool important) 4389 4344 { … … 4435 4390 bool CSSParser::parseFontWeight(bool important) 4436 4391 { 4437 RefPtr<CSSValueList> values; 4438 if (m_valueList->size() > 1) 4439 values = CSSValueList::createCommaSeparated(); 4440 CSSParserValue* val; 4441 bool expectComma = false; 4442 while ((val = m_valueList->current())) { 4443 RefPtr<CSSPrimitiveValue> parsedValue; 4444 if (!expectComma) { 4445 expectComma = true; 4446 if (val->unit == CSSPrimitiveValue::CSS_IDENT) { 4447 if (val->id >= CSSValueNormal && val->id <= CSSValue900) 4448 parsedValue = cssValuePool()->createIdentifierValue(val->id); 4449 else if (val->id == CSSValueAll && !values) { 4450 // 'all' is only allowed in @font-face and with no other values. Make a value list to 4451 // indicate that we are in the @font-face case. 4452 values = CSSValueList::createCommaSeparated(); 4453 parsedValue = cssValuePool()->createIdentifierValue(val->id); 4454 } 4455 } else if (validUnit(val, FInteger | FNonNeg, false)) { 4456 int weight = static_cast<int>(val->fValue); 4457 if (!(weight % 100) && weight >= 100 && weight <= 900) 4458 parsedValue = cssValuePool()->createIdentifierValue(CSSValue100 + weight / 100 - 1); 4459 } 4460 } else if (val->unit == CSSParserValue::Operator && val->iValue == ',') { 4461 expectComma = false; 4462 m_valueList->next(); 4463 continue; 4464 } 4465 4466 if (!parsedValue) 4467 return false; 4468 4469 m_valueList->next(); 4470 4471 if (values) 4472 values->append(parsedValue.release()); 4473 else { 4474 addProperty(CSSPropertyFontWeight, parsedValue.release(), important); 4475 return true; 4476 } 4477 } 4478 4479 if (values && values->length()) { 4480 m_hasFontFaceOnlyValues = true; 4481 addProperty(CSSPropertyFontWeight, values.release(), important); 4392 if (m_valueList->size() != 1) 4393 return false; 4394 4395 CSSParserValue* value = m_valueList->current(); 4396 if ((value->id >= CSSValueNormal) && (value->id <= CSSValue900)) { 4397 addProperty(CSSPropertyFontWeight, cssValuePool()->createIdentifierValue(value->id), important); 4482 4398 return true; 4483 4399 } 4484 4400 if (validUnit(value, FInteger | FNonNeg, false)) { 4401 int weight = static_cast<int>(value->fValue); 4402 if (!(weight % 100) && weight >= 100 && weight <= 900) 4403 addProperty(CSSPropertyFontWeight, cssValuePool()->createIdentifierValue(CSSValue100 + weight / 100 - 1), important); 4404 return true; 4405 } 4485 4406 return false; 4486 4407 } … … 8857 8778 CSSProperty* property = m_parsedProperties[i]; 8858 8779 int id = property->id(); 8859 if ( (id == CSSPropertyFontWeight || id == CSSPropertyFontStyle || id == CSSPropertyFontVariant)&& property->value()->isPrimitiveValue()) {8780 if (id == CSSPropertyFontVariant && property->value()->isPrimitiveValue()) { 8860 8781 RefPtr<CSSValue> value = property->m_value.release(); 8861 8782 property->m_value = CSSValueList::createCommaSeparated(); … … 9002 8923 CSSProperty* property = m_parsedProperties[i]; 9003 8924 int id = property->id(); 9004 if ( (id == CSSPropertyFontWeight || id == CSSPropertyFontStyle || id == CSSPropertyFontVariant)&& property->value()->isValueList()) {8925 if (id == CSSPropertyFontVariant && property->value()->isValueList()) { 9005 8926 delete property; 9006 8927 deletedProperties++; -
trunk/Source/WebCore/css/CSSParser.h
r106756 r107516 157 157 static bool fastParseColor(RGBA32&, const String&, bool strict); 158 158 159 bool parseFontStyle(bool important);160 159 bool parseFontVariant(bool important); 161 160 bool parseFontWeight(bool important);
Note:
See TracChangeset
for help on using the changeset viewer.