Upstream version 9.38.198.0
[platform/framework/web/crosswalk.git] / src / third_party / WebKit / Source / core / css / resolver / AnimatedStyleBuilder.cpp
1 /*
2  * Copyright (C) 2013 Google Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are
6  * met:
7  *
8  *     * Redistributions of source code must retain the above copyright
9  * notice, this list of conditions and the following disclaimer.
10  *     * Redistributions in binary form must reproduce the above
11  * copyright notice, this list of conditions and the following disclaimer
12  * in the documentation and/or other materials provided with the
13  * distribution.
14  *     * Neither the name of Google Inc. nor the names of its
15  * contributors may be used to endorse or promote products derived from
16  * this software without specific prior written permission.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29  */
30
31 #include "config.h"
32 #include "core/css/resolver/AnimatedStyleBuilder.h"
33
34 #include "core/animation/animatable/AnimatableClipPathOperation.h"
35 #include "core/animation/animatable/AnimatableColor.h"
36 #include "core/animation/animatable/AnimatableDouble.h"
37 #include "core/animation/animatable/AnimatableFilterOperations.h"
38 #include "core/animation/animatable/AnimatableImage.h"
39 #include "core/animation/animatable/AnimatableLength.h"
40 #include "core/animation/animatable/AnimatableLengthBox.h"
41 #include "core/animation/animatable/AnimatableLengthBoxAndBool.h"
42 #include "core/animation/animatable/AnimatableLengthPoint.h"
43 #include "core/animation/animatable/AnimatableLengthPoint3D.h"
44 #include "core/animation/animatable/AnimatableLengthSize.h"
45 #include "core/animation/animatable/AnimatableRepeatable.h"
46 #include "core/animation/animatable/AnimatableSVGLength.h"
47 #include "core/animation/animatable/AnimatableSVGPaint.h"
48 #include "core/animation/animatable/AnimatableShadow.h"
49 #include "core/animation/animatable/AnimatableShapeValue.h"
50 #include "core/animation/animatable/AnimatableStrokeDasharrayList.h"
51 #include "core/animation/animatable/AnimatableTransform.h"
52 #include "core/animation/animatable/AnimatableUnknown.h"
53 #include "core/animation/animatable/AnimatableValue.h"
54 #include "core/animation/animatable/AnimatableVisibility.h"
55 #include "core/css/CSSPrimitiveValueMappings.h"
56 #include "core/css/CSSPropertyMetadata.h"
57 #include "core/css/resolver/StyleBuilder.h"
58 #include "core/css/resolver/StyleResolverState.h"
59 #include "core/rendering/style/RenderStyle.h"
60 #include "wtf/MathExtras.h"
61 #include "wtf/TypeTraits.h"
62
63 namespace blink {
64
65 namespace {
66
67 Length animatableValueToLength(const AnimatableValue* value, const StyleResolverState& state, ValueRange range = ValueRangeAll)
68 {
69     if (value->isLength())
70         return toAnimatableLength(value)->length(state.style()->effectiveZoom(), range);
71     RefPtrWillBeRawPtr<CSSValue> cssValue = toAnimatableUnknown(value)->toCSSValue();
72     CSSPrimitiveValue* cssPrimitiveValue = toCSSPrimitiveValue(cssValue.get());
73     return cssPrimitiveValue->convertToLength<AnyConversion>(state.cssToLengthConversionData());
74 }
75
76 BorderImageLength animatableValueToBorderImageLength(const AnimatableValue* value, const StyleResolverState& state)
77 {
78     if (value->isLength())
79         return BorderImageLength(toAnimatableLength(value)->length(state.style()->effectiveZoom(), ValueRangeNonNegative));
80     if (value->isDouble())
81         return BorderImageLength(clampTo<double>(toAnimatableDouble(value)->toDouble(), 0));
82     RefPtrWillBeRawPtr<CSSValue> cssValue = toAnimatableUnknown(value)->toCSSValue();
83     CSSPrimitiveValue* cssPrimitiveValue = toCSSPrimitiveValue(cssValue.get());
84     return BorderImageLength(cssPrimitiveValue->convertToLength<AnyConversion>(state.cssToLengthConversionData()));
85 }
86
87 template<typename T> T animatableValueRoundClampTo(const AnimatableValue* value, T min = defaultMinimumForClamp<T>(), T max = defaultMaximumForClamp<T>())
88 {
89     COMPILE_ASSERT(WTF::IsInteger<T>::value, ShouldUseIntegralTypeTWhenRoundingValues);
90     return clampTo<T>(round(toAnimatableDouble(value)->toDouble()), min, max);
91 }
92
93 LengthBox animatableValueToLengthBox(const AnimatableValue* value, const StyleResolverState& state, ValueRange range = ValueRangeAll)
94 {
95     const AnimatableLengthBox* animatableLengthBox = toAnimatableLengthBox(value);
96     return LengthBox(
97         animatableValueToLength(animatableLengthBox->top(), state, range),
98         animatableValueToLength(animatableLengthBox->right(), state, range),
99         animatableValueToLength(animatableLengthBox->bottom(), state, range),
100         animatableValueToLength(animatableLengthBox->left(), state, range));
101 }
102
103 BorderImageLengthBox animatableValueToBorderImageLengthBox(const AnimatableValue* value, const StyleResolverState& state)
104 {
105     const AnimatableLengthBox* animatableLengthBox = toAnimatableLengthBox(value);
106     return BorderImageLengthBox(
107         animatableValueToBorderImageLength(animatableLengthBox->top(), state),
108         animatableValueToBorderImageLength(animatableLengthBox->right(), state),
109         animatableValueToBorderImageLength(animatableLengthBox->bottom(), state),
110         animatableValueToBorderImageLength(animatableLengthBox->left(), state));
111 }
112
113 LengthPoint animatableValueToLengthPoint(const AnimatableValue* value, const StyleResolverState& state, ValueRange range = ValueRangeAll)
114 {
115     const AnimatableLengthPoint* animatableLengthPoint = toAnimatableLengthPoint(value);
116     return LengthPoint(
117         animatableValueToLength(animatableLengthPoint->x(), state, range),
118         animatableValueToLength(animatableLengthPoint->y(), state, range));
119 }
120
121 LengthSize animatableValueToLengthSize(const AnimatableValue* value, const StyleResolverState& state, ValueRange range)
122 {
123     const AnimatableLengthSize* animatableLengthSize = toAnimatableLengthSize(value);
124     return LengthSize(
125         animatableValueToLength(animatableLengthSize->width(), state, range),
126         animatableValueToLength(animatableLengthSize->height(), state, range));
127 }
128
129 void setFillSize(FillLayer* fillLayer, const AnimatableValue* value, const StyleResolverState& state)
130 {
131     if (value->isLengthSize())
132         fillLayer->setSize(FillSize(SizeLength, animatableValueToLengthSize(value, state, ValueRangeNonNegative)));
133     else
134         state.styleMap().mapFillSize(fillLayer, toAnimatableUnknown(value)->toCSSValue().get());
135 }
136
137 PassRefPtr<SVGLength> animatableValueToNonNegativeSVGLength(const AnimatableValue* value)
138 {
139     RefPtr<SVGLength> length = toAnimatableSVGLength(value)->toSVGLength();
140     if (length->valueInSpecifiedUnits() < 0)
141         length->setValueInSpecifiedUnits(0);
142     return length.release();
143 }
144
145 template <CSSPropertyID property>
146 void setOnFillLayers(FillLayer& fillLayers, const AnimatableValue* value, StyleResolverState& state)
147 {
148     const WillBeHeapVector<RefPtrWillBeMember<AnimatableValue> >& values = toAnimatableRepeatable(value)->values();
149     ASSERT(!values.isEmpty());
150     FillLayer* fillLayer = &fillLayers;
151     FillLayer* prev = 0;
152     for (size_t i = 0; i < values.size(); ++i) {
153         if (!fillLayer)
154             fillLayer = prev->ensureNext();
155         const AnimatableValue* layerValue = values[i].get();
156         switch (property) {
157         case CSSPropertyBackgroundImage:
158         case CSSPropertyWebkitMaskImage:
159             if (layerValue->isImage()) {
160                 fillLayer->setImage(state.styleImage(property, toAnimatableImage(layerValue)->toCSSValue()));
161             } else {
162                 ASSERT(toAnimatableUnknown(layerValue)->toCSSValueID() == CSSValueNone);
163                 fillLayer->setImage(nullptr);
164             }
165             break;
166         case CSSPropertyBackgroundPositionX:
167         case CSSPropertyWebkitMaskPositionX:
168             fillLayer->setXPosition(animatableValueToLength(layerValue, state));
169             break;
170         case CSSPropertyBackgroundPositionY:
171         case CSSPropertyWebkitMaskPositionY:
172             fillLayer->setYPosition(animatableValueToLength(layerValue, state));
173             break;
174         case CSSPropertyBackgroundSize:
175         case CSSPropertyWebkitBackgroundSize:
176         case CSSPropertyWebkitMaskSize:
177             setFillSize(fillLayer, layerValue, state);
178             break;
179         default:
180             ASSERT_NOT_REACHED();
181         }
182         prev = fillLayer;
183         fillLayer = fillLayer->next();
184     }
185     while (fillLayer) {
186         switch (property) {
187         case CSSPropertyBackgroundImage:
188         case CSSPropertyWebkitMaskImage:
189             fillLayer->clearImage();
190             break;
191         case CSSPropertyBackgroundPositionX:
192         case CSSPropertyWebkitMaskPositionX:
193             fillLayer->clearXPosition();
194             break;
195         case CSSPropertyBackgroundPositionY:
196         case CSSPropertyWebkitMaskPositionY:
197             fillLayer->clearYPosition();
198             break;
199         case CSSPropertyBackgroundSize:
200         case CSSPropertyWebkitBackgroundSize:
201         case CSSPropertyWebkitMaskSize:
202             fillLayer->clearSize();
203             break;
204         default:
205             ASSERT_NOT_REACHED();
206         }
207         fillLayer = fillLayer->next();
208     }
209 }
210
211 FontStretch animatableValueToFontStretch(const AnimatableValue* value)
212 {
213     ASSERT(FontStretchUltraCondensed == 1 && FontStretchUltraExpanded == 9);
214     unsigned index = round(toAnimatableDouble(value)->toDouble()) - 1;
215     static const FontStretch stretchValues[] = {
216         FontStretchUltraCondensed,
217         FontStretchExtraCondensed,
218         FontStretchCondensed,
219         FontStretchSemiCondensed,
220         FontStretchNormal,
221         FontStretchSemiExpanded,
222         FontStretchExpanded,
223         FontStretchExtraExpanded,
224         FontStretchUltraExpanded
225     };
226
227     index = clampTo<unsigned>(index, 0, WTF_ARRAY_LENGTH(stretchValues) - 1);
228     return stretchValues[index];
229 }
230
231 FontWeight animatableValueToFontWeight(const AnimatableValue* value)
232 {
233     int index = round(toAnimatableDouble(value)->toDouble() / 100) - 1;
234
235     static const FontWeight weights[] = {
236         FontWeight100,
237         FontWeight200,
238         FontWeight300,
239         FontWeight400,
240         FontWeight500,
241         FontWeight600,
242         FontWeight700,
243         FontWeight800,
244         FontWeight900
245     };
246
247     index = clampTo<int>(index, 0, WTF_ARRAY_LENGTH(weights) - 1);
248
249     return weights[index];
250 }
251
252 } // namespace
253
254 // FIXME: Generate this function.
255 void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverState& state, const AnimatableValue* value)
256 {
257     ASSERT(CSSPropertyMetadata::isAnimatableProperty(property));
258     if (value->isUnknown()) {
259         StyleBuilder::applyProperty(property, state, toAnimatableUnknown(value)->toCSSValue().get());
260         return;
261     }
262     RenderStyle* style = state.style();
263     switch (property) {
264     case CSSPropertyBackgroundColor:
265         style->setBackgroundColor(toAnimatableColor(value)->color());
266         style->setVisitedLinkBackgroundColor(toAnimatableColor(value)->visitedLinkColor());
267         return;
268     case CSSPropertyBackgroundImage:
269         setOnFillLayers<CSSPropertyBackgroundImage>(style->accessBackgroundLayers(), value, state);
270         return;
271     case CSSPropertyBackgroundPositionX:
272         setOnFillLayers<CSSPropertyBackgroundPositionX>(style->accessBackgroundLayers(), value, state);
273         return;
274     case CSSPropertyBackgroundPositionY:
275         setOnFillLayers<CSSPropertyBackgroundPositionY>(style->accessBackgroundLayers(), value, state);
276         return;
277     case CSSPropertyBackgroundSize:
278         setOnFillLayers<CSSPropertyBackgroundSize>(style->accessBackgroundLayers(), value, state);
279         return;
280     case CSSPropertyBaselineShift:
281         style->setBaselineShiftValue(toAnimatableSVGLength(value)->toSVGLength());
282         return;
283     case CSSPropertyBorderBottomColor:
284         style->setBorderBottomColor(toAnimatableColor(value)->color());
285         style->setVisitedLinkBorderBottomColor(toAnimatableColor(value)->visitedLinkColor());
286         return;
287     case CSSPropertyBorderBottomLeftRadius:
288         style->setBorderBottomLeftRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
289         return;
290     case CSSPropertyBorderBottomRightRadius:
291         style->setBorderBottomRightRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
292         return;
293     case CSSPropertyBorderBottomWidth:
294         style->setBorderBottomWidth(animatableValueRoundClampTo<unsigned>(value));
295         return;
296     case CSSPropertyBorderImageOutset:
297         style->setBorderImageOutset(animatableValueToBorderImageLengthBox(value, state));
298         return;
299     case CSSPropertyBorderImageSlice:
300         style->setBorderImageSlices(animatableValueToLengthBox(value, state, ValueRangeNonNegative));
301         return;
302     case CSSPropertyBorderImageSource:
303         style->setBorderImageSource(state.styleImage(property, toAnimatableImage(value)->toCSSValue()));
304         return;
305     case CSSPropertyBorderImageWidth:
306         style->setBorderImageWidth(animatableValueToBorderImageLengthBox(value, state));
307         return;
308     case CSSPropertyBorderLeftColor:
309         style->setBorderLeftColor(toAnimatableColor(value)->color());
310         style->setVisitedLinkBorderLeftColor(toAnimatableColor(value)->visitedLinkColor());
311         return;
312     case CSSPropertyBorderLeftWidth:
313         style->setBorderLeftWidth(animatableValueRoundClampTo<unsigned>(value));
314         return;
315     case CSSPropertyBorderRightColor:
316         style->setBorderRightColor(toAnimatableColor(value)->color());
317         style->setVisitedLinkBorderRightColor(toAnimatableColor(value)->visitedLinkColor());
318         return;
319     case CSSPropertyBorderRightWidth:
320         style->setBorderRightWidth(animatableValueRoundClampTo<unsigned>(value));
321         return;
322     case CSSPropertyBorderTopColor:
323         style->setBorderTopColor(toAnimatableColor(value)->color());
324         style->setVisitedLinkBorderTopColor(toAnimatableColor(value)->visitedLinkColor());
325         return;
326     case CSSPropertyBorderTopLeftRadius:
327         style->setBorderTopLeftRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
328         return;
329     case CSSPropertyBorderTopRightRadius:
330         style->setBorderTopRightRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
331         return;
332     case CSSPropertyBorderTopWidth:
333         style->setBorderTopWidth(animatableValueRoundClampTo<unsigned>(value));
334         return;
335     case CSSPropertyBottom:
336         style->setBottom(animatableValueToLength(value, state));
337         return;
338     case CSSPropertyBoxShadow:
339     case CSSPropertyWebkitBoxShadow:
340         style->setBoxShadow(toAnimatableShadow(value)->shadowList());
341         return;
342     case CSSPropertyClip:
343         style->setClip(animatableValueToLengthBox(value, state));
344         style->setHasClip(true);
345         return;
346     case CSSPropertyColor:
347         style->setColor(toAnimatableColor(value)->color());
348         style->setVisitedLinkColor(toAnimatableColor(value)->visitedLinkColor());
349         return;
350     case CSSPropertyFillOpacity:
351         style->setFillOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
352         return;
353     case CSSPropertyFill:
354         {
355             const AnimatableSVGPaint* svgPaint = toAnimatableSVGPaint(value);
356             style->accessSVGStyle().setFillPaint(svgPaint->paintType(), svgPaint->color(), svgPaint->uri(), true, false);
357             style->accessSVGStyle().setFillPaint(svgPaint->visitedLinkPaintType(), svgPaint->visitedLinkColor(), svgPaint->visitedLinkURI(), false, true);
358         }
359         return;
360     case CSSPropertyFlexGrow:
361         style->setFlexGrow(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0));
362         return;
363     case CSSPropertyFlexShrink:
364         style->setFlexShrink(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0));
365         return;
366     case CSSPropertyFlexBasis:
367         style->setFlexBasis(animatableValueToLength(value, state, ValueRangeNonNegative));
368         return;
369     case CSSPropertyFloodColor:
370         style->setFloodColor(toAnimatableColor(value)->color());
371         return;
372     case CSSPropertyFloodOpacity:
373         style->setFloodOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
374         return;
375     case CSSPropertyFontSize:
376         style->setFontSize(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0));
377         return;
378     case CSSPropertyFontStretch:
379         style->setFontStretch(animatableValueToFontStretch(value));
380         return;
381     case CSSPropertyFontWeight:
382         style->setFontWeight(animatableValueToFontWeight(value));
383         return;
384     case CSSPropertyHeight:
385         style->setHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
386         return;
387     case CSSPropertyLeft:
388         style->setLeft(animatableValueToLength(value, state));
389         return;
390     case CSSPropertyLightingColor:
391         style->setLightingColor(toAnimatableColor(value)->color());
392         return;
393     case CSSPropertyLineHeight:
394         if (value->isLength())
395             style->setLineHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
396         else
397             style->setLineHeight(Length(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0), Percent));
398         return;
399     case CSSPropertyListStyleImage:
400         style->setListStyleImage(state.styleImage(property, toAnimatableImage(value)->toCSSValue()));
401         return;
402     case CSSPropertyLetterSpacing:
403         style->setLetterSpacing(clampTo<float>(toAnimatableDouble(value)->toDouble()));
404         return;
405     case CSSPropertyMarginBottom:
406         style->setMarginBottom(animatableValueToLength(value, state));
407         return;
408     case CSSPropertyMarginLeft:
409         style->setMarginLeft(animatableValueToLength(value, state));
410         return;
411     case CSSPropertyMarginRight:
412         style->setMarginRight(animatableValueToLength(value, state));
413         return;
414     case CSSPropertyMarginTop:
415         style->setMarginTop(animatableValueToLength(value, state));
416         return;
417     case CSSPropertyMaxHeight:
418         style->setMaxHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
419         return;
420     case CSSPropertyMaxWidth:
421         style->setMaxWidth(animatableValueToLength(value, state, ValueRangeNonNegative));
422         return;
423     case CSSPropertyMinHeight:
424         style->setMinHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
425         return;
426     case CSSPropertyMinWidth:
427         style->setMinWidth(animatableValueToLength(value, state, ValueRangeNonNegative));
428         return;
429     case CSSPropertyObjectPosition:
430         style->setObjectPosition(animatableValueToLengthPoint(value, state));
431         return;
432     case CSSPropertyOpacity:
433         // Avoiding a value of 1 forces a layer to be created.
434         style->setOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, nextafterf(1, 0)));
435         return;
436     case CSSPropertyOrphans:
437         style->setOrphans(animatableValueRoundClampTo<unsigned short>(value, 1));
438         return;
439     case CSSPropertyOutlineColor:
440         style->setOutlineColor(toAnimatableColor(value)->color());
441         style->setVisitedLinkOutlineColor(toAnimatableColor(value)->visitedLinkColor());
442         return;
443     case CSSPropertyOutlineOffset:
444         style->setOutlineOffset(animatableValueRoundClampTo<int>(value));
445         return;
446     case CSSPropertyOutlineWidth:
447         style->setOutlineWidth(animatableValueRoundClampTo<unsigned short>(value));
448         return;
449     case CSSPropertyPaddingBottom:
450         style->setPaddingBottom(animatableValueToLength(value, state, ValueRangeNonNegative));
451         return;
452     case CSSPropertyPaddingLeft:
453         style->setPaddingLeft(animatableValueToLength(value, state, ValueRangeNonNegative));
454         return;
455     case CSSPropertyPaddingRight:
456         style->setPaddingRight(animatableValueToLength(value, state, ValueRangeNonNegative));
457         return;
458     case CSSPropertyPaddingTop:
459         style->setPaddingTop(animatableValueToLength(value, state, ValueRangeNonNegative));
460         return;
461     case CSSPropertyRight:
462         style->setRight(animatableValueToLength(value, state));
463         return;
464     case CSSPropertyStrokeWidth:
465         style->setStrokeWidth(animatableValueToNonNegativeSVGLength(value));
466         return;
467     case CSSPropertyStopColor:
468         style->setStopColor(toAnimatableColor(value)->color());
469         return;
470     case CSSPropertyStopOpacity:
471         style->setStopOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
472         return;
473     case CSSPropertyStrokeDasharray:
474         style->setStrokeDashArray(toAnimatableStrokeDasharrayList(value)->toSVGLengthList());
475         return;
476     case CSSPropertyStrokeDashoffset:
477         style->setStrokeDashOffset(toAnimatableSVGLength(value)->toSVGLength());
478         return;
479     case CSSPropertyStrokeMiterlimit:
480         style->setStrokeMiterLimit(clampTo<float>(toAnimatableDouble(value)->toDouble(), 1));
481         return;
482     case CSSPropertyStrokeOpacity:
483         style->setStrokeOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
484         return;
485     case CSSPropertyStroke:
486         {
487             const AnimatableSVGPaint* svgPaint = toAnimatableSVGPaint(value);
488             style->accessSVGStyle().setStrokePaint(svgPaint->paintType(), svgPaint->color(), svgPaint->uri(), true, false);
489             style->accessSVGStyle().setStrokePaint(svgPaint->visitedLinkPaintType(), svgPaint->visitedLinkColor(), svgPaint->visitedLinkURI(), false, true);
490         }
491         return;
492     case CSSPropertyTextDecorationColor:
493         style->setTextDecorationColor(toAnimatableColor(value)->color());
494         style->setVisitedLinkTextDecorationColor(toAnimatableColor(value)->visitedLinkColor());
495         return;
496     case CSSPropertyTextIndent:
497         style->setTextIndent(animatableValueToLength(value, state));
498         return;
499     case CSSPropertyTextShadow:
500         style->setTextShadow(toAnimatableShadow(value)->shadowList());
501         return;
502     case CSSPropertyTop:
503         style->setTop(animatableValueToLength(value, state));
504         return;
505     case CSSPropertyWebkitBackgroundSize:
506         setOnFillLayers<CSSPropertyWebkitBackgroundSize>(style->accessBackgroundLayers(), value, state);
507         return;
508     case CSSPropertyWebkitBorderHorizontalSpacing:
509         style->setHorizontalBorderSpacing(animatableValueRoundClampTo<unsigned short>(value));
510         return;
511     case CSSPropertyWebkitBorderVerticalSpacing:
512         style->setVerticalBorderSpacing(animatableValueRoundClampTo<unsigned short>(value));
513         return;
514     case CSSPropertyWebkitClipPath:
515         style->setClipPath(toAnimatableClipPathOperation(value)->clipPathOperation());
516         return;
517     case CSSPropertyWebkitColumnCount:
518         style->setColumnCount(animatableValueRoundClampTo<unsigned short>(value, 1));
519         return;
520     case CSSPropertyWebkitColumnGap:
521         style->setColumnGap(clampTo(toAnimatableDouble(value)->toDouble(), 0));
522         return;
523     case CSSPropertyWebkitColumnRuleColor:
524         style->setColumnRuleColor(toAnimatableColor(value)->color());
525         style->setVisitedLinkColumnRuleColor(toAnimatableColor(value)->visitedLinkColor());
526         return;
527     case CSSPropertyWebkitColumnWidth:
528         style->setColumnWidth(clampTo(toAnimatableDouble(value)->toDouble(), std::numeric_limits<float>::epsilon()));
529         return;
530     case CSSPropertyWebkitColumnRuleWidth:
531         style->setColumnRuleWidth(animatableValueRoundClampTo<unsigned short>(value));
532         return;
533     case CSSPropertyWebkitFilter:
534         style->setFilter(toAnimatableFilterOperations(value)->operations());
535         return;
536     case CSSPropertyWebkitMaskBoxImageOutset:
537         style->setMaskBoxImageOutset(animatableValueToBorderImageLengthBox(value, state));
538         return;
539     case CSSPropertyWebkitMaskBoxImageSlice:
540         style->setMaskBoxImageSlices(animatableValueToLengthBox(toAnimatableLengthBoxAndBool(value)->box(), state, ValueRangeNonNegative));
541         style->setMaskBoxImageSlicesFill(toAnimatableLengthBoxAndBool(value)->flag());
542         return;
543     case CSSPropertyWebkitMaskBoxImageSource:
544         style->setMaskBoxImageSource(state.styleImage(property, toAnimatableImage(value)->toCSSValue()));
545         return;
546     case CSSPropertyWebkitMaskBoxImageWidth:
547         style->setMaskBoxImageWidth(animatableValueToBorderImageLengthBox(value, state));
548         return;
549     case CSSPropertyWebkitMaskImage:
550         setOnFillLayers<CSSPropertyWebkitMaskImage>(style->accessMaskLayers(), value, state);
551         return;
552     case CSSPropertyWebkitMaskPositionX:
553         setOnFillLayers<CSSPropertyWebkitMaskPositionX>(style->accessMaskLayers(), value, state);
554         return;
555     case CSSPropertyWebkitMaskPositionY:
556         setOnFillLayers<CSSPropertyWebkitMaskPositionY>(style->accessMaskLayers(), value, state);
557         return;
558     case CSSPropertyWebkitMaskSize:
559         setOnFillLayers<CSSPropertyWebkitMaskSize>(style->accessMaskLayers(), value, state);
560         return;
561     case CSSPropertyPerspective:
562         style->setPerspective(clampTo<float>(toAnimatableDouble(value)->toDouble()));
563         return;
564     case CSSPropertyPerspectiveOrigin: {
565         const AnimatableLengthPoint* animatableLengthPoint = toAnimatableLengthPoint(value);
566         style->setPerspectiveOriginX(animatableValueToLength(animatableLengthPoint->x(), state));
567         style->setPerspectiveOriginY(animatableValueToLength(animatableLengthPoint->y(), state));
568         return;
569     }
570     case CSSPropertyShapeOutside:
571         style->setShapeOutside(toAnimatableShapeValue(value)->shapeValue());
572         return;
573     case CSSPropertyShapeMargin:
574         style->setShapeMargin(animatableValueToLength(value, state, ValueRangeNonNegative));
575         return;
576     case CSSPropertyShapeImageThreshold:
577         style->setShapeImageThreshold(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
578         return;
579     case CSSPropertyWebkitTextStrokeColor:
580         style->setTextStrokeColor(toAnimatableColor(value)->color());
581         style->setVisitedLinkTextStrokeColor(toAnimatableColor(value)->visitedLinkColor());
582         return;
583     case CSSPropertyTransform: {
584         const TransformOperations& operations = toAnimatableTransform(value)->transformOperations();
585         // FIXME: This normalization (handling of 'none') should be performed at input in AnimatableValueFactory.
586         style->setTransform(operations.size() ? operations : TransformOperations(true));
587         return;
588     }
589     case CSSPropertyTransformOrigin: {
590         const AnimatableLengthPoint3D* animatableLengthPoint3D = toAnimatableLengthPoint3D(value);
591         style->setTransformOriginX(animatableValueToLength(animatableLengthPoint3D->x(), state));
592         style->setTransformOriginY(animatableValueToLength(animatableLengthPoint3D->y(), state));
593         style->setTransformOriginZ(clampTo<float>(toAnimatableDouble(animatableLengthPoint3D->z())->toDouble()));
594         return;
595     }
596     case CSSPropertyWidows:
597         style->setWidows(animatableValueRoundClampTo<unsigned short>(value, 1));
598         return;
599     case CSSPropertyWidth:
600         style->setWidth(animatableValueToLength(value, state, ValueRangeNonNegative));
601         return;
602     case CSSPropertyWordSpacing:
603         style->setWordSpacing(clampTo<float>(toAnimatableDouble(value)->toDouble()));
604         return;
605     case CSSPropertyVerticalAlign:
606         style->setVerticalAlignLength(animatableValueToLength(value, state));
607         return;
608     case CSSPropertyVisibility:
609         style->setVisibility(toAnimatableVisibility(value)->visibility());
610         return;
611     case CSSPropertyZIndex:
612         style->setZIndex(animatableValueRoundClampTo<int>(value));
613         return;
614     case CSSPropertyZoom:
615         style->setZoom(clampTo<float>(toAnimatableDouble(value)->toDouble(), std::numeric_limits<float>::denorm_min()));
616         return;
617     default:
618         ASSERT_NOT_REACHED();
619     }
620 }
621
622 } // namespace blink