summaryrefslogtreecommitdiffstats
path: root/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp')
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp314
1 files changed, 298 insertions, 16 deletions
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
index d3ffb158dce..fe94e10930e 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
@@ -27,26 +27,210 @@
#include "config.h"
#include "core/css/resolver/StyleBuilderConverter.h"
+#include "core/css/CSSFunctionValue.h"
+#include "core/css/CSSGridLineNamesValue.h"
#include "core/css/CSSPrimitiveValueMappings.h"
+#include "core/css/CSSReflectValue.h"
#include "core/css/CSSShadowValue.h"
#include "core/css/Pair.h"
#include "core/svg/SVGURIReference.h"
namespace WebCore {
-String StyleBuilderConverter::convertFragmentIdentifier(StyleResolverState& state, CSSValue* value)
+namespace {
+
+static GridLength convertGridTrackBreadth(const StyleResolverState& state, CSSPrimitiveValue* primitiveValue)
+{
+ if (primitiveValue->getValueID() == CSSValueMinContent)
+ return Length(MinContent);
+
+ if (primitiveValue->getValueID() == CSSValueMaxContent)
+ return Length(MaxContent);
+
+ // Fractional unit.
+ if (primitiveValue->isFlex())
+ return GridLength(primitiveValue->getDoubleValue());
+
+ return primitiveValue->convertToLength<FixedConversion | PercentConversion | AutoConversion>(state.cssToLengthConversionData());
+}
+
+} // namespace
+
+PassRefPtr<StyleReflection> StyleBuilderConverter::convertBoxReflect(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue()) {
+ ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNone);
+ return RenderStyle::initialBoxReflect();
+ }
+
+ CSSReflectValue* reflectValue = toCSSReflectValue(value);
+ RefPtr<StyleReflection> reflection = StyleReflection::create();
+ reflection->setDirection(*reflectValue->direction());
+ if (reflectValue->offset())
+ reflection->setOffset(reflectValue->offset()->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData()));
+ NinePieceImage mask;
+ mask.setMaskDefaults();
+ state.styleMap().mapNinePieceImage(state.style(), CSSPropertyWebkitBoxReflect, reflectValue->mask(), mask);
+ reflection->setMask(mask);
+
+ return reflection.release();
+}
+
+AtomicString StyleBuilderConverter::convertFragmentIdentifier(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->isURI())
- return SVGURIReference::fragmentIdentifierFromIRIString(primitiveValue->getStringValue(), state.document());
- return String();
+ return SVGURIReference::fragmentIdentifierFromIRIString(primitiveValue->getStringValue(), state.element()->treeScope());
+ return nullAtom;
+}
+
+EGlyphOrientation StyleBuilderConverter::convertGlyphOrientation(StyleResolverState&, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
+ return GO_0DEG;
+
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->primitiveType() != CSSPrimitiveValue::CSS_DEG)
+ return GO_0DEG;
+
+ float angle = fabsf(fmodf(primitiveValue->getFloatValue(), 360.0f));
+
+ if (angle <= 45.0f || angle > 315.0f)
+ return GO_0DEG;
+ if (angle > 45.0f && angle <= 135.0f)
+ return GO_90DEG;
+ if (angle > 135.0f && angle <= 225.0f)
+ return GO_180DEG;
+ return GO_270DEG;
+}
+
+GridPosition StyleBuilderConverter::convertGridPosition(StyleResolverState&, CSSValue* value)
+{
+ // We accept the specification's grammar:
+ // 'auto' | [ <integer> || <custom-ident> ] | [ span && [ <integer> || <custom-ident> ] ] | <custom-ident>
+
+ GridPosition position;
+
+ if (value->isPrimitiveValue()) {
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ // We translate <custom-ident> to <string> during parsing as it
+ // makes handling it more simple.
+ if (primitiveValue->isString()) {
+ position.setNamedGridArea(primitiveValue->getStringValue());
+ return position;
+ }
+
+ ASSERT(primitiveValue->getValueID() == CSSValueAuto);
+ return position;
+ }
+
+ CSSValueList* values = toCSSValueList(value);
+ ASSERT(values->length());
+
+ bool isSpanPosition = false;
+ // The specification makes the <integer> optional, in which case it default to '1'.
+ int gridLineNumber = 1;
+ String gridLineName;
+
+ CSSValueListIterator it = values;
+ CSSPrimitiveValue* currentValue = toCSSPrimitiveValue(it.value());
+ if (currentValue->getValueID() == CSSValueSpan) {
+ isSpanPosition = true;
+ it.advance();
+ currentValue = it.hasMore() ? toCSSPrimitiveValue(it.value()) : 0;
+ }
+
+ if (currentValue && currentValue->isNumber()) {
+ gridLineNumber = currentValue->getIntValue();
+ it.advance();
+ currentValue = it.hasMore() ? toCSSPrimitiveValue(it.value()) : 0;
+ }
+
+ if (currentValue && currentValue->isString()) {
+ gridLineName = currentValue->getStringValue();
+ it.advance();
+ }
+
+ ASSERT(!it.hasMore());
+ if (isSpanPosition)
+ position.setSpanPosition(gridLineNumber, gridLineName);
+ else
+ position.setExplicitPosition(gridLineNumber, gridLineName);
+
+ return position;
+}
+
+GridTrackSize StyleBuilderConverter::convertGridTrackSize(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue())
+ return GridTrackSize(convertGridTrackBreadth(state, toCSSPrimitiveValue(value)));
+
+ CSSFunctionValue* minmaxFunction = toCSSFunctionValue(value);
+ CSSValueList* arguments = minmaxFunction->arguments();
+ ASSERT_WITH_SECURITY_IMPLICATION(arguments->length() == 2);
+ GridLength minTrackBreadth(convertGridTrackBreadth(state, toCSSPrimitiveValue(arguments->itemWithoutBoundsCheck(0))));
+ GridLength maxTrackBreadth(convertGridTrackBreadth(state, toCSSPrimitiveValue(arguments->itemWithoutBoundsCheck(1))));
+ return GridTrackSize(minTrackBreadth, maxTrackBreadth);
+}
+
+bool StyleBuilderConverter::convertGridTrackList(CSSValue* value, Vector<GridTrackSize>& trackSizes, NamedGridLinesMap& namedGridLines, OrderedNamedGridLines& orderedNamedGridLines, StyleResolverState& state)
+{
+ // Handle 'none'.
+ if (value->isPrimitiveValue()) {
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ return primitiveValue->getValueID() == CSSValueNone;
+ }
+
+ if (!value->isValueList())
+ return false;
+
+ size_t currentNamedGridLine = 0;
+ for (CSSValueListIterator i = value; i.hasMore(); i.advance()) {
+ CSSValue* currValue = i.value();
+ if (currValue->isGridLineNamesValue()) {
+ CSSGridLineNamesValue* lineNamesValue = toCSSGridLineNamesValue(currValue);
+ for (CSSValueListIterator j = lineNamesValue; j.hasMore(); j.advance()) {
+ String namedGridLine = toCSSPrimitiveValue(j.value())->getStringValue();
+ NamedGridLinesMap::AddResult result = namedGridLines.add(namedGridLine, Vector<size_t>());
+ result.storedValue->value.append(currentNamedGridLine);
+ OrderedNamedGridLines::AddResult orderedInsertionResult = orderedNamedGridLines.add(currentNamedGridLine, Vector<String>());
+ orderedInsertionResult.storedValue->value.append(namedGridLine);
+ }
+ continue;
+ }
+
+ ++currentNamedGridLine;
+ trackSizes.append(convertGridTrackSize(state, currValue));
+ }
+
+ // The parser should have rejected any <track-list> without any <track-size> as
+ // this is not conformant to the syntax.
+ ASSERT(!trackSizes.isEmpty());
+ return true;
+}
+
+void StyleBuilderConverter::createImplicitNamedGridLinesFromGridArea(const NamedGridAreaMap& namedGridAreas, NamedGridLinesMap& namedGridLines, GridTrackSizingDirection direction)
+{
+ NamedGridAreaMap::const_iterator end = namedGridAreas.end();
+ for (NamedGridAreaMap::const_iterator it = namedGridAreas.begin(); it != end; ++it) {
+ GridSpan areaSpan = direction == ForRows ? it->value.rows : it->value.columns;
+ {
+ NamedGridLinesMap::AddResult startResult = namedGridLines.add(it->key + "-start", Vector<size_t>());
+ startResult.storedValue->value.append(areaSpan.resolvedInitialPosition.toInt());
+ std::sort(startResult.storedValue->value.begin(), startResult.storedValue->value.end());
+ }
+ {
+ NamedGridLinesMap::AddResult endResult = namedGridLines.add(it->key + "-end", Vector<size_t>());
+ endResult.storedValue->value.append(areaSpan.resolvedFinalPosition.toInt() + 1);
+ std::sort(endResult.storedValue->value.begin(), endResult.storedValue->value.end());
+ }
+ }
}
Length StyleBuilderConverter::convertLength(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
Length result = primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData());
- ASSERT(!result.isUndefined());
result.setQuirk(primitiveValue->isQuirkValue());
return result;
}
@@ -55,7 +239,6 @@ Length StyleBuilderConverter::convertLengthOrAuto(StyleResolverState& state, CSS
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
Length result = primitiveValue->convertToLength<FixedConversion | PercentConversion | AutoConversion>(state.cssToLengthConversionData());
- ASSERT(!result.isUndefined());
result.setQuirk(primitiveValue->isQuirkValue());
return result;
}
@@ -103,6 +286,16 @@ LengthPoint StyleBuilderConverter::convertLengthPoint(StyleResolverState& state,
return LengthPoint(x, y);
}
+LineBoxContain StyleBuilderConverter::convertLineBoxContain(StyleResolverState&, CSSValue* value)
+{
+ if (value->isPrimitiveValue()) {
+ ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNone);
+ return LineBoxContainNone;
+ }
+
+ return toCSSLineBoxContainValue(value)->value();
+}
+
float StyleBuilderConverter::convertNumberOrPercentage(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
@@ -112,6 +305,59 @@ float StyleBuilderConverter::convertNumberOrPercentage(StyleResolverState& state
return primitiveValue->getFloatValue() / 100.0f;
}
+EPaintOrder StyleBuilderConverter::convertPaintOrder(StyleResolverState&, CSSValue* cssPaintOrder)
+{
+ if (cssPaintOrder->isValueList()) {
+ int paintOrder = 0;
+ CSSValueListInspector iter(cssPaintOrder);
+ for (size_t i = 0; i < iter.length(); i++) {
+ CSSPrimitiveValue* value = toCSSPrimitiveValue(iter.item(i));
+
+ EPaintOrderType paintOrderType = PT_NONE;
+ switch (value->getValueID()) {
+ case CSSValueFill:
+ paintOrderType = PT_FILL;
+ break;
+ case CSSValueStroke:
+ paintOrderType = PT_STROKE;
+ break;
+ case CSSValueMarkers:
+ paintOrderType = PT_MARKERS;
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+
+ paintOrder |= (paintOrderType << kPaintOrderBitwidth*i);
+ }
+ return (EPaintOrder)paintOrder;
+ }
+
+ return PO_NORMAL;
+}
+
+PassRefPtr<QuotesData> StyleBuilderConverter::convertQuotes(StyleResolverState&, CSSValue* value)
+{
+ if (value->isValueList()) {
+ CSSValueList* list = toCSSValueList(value);
+ RefPtr<QuotesData> quotes = QuotesData::create();
+ for (size_t i = 0; i < list->length(); i += 2) {
+ CSSValue* first = list->itemWithoutBoundsCheck(i);
+ // item() returns null if out of bounds so this is safe.
+ CSSValue* second = list->item(i + 1);
+ if (!second)
+ continue;
+ String startQuote = toCSSPrimitiveValue(first)->getStringValue();
+ String endQuote = toCSSPrimitiveValue(second)->getStringValue();
+ quotes->addPair(std::make_pair(startQuote, endQuote));
+ }
+ return quotes.release();
+ }
+ // FIXME: We should assert we're a primitive value with valueID = CSSValueNone
+ return QuotesData::create();
+}
+
LengthSize StyleBuilderConverter::convertRadius(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
@@ -138,20 +384,17 @@ PassRefPtr<ShadowList> StyleBuilderConverter::convertShadow(StyleResolverState&
ShadowDataVector shadows;
for (size_t i = 0; i < shadowCount; ++i) {
const CSSShadowValue* item = toCSSShadowValue(valueList->item(i));
- int x = item->x->computeLength<int>(state.cssToLengthConversionData());
- int y = item->y->computeLength<int>(state.cssToLengthConversionData());
- int blur = item->blur ? item->blur->computeLength<int>(state.cssToLengthConversionData()) : 0;
- int spread = item->spread ? item->spread->computeLength<int>(state.cssToLengthConversionData()) : 0;
+ float x = item->x->computeLength<float>(state.cssToLengthConversionData());
+ float y = item->y->computeLength<float>(state.cssToLengthConversionData());
+ float blur = item->blur ? item->blur->computeLength<float>(state.cssToLengthConversionData()) : 0;
+ float spread = item->spread ? item->spread->computeLength<float>(state.cssToLengthConversionData()) : 0;
ShadowStyle shadowStyle = item->style && item->style->getValueID() == CSSValueInset ? Inset : Normal;
Color color;
if (item->color)
color = state.document().textLinkColors().colorFromPrimitiveValue(item->color.get(), state.style()->color());
else
color = state.style()->color();
-
- if (!color.isValid())
- color = Color::transparent;
- shadows.append(ShadowData(IntPoint(x, y), blur, spread, shadowStyle, color));
+ shadows.append(ShadowData(FloatPoint(x, y), blur, spread, shadowStyle, color));
}
return ShadowList::adopt(shadows);
}
@@ -161,14 +404,53 @@ float StyleBuilderConverter::convertSpacing(StyleResolverState& state, CSSValue*
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->getValueID() == CSSValueNormal)
return 0;
- if (state.useSVGZoomRules())
- return primitiveValue->computeLength<float>(state.cssToLengthConversionData().copyWithAdjustedZoom(1));
return primitiveValue->computeLength<float>(state.cssToLengthConversionData());
}
-SVGLength StyleBuilderConverter::convertSVGLength(StyleResolverState&, CSSValue* value)
+PassRefPtr<SVGLengthList> StyleBuilderConverter::convertStrokeDasharray(StyleResolverState&, CSSValue* value)
+{
+ if (!value->isValueList()) {
+ return SVGRenderStyle::initialStrokeDashArray();
+ }
+
+ CSSValueList* dashes = toCSSValueList(value);
+
+ RefPtr<SVGLengthList> array = SVGLengthList::create();
+ size_t length = dashes->length();
+ for (size_t i = 0; i < length; ++i) {
+ CSSValue* currValue = dashes->itemWithoutBoundsCheck(i);
+ if (!currValue->isPrimitiveValue())
+ continue;
+
+ CSSPrimitiveValue* dash = toCSSPrimitiveValue(dashes->itemWithoutBoundsCheck(i));
+ array->append(SVGLength::fromCSSPrimitiveValue(dash));
+ }
+
+ return array.release();
+}
+
+Color StyleBuilderConverter::convertSVGColor(StyleResolverState& state, CSSValue* value)
+{
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->isRGBColor())
+ return primitiveValue->getRGBA32Value();
+ ASSERT(primitiveValue->getValueID() == CSSValueCurrentcolor);
+ return state.style()->color();
+}
+
+PassRefPtr<SVGLength> StyleBuilderConverter::convertSVGLength(StyleResolverState&, CSSValue* value)
{
return SVGLength::fromCSSPrimitiveValue(toCSSPrimitiveValue(value));
}
+float StyleBuilderConverter::convertTextStrokeWidth(StyleResolverState& state, CSSValue* value)
+{
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->getValueID()) {
+ float multiplier = convertLineWidth<float>(state, value);
+ return CSSPrimitiveValue::create(multiplier / 48, CSSPrimitiveValue::CSS_EMS)->computeLength<float>(state.cssToLengthConversionData());
+ }
+ return primitiveValue->computeLength<float>(state.cssToLengthConversionData());
+}
+
} // namespace WebCore