OLD | NEW |
---|---|
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "config.h" | 5 #include "config.h" |
6 #include "core/css/parser/CSSPropertyParser.h" | 6 #include "core/css/parser/CSSPropertyParser.h" |
7 | 7 |
8 #include "core/StylePropertyShorthand.h" | 8 #include "core/StylePropertyShorthand.h" |
9 #include "core/css/CSSCalculationValue.h" | 9 #include "core/css/CSSCalculationValue.h" |
10 #include "core/css/CSSCustomIdentValue.h" | 10 #include "core/css/CSSCustomIdentValue.h" |
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
163 CSSPrimitiveValue::UnitType unitType = m_calcValue->isInt() ? CSSPrimiti veValue::UnitType::Integer : CSSPrimitiveValue::UnitType::Number; | 163 CSSPrimitiveValue::UnitType unitType = m_calcValue->isInt() ? CSSPrimiti veValue::UnitType::Integer : CSSPrimitiveValue::UnitType::Number; |
164 return cssValuePool().createValue(m_calcValue->doubleValue(), unitType); | 164 return cssValuePool().createValue(m_calcValue->doubleValue(), unitType); |
165 } | 165 } |
166 | 166 |
167 private: | 167 private: |
168 CSSParserTokenRange& m_sourceRange; | 168 CSSParserTokenRange& m_sourceRange; |
169 CSSParserTokenRange m_range; | 169 CSSParserTokenRange m_range; |
170 RefPtrWillBeMember<CSSCalcValue> m_calcValue; | 170 RefPtrWillBeMember<CSSCalcValue> m_calcValue; |
171 }; | 171 }; |
172 | 172 |
173 static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> consumeInteger(CSSParserTokenRa nge& range, CSSParserMode cssParserMode, double minimumValue = -std::numeric_lim its<double>::max()) | 173 static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> consumeInteger(CSSParserTokenRa nge& range, double minimumValue = -std::numeric_limits<double>::max()) |
174 { | 174 { |
175 const CSSParserToken& token = range.peek(); | 175 const CSSParserToken& token = range.peek(); |
176 if (token.type() == NumberToken) { | 176 if (token.type() == NumberToken) { |
177 if (token.numericValueType() == NumberValueType || token.numericValue() < minimumValue) | 177 if (token.numericValueType() == NumberValueType || token.numericValue() < minimumValue) |
178 return nullptr; | 178 return nullptr; |
179 return cssValuePool().createValue(range.consumeIncludingWhitespace().num ericValue(), token.unitType()); | 179 return cssValuePool().createValue(range.consumeIncludingWhitespace().num ericValue(), token.unitType()); |
180 } | 180 } |
181 CalcParser calcParser(range); | 181 CalcParser calcParser(range); |
182 if (const CSSCalcValue* calculation = calcParser.value()) { | 182 if (const CSSCalcValue* calculation = calcParser.value()) { |
183 if (calculation->category() != CalcNumber || !calculation->isInt()) | 183 if (calculation->category() != CalcNumber || !calculation->isInt()) |
184 return nullptr; | 184 return nullptr; |
185 double value = calculation->doubleValue(); | 185 double value = calculation->doubleValue(); |
186 if (value < minimumValue) | 186 if (value < minimumValue) |
187 return nullptr; | 187 return nullptr; |
188 return calcParser.consumeNumber(); | 188 return calcParser.consumeNumber(); |
189 } | 189 } |
190 return nullptr; | 190 return nullptr; |
191 } | 191 } |
192 | 192 |
193 static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> consumePositiveInteger(CSSParse rTokenRange& range) | |
194 { | |
195 return consumeInteger(range, 1); | |
196 } | |
197 | |
193 static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> consumeNumber(CSSParserTokenRan ge& range, ValueRange valueRange) | 198 static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> consumeNumber(CSSParserTokenRan ge& range, ValueRange valueRange) |
194 { | 199 { |
195 const CSSParserToken& token = range.peek(); | 200 const CSSParserToken& token = range.peek(); |
196 if (token.type() == NumberToken) { | 201 if (token.type() == NumberToken) { |
197 if (valueRange == ValueRangeNonNegative && token.numericValue() < 0) | 202 if (valueRange == ValueRangeNonNegative && token.numericValue() < 0) |
198 return nullptr; | 203 return nullptr; |
199 return cssValuePool().createValue(range.consumeIncludingWhitespace().num ericValue(), token.unitType()); | 204 return cssValuePool().createValue(range.consumeIncludingWhitespace().num ericValue(), token.unitType()); |
200 } | 205 } |
201 CalcParser calcParser(range, ValueRangeAll); | 206 CalcParser calcParser(range, ValueRangeAll); |
202 if (const CSSCalcValue* calculation = calcParser.value()) { | 207 if (const CSSCalcValue* calculation = calcParser.value()) { |
(...skipping 386 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
589 static PassRefPtrWillBeRawPtr<CSSValue> consumeSpacing(CSSParserTokenRange& rang e, CSSParserMode cssParserMode) | 594 static PassRefPtrWillBeRawPtr<CSSValue> consumeSpacing(CSSParserTokenRange& rang e, CSSParserMode cssParserMode) |
590 { | 595 { |
591 if (range.peek().id() == CSSValueNormal) | 596 if (range.peek().id() == CSSValueNormal) |
592 return consumeIdent(range); | 597 return consumeIdent(range); |
593 // TODO(timloh): Don't allow unitless values, and allow <percentage>s in wor d-spacing. | 598 // TODO(timloh): Don't allow unitless values, and allow <percentage>s in wor d-spacing. |
594 return consumeLength(range, cssParserMode, ValueRangeAll, UnitlessQuirk::All ow); | 599 return consumeLength(range, cssParserMode, ValueRangeAll, UnitlessQuirk::All ow); |
595 } | 600 } |
596 | 601 |
597 static PassRefPtrWillBeRawPtr<CSSValue> consumeTabSize(CSSParserTokenRange& rang e, CSSParserMode cssParserMode) | 602 static PassRefPtrWillBeRawPtr<CSSValue> consumeTabSize(CSSParserTokenRange& rang e, CSSParserMode cssParserMode) |
598 { | 603 { |
599 RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue = consumeInteger(range, cs sParserMode, 0); | 604 RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue = consumeInteger(range, 0) ; |
600 if (parsedValue) | 605 if (parsedValue) |
601 return parsedValue; | 606 return parsedValue; |
602 return consumeLength(range, cssParserMode, ValueRangeNonNegative); | 607 return consumeLength(range, cssParserMode, ValueRangeNonNegative); |
603 } | 608 } |
604 | 609 |
605 static PassRefPtrWillBeRawPtr<CSSValue> consumeFontSize(CSSParserTokenRange& ran ge, CSSParserMode cssParserMode, UnitlessQuirk unitless = UnitlessQuirk::Forbid) | 610 static PassRefPtrWillBeRawPtr<CSSValue> consumeFontSize(CSSParserTokenRange& ran ge, CSSParserMode cssParserMode, UnitlessQuirk unitless = UnitlessQuirk::Forbid) |
606 { | 611 { |
607 if (range.peek().id() >= CSSValueXxSmall && range.peek().id() <= CSSValueLar ger) | 612 if (range.peek().id() >= CSSValueXxSmall && range.peek().id() <= CSSValueLar ger) |
608 return consumeIdent(range); | 613 return consumeIdent(range); |
609 return consumeLengthOrPercent(range, cssParserMode, ValueRangeNonNegative, u nitless); | 614 return consumeLengthOrPercent(range, cssParserMode, ValueRangeNonNegative, u nitless); |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
648 if (range.peek().id() == CSSValueNone) | 653 if (range.peek().id() == CSSValueNone) |
649 return consumeIdent(range); | 654 return consumeIdent(range); |
650 | 655 |
651 // TODO(rwlbuis): should be space separated list. | 656 // TODO(rwlbuis): should be space separated list. |
652 RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated() ; | 657 RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated() ; |
653 do { | 658 do { |
654 RefPtrWillBeRawPtr<CSSCustomIdentValue> counterName = consumeCustomIdent (range); | 659 RefPtrWillBeRawPtr<CSSCustomIdentValue> counterName = consumeCustomIdent (range); |
655 if (!counterName) | 660 if (!counterName) |
656 return nullptr; | 661 return nullptr; |
657 int i = defaultValue; | 662 int i = defaultValue; |
658 if (RefPtrWillBeRawPtr<CSSPrimitiveValue> counterValue = consumeInteger( range, cssParserMode)) | 663 if (RefPtrWillBeRawPtr<CSSPrimitiveValue> counterValue = consumeInteger( range)) |
659 i = clampTo<int>(counterValue->getDoubleValue()); | 664 i = clampTo<int>(counterValue->getDoubleValue()); |
660 list->append(CSSValuePair::create(counterName.release(), | 665 list->append(CSSValuePair::create(counterName.release(), |
661 cssValuePool().createValue(i, CSSPrimitiveValue::UnitType::Number), | 666 cssValuePool().createValue(i, CSSPrimitiveValue::UnitType::Number), |
662 CSSValuePair::DropIdenticalValues)); | 667 CSSValuePair::DropIdenticalValues)); |
663 } while (!range.atEnd()); | 668 } while (!range.atEnd()); |
664 return list.release(); | 669 return list.release(); |
665 } | 670 } |
666 | 671 |
667 static PassRefPtrWillBeRawPtr<CSSValue> consumePageSize(CSSParserTokenRange& ran ge) | 672 static PassRefPtrWillBeRawPtr<CSSValue> consumePageSize(CSSParserTokenRange& ran ge) |
668 { | 673 { |
(...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
868 if (!range.atEnd() && !consumePan(range, panX, panY)) | 873 if (!range.atEnd() && !consumePan(range, panX, panY)) |
869 return nullptr; | 874 return nullptr; |
870 | 875 |
871 if (panX) | 876 if (panX) |
872 list->append(panX.release()); | 877 list->append(panX.release()); |
873 if (panY) | 878 if (panY) |
874 list->append(panY.release()); | 879 list->append(panY.release()); |
875 return list.release(); | 880 return list.release(); |
876 } | 881 } |
877 | 882 |
883 static PassRefPtrWillBeRawPtr<CSSValue> consumeColumnWidth(CSSParserTokenRange& range) | |
884 { | |
885 if (range.peek().id() == CSSValueAuto) | |
886 return consumeIdent(range); | |
887 // Always parse lengths in strict mode here, since it would be ambiguous oth erwise when used in | |
888 // the 'columns' shorthand property. | |
889 RefPtrWillBeRawPtr<CSSPrimitiveValue> columnWidth = consumeLength(range, HTM LStandardMode, ValueRangeNonNegative); | |
890 if (!columnWidth || (!columnWidth->isCalculated() && columnWidth->getDoubleV alue() == 0)) | |
891 return nullptr; | |
892 return columnWidth.release(); | |
893 } | |
894 | |
895 static PassRefPtrWillBeRawPtr<CSSValue> consumeColumnCount(CSSParserTokenRange& range) | |
896 { | |
897 if (range.peek().id() == CSSValueAuto) | |
898 return consumeIdent(range); | |
899 return consumePositiveInteger(range); | |
900 } | |
901 | |
902 static PassRefPtrWillBeRawPtr<CSSValue> consumeColumnGap(CSSParserTokenRange& ra nge, CSSParserMode cssParserMode) | |
903 { | |
904 if (range.peek().id() == CSSValueNormal) | |
905 return consumeIdent(range); | |
906 return consumeLength(range, cssParserMode, ValueRangeNonNegative); | |
907 } | |
908 | |
909 static PassRefPtrWillBeRawPtr<CSSValue> consumeColumnSpan(CSSParserTokenRange& r ange, CSSParserMode cssParserMode) | |
910 { | |
911 CSSValueID id = range.peek().id(); | |
912 if (id == CSSValueAll || id == CSSValueNone) | |
913 return consumeIdent(range); | |
914 if (range.peek().type() != NumberToken) | |
915 return nullptr; | |
916 if (RefPtrWillBeRawPtr<CSSPrimitiveValue> spanValue = consumeInteger(range)) { | |
917 // 1 (will be dropped in the unprefixed property). | |
918 if (spanValue->getIntValue() == 1) | |
919 return spanValue.release(); | |
920 } | |
921 return nullptr; | |
922 } | |
923 | |
878 PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseSingleValue(CSSProperty ID propId) | 924 PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseSingleValue(CSSProperty ID propId) |
879 { | 925 { |
880 m_range.consumeWhitespace(); | 926 m_range.consumeWhitespace(); |
881 switch (propId) { | 927 switch (propId) { |
882 case CSSPropertyWillChange: | 928 case CSSPropertyWillChange: |
883 return consumeWillChange(m_range); | 929 return consumeWillChange(m_range); |
884 case CSSPropertyPage: | 930 case CSSPropertyPage: |
885 return consumePage(m_range); | 931 return consumePage(m_range); |
886 case CSSPropertyQuotes: | 932 case CSSPropertyQuotes: |
887 return consumeQuotes(m_range); | 933 return consumeQuotes(m_range); |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
931 return consumeWidthOrHeight(m_range, m_context, UnitlessQuirk::Allow); | 977 return consumeWidthOrHeight(m_range, m_context, UnitlessQuirk::Allow); |
932 case CSSPropertyWebkitMinLogicalWidth: | 978 case CSSPropertyWebkitMinLogicalWidth: |
933 case CSSPropertyWebkitMinLogicalHeight: | 979 case CSSPropertyWebkitMinLogicalHeight: |
934 case CSSPropertyWebkitLogicalWidth: | 980 case CSSPropertyWebkitLogicalWidth: |
935 case CSSPropertyWebkitLogicalHeight: | 981 case CSSPropertyWebkitLogicalHeight: |
936 return consumeWidthOrHeight(m_range, m_context); | 982 return consumeWidthOrHeight(m_range, m_context); |
937 case CSSPropertyClip: | 983 case CSSPropertyClip: |
938 return consumeClip(m_range, m_context.mode()); | 984 return consumeClip(m_range, m_context.mode()); |
939 case CSSPropertyTouchAction: | 985 case CSSPropertyTouchAction: |
940 return consumeTouchAction(m_range); | 986 return consumeTouchAction(m_range); |
987 case CSSPropertyWebkitColumnWidth: | |
988 return consumeColumnWidth(m_range); | |
989 case CSSPropertyWebkitColumnCount: | |
990 return consumeColumnCount(m_range); | |
991 case CSSPropertyWebkitColumnGap: | |
992 return consumeColumnGap(m_range, m_context.mode()); | |
993 case CSSPropertyWebkitColumnSpan: | |
994 return consumeColumnSpan(m_range, m_context.mode()); | |
941 default: | 995 default: |
942 return nullptr; | 996 return nullptr; |
943 } | 997 } |
944 } | 998 } |
945 | 999 |
946 static PassRefPtrWillBeRawPtr<CSSValueList> consumeFontFaceUnicodeRange(CSSParse rTokenRange& range) | 1000 static PassRefPtrWillBeRawPtr<CSSValueList> consumeFontFaceUnicodeRange(CSSParse rTokenRange& range) |
947 { | 1001 { |
948 RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createCommaSeparated (); | 1002 RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createCommaSeparated (); |
949 | 1003 |
950 do { | 1004 do { |
(...skipping 314 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1265 if (!parsedValue || !m_range.atEnd()) | 1319 if (!parsedValue || !m_range.atEnd()) |
1266 return false; | 1320 return false; |
1267 addProperty(propId, parsedValue.release(), important); | 1321 addProperty(propId, parsedValue.release(), important); |
1268 return true; | 1322 return true; |
1269 } | 1323 } |
1270 default: | 1324 default: |
1271 return false; | 1325 return false; |
1272 } | 1326 } |
1273 } | 1327 } |
1274 | 1328 |
1329 static void consumeColumnWidthOrCount(CSSParserTokenRange& range, CSSParserMode cssParserMode, RefPtrWillBeRawPtr<CSSValue> &columnWidth, RefPtrWillBeRawPtr<CSS Value> &columnCount) | |
1330 { | |
1331 if (range.peek().id() == CSSValueAuto) { | |
1332 consumeIdent(range); | |
1333 return; | |
1334 } | |
1335 if (!columnWidth) { | |
1336 if ((columnWidth = consumeColumnWidth(range))) | |
1337 return; | |
1338 } | |
1339 if (!columnCount) | |
1340 columnCount = consumeColumnCount(range); | |
1341 } | |
1342 | |
1343 bool CSSPropertyParser::consumeColumns(bool important) | |
1344 { | |
1345 RefPtrWillBeRawPtr<CSSValue> columnWidth = nullptr; | |
1346 RefPtrWillBeRawPtr<CSSValue> columnCount = nullptr; | |
1347 consumeColumnWidthOrCount(m_range, m_context.mode(), columnWidth, columnCoun t); | |
1348 consumeColumnWidthOrCount(m_range, m_context.mode(), columnWidth, columnCoun t); | |
1349 if (!m_range.atEnd()) | |
1350 return false; | |
1351 if (!columnWidth) | |
1352 columnWidth = cssValuePool().createIdentifierValue(CSSValueAuto); | |
1353 if (!columnCount) | |
1354 columnCount = cssValuePool().createIdentifierValue(CSSValueAuto); | |
1355 addProperty(CSSPropertyWebkitColumnWidth, columnWidth.release(), important); | |
1356 addProperty(CSSPropertyWebkitColumnCount, columnCount.release(), important); | |
1357 return true; | |
1358 } | |
1359 | |
1275 bool CSSPropertyParser::parseShorthand(CSSPropertyID propId, bool important) | 1360 bool CSSPropertyParser::parseShorthand(CSSPropertyID propId, bool important) |
1276 { | 1361 { |
1277 m_range.consumeWhitespace(); | 1362 m_range.consumeWhitespace(); |
1278 CSSPropertyID oldShorthand = m_currentShorthand; | 1363 CSSPropertyID oldShorthand = m_currentShorthand; |
1279 // TODO(rob.buis): Remove this when the legacy property parser is gone | 1364 // TODO(rob.buis): Remove this when the legacy property parser is gone |
1280 m_currentShorthand = propId; | 1365 m_currentShorthand = propId; |
1281 switch (propId) { | 1366 switch (propId) { |
1282 case CSSPropertyWebkitMarginCollapse: { | 1367 case CSSPropertyWebkitMarginCollapse: { |
1283 CSSValueID id = m_range.consumeIncludingWhitespace().id(); | 1368 CSSValueID id = m_range.consumeIncludingWhitespace().id(); |
1284 if (!CSSParserFastPaths::isValidKeywordPropertyAndValue(CSSPropertyWebki tMarginBeforeCollapse, id)) | 1369 if (!CSSParserFastPaths::isValidKeywordPropertyAndValue(CSSPropertyWebki tMarginBeforeCollapse, id)) |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1318 return true; | 1403 return true; |
1319 } | 1404 } |
1320 case CSSPropertyFont: { | 1405 case CSSPropertyFont: { |
1321 const CSSParserToken& token = m_range.peek(); | 1406 const CSSParserToken& token = m_range.peek(); |
1322 if (token.id() >= CSSValueCaption && token.id() <= CSSValueStatusBar) | 1407 if (token.id() >= CSSValueCaption && token.id() <= CSSValueStatusBar) |
1323 return consumeSystemFont(important); | 1408 return consumeSystemFont(important); |
1324 return consumeFont(important); | 1409 return consumeFont(important); |
1325 } | 1410 } |
1326 case CSSPropertyBorderSpacing: | 1411 case CSSPropertyBorderSpacing: |
1327 return consumeBorderSpacing(important); | 1412 return consumeBorderSpacing(important); |
1413 case CSSPropertyWebkitColumns: { | |
1414 m_currentShorthand = oldShorthand; | |
Timothy Loh
2015/10/19 04:55:59
ok, but TODO to remove this
| |
1415 return consumeColumns(important); | |
1416 } | |
1328 default: | 1417 default: |
1329 m_currentShorthand = oldShorthand; | 1418 m_currentShorthand = oldShorthand; |
1330 return false; | 1419 return false; |
1331 } | 1420 } |
1332 } | 1421 } |
1333 | 1422 |
1334 } // namespace blink | 1423 } // namespace blink |
OLD | NEW |