1/*
2 * Copyright (C) 2007 Alexey Proskuryakov <ap@nypop.com>.
3 * Copyright (C) 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
4 * Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
5 * Copyright (C) 2009 Jeff Schiller <codedread@gmail.com>
6 * Copyright (C) Research In Motion Limited 2010. All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 *
12 * 1. Redistributions of source code must retain the above copyright
13 *    notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 *    notice, this list of conditions and the following disclaimer in the
16 *    documentation and/or other materials provided with the distribution.
17 *
18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 */
29
30#ifndef CSSPrimitiveValueMappings_h
31#define CSSPrimitiveValueMappings_h
32
33#include "core/CSSValueKeywords.h"
34#include "core/css/CSSCalculationValue.h"
35#include "core/css/CSSPrimitiveValue.h"
36#include "core/css/CSSReflectionDirection.h"
37#include "core/css/CSSToLengthConversionData.h"
38#include "core/rendering/style/LineClampValue.h"
39#include "core/rendering/style/RenderStyleConstants.h"
40#include "core/rendering/style/SVGRenderStyleDefs.h"
41#include "platform/Length.h"
42#include "platform/ThemeTypes.h"
43#include "platform/fonts/FontDescription.h"
44#include "platform/fonts/FontSmoothingMode.h"
45#include "platform/fonts/TextRenderingMode.h"
46#include "platform/graphics/GraphicsTypes.h"
47#include "platform/graphics/Path.h"
48#include "platform/scroll/ScrollableArea.h"
49#include "platform/text/TextDirection.h"
50#include "platform/text/UnicodeBidi.h"
51#include "platform/text/WritingMode.h"
52#include "wtf/MathExtras.h"
53
54namespace WebCore {
55
56template<> inline CSSPrimitiveValue::CSSPrimitiveValue(short i)
57    : CSSValue(PrimitiveClass)
58{
59    m_primitiveUnitType = CSS_NUMBER;
60    m_value.num = static_cast<double>(i);
61}
62
63template<> inline CSSPrimitiveValue::operator short() const
64{
65    ASSERT(isNumber());
66    return clampTo<short>(getDoubleValue());
67}
68
69template<> inline CSSPrimitiveValue::CSSPrimitiveValue(unsigned short i)
70    : CSSValue(PrimitiveClass)
71{
72    m_primitiveUnitType = CSS_NUMBER;
73    m_value.num = static_cast<double>(i);
74}
75
76template<> inline CSSPrimitiveValue::operator unsigned short() const
77{
78    ASSERT(isNumber());
79    return clampTo<unsigned short>(getDoubleValue());
80}
81
82template<> inline CSSPrimitiveValue::operator int() const
83{
84    ASSERT(isNumber());
85    return clampTo<int>(getDoubleValue());
86}
87
88template<> inline CSSPrimitiveValue::operator unsigned() const
89{
90    ASSERT(isNumber());
91    return clampTo<unsigned>(getDoubleValue());
92}
93
94
95template<> inline CSSPrimitiveValue::CSSPrimitiveValue(float i)
96    : CSSValue(PrimitiveClass)
97{
98    m_primitiveUnitType = CSS_NUMBER;
99    m_value.num = static_cast<double>(i);
100}
101
102template<> inline CSSPrimitiveValue::operator float() const
103{
104    ASSERT(isNumber());
105    return clampTo<float>(getDoubleValue());
106}
107
108template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineClampValue i)
109    : CSSValue(PrimitiveClass)
110{
111    m_primitiveUnitType = i.isPercentage() ? CSS_PERCENTAGE : CSS_NUMBER;
112    m_value.num = static_cast<double>(i.value());
113}
114
115template<> inline CSSPrimitiveValue::operator LineClampValue() const
116{
117    if (m_primitiveUnitType == CSS_NUMBER)
118        return LineClampValue(clampTo<int>(m_value.num), LineClampLineCount);
119
120    if (m_primitiveUnitType == CSS_PERCENTAGE)
121        return LineClampValue(clampTo<int>(m_value.num), LineClampPercentage);
122
123    ASSERT_NOT_REACHED();
124    return LineClampValue();
125}
126
127template<> inline CSSPrimitiveValue::CSSPrimitiveValue(CSSReflectionDirection e)
128    : CSSValue(PrimitiveClass)
129{
130    m_primitiveUnitType = CSS_VALUE_ID;
131    switch (e) {
132    case ReflectionAbove:
133        m_value.valueID = CSSValueAbove;
134        break;
135    case ReflectionBelow:
136        m_value.valueID = CSSValueBelow;
137        break;
138    case ReflectionLeft:
139        m_value.valueID = CSSValueLeft;
140        break;
141    case ReflectionRight:
142        m_value.valueID = CSSValueRight;
143    }
144}
145
146template<> inline CSSPrimitiveValue::operator CSSReflectionDirection() const
147{
148    ASSERT(isValueID());
149    switch (m_value.valueID) {
150    case CSSValueAbove:
151        return ReflectionAbove;
152    case CSSValueBelow:
153        return ReflectionBelow;
154    case CSSValueLeft:
155        return ReflectionLeft;
156    case CSSValueRight:
157        return ReflectionRight;
158    default:
159        break;
160    }
161
162    ASSERT_NOT_REACHED();
163    return ReflectionBelow;
164}
165
166template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ColumnFill columnFill)
167    : CSSValue(PrimitiveClass)
168{
169    m_primitiveUnitType = CSS_VALUE_ID;
170    switch (columnFill) {
171    case ColumnFillAuto:
172        m_value.valueID = CSSValueAuto;
173        break;
174    case ColumnFillBalance:
175        m_value.valueID = CSSValueBalance;
176        break;
177    }
178}
179
180template<> inline CSSPrimitiveValue::operator ColumnFill() const
181{
182    if (m_primitiveUnitType == CSS_VALUE_ID) {
183        if (m_value.valueID == CSSValueBalance)
184            return ColumnFillBalance;
185        if (m_value.valueID == CSSValueAuto)
186            return ColumnFillAuto;
187    }
188    ASSERT_NOT_REACHED();
189    return ColumnFillBalance;
190}
191
192template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ColumnSpan columnSpan)
193    : CSSValue(PrimitiveClass)
194{
195    m_primitiveUnitType = CSS_VALUE_ID;
196    switch (columnSpan) {
197    case ColumnSpanAll:
198        m_value.valueID = CSSValueAll;
199        break;
200    case ColumnSpanNone:
201        m_value.valueID = CSSValueNone;
202        break;
203    }
204}
205
206template<> inline CSSPrimitiveValue::operator ColumnSpan() const
207{
208    // Map 1 to none for compatibility reasons.
209    if (m_primitiveUnitType == CSS_NUMBER && m_value.num == 1)
210        return ColumnSpanNone;
211
212    ASSERT(isValueID());
213    switch (m_value.valueID) {
214    case CSSValueAll:
215        return ColumnSpanAll;
216    case CSSValueNone:
217        return ColumnSpanNone;
218    default:
219        break;
220    }
221
222    ASSERT_NOT_REACHED();
223    return ColumnSpanNone;
224}
225
226
227template<> inline CSSPrimitiveValue::CSSPrimitiveValue(PrintColorAdjust value)
228    : CSSValue(PrimitiveClass)
229{
230    m_primitiveUnitType = CSS_VALUE_ID;
231    switch (value) {
232    case PrintColorAdjustExact:
233        m_value.valueID = CSSValueExact;
234        break;
235    case PrintColorAdjustEconomy:
236        m_value.valueID = CSSValueEconomy;
237        break;
238    }
239}
240
241template<> inline CSSPrimitiveValue::operator PrintColorAdjust() const
242{
243    ASSERT(isValueID());
244    switch (m_value.valueID) {
245    case CSSValueEconomy:
246        return PrintColorAdjustEconomy;
247    case CSSValueExact:
248        return PrintColorAdjustExact;
249    default:
250        break;
251    }
252
253    ASSERT_NOT_REACHED();
254    return PrintColorAdjustEconomy;
255}
256
257
258template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBorderStyle e)
259    : CSSValue(PrimitiveClass)
260{
261    m_primitiveUnitType = CSS_VALUE_ID;
262    switch (e) {
263    case BNONE:
264        m_value.valueID = CSSValueNone;
265        break;
266    case BHIDDEN:
267        m_value.valueID = CSSValueHidden;
268        break;
269    case INSET:
270        m_value.valueID = CSSValueInset;
271        break;
272    case GROOVE:
273        m_value.valueID = CSSValueGroove;
274        break;
275    case RIDGE:
276        m_value.valueID = CSSValueRidge;
277        break;
278    case OUTSET:
279        m_value.valueID = CSSValueOutset;
280        break;
281    case DOTTED:
282        m_value.valueID = CSSValueDotted;
283        break;
284    case DASHED:
285        m_value.valueID = CSSValueDashed;
286        break;
287    case SOLID:
288        m_value.valueID = CSSValueSolid;
289        break;
290    case DOUBLE:
291        m_value.valueID = CSSValueDouble;
292        break;
293    }
294}
295
296template<> inline CSSPrimitiveValue::operator EBorderStyle() const
297{
298    ASSERT(isValueID());
299    if (m_value.valueID == CSSValueAuto) // Valid for CSS outline-style
300        return DOTTED;
301    return (EBorderStyle)(m_value.valueID - CSSValueNone);
302}
303
304template<> inline CSSPrimitiveValue::operator OutlineIsAuto() const
305{
306    if (m_value.valueID == CSSValueAuto)
307        return AUTO_ON;
308    return AUTO_OFF;
309}
310
311template<> inline CSSPrimitiveValue::CSSPrimitiveValue(CompositeOperator e)
312    : CSSValue(PrimitiveClass)
313{
314    m_primitiveUnitType = CSS_VALUE_ID;
315    switch (e) {
316    case CompositeClear:
317        m_value.valueID = CSSValueClear;
318        break;
319    case CompositeCopy:
320        m_value.valueID = CSSValueCopy;
321        break;
322    case CompositeSourceOver:
323        m_value.valueID = CSSValueSourceOver;
324        break;
325    case CompositeSourceIn:
326        m_value.valueID = CSSValueSourceIn;
327        break;
328    case CompositeSourceOut:
329        m_value.valueID = CSSValueSourceOut;
330        break;
331    case CompositeSourceAtop:
332        m_value.valueID = CSSValueSourceAtop;
333        break;
334    case CompositeDestinationOver:
335        m_value.valueID = CSSValueDestinationOver;
336        break;
337    case CompositeDestinationIn:
338        m_value.valueID = CSSValueDestinationIn;
339        break;
340    case CompositeDestinationOut:
341        m_value.valueID = CSSValueDestinationOut;
342        break;
343    case CompositeDestinationAtop:
344        m_value.valueID = CSSValueDestinationAtop;
345        break;
346    case CompositeXOR:
347        m_value.valueID = CSSValueXor;
348        break;
349    case CompositePlusDarker:
350        m_value.valueID = CSSValuePlusDarker;
351        break;
352    case CompositePlusLighter:
353        m_value.valueID = CSSValuePlusLighter;
354        break;
355    case CompositeDifference:
356        ASSERT_NOT_REACHED();
357        break;
358    }
359}
360
361template<> inline CSSPrimitiveValue::operator CompositeOperator() const
362{
363    ASSERT(isValueID());
364    switch (m_value.valueID) {
365    case CSSValueClear:
366        return CompositeClear;
367    case CSSValueCopy:
368        return CompositeCopy;
369    case CSSValueSourceOver:
370        return CompositeSourceOver;
371    case CSSValueSourceIn:
372        return CompositeSourceIn;
373    case CSSValueSourceOut:
374        return CompositeSourceOut;
375    case CSSValueSourceAtop:
376        return CompositeSourceAtop;
377    case CSSValueDestinationOver:
378        return CompositeDestinationOver;
379    case CSSValueDestinationIn:
380        return CompositeDestinationIn;
381    case CSSValueDestinationOut:
382        return CompositeDestinationOut;
383    case CSSValueDestinationAtop:
384        return CompositeDestinationAtop;
385    case CSSValueXor:
386        return CompositeXOR;
387    case CSSValuePlusDarker:
388        return CompositePlusDarker;
389    case CSSValuePlusLighter:
390        return CompositePlusLighter;
391    default:
392        break;
393    }
394
395    ASSERT_NOT_REACHED();
396    return CompositeClear;
397}
398
399template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ControlPart e)
400    : CSSValue(PrimitiveClass)
401{
402    m_primitiveUnitType = CSS_VALUE_ID;
403    switch (e) {
404    case NoControlPart:
405        m_value.valueID = CSSValueNone;
406        break;
407    case CheckboxPart:
408        m_value.valueID = CSSValueCheckbox;
409        break;
410    case RadioPart:
411        m_value.valueID = CSSValueRadio;
412        break;
413    case PushButtonPart:
414        m_value.valueID = CSSValuePushButton;
415        break;
416    case SquareButtonPart:
417        m_value.valueID = CSSValueSquareButton;
418        break;
419    case ButtonPart:
420        m_value.valueID = CSSValueButton;
421        break;
422    case ButtonBevelPart:
423        m_value.valueID = CSSValueButtonBevel;
424        break;
425    case InnerSpinButtonPart:
426        m_value.valueID = CSSValueInnerSpinButton;
427        break;
428    case ListboxPart:
429        m_value.valueID = CSSValueListbox;
430        break;
431    case ListItemPart:
432        m_value.valueID = CSSValueListitem;
433        break;
434    case MediaEnterFullscreenButtonPart:
435        m_value.valueID = CSSValueMediaEnterFullscreenButton;
436        break;
437    case MediaExitFullscreenButtonPart:
438        m_value.valueID = CSSValueMediaExitFullscreenButton;
439        break;
440    case MediaPlayButtonPart:
441        m_value.valueID = CSSValueMediaPlayButton;
442        break;
443    case MediaOverlayPlayButtonPart:
444        m_value.valueID = CSSValueMediaOverlayPlayButton;
445        break;
446    case MediaMuteButtonPart:
447        m_value.valueID = CSSValueMediaMuteButton;
448        break;
449    case MediaToggleClosedCaptionsButtonPart:
450        m_value.valueID = CSSValueMediaToggleClosedCaptionsButton;
451        break;
452    case MediaSliderPart:
453        m_value.valueID = CSSValueMediaSlider;
454        break;
455    case MediaSliderThumbPart:
456        m_value.valueID = CSSValueMediaSliderthumb;
457        break;
458    case MediaVolumeSliderContainerPart:
459        m_value.valueID = CSSValueMediaVolumeSliderContainer;
460        break;
461    case MediaVolumeSliderPart:
462        m_value.valueID = CSSValueMediaVolumeSlider;
463        break;
464    case MediaVolumeSliderThumbPart:
465        m_value.valueID = CSSValueMediaVolumeSliderthumb;
466        break;
467    case MediaControlsBackgroundPart:
468        m_value.valueID = CSSValueMediaControlsBackground;
469        break;
470    case MediaControlsFullscreenBackgroundPart:
471        m_value.valueID = CSSValueMediaControlsFullscreenBackground;
472        break;
473    case MediaFullScreenVolumeSliderPart:
474        m_value.valueID = CSSValueMediaFullscreenVolumeSlider;
475        break;
476    case MediaFullScreenVolumeSliderThumbPart:
477        m_value.valueID = CSSValueMediaFullscreenVolumeSliderThumb;
478        break;
479    case MediaCurrentTimePart:
480        m_value.valueID = CSSValueMediaCurrentTimeDisplay;
481        break;
482    case MediaTimeRemainingPart:
483        m_value.valueID = CSSValueMediaTimeRemainingDisplay;
484        break;
485    case MenulistPart:
486        m_value.valueID = CSSValueMenulist;
487        break;
488    case MenulistButtonPart:
489        m_value.valueID = CSSValueMenulistButton;
490        break;
491    case MenulistTextPart:
492        m_value.valueID = CSSValueMenulistText;
493        break;
494    case MenulistTextFieldPart:
495        m_value.valueID = CSSValueMenulistTextfield;
496        break;
497    case MeterPart:
498        m_value.valueID = CSSValueMeter;
499        break;
500    case RelevancyLevelIndicatorPart:
501        m_value.valueID = CSSValueRelevancyLevelIndicator;
502        break;
503    case ContinuousCapacityLevelIndicatorPart:
504        m_value.valueID = CSSValueContinuousCapacityLevelIndicator;
505        break;
506    case DiscreteCapacityLevelIndicatorPart:
507        m_value.valueID = CSSValueDiscreteCapacityLevelIndicator;
508        break;
509    case RatingLevelIndicatorPart:
510        m_value.valueID = CSSValueRatingLevelIndicator;
511        break;
512    case ProgressBarPart:
513        m_value.valueID = CSSValueProgressBar;
514        break;
515    case ProgressBarValuePart:
516        m_value.valueID = CSSValueProgressBarValue;
517        break;
518    case SliderHorizontalPart:
519        m_value.valueID = CSSValueSliderHorizontal;
520        break;
521    case SliderVerticalPart:
522        m_value.valueID = CSSValueSliderVertical;
523        break;
524    case SliderThumbHorizontalPart:
525        m_value.valueID = CSSValueSliderthumbHorizontal;
526        break;
527    case SliderThumbVerticalPart:
528        m_value.valueID = CSSValueSliderthumbVertical;
529        break;
530    case CaretPart:
531        m_value.valueID = CSSValueCaret;
532        break;
533    case SearchFieldPart:
534        m_value.valueID = CSSValueSearchfield;
535        break;
536    case SearchFieldDecorationPart:
537        m_value.valueID = CSSValueSearchfieldDecoration;
538        break;
539    case SearchFieldResultsDecorationPart:
540        m_value.valueID = CSSValueSearchfieldResultsDecoration;
541        break;
542    case SearchFieldCancelButtonPart:
543        m_value.valueID = CSSValueSearchfieldCancelButton;
544        break;
545    case TextFieldPart:
546        m_value.valueID = CSSValueTextfield;
547        break;
548    case TextAreaPart:
549        m_value.valueID = CSSValueTextarea;
550        break;
551    case CapsLockIndicatorPart:
552        m_value.valueID = CSSValueCapsLockIndicator;
553        break;
554    }
555}
556
557template<> inline CSSPrimitiveValue::operator ControlPart() const
558{
559    ASSERT(isValueID());
560    if (m_value.valueID == CSSValueNone)
561        return NoControlPart;
562    return ControlPart(m_value.valueID - CSSValueCheckbox + 1);
563}
564
565template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBackfaceVisibility e)
566    : CSSValue(PrimitiveClass)
567{
568    m_primitiveUnitType = CSS_VALUE_ID;
569    switch (e) {
570    case BackfaceVisibilityVisible:
571        m_value.valueID = CSSValueVisible;
572        break;
573    case BackfaceVisibilityHidden:
574        m_value.valueID = CSSValueHidden;
575        break;
576    }
577}
578
579template<> inline CSSPrimitiveValue::operator EBackfaceVisibility() const
580{
581    ASSERT(isValueID());
582    switch (m_value.valueID) {
583    case CSSValueVisible:
584        return BackfaceVisibilityVisible;
585    case CSSValueHidden:
586        return BackfaceVisibilityHidden;
587    default:
588        break;
589    }
590
591    ASSERT_NOT_REACHED();
592    return BackfaceVisibilityHidden;
593}
594
595
596template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFillAttachment e)
597    : CSSValue(PrimitiveClass)
598{
599    m_primitiveUnitType = CSS_VALUE_ID;
600    switch (e) {
601    case ScrollBackgroundAttachment:
602        m_value.valueID = CSSValueScroll;
603        break;
604    case LocalBackgroundAttachment:
605        m_value.valueID = CSSValueLocal;
606        break;
607    case FixedBackgroundAttachment:
608        m_value.valueID = CSSValueFixed;
609        break;
610    }
611}
612
613template<> inline CSSPrimitiveValue::operator EFillAttachment() const
614{
615    ASSERT(isValueID());
616    switch (m_value.valueID) {
617    case CSSValueScroll:
618        return ScrollBackgroundAttachment;
619    case CSSValueLocal:
620        return LocalBackgroundAttachment;
621    case CSSValueFixed:
622        return FixedBackgroundAttachment;
623    default:
624        break;
625    }
626
627    ASSERT_NOT_REACHED();
628    return ScrollBackgroundAttachment;
629}
630
631template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFillBox e)
632    : CSSValue(PrimitiveClass)
633{
634    m_primitiveUnitType = CSS_VALUE_ID;
635    switch (e) {
636    case BorderFillBox:
637        m_value.valueID = CSSValueBorderBox;
638        break;
639    case PaddingFillBox:
640        m_value.valueID = CSSValuePaddingBox;
641        break;
642    case ContentFillBox:
643        m_value.valueID = CSSValueContentBox;
644        break;
645    case TextFillBox:
646        m_value.valueID = CSSValueText;
647        break;
648    }
649}
650
651template<> inline CSSPrimitiveValue::operator EFillBox() const
652{
653    ASSERT(isValueID());
654    switch (m_value.valueID) {
655    case CSSValueBorder:
656    case CSSValueBorderBox:
657        return BorderFillBox;
658    case CSSValuePadding:
659    case CSSValuePaddingBox:
660        return PaddingFillBox;
661    case CSSValueContent:
662    case CSSValueContentBox:
663        return ContentFillBox;
664    case CSSValueText:
665    case CSSValueWebkitText:
666        return TextFillBox;
667    default:
668        break;
669    }
670
671    ASSERT_NOT_REACHED();
672    return BorderFillBox;
673}
674
675template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFillRepeat e)
676    : CSSValue(PrimitiveClass)
677{
678    m_primitiveUnitType = CSS_VALUE_ID;
679    switch (e) {
680    case RepeatFill:
681        m_value.valueID = CSSValueRepeat;
682        break;
683    case NoRepeatFill:
684        m_value.valueID = CSSValueNoRepeat;
685        break;
686    case RoundFill:
687        m_value.valueID = CSSValueRound;
688        break;
689    case SpaceFill:
690        m_value.valueID = CSSValueSpace;
691        break;
692    }
693}
694
695template<> inline CSSPrimitiveValue::operator EFillRepeat() const
696{
697    ASSERT(isValueID());
698    switch (m_value.valueID) {
699    case CSSValueRepeat:
700        return RepeatFill;
701    case CSSValueNoRepeat:
702        return NoRepeatFill;
703    case CSSValueRound:
704        return RoundFill;
705    case CSSValueSpace:
706        return SpaceFill;
707    default:
708        break;
709    }
710
711    ASSERT_NOT_REACHED();
712    return RepeatFill;
713}
714
715template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxPack e)
716    : CSSValue(PrimitiveClass)
717{
718    m_primitiveUnitType = CSS_VALUE_ID;
719    switch (e) {
720    case Start:
721        m_value.valueID = CSSValueStart;
722        break;
723    case Center:
724        m_value.valueID = CSSValueCenter;
725        break;
726    case End:
727        m_value.valueID = CSSValueEnd;
728        break;
729    case Justify:
730        m_value.valueID = CSSValueJustify;
731        break;
732    }
733}
734
735template<> inline CSSPrimitiveValue::operator EBoxPack() const
736{
737    ASSERT(isValueID());
738    switch (m_value.valueID) {
739    case CSSValueStart:
740        return Start;
741    case CSSValueEnd:
742        return End;
743    case CSSValueCenter:
744        return Center;
745    case CSSValueJustify:
746        return Justify;
747    default:
748        break;
749    }
750
751    ASSERT_NOT_REACHED();
752    return Justify;
753}
754
755template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxAlignment e)
756    : CSSValue(PrimitiveClass)
757{
758    m_primitiveUnitType = CSS_VALUE_ID;
759    switch (e) {
760    case BSTRETCH:
761        m_value.valueID = CSSValueStretch;
762        break;
763    case BSTART:
764        m_value.valueID = CSSValueStart;
765        break;
766    case BCENTER:
767        m_value.valueID = CSSValueCenter;
768        break;
769    case BEND:
770        m_value.valueID = CSSValueEnd;
771        break;
772    case BBASELINE:
773        m_value.valueID = CSSValueBaseline;
774        break;
775    }
776}
777
778template<> inline CSSPrimitiveValue::operator EBoxAlignment() const
779{
780    ASSERT(isValueID());
781    switch (m_value.valueID) {
782    case CSSValueStretch:
783        return BSTRETCH;
784    case CSSValueStart:
785        return BSTART;
786    case CSSValueEnd:
787        return BEND;
788    case CSSValueCenter:
789        return BCENTER;
790    case CSSValueBaseline:
791        return BBASELINE;
792    default:
793        break;
794    }
795
796    ASSERT_NOT_REACHED();
797    return BSTRETCH;
798}
799
800template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxDecorationBreak e)
801    : CSSValue(PrimitiveClass)
802{
803    m_primitiveUnitType = CSS_VALUE_ID;
804    switch (e) {
805    case DSLICE:
806        m_value.valueID = CSSValueSlice;
807        break;
808    case DCLONE:
809        m_value.valueID = CSSValueClone;
810        break;
811    }
812}
813
814template<> inline CSSPrimitiveValue::operator EBoxDecorationBreak() const
815{
816    ASSERT(isValueID());
817    switch (m_value.valueID) {
818    case CSSValueSlice:
819        return DSLICE;
820    case CSSValueClone:
821        return DCLONE;
822    default:
823        break;
824    }
825
826    ASSERT_NOT_REACHED();
827    return DSLICE;
828}
829
830template<> inline CSSPrimitiveValue::CSSPrimitiveValue(BackgroundEdgeOrigin e)
831    : CSSValue(PrimitiveClass)
832{
833    m_primitiveUnitType = CSS_VALUE_ID;
834    switch (e) {
835    case TopEdge:
836        m_value.valueID = CSSValueTop;
837        break;
838    case RightEdge:
839        m_value.valueID = CSSValueRight;
840        break;
841    case BottomEdge:
842        m_value.valueID = CSSValueBottom;
843        break;
844    case LeftEdge:
845        m_value.valueID = CSSValueLeft;
846        break;
847    }
848}
849
850template<> inline CSSPrimitiveValue::operator BackgroundEdgeOrigin() const
851{
852    ASSERT(isValueID());
853    switch (m_value.valueID) {
854    case CSSValueTop:
855        return TopEdge;
856    case CSSValueRight:
857        return RightEdge;
858    case CSSValueBottom:
859        return BottomEdge;
860    case CSSValueLeft:
861        return LeftEdge;
862    default:
863        break;
864    }
865
866    ASSERT_NOT_REACHED();
867    return TopEdge;
868}
869
870template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxSizing e)
871    : CSSValue(PrimitiveClass)
872{
873    m_primitiveUnitType = CSS_VALUE_ID;
874    switch (e) {
875    case BORDER_BOX:
876        m_value.valueID = CSSValueBorderBox;
877        break;
878    case CONTENT_BOX:
879        m_value.valueID = CSSValueContentBox;
880        break;
881    }
882}
883
884template<> inline CSSPrimitiveValue::operator EBoxSizing() const
885{
886    ASSERT(isValueID());
887    switch (m_value.valueID) {
888    case CSSValueBorderBox:
889        return BORDER_BOX;
890    case CSSValueContentBox:
891        return CONTENT_BOX;
892    default:
893        break;
894    }
895
896    ASSERT_NOT_REACHED();
897    return BORDER_BOX;
898}
899
900template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxDirection e)
901    : CSSValue(PrimitiveClass)
902{
903    m_primitiveUnitType = CSS_VALUE_ID;
904    switch (e) {
905    case BNORMAL:
906        m_value.valueID = CSSValueNormal;
907        break;
908    case BREVERSE:
909        m_value.valueID = CSSValueReverse;
910        break;
911    }
912}
913
914template<> inline CSSPrimitiveValue::operator EBoxDirection() const
915{
916    ASSERT(isValueID());
917    switch (m_value.valueID) {
918    case CSSValueNormal:
919        return BNORMAL;
920    case CSSValueReverse:
921        return BREVERSE;
922    default:
923        break;
924    }
925
926    ASSERT_NOT_REACHED();
927    return BNORMAL;
928}
929
930template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxLines e)
931    : CSSValue(PrimitiveClass)
932{
933    m_primitiveUnitType = CSS_VALUE_ID;
934    switch (e) {
935    case SINGLE:
936        m_value.valueID = CSSValueSingle;
937        break;
938    case MULTIPLE:
939        m_value.valueID = CSSValueMultiple;
940        break;
941    }
942}
943
944template<> inline CSSPrimitiveValue::operator EBoxLines() const
945{
946    ASSERT(isValueID());
947    switch (m_value.valueID) {
948    case CSSValueSingle:
949        return SINGLE;
950    case CSSValueMultiple:
951        return MULTIPLE;
952    default:
953        break;
954    }
955
956    ASSERT_NOT_REACHED();
957    return SINGLE;
958}
959
960template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBoxOrient e)
961    : CSSValue(PrimitiveClass)
962{
963    m_primitiveUnitType = CSS_VALUE_ID;
964    switch (e) {
965    case HORIZONTAL:
966        m_value.valueID = CSSValueHorizontal;
967        break;
968    case VERTICAL:
969        m_value.valueID = CSSValueVertical;
970        break;
971    }
972}
973
974template<> inline CSSPrimitiveValue::operator EBoxOrient() const
975{
976    ASSERT(isValueID());
977    switch (m_value.valueID) {
978    case CSSValueHorizontal:
979    case CSSValueInlineAxis:
980        return HORIZONTAL;
981    case CSSValueVertical:
982    case CSSValueBlockAxis:
983        return VERTICAL;
984    default:
985        break;
986    }
987
988    ASSERT_NOT_REACHED();
989    return HORIZONTAL;
990}
991
992template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ECaptionSide e)
993    : CSSValue(PrimitiveClass)
994{
995    m_primitiveUnitType = CSS_VALUE_ID;
996    switch (e) {
997    case CAPLEFT:
998        m_value.valueID = CSSValueLeft;
999        break;
1000    case CAPRIGHT:
1001        m_value.valueID = CSSValueRight;
1002        break;
1003    case CAPTOP:
1004        m_value.valueID = CSSValueTop;
1005        break;
1006    case CAPBOTTOM:
1007        m_value.valueID = CSSValueBottom;
1008        break;
1009    }
1010}
1011
1012template<> inline CSSPrimitiveValue::operator ECaptionSide() const
1013{
1014    ASSERT(isValueID());
1015    switch (m_value.valueID) {
1016    case CSSValueLeft:
1017        return CAPLEFT;
1018    case CSSValueRight:
1019        return CAPRIGHT;
1020    case CSSValueTop:
1021        return CAPTOP;
1022    case CSSValueBottom:
1023        return CAPBOTTOM;
1024    default:
1025        break;
1026    }
1027
1028    ASSERT_NOT_REACHED();
1029    return CAPTOP;
1030}
1031
1032template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EClear e)
1033    : CSSValue(PrimitiveClass)
1034{
1035    m_primitiveUnitType = CSS_VALUE_ID;
1036    switch (e) {
1037    case CNONE:
1038        m_value.valueID = CSSValueNone;
1039        break;
1040    case CLEFT:
1041        m_value.valueID = CSSValueLeft;
1042        break;
1043    case CRIGHT:
1044        m_value.valueID = CSSValueRight;
1045        break;
1046    case CBOTH:
1047        m_value.valueID = CSSValueBoth;
1048        break;
1049    }
1050}
1051
1052template<> inline CSSPrimitiveValue::operator EClear() const
1053{
1054    ASSERT(isValueID());
1055    switch (m_value.valueID) {
1056    case CSSValueNone:
1057        return CNONE;
1058    case CSSValueLeft:
1059        return CLEFT;
1060    case CSSValueRight:
1061        return CRIGHT;
1062    case CSSValueBoth:
1063        return CBOTH;
1064    default:
1065        break;
1066    }
1067
1068    ASSERT_NOT_REACHED();
1069    return CNONE;
1070}
1071
1072template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ECursor e)
1073    : CSSValue(PrimitiveClass)
1074{
1075    m_primitiveUnitType = CSS_VALUE_ID;
1076    switch (e) {
1077    case CURSOR_AUTO:
1078        m_value.valueID = CSSValueAuto;
1079        break;
1080    case CURSOR_CROSS:
1081        m_value.valueID = CSSValueCrosshair;
1082        break;
1083    case CURSOR_DEFAULT:
1084        m_value.valueID = CSSValueDefault;
1085        break;
1086    case CURSOR_POINTER:
1087        m_value.valueID = CSSValuePointer;
1088        break;
1089    case CURSOR_MOVE:
1090        m_value.valueID = CSSValueMove;
1091        break;
1092    case CURSOR_CELL:
1093        m_value.valueID = CSSValueCell;
1094        break;
1095    case CURSOR_VERTICAL_TEXT:
1096        m_value.valueID = CSSValueVerticalText;
1097        break;
1098    case CURSOR_CONTEXT_MENU:
1099        m_value.valueID = CSSValueContextMenu;
1100        break;
1101    case CURSOR_ALIAS:
1102        m_value.valueID = CSSValueAlias;
1103        break;
1104    case CURSOR_COPY:
1105        m_value.valueID = CSSValueCopy;
1106        break;
1107    case CURSOR_NONE:
1108        m_value.valueID = CSSValueNone;
1109        break;
1110    case CURSOR_PROGRESS:
1111        m_value.valueID = CSSValueProgress;
1112        break;
1113    case CURSOR_NO_DROP:
1114        m_value.valueID = CSSValueNoDrop;
1115        break;
1116    case CURSOR_NOT_ALLOWED:
1117        m_value.valueID = CSSValueNotAllowed;
1118        break;
1119    case CURSOR_ZOOM_IN:
1120        m_value.valueID = CSSValueZoomIn;
1121        break;
1122    case CURSOR_ZOOM_OUT:
1123        m_value.valueID = CSSValueZoomOut;
1124        break;
1125    case CURSOR_E_RESIZE:
1126        m_value.valueID = CSSValueEResize;
1127        break;
1128    case CURSOR_NE_RESIZE:
1129        m_value.valueID = CSSValueNeResize;
1130        break;
1131    case CURSOR_NW_RESIZE:
1132        m_value.valueID = CSSValueNwResize;
1133        break;
1134    case CURSOR_N_RESIZE:
1135        m_value.valueID = CSSValueNResize;
1136        break;
1137    case CURSOR_SE_RESIZE:
1138        m_value.valueID = CSSValueSeResize;
1139        break;
1140    case CURSOR_SW_RESIZE:
1141        m_value.valueID = CSSValueSwResize;
1142        break;
1143    case CURSOR_S_RESIZE:
1144        m_value.valueID = CSSValueSResize;
1145        break;
1146    case CURSOR_W_RESIZE:
1147        m_value.valueID = CSSValueWResize;
1148        break;
1149    case CURSOR_EW_RESIZE:
1150        m_value.valueID = CSSValueEwResize;
1151        break;
1152    case CURSOR_NS_RESIZE:
1153        m_value.valueID = CSSValueNsResize;
1154        break;
1155    case CURSOR_NESW_RESIZE:
1156        m_value.valueID = CSSValueNeswResize;
1157        break;
1158    case CURSOR_NWSE_RESIZE:
1159        m_value.valueID = CSSValueNwseResize;
1160        break;
1161    case CURSOR_COL_RESIZE:
1162        m_value.valueID = CSSValueColResize;
1163        break;
1164    case CURSOR_ROW_RESIZE:
1165        m_value.valueID = CSSValueRowResize;
1166        break;
1167    case CURSOR_TEXT:
1168        m_value.valueID = CSSValueText;
1169        break;
1170    case CURSOR_WAIT:
1171        m_value.valueID = CSSValueWait;
1172        break;
1173    case CURSOR_HELP:
1174        m_value.valueID = CSSValueHelp;
1175        break;
1176    case CURSOR_ALL_SCROLL:
1177        m_value.valueID = CSSValueAllScroll;
1178        break;
1179    case CURSOR_WEBKIT_GRAB:
1180        m_value.valueID = CSSValueWebkitGrab;
1181        break;
1182    case CURSOR_WEBKIT_GRABBING:
1183        m_value.valueID = CSSValueWebkitGrabbing;
1184        break;
1185    }
1186}
1187
1188template<> inline CSSPrimitiveValue::operator ECursor() const
1189{
1190    ASSERT(isValueID());
1191    switch (m_value.valueID) {
1192    case CSSValueCopy:
1193        return CURSOR_COPY;
1194    case CSSValueWebkitZoomIn:
1195        return CURSOR_ZOOM_IN;
1196    case CSSValueWebkitZoomOut:
1197        return CURSOR_ZOOM_OUT;
1198    case CSSValueNone:
1199        return CURSOR_NONE;
1200    default:
1201        return static_cast<ECursor>(m_value.valueID - CSSValueAuto);
1202    }
1203}
1204
1205template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EDisplay e)
1206    : CSSValue(PrimitiveClass)
1207{
1208    m_primitiveUnitType = CSS_VALUE_ID;
1209    switch (e) {
1210    case INLINE:
1211        m_value.valueID = CSSValueInline;
1212        break;
1213    case BLOCK:
1214        m_value.valueID = CSSValueBlock;
1215        break;
1216    case LIST_ITEM:
1217        m_value.valueID = CSSValueListItem;
1218        break;
1219    case INLINE_BLOCK:
1220        m_value.valueID = CSSValueInlineBlock;
1221        break;
1222    case TABLE:
1223        m_value.valueID = CSSValueTable;
1224        break;
1225    case INLINE_TABLE:
1226        m_value.valueID = CSSValueInlineTable;
1227        break;
1228    case TABLE_ROW_GROUP:
1229        m_value.valueID = CSSValueTableRowGroup;
1230        break;
1231    case TABLE_HEADER_GROUP:
1232        m_value.valueID = CSSValueTableHeaderGroup;
1233        break;
1234    case TABLE_FOOTER_GROUP:
1235        m_value.valueID = CSSValueTableFooterGroup;
1236        break;
1237    case TABLE_ROW:
1238        m_value.valueID = CSSValueTableRow;
1239        break;
1240    case TABLE_COLUMN_GROUP:
1241        m_value.valueID = CSSValueTableColumnGroup;
1242        break;
1243    case TABLE_COLUMN:
1244        m_value.valueID = CSSValueTableColumn;
1245        break;
1246    case TABLE_CELL:
1247        m_value.valueID = CSSValueTableCell;
1248        break;
1249    case TABLE_CAPTION:
1250        m_value.valueID = CSSValueTableCaption;
1251        break;
1252    case BOX:
1253        m_value.valueID = CSSValueWebkitBox;
1254        break;
1255    case INLINE_BOX:
1256        m_value.valueID = CSSValueWebkitInlineBox;
1257        break;
1258    case FLEX:
1259        m_value.valueID = CSSValueFlex;
1260        break;
1261    case INLINE_FLEX:
1262        m_value.valueID = CSSValueInlineFlex;
1263        break;
1264    case GRID:
1265        m_value.valueID = CSSValueGrid;
1266        break;
1267    case INLINE_GRID:
1268        m_value.valueID = CSSValueInlineGrid;
1269        break;
1270    case NONE:
1271        m_value.valueID = CSSValueNone;
1272        break;
1273    }
1274}
1275
1276template<> inline CSSPrimitiveValue::operator EDisplay() const
1277{
1278    ASSERT(isValueID());
1279    if (m_value.valueID == CSSValueNone)
1280        return NONE;
1281
1282    if (m_value.valueID == CSSValueWebkitFlex)
1283        return FLEX;
1284    if (m_value.valueID == CSSValueWebkitInlineFlex)
1285        return INLINE_FLEX;
1286
1287    EDisplay display = static_cast<EDisplay>(m_value.valueID - CSSValueInline);
1288    ASSERT(display >= INLINE && display <= NONE);
1289    return display;
1290}
1291
1292template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EEmptyCell e)
1293    : CSSValue(PrimitiveClass)
1294{
1295    m_primitiveUnitType = CSS_VALUE_ID;
1296    switch (e) {
1297    case SHOW:
1298        m_value.valueID = CSSValueShow;
1299        break;
1300    case HIDE:
1301        m_value.valueID = CSSValueHide;
1302        break;
1303    }
1304}
1305
1306template<> inline CSSPrimitiveValue::operator EEmptyCell() const
1307{
1308    ASSERT(isValueID());
1309    switch (m_value.valueID) {
1310    case CSSValueShow:
1311        return SHOW;
1312    case CSSValueHide:
1313        return HIDE;
1314    default:
1315        break;
1316    }
1317
1318    ASSERT_NOT_REACHED();
1319    return SHOW;
1320}
1321
1322template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EJustifyContent e)
1323    : CSSValue(PrimitiveClass)
1324{
1325    m_primitiveUnitType = CSS_VALUE_ID;
1326    switch (e) {
1327    case JustifyFlexStart:
1328        m_value.valueID = CSSValueFlexStart;
1329        break;
1330    case JustifyFlexEnd:
1331        m_value.valueID = CSSValueFlexEnd;
1332        break;
1333    case JustifyCenter:
1334        m_value.valueID = CSSValueCenter;
1335        break;
1336    case JustifySpaceBetween:
1337        m_value.valueID = CSSValueSpaceBetween;
1338        break;
1339    case JustifySpaceAround:
1340        m_value.valueID = CSSValueSpaceAround;
1341        break;
1342    }
1343}
1344
1345template<> inline CSSPrimitiveValue::operator EJustifyContent() const
1346{
1347    ASSERT(isValueID());
1348    switch (m_value.valueID) {
1349    case CSSValueFlexStart:
1350        return JustifyFlexStart;
1351    case CSSValueFlexEnd:
1352        return JustifyFlexEnd;
1353    case CSSValueCenter:
1354        return JustifyCenter;
1355    case CSSValueSpaceBetween:
1356        return JustifySpaceBetween;
1357    case CSSValueSpaceAround:
1358        return JustifySpaceAround;
1359    default:
1360        break;
1361    }
1362
1363    ASSERT_NOT_REACHED();
1364    return JustifyFlexStart;
1365}
1366
1367template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFlexDirection e)
1368    : CSSValue(PrimitiveClass)
1369{
1370    m_primitiveUnitType = CSS_VALUE_ID;
1371    switch (e) {
1372    case FlowRow:
1373        m_value.valueID = CSSValueRow;
1374        break;
1375    case FlowRowReverse:
1376        m_value.valueID = CSSValueRowReverse;
1377        break;
1378    case FlowColumn:
1379        m_value.valueID = CSSValueColumn;
1380        break;
1381    case FlowColumnReverse:
1382        m_value.valueID = CSSValueColumnReverse;
1383        break;
1384    }
1385}
1386
1387template<> inline CSSPrimitiveValue::operator EFlexDirection() const
1388{
1389    ASSERT(isValueID());
1390    switch (m_value.valueID) {
1391    case CSSValueRow:
1392        return FlowRow;
1393    case CSSValueRowReverse:
1394        return FlowRowReverse;
1395    case CSSValueColumn:
1396        return FlowColumn;
1397    case CSSValueColumnReverse:
1398        return FlowColumnReverse;
1399    default:
1400        break;
1401    }
1402
1403    ASSERT_NOT_REACHED();
1404    return FlowRow;
1405}
1406
1407template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EAlignContent e)
1408    : CSSValue(PrimitiveClass)
1409{
1410    m_primitiveUnitType = CSS_VALUE_ID;
1411    switch (e) {
1412    case AlignContentFlexStart:
1413        m_value.valueID = CSSValueFlexStart;
1414        break;
1415    case AlignContentFlexEnd:
1416        m_value.valueID = CSSValueFlexEnd;
1417        break;
1418    case AlignContentCenter:
1419        m_value.valueID = CSSValueCenter;
1420        break;
1421    case AlignContentSpaceBetween:
1422        m_value.valueID = CSSValueSpaceBetween;
1423        break;
1424    case AlignContentSpaceAround:
1425        m_value.valueID = CSSValueSpaceAround;
1426        break;
1427    case AlignContentStretch:
1428        m_value.valueID = CSSValueStretch;
1429        break;
1430    }
1431}
1432
1433template<> inline CSSPrimitiveValue::operator EAlignContent() const
1434{
1435    ASSERT(isValueID());
1436    switch (m_value.valueID) {
1437    case CSSValueFlexStart:
1438        return AlignContentFlexStart;
1439    case CSSValueFlexEnd:
1440        return AlignContentFlexEnd;
1441    case CSSValueCenter:
1442        return AlignContentCenter;
1443    case CSSValueSpaceBetween:
1444        return AlignContentSpaceBetween;
1445    case CSSValueSpaceAround:
1446        return AlignContentSpaceAround;
1447    case CSSValueStretch:
1448        return AlignContentStretch;
1449    default:
1450        break;
1451    }
1452
1453    ASSERT_NOT_REACHED();
1454    return AlignContentStretch;
1455}
1456
1457template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFlexWrap e)
1458    : CSSValue(PrimitiveClass)
1459{
1460    m_primitiveUnitType = CSS_VALUE_ID;
1461    switch (e) {
1462    case FlexNoWrap:
1463        m_value.valueID = CSSValueNowrap;
1464        break;
1465    case FlexWrap:
1466        m_value.valueID = CSSValueWrap;
1467        break;
1468    case FlexWrapReverse:
1469        m_value.valueID = CSSValueWrapReverse;
1470        break;
1471    }
1472}
1473
1474template<> inline CSSPrimitiveValue::operator EFlexWrap() const
1475{
1476    ASSERT(isValueID());
1477    switch (m_value.valueID) {
1478    case CSSValueNowrap:
1479        return FlexNoWrap;
1480    case CSSValueWrap:
1481        return FlexWrap;
1482    case CSSValueWrapReverse:
1483        return FlexWrapReverse;
1484    default:
1485        break;
1486    }
1487
1488    ASSERT_NOT_REACHED();
1489    return FlexNoWrap;
1490}
1491
1492template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFloat e)
1493    : CSSValue(PrimitiveClass)
1494{
1495    m_primitiveUnitType = CSS_VALUE_ID;
1496    switch (e) {
1497    case NoFloat:
1498        m_value.valueID = CSSValueNone;
1499        break;
1500    case LeftFloat:
1501        m_value.valueID = CSSValueLeft;
1502        break;
1503    case RightFloat:
1504        m_value.valueID = CSSValueRight;
1505        break;
1506    }
1507}
1508
1509template<> inline CSSPrimitiveValue::operator EFloat() const
1510{
1511    ASSERT(isValueID());
1512    switch (m_value.valueID) {
1513    case CSSValueLeft:
1514        return LeftFloat;
1515    case CSSValueRight:
1516        return RightFloat;
1517    case CSSValueNone:
1518    case CSSValueCenter: // Non-standard CSS value.
1519        return NoFloat;
1520    default:
1521        break;
1522    }
1523
1524    ASSERT_NOT_REACHED();
1525    return NoFloat;
1526}
1527
1528template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineBreak e)
1529    : CSSValue(PrimitiveClass)
1530{
1531    m_primitiveUnitType = CSS_VALUE_ID;
1532    switch (e) {
1533    case LineBreakAuto:
1534        m_value.valueID = CSSValueAuto;
1535        break;
1536    case LineBreakLoose:
1537        m_value.valueID = CSSValueLoose;
1538        break;
1539    case LineBreakNormal:
1540        m_value.valueID = CSSValueNormal;
1541        break;
1542    case LineBreakStrict:
1543        m_value.valueID = CSSValueStrict;
1544        break;
1545    case LineBreakAfterWhiteSpace:
1546        m_value.valueID = CSSValueAfterWhiteSpace;
1547        break;
1548    }
1549}
1550
1551template<> inline CSSPrimitiveValue::operator LineBreak() const
1552{
1553    ASSERT(isValueID());
1554    switch (m_value.valueID) {
1555    case CSSValueAuto:
1556        return LineBreakAuto;
1557    case CSSValueLoose:
1558        return LineBreakLoose;
1559    case CSSValueNormal:
1560        return LineBreakNormal;
1561    case CSSValueStrict:
1562        return LineBreakStrict;
1563    case CSSValueAfterWhiteSpace:
1564        return LineBreakAfterWhiteSpace;
1565    default:
1566        break;
1567    }
1568
1569    ASSERT_NOT_REACHED();
1570    return LineBreakAuto;
1571}
1572
1573template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EListStylePosition e)
1574    : CSSValue(PrimitiveClass)
1575{
1576    m_primitiveUnitType = CSS_VALUE_ID;
1577    switch (e) {
1578    case OUTSIDE:
1579        m_value.valueID = CSSValueOutside;
1580        break;
1581    case INSIDE:
1582        m_value.valueID = CSSValueInside;
1583        break;
1584    }
1585}
1586
1587template<> inline CSSPrimitiveValue::operator EListStylePosition() const
1588{
1589    ASSERT(isValueID());
1590    switch (m_value.valueID) {
1591    case CSSValueOutside:
1592        return OUTSIDE;
1593    case CSSValueInside:
1594        return INSIDE;
1595    default:
1596        break;
1597    }
1598
1599    ASSERT_NOT_REACHED();
1600    return OUTSIDE;
1601}
1602
1603template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EListStyleType e)
1604    : CSSValue(PrimitiveClass)
1605{
1606    m_primitiveUnitType = CSS_VALUE_ID;
1607    switch (e) {
1608    case Afar:
1609        m_value.valueID = CSSValueAfar;
1610        break;
1611    case Amharic:
1612        m_value.valueID = CSSValueAmharic;
1613        break;
1614    case AmharicAbegede:
1615        m_value.valueID = CSSValueAmharicAbegede;
1616        break;
1617    case ArabicIndic:
1618        m_value.valueID = CSSValueArabicIndic;
1619        break;
1620    case Armenian:
1621        m_value.valueID = CSSValueArmenian;
1622        break;
1623    case Asterisks:
1624        m_value.valueID = CSSValueAsterisks;
1625        break;
1626    case BinaryListStyle:
1627        m_value.valueID = CSSValueBinary;
1628        break;
1629    case Bengali:
1630        m_value.valueID = CSSValueBengali;
1631        break;
1632    case Cambodian:
1633        m_value.valueID = CSSValueCambodian;
1634        break;
1635    case Circle:
1636        m_value.valueID = CSSValueCircle;
1637        break;
1638    case CjkEarthlyBranch:
1639        m_value.valueID = CSSValueCjkEarthlyBranch;
1640        break;
1641    case CjkHeavenlyStem:
1642        m_value.valueID = CSSValueCjkHeavenlyStem;
1643        break;
1644    case CJKIdeographic:
1645        m_value.valueID = CSSValueCjkIdeographic;
1646        break;
1647    case DecimalLeadingZero:
1648        m_value.valueID = CSSValueDecimalLeadingZero;
1649        break;
1650    case DecimalListStyle:
1651        m_value.valueID = CSSValueDecimal;
1652        break;
1653    case Devanagari:
1654        m_value.valueID = CSSValueDevanagari;
1655        break;
1656    case Disc:
1657        m_value.valueID = CSSValueDisc;
1658        break;
1659    case Ethiopic:
1660        m_value.valueID = CSSValueEthiopic;
1661        break;
1662    case EthiopicAbegede:
1663        m_value.valueID = CSSValueEthiopicAbegede;
1664        break;
1665    case EthiopicAbegedeAmEt:
1666        m_value.valueID = CSSValueEthiopicAbegedeAmEt;
1667        break;
1668    case EthiopicAbegedeGez:
1669        m_value.valueID = CSSValueEthiopicAbegedeGez;
1670        break;
1671    case EthiopicAbegedeTiEr:
1672        m_value.valueID = CSSValueEthiopicAbegedeTiEr;
1673        break;
1674    case EthiopicAbegedeTiEt:
1675        m_value.valueID = CSSValueEthiopicAbegedeTiEt;
1676        break;
1677    case EthiopicHalehameAaEr:
1678        m_value.valueID = CSSValueEthiopicHalehameAaEr;
1679        break;
1680    case EthiopicHalehameAaEt:
1681        m_value.valueID = CSSValueEthiopicHalehameAaEt;
1682        break;
1683    case EthiopicHalehameAmEt:
1684        m_value.valueID = CSSValueEthiopicHalehameAmEt;
1685        break;
1686    case EthiopicHalehameGez:
1687        m_value.valueID = CSSValueEthiopicHalehameGez;
1688        break;
1689    case EthiopicHalehameOmEt:
1690        m_value.valueID = CSSValueEthiopicHalehameOmEt;
1691        break;
1692    case EthiopicHalehameSidEt:
1693        m_value.valueID = CSSValueEthiopicHalehameSidEt;
1694        break;
1695    case EthiopicHalehameSoEt:
1696        m_value.valueID = CSSValueEthiopicHalehameSoEt;
1697        break;
1698    case EthiopicHalehameTiEr:
1699        m_value.valueID = CSSValueEthiopicHalehameTiEr;
1700        break;
1701    case EthiopicHalehameTiEt:
1702        m_value.valueID = CSSValueEthiopicHalehameTiEt;
1703        break;
1704    case EthiopicHalehameTig:
1705        m_value.valueID = CSSValueEthiopicHalehameTig;
1706        break;
1707    case Footnotes:
1708        m_value.valueID = CSSValueFootnotes;
1709        break;
1710    case Georgian:
1711        m_value.valueID = CSSValueGeorgian;
1712        break;
1713    case Gujarati:
1714        m_value.valueID = CSSValueGujarati;
1715        break;
1716    case Gurmukhi:
1717        m_value.valueID = CSSValueGurmukhi;
1718        break;
1719    case Hangul:
1720        m_value.valueID = CSSValueHangul;
1721        break;
1722    case HangulConsonant:
1723        m_value.valueID = CSSValueHangulConsonant;
1724        break;
1725    case Hebrew:
1726        m_value.valueID = CSSValueHebrew;
1727        break;
1728    case Hiragana:
1729        m_value.valueID = CSSValueHiragana;
1730        break;
1731    case HiraganaIroha:
1732        m_value.valueID = CSSValueHiraganaIroha;
1733        break;
1734    case Kannada:
1735        m_value.valueID = CSSValueKannada;
1736        break;
1737    case Katakana:
1738        m_value.valueID = CSSValueKatakana;
1739        break;
1740    case KatakanaIroha:
1741        m_value.valueID = CSSValueKatakanaIroha;
1742        break;
1743    case Khmer:
1744        m_value.valueID = CSSValueKhmer;
1745        break;
1746    case Lao:
1747        m_value.valueID = CSSValueLao;
1748        break;
1749    case LowerAlpha:
1750        m_value.valueID = CSSValueLowerAlpha;
1751        break;
1752    case LowerArmenian:
1753        m_value.valueID = CSSValueLowerArmenian;
1754        break;
1755    case LowerGreek:
1756        m_value.valueID = CSSValueLowerGreek;
1757        break;
1758    case LowerHexadecimal:
1759        m_value.valueID = CSSValueLowerHexadecimal;
1760        break;
1761    case LowerLatin:
1762        m_value.valueID = CSSValueLowerLatin;
1763        break;
1764    case LowerNorwegian:
1765        m_value.valueID = CSSValueLowerNorwegian;
1766        break;
1767    case LowerRoman:
1768        m_value.valueID = CSSValueLowerRoman;
1769        break;
1770    case Malayalam:
1771        m_value.valueID = CSSValueMalayalam;
1772        break;
1773    case Mongolian:
1774        m_value.valueID = CSSValueMongolian;
1775        break;
1776    case Myanmar:
1777        m_value.valueID = CSSValueMyanmar;
1778        break;
1779    case NoneListStyle:
1780        m_value.valueID = CSSValueNone;
1781        break;
1782    case Octal:
1783        m_value.valueID = CSSValueOctal;
1784        break;
1785    case Oriya:
1786        m_value.valueID = CSSValueOriya;
1787        break;
1788    case Oromo:
1789        m_value.valueID = CSSValueOromo;
1790        break;
1791    case Persian:
1792        m_value.valueID = CSSValuePersian;
1793        break;
1794    case Sidama:
1795        m_value.valueID = CSSValueSidama;
1796        break;
1797    case Somali:
1798        m_value.valueID = CSSValueSomali;
1799        break;
1800    case Square:
1801        m_value.valueID = CSSValueSquare;
1802        break;
1803    case Telugu:
1804        m_value.valueID = CSSValueTelugu;
1805        break;
1806    case Thai:
1807        m_value.valueID = CSSValueThai;
1808        break;
1809    case Tibetan:
1810        m_value.valueID = CSSValueTibetan;
1811        break;
1812    case Tigre:
1813        m_value.valueID = CSSValueTigre;
1814        break;
1815    case TigrinyaEr:
1816        m_value.valueID = CSSValueTigrinyaEr;
1817        break;
1818    case TigrinyaErAbegede:
1819        m_value.valueID = CSSValueTigrinyaErAbegede;
1820        break;
1821    case TigrinyaEt:
1822        m_value.valueID = CSSValueTigrinyaEt;
1823        break;
1824    case TigrinyaEtAbegede:
1825        m_value.valueID = CSSValueTigrinyaEtAbegede;
1826        break;
1827    case UpperAlpha:
1828        m_value.valueID = CSSValueUpperAlpha;
1829        break;
1830    case UpperArmenian:
1831        m_value.valueID = CSSValueUpperArmenian;
1832        break;
1833    case UpperGreek:
1834        m_value.valueID = CSSValueUpperGreek;
1835        break;
1836    case UpperHexadecimal:
1837        m_value.valueID = CSSValueUpperHexadecimal;
1838        break;
1839    case UpperLatin:
1840        m_value.valueID = CSSValueUpperLatin;
1841        break;
1842    case UpperNorwegian:
1843        m_value.valueID = CSSValueUpperNorwegian;
1844        break;
1845    case UpperRoman:
1846        m_value.valueID = CSSValueUpperRoman;
1847        break;
1848    case Urdu:
1849        m_value.valueID = CSSValueUrdu;
1850        break;
1851    }
1852}
1853
1854template<> inline CSSPrimitiveValue::operator EListStyleType() const
1855{
1856    ASSERT(isValueID());
1857    switch (m_value.valueID) {
1858    case CSSValueNone:
1859        return NoneListStyle;
1860    default:
1861        return static_cast<EListStyleType>(m_value.valueID - CSSValueDisc);
1862    }
1863}
1864
1865template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EMarginCollapse e)
1866    : CSSValue(PrimitiveClass)
1867{
1868    m_primitiveUnitType = CSS_VALUE_ID;
1869    switch (e) {
1870    case MCOLLAPSE:
1871        m_value.valueID = CSSValueCollapse;
1872        break;
1873    case MSEPARATE:
1874        m_value.valueID = CSSValueSeparate;
1875        break;
1876    case MDISCARD:
1877        m_value.valueID = CSSValueDiscard;
1878        break;
1879    }
1880}
1881
1882template<> inline CSSPrimitiveValue::operator EMarginCollapse() const
1883{
1884    ASSERT(isValueID());
1885    switch (m_value.valueID) {
1886    case CSSValueCollapse:
1887        return MCOLLAPSE;
1888    case CSSValueSeparate:
1889        return MSEPARATE;
1890    case CSSValueDiscard:
1891        return MDISCARD;
1892    default:
1893        break;
1894    }
1895
1896    ASSERT_NOT_REACHED();
1897    return MCOLLAPSE;
1898}
1899
1900template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EMarqueeBehavior e)
1901    : CSSValue(PrimitiveClass)
1902{
1903    m_primitiveUnitType = CSS_VALUE_ID;
1904    switch (e) {
1905    case MNONE:
1906        m_value.valueID = CSSValueNone;
1907        break;
1908    case MSCROLL:
1909        m_value.valueID = CSSValueScroll;
1910        break;
1911    case MSLIDE:
1912        m_value.valueID = CSSValueSlide;
1913        break;
1914    case MALTERNATE:
1915        m_value.valueID = CSSValueAlternate;
1916        break;
1917    }
1918}
1919
1920template<> inline CSSPrimitiveValue::operator EMarqueeBehavior() const
1921{
1922    ASSERT(isValueID());
1923    switch (m_value.valueID) {
1924    case CSSValueNone:
1925        return MNONE;
1926    case CSSValueScroll:
1927        return MSCROLL;
1928    case CSSValueSlide:
1929        return MSLIDE;
1930    case CSSValueAlternate:
1931        return MALTERNATE;
1932    default:
1933        break;
1934    }
1935
1936    ASSERT_NOT_REACHED();
1937    return MNONE;
1938}
1939
1940template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EMarqueeDirection e)
1941    : CSSValue(PrimitiveClass)
1942{
1943    m_primitiveUnitType = CSS_VALUE_ID;
1944    switch (e) {
1945    case MFORWARD:
1946        m_value.valueID = CSSValueForwards;
1947        break;
1948    case MBACKWARD:
1949        m_value.valueID = CSSValueBackwards;
1950        break;
1951    case MAUTO:
1952        m_value.valueID = CSSValueAuto;
1953        break;
1954    case MUP:
1955        m_value.valueID = CSSValueUp;
1956        break;
1957    case MDOWN:
1958        m_value.valueID = CSSValueDown;
1959        break;
1960    case MLEFT:
1961        m_value.valueID = CSSValueLeft;
1962        break;
1963    case MRIGHT:
1964        m_value.valueID = CSSValueRight;
1965        break;
1966    }
1967}
1968
1969template<> inline CSSPrimitiveValue::operator EMarqueeDirection() const
1970{
1971    ASSERT(isValueID());
1972    switch (m_value.valueID) {
1973    case CSSValueForwards:
1974        return MFORWARD;
1975    case CSSValueBackwards:
1976        return MBACKWARD;
1977    case CSSValueAuto:
1978        return MAUTO;
1979    case CSSValueAhead:
1980    case CSSValueUp: // We don't support vertical languages, so AHEAD just maps to UP.
1981        return MUP;
1982    case CSSValueReverse:
1983    case CSSValueDown: // REVERSE just maps to DOWN, since we don't do vertical text.
1984        return MDOWN;
1985    case CSSValueLeft:
1986        return MLEFT;
1987    case CSSValueRight:
1988        return MRIGHT;
1989    default:
1990        break;
1991    }
1992
1993    ASSERT_NOT_REACHED();
1994    return MAUTO;
1995}
1996
1997template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EOverflow e)
1998    : CSSValue(PrimitiveClass)
1999{
2000    m_primitiveUnitType = CSS_VALUE_ID;
2001    switch (e) {
2002    case OVISIBLE:
2003        m_value.valueID = CSSValueVisible;
2004        break;
2005    case OHIDDEN:
2006        m_value.valueID = CSSValueHidden;
2007        break;
2008    case OSCROLL:
2009        m_value.valueID = CSSValueScroll;
2010        break;
2011    case OAUTO:
2012        m_value.valueID = CSSValueAuto;
2013        break;
2014    case OOVERLAY:
2015        m_value.valueID = CSSValueOverlay;
2016        break;
2017    case OPAGEDX:
2018        m_value.valueID = CSSValueWebkitPagedX;
2019        break;
2020    case OPAGEDY:
2021        m_value.valueID = CSSValueWebkitPagedY;
2022        break;
2023    }
2024}
2025
2026template<> inline CSSPrimitiveValue::operator EOverflow() const
2027{
2028    ASSERT(isValueID());
2029    switch (m_value.valueID) {
2030    case CSSValueVisible:
2031        return OVISIBLE;
2032    case CSSValueHidden:
2033        return OHIDDEN;
2034    case CSSValueScroll:
2035        return OSCROLL;
2036    case CSSValueAuto:
2037        return OAUTO;
2038    case CSSValueOverlay:
2039        return OOVERLAY;
2040    case CSSValueWebkitPagedX:
2041        return OPAGEDX;
2042    case CSSValueWebkitPagedY:
2043        return OPAGEDY;
2044    default:
2045        break;
2046    }
2047
2048    ASSERT_NOT_REACHED();
2049    return OVISIBLE;
2050}
2051
2052template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EPageBreak e)
2053    : CSSValue(PrimitiveClass)
2054{
2055    m_primitiveUnitType = CSS_VALUE_ID;
2056    switch (e) {
2057    case PBAUTO:
2058        m_value.valueID = CSSValueAuto;
2059        break;
2060    case PBALWAYS:
2061        m_value.valueID = CSSValueAlways;
2062        break;
2063    case PBAVOID:
2064        m_value.valueID = CSSValueAvoid;
2065        break;
2066    }
2067}
2068
2069template<> inline CSSPrimitiveValue::operator EPageBreak() const
2070{
2071    ASSERT(isValueID());
2072    switch (m_value.valueID) {
2073    case CSSValueAuto:
2074        return PBAUTO;
2075    case CSSValueLeft:
2076    case CSSValueRight:
2077    case CSSValueAlways:
2078        return PBALWAYS; // CSS2.1: "Conforming user agents may map left/right to always."
2079    case CSSValueAvoid:
2080        return PBAVOID;
2081    default:
2082        break;
2083    }
2084
2085    ASSERT_NOT_REACHED();
2086    return PBAUTO;
2087}
2088
2089template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EPosition e)
2090    : CSSValue(PrimitiveClass)
2091{
2092    m_primitiveUnitType = CSS_VALUE_ID;
2093    switch (e) {
2094    case StaticPosition:
2095        m_value.valueID = CSSValueStatic;
2096        break;
2097    case RelativePosition:
2098        m_value.valueID = CSSValueRelative;
2099        break;
2100    case AbsolutePosition:
2101        m_value.valueID = CSSValueAbsolute;
2102        break;
2103    case FixedPosition:
2104        m_value.valueID = CSSValueFixed;
2105        break;
2106    case StickyPosition:
2107        m_value.valueID = CSSValueSticky;
2108        break;
2109    }
2110}
2111
2112template<> inline CSSPrimitiveValue::operator EPosition() const
2113{
2114    ASSERT(isValueID());
2115    switch (m_value.valueID) {
2116    case CSSValueStatic:
2117        return StaticPosition;
2118    case CSSValueRelative:
2119        return RelativePosition;
2120    case CSSValueAbsolute:
2121        return AbsolutePosition;
2122    case CSSValueFixed:
2123        return FixedPosition;
2124    case CSSValueSticky:
2125        return StickyPosition;
2126    default:
2127        break;
2128    }
2129
2130    ASSERT_NOT_REACHED();
2131    return StaticPosition;
2132}
2133
2134template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EResize e)
2135    : CSSValue(PrimitiveClass)
2136{
2137    m_primitiveUnitType = CSS_VALUE_ID;
2138    switch (e) {
2139    case RESIZE_BOTH:
2140        m_value.valueID = CSSValueBoth;
2141        break;
2142    case RESIZE_HORIZONTAL:
2143        m_value.valueID = CSSValueHorizontal;
2144        break;
2145    case RESIZE_VERTICAL:
2146        m_value.valueID = CSSValueVertical;
2147        break;
2148    case RESIZE_NONE:
2149        m_value.valueID = CSSValueNone;
2150        break;
2151    }
2152}
2153
2154template<> inline CSSPrimitiveValue::operator EResize() const
2155{
2156    ASSERT(isValueID());
2157    switch (m_value.valueID) {
2158    case CSSValueBoth:
2159        return RESIZE_BOTH;
2160    case CSSValueHorizontal:
2161        return RESIZE_HORIZONTAL;
2162    case CSSValueVertical:
2163        return RESIZE_VERTICAL;
2164    case CSSValueAuto:
2165        ASSERT_NOT_REACHED(); // Depends on settings, thus should be handled by the caller.
2166        return RESIZE_NONE;
2167    case CSSValueNone:
2168        return RESIZE_NONE;
2169    default:
2170        break;
2171    }
2172
2173    ASSERT_NOT_REACHED();
2174    return RESIZE_NONE;
2175}
2176
2177template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ETableLayout e)
2178    : CSSValue(PrimitiveClass)
2179{
2180    m_primitiveUnitType = CSS_VALUE_ID;
2181    switch (e) {
2182    case TAUTO:
2183        m_value.valueID = CSSValueAuto;
2184        break;
2185    case TFIXED:
2186        m_value.valueID = CSSValueFixed;
2187        break;
2188    }
2189}
2190
2191template<> inline CSSPrimitiveValue::operator ETableLayout() const
2192{
2193    ASSERT(isValueID());
2194    switch (m_value.valueID) {
2195    case CSSValueFixed:
2196        return TFIXED;
2197    case CSSValueAuto:
2198        return TAUTO;
2199    default:
2200        break;
2201    }
2202
2203    ASSERT_NOT_REACHED();
2204    return TAUTO;
2205}
2206
2207template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ETextAlign e)
2208    : CSSValue(PrimitiveClass)
2209{
2210    m_primitiveUnitType = CSS_VALUE_ID;
2211    switch (e) {
2212    case TASTART:
2213        m_value.valueID = CSSValueStart;
2214        break;
2215    case TAEND:
2216        m_value.valueID = CSSValueEnd;
2217        break;
2218    case LEFT:
2219        m_value.valueID = CSSValueLeft;
2220        break;
2221    case RIGHT:
2222        m_value.valueID = CSSValueRight;
2223        break;
2224    case CENTER:
2225        m_value.valueID = CSSValueCenter;
2226        break;
2227    case JUSTIFY:
2228        m_value.valueID = CSSValueJustify;
2229        break;
2230    case WEBKIT_LEFT:
2231        m_value.valueID = CSSValueWebkitLeft;
2232        break;
2233    case WEBKIT_RIGHT:
2234        m_value.valueID = CSSValueWebkitRight;
2235        break;
2236    case WEBKIT_CENTER:
2237        m_value.valueID = CSSValueWebkitCenter;
2238        break;
2239    }
2240}
2241
2242template<> inline CSSPrimitiveValue::operator ETextAlign() const
2243{
2244    ASSERT(isValueID());
2245    switch (m_value.valueID) {
2246    case CSSValueWebkitAuto: // Legacy -webkit-auto. Eqiuvalent to start.
2247    case CSSValueStart:
2248        return TASTART;
2249    case CSSValueEnd:
2250        return TAEND;
2251    default:
2252        return static_cast<ETextAlign>(m_value.valueID - CSSValueLeft);
2253    }
2254}
2255
2256template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextAlignLast e)
2257    : CSSValue(PrimitiveClass)
2258{
2259    m_primitiveUnitType = CSS_VALUE_ID;
2260    switch (e) {
2261    case TextAlignLastStart:
2262        m_value.valueID = CSSValueStart;
2263        break;
2264    case TextAlignLastEnd:
2265        m_value.valueID = CSSValueEnd;
2266        break;
2267    case TextAlignLastLeft:
2268        m_value.valueID = CSSValueLeft;
2269        break;
2270    case TextAlignLastRight:
2271        m_value.valueID = CSSValueRight;
2272        break;
2273    case TextAlignLastCenter:
2274        m_value.valueID = CSSValueCenter;
2275        break;
2276    case TextAlignLastJustify:
2277        m_value.valueID = CSSValueJustify;
2278        break;
2279    case TextAlignLastAuto:
2280        m_value.valueID = CSSValueAuto;
2281        break;
2282    }
2283}
2284
2285template<> inline CSSPrimitiveValue::operator TextAlignLast() const
2286{
2287    ASSERT(isValueID());
2288    switch (m_value.valueID) {
2289    case CSSValueAuto:
2290        return TextAlignLastAuto;
2291    case CSSValueStart:
2292        return TextAlignLastStart;
2293    case CSSValueEnd:
2294        return TextAlignLastEnd;
2295    case CSSValueLeft:
2296        return TextAlignLastLeft;
2297    case CSSValueRight:
2298        return TextAlignLastRight;
2299    case CSSValueCenter:
2300        return TextAlignLastCenter;
2301    case CSSValueJustify:
2302        return TextAlignLastJustify;
2303    default:
2304        break;
2305    }
2306
2307    ASSERT_NOT_REACHED();
2308    return TextAlignLastAuto;
2309}
2310
2311template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextJustify e)
2312    : CSSValue(PrimitiveClass)
2313{
2314    m_primitiveUnitType = CSS_VALUE_ID;
2315    switch (e) {
2316    case TextJustifyAuto:
2317        m_value.valueID = CSSValueAuto;
2318        break;
2319    case TextJustifyNone:
2320        m_value.valueID = CSSValueNone;
2321        break;
2322    case TextJustifyInterWord:
2323        m_value.valueID = CSSValueInterWord;
2324        break;
2325    case TextJustifyDistribute:
2326        m_value.valueID = CSSValueDistribute;
2327        break;
2328    }
2329}
2330
2331template<> inline CSSPrimitiveValue::operator TextJustify() const
2332{
2333    switch (m_value.valueID) {
2334    case CSSValueAuto:
2335        return TextJustifyAuto;
2336    case CSSValueNone:
2337        return TextJustifyNone;
2338    case CSSValueInterWord:
2339        return TextJustifyInterWord;
2340    case CSSValueDistribute:
2341        return TextJustifyDistribute;
2342    default:
2343        break;
2344    }
2345
2346    ASSERT_NOT_REACHED();
2347    return TextJustifyAuto;
2348}
2349
2350template<> inline CSSPrimitiveValue::operator TextDecoration() const
2351{
2352    ASSERT(isValueID());
2353    switch (m_value.valueID) {
2354    case CSSValueNone:
2355        return TextDecorationNone;
2356    case CSSValueUnderline:
2357        return TextDecorationUnderline;
2358    case CSSValueOverline:
2359        return TextDecorationOverline;
2360    case CSSValueLineThrough:
2361        return TextDecorationLineThrough;
2362    case CSSValueBlink:
2363        return TextDecorationBlink;
2364    default:
2365        break;
2366    }
2367
2368    ASSERT_NOT_REACHED();
2369    return TextDecorationNone;
2370}
2371
2372template<> inline CSSPrimitiveValue::operator TextDecorationStyle() const
2373{
2374    ASSERT(isValueID());
2375    switch (m_value.valueID) {
2376    case CSSValueSolid:
2377        return TextDecorationStyleSolid;
2378    case CSSValueDouble:
2379        return TextDecorationStyleDouble;
2380    case CSSValueDotted:
2381        return TextDecorationStyleDotted;
2382    case CSSValueDashed:
2383        return TextDecorationStyleDashed;
2384    case CSSValueWavy:
2385        return TextDecorationStyleWavy;
2386    default:
2387        break;
2388    }
2389
2390    ASSERT_NOT_REACHED();
2391    return TextDecorationStyleSolid;
2392}
2393
2394template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextUnderlinePosition e)
2395    : CSSValue(PrimitiveClass)
2396{
2397    m_primitiveUnitType = CSS_VALUE_ID;
2398    switch (e) {
2399    case TextUnderlinePositionAuto:
2400        m_value.valueID = CSSValueAuto;
2401        break;
2402    case TextUnderlinePositionUnder:
2403        m_value.valueID = CSSValueUnder;
2404        break;
2405    }
2406
2407    // FIXME: Implement support for 'under left' and 'under right' values.
2408}
2409
2410template<> inline CSSPrimitiveValue::operator TextUnderlinePosition() const
2411{
2412    ASSERT(isValueID());
2413    switch (m_value.valueID) {
2414    case CSSValueAuto:
2415        return TextUnderlinePositionAuto;
2416    case CSSValueUnder:
2417        return TextUnderlinePositionUnder;
2418    default:
2419        break;
2420    }
2421
2422    // FIXME: Implement support for 'under left' and 'under right' values.
2423
2424    ASSERT_NOT_REACHED();
2425    return TextUnderlinePositionAuto;
2426}
2427
2428template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ETextSecurity e)
2429    : CSSValue(PrimitiveClass)
2430{
2431    m_primitiveUnitType = CSS_VALUE_ID;
2432    switch (e) {
2433    case TSNONE:
2434        m_value.valueID = CSSValueNone;
2435        break;
2436    case TSDISC:
2437        m_value.valueID = CSSValueDisc;
2438        break;
2439    case TSCIRCLE:
2440        m_value.valueID = CSSValueCircle;
2441        break;
2442    case TSSQUARE:
2443        m_value.valueID = CSSValueSquare;
2444        break;
2445    }
2446}
2447
2448template<> inline CSSPrimitiveValue::operator ETextSecurity() const
2449{
2450    ASSERT(isValueID());
2451    switch (m_value.valueID) {
2452    case CSSValueNone:
2453        return TSNONE;
2454    case CSSValueDisc:
2455        return TSDISC;
2456    case CSSValueCircle:
2457        return TSCIRCLE;
2458    case CSSValueSquare:
2459        return TSSQUARE;
2460    default:
2461        break;
2462    }
2463
2464    ASSERT_NOT_REACHED();
2465    return TSNONE;
2466}
2467
2468template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ETextTransform e)
2469    : CSSValue(PrimitiveClass)
2470{
2471    m_primitiveUnitType = CSS_VALUE_ID;
2472    switch (e) {
2473    case CAPITALIZE:
2474        m_value.valueID = CSSValueCapitalize;
2475        break;
2476    case UPPERCASE:
2477        m_value.valueID = CSSValueUppercase;
2478        break;
2479    case LOWERCASE:
2480        m_value.valueID = CSSValueLowercase;
2481        break;
2482    case TTNONE:
2483        m_value.valueID = CSSValueNone;
2484        break;
2485    }
2486}
2487
2488template<> inline CSSPrimitiveValue::operator ETextTransform() const
2489{
2490    ASSERT(isValueID());
2491    switch (m_value.valueID) {
2492    case CSSValueCapitalize:
2493        return CAPITALIZE;
2494    case CSSValueUppercase:
2495        return UPPERCASE;
2496    case CSSValueLowercase:
2497        return LOWERCASE;
2498    case CSSValueNone:
2499        return TTNONE;
2500    default:
2501        break;
2502    }
2503
2504    ASSERT_NOT_REACHED();
2505    return TTNONE;
2506}
2507
2508template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EUnicodeBidi e)
2509    : CSSValue(PrimitiveClass)
2510{
2511    m_primitiveUnitType = CSS_VALUE_ID;
2512    switch (e) {
2513    case UBNormal:
2514        m_value.valueID = CSSValueNormal;
2515        break;
2516    case Embed:
2517        m_value.valueID = CSSValueEmbed;
2518        break;
2519    case Override:
2520        m_value.valueID = CSSValueBidiOverride;
2521        break;
2522    case Isolate:
2523        m_value.valueID = CSSValueWebkitIsolate;
2524        break;
2525    case IsolateOverride:
2526        m_value.valueID = CSSValueWebkitIsolateOverride;
2527        break;
2528    case Plaintext:
2529        m_value.valueID = CSSValueWebkitPlaintext;
2530        break;
2531    }
2532}
2533
2534template<> inline CSSPrimitiveValue::operator EUnicodeBidi() const
2535{
2536    ASSERT(isValueID());
2537    switch (m_value.valueID) {
2538    case CSSValueNormal:
2539        return UBNormal;
2540    case CSSValueEmbed:
2541        return Embed;
2542    case CSSValueBidiOverride:
2543        return Override;
2544    case CSSValueWebkitIsolate:
2545        return Isolate;
2546    case CSSValueWebkitIsolateOverride:
2547        return IsolateOverride;
2548    case CSSValueWebkitPlaintext:
2549        return Plaintext;
2550    default:
2551        break;
2552    }
2553
2554    ASSERT_NOT_REACHED();
2555    return UBNormal;
2556}
2557
2558template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EUserDrag e)
2559    : CSSValue(PrimitiveClass)
2560{
2561    m_primitiveUnitType = CSS_VALUE_ID;
2562    switch (e) {
2563    case DRAG_AUTO:
2564        m_value.valueID = CSSValueAuto;
2565        break;
2566    case DRAG_NONE:
2567        m_value.valueID = CSSValueNone;
2568        break;
2569    case DRAG_ELEMENT:
2570        m_value.valueID = CSSValueElement;
2571        break;
2572    default:
2573        break;
2574    }
2575}
2576
2577template<> inline CSSPrimitiveValue::operator EUserDrag() const
2578{
2579    ASSERT(isValueID());
2580    switch (m_value.valueID) {
2581    case CSSValueAuto:
2582        return DRAG_AUTO;
2583    case CSSValueNone:
2584        return DRAG_NONE;
2585    case CSSValueElement:
2586        return DRAG_ELEMENT;
2587    default:
2588        break;
2589    }
2590
2591    ASSERT_NOT_REACHED();
2592    return DRAG_AUTO;
2593}
2594
2595template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EUserModify e)
2596    : CSSValue(PrimitiveClass)
2597{
2598    m_primitiveUnitType = CSS_VALUE_ID;
2599    switch (e) {
2600    case READ_ONLY:
2601        m_value.valueID = CSSValueReadOnly;
2602        break;
2603    case READ_WRITE:
2604        m_value.valueID = CSSValueReadWrite;
2605        break;
2606    case READ_WRITE_PLAINTEXT_ONLY:
2607        m_value.valueID = CSSValueReadWritePlaintextOnly;
2608        break;
2609    }
2610}
2611
2612template<> inline CSSPrimitiveValue::operator EUserModify() const
2613{
2614    ASSERT(isValueID());
2615    switch (m_value.valueID) {
2616    case CSSValueReadOnly:
2617        return READ_ONLY;
2618    case CSSValueReadWrite:
2619        return READ_WRITE;
2620    case CSSValueReadWritePlaintextOnly:
2621        return READ_WRITE_PLAINTEXT_ONLY;
2622    default:
2623        break;
2624    }
2625
2626    ASSERT_NOT_REACHED();
2627    return READ_ONLY;
2628}
2629
2630template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EUserSelect e)
2631    : CSSValue(PrimitiveClass)
2632{
2633    m_primitiveUnitType = CSS_VALUE_ID;
2634    switch (e) {
2635    case SELECT_NONE:
2636        m_value.valueID = CSSValueNone;
2637        break;
2638    case SELECT_TEXT:
2639        m_value.valueID = CSSValueText;
2640        break;
2641    case SELECT_ALL:
2642        m_value.valueID = CSSValueAll;
2643        break;
2644    }
2645}
2646
2647template<> inline CSSPrimitiveValue::operator EUserSelect() const
2648{
2649    ASSERT(isValueID());
2650    switch (m_value.valueID) {
2651    case CSSValueAuto:
2652        return SELECT_TEXT;
2653    case CSSValueNone:
2654        return SELECT_NONE;
2655    case CSSValueText:
2656        return SELECT_TEXT;
2657    case CSSValueAll:
2658        return SELECT_ALL;
2659    default:
2660        break;
2661    }
2662
2663    ASSERT_NOT_REACHED();
2664    return SELECT_TEXT;
2665}
2666
2667template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EVerticalAlign a)
2668    : CSSValue(PrimitiveClass)
2669{
2670    m_primitiveUnitType = CSS_VALUE_ID;
2671    switch (a) {
2672    case TOP:
2673        m_value.valueID = CSSValueTop;
2674        break;
2675    case BOTTOM:
2676        m_value.valueID = CSSValueBottom;
2677        break;
2678    case MIDDLE:
2679        m_value.valueID = CSSValueMiddle;
2680        break;
2681    case BASELINE:
2682        m_value.valueID = CSSValueBaseline;
2683        break;
2684    case TEXT_BOTTOM:
2685        m_value.valueID = CSSValueTextBottom;
2686        break;
2687    case TEXT_TOP:
2688        m_value.valueID = CSSValueTextTop;
2689        break;
2690    case SUB:
2691        m_value.valueID = CSSValueSub;
2692        break;
2693    case SUPER:
2694        m_value.valueID = CSSValueSuper;
2695        break;
2696    case BASELINE_MIDDLE:
2697        m_value.valueID = CSSValueWebkitBaselineMiddle;
2698        break;
2699    case LENGTH:
2700        m_value.valueID = CSSValueInvalid;
2701    }
2702}
2703
2704template<> inline CSSPrimitiveValue::operator EVerticalAlign() const
2705{
2706    ASSERT(isValueID());
2707    switch (m_value.valueID) {
2708    case CSSValueTop:
2709        return TOP;
2710    case CSSValueBottom:
2711        return BOTTOM;
2712    case CSSValueMiddle:
2713        return MIDDLE;
2714    case CSSValueBaseline:
2715        return BASELINE;
2716    case CSSValueTextBottom:
2717        return TEXT_BOTTOM;
2718    case CSSValueTextTop:
2719        return TEXT_TOP;
2720    case CSSValueSub:
2721        return SUB;
2722    case CSSValueSuper:
2723        return SUPER;
2724    case CSSValueWebkitBaselineMiddle:
2725        return BASELINE_MIDDLE;
2726    default:
2727        break;
2728    }
2729
2730    ASSERT_NOT_REACHED();
2731    return TOP;
2732}
2733
2734template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EVisibility e)
2735    : CSSValue(PrimitiveClass)
2736{
2737    m_primitiveUnitType = CSS_VALUE_ID;
2738    switch (e) {
2739    case VISIBLE:
2740        m_value.valueID = CSSValueVisible;
2741        break;
2742    case HIDDEN:
2743        m_value.valueID = CSSValueHidden;
2744        break;
2745    case COLLAPSE:
2746        m_value.valueID = CSSValueCollapse;
2747        break;
2748    }
2749}
2750
2751template<> inline CSSPrimitiveValue::operator EVisibility() const
2752{
2753    ASSERT(isValueID());
2754    switch (m_value.valueID) {
2755    case CSSValueHidden:
2756        return HIDDEN;
2757    case CSSValueVisible:
2758        return VISIBLE;
2759    case CSSValueCollapse:
2760        return COLLAPSE;
2761    default:
2762        break;
2763    }
2764
2765    ASSERT_NOT_REACHED();
2766    return VISIBLE;
2767}
2768
2769template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EWhiteSpace e)
2770    : CSSValue(PrimitiveClass)
2771{
2772    m_primitiveUnitType = CSS_VALUE_ID;
2773    switch (e) {
2774    case NORMAL:
2775        m_value.valueID = CSSValueNormal;
2776        break;
2777    case PRE:
2778        m_value.valueID = CSSValuePre;
2779        break;
2780    case PRE_WRAP:
2781        m_value.valueID = CSSValuePreWrap;
2782        break;
2783    case PRE_LINE:
2784        m_value.valueID = CSSValuePreLine;
2785        break;
2786    case NOWRAP:
2787        m_value.valueID = CSSValueNowrap;
2788        break;
2789    case KHTML_NOWRAP:
2790        m_value.valueID = CSSValueWebkitNowrap;
2791        break;
2792    }
2793}
2794
2795template<> inline CSSPrimitiveValue::operator EWhiteSpace() const
2796{
2797    ASSERT(isValueID());
2798    switch (m_value.valueID) {
2799    case CSSValueWebkitNowrap:
2800        return KHTML_NOWRAP;
2801    case CSSValueNowrap:
2802        return NOWRAP;
2803    case CSSValuePre:
2804        return PRE;
2805    case CSSValuePreWrap:
2806        return PRE_WRAP;
2807    case CSSValuePreLine:
2808        return PRE_LINE;
2809    case CSSValueNormal:
2810        return NORMAL;
2811    default:
2812        break;
2813    }
2814
2815    ASSERT_NOT_REACHED();
2816    return NORMAL;
2817}
2818
2819template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EWordBreak e)
2820    : CSSValue(PrimitiveClass)
2821{
2822    m_primitiveUnitType = CSS_VALUE_ID;
2823    switch (e) {
2824    case NormalWordBreak:
2825        m_value.valueID = CSSValueNormal;
2826        break;
2827    case BreakAllWordBreak:
2828        m_value.valueID = CSSValueBreakAll;
2829        break;
2830    case BreakWordBreak:
2831        m_value.valueID = CSSValueBreakWord;
2832        break;
2833    }
2834}
2835
2836template<> inline CSSPrimitiveValue::operator EWordBreak() const
2837{
2838    ASSERT(isValueID());
2839    switch (m_value.valueID) {
2840    case CSSValueBreakAll:
2841        return BreakAllWordBreak;
2842    case CSSValueBreakWord:
2843        return BreakWordBreak;
2844    case CSSValueNormal:
2845        return NormalWordBreak;
2846    default:
2847        break;
2848    }
2849
2850    ASSERT_NOT_REACHED();
2851    return NormalWordBreak;
2852}
2853
2854template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EOverflowWrap e)
2855    : CSSValue(PrimitiveClass)
2856{
2857    m_primitiveUnitType = CSS_VALUE_ID;
2858    switch (e) {
2859    case NormalOverflowWrap:
2860        m_value.valueID = CSSValueNormal;
2861        break;
2862    case BreakOverflowWrap:
2863        m_value.valueID = CSSValueBreakWord;
2864        break;
2865    }
2866}
2867
2868template<> inline CSSPrimitiveValue::operator EOverflowWrap() const
2869{
2870    ASSERT(isValueID());
2871    switch (m_value.valueID) {
2872    case CSSValueBreakWord:
2873        return BreakOverflowWrap;
2874    case CSSValueNormal:
2875        return NormalOverflowWrap;
2876    default:
2877        break;
2878    }
2879
2880    ASSERT_NOT_REACHED();
2881    return NormalOverflowWrap;
2882}
2883
2884template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextDirection e)
2885    : CSSValue(PrimitiveClass)
2886{
2887    m_primitiveUnitType = CSS_VALUE_ID;
2888    switch (e) {
2889    case LTR:
2890        m_value.valueID = CSSValueLtr;
2891        break;
2892    case RTL:
2893        m_value.valueID = CSSValueRtl;
2894        break;
2895    }
2896}
2897
2898template<> inline CSSPrimitiveValue::operator TextDirection() const
2899{
2900    ASSERT(isValueID());
2901    switch (m_value.valueID) {
2902    case CSSValueLtr:
2903        return LTR;
2904    case CSSValueRtl:
2905        return RTL;
2906    default:
2907        break;
2908    }
2909
2910    ASSERT_NOT_REACHED();
2911    return LTR;
2912}
2913
2914template<> inline CSSPrimitiveValue::CSSPrimitiveValue(WritingMode e)
2915    : CSSValue(PrimitiveClass)
2916{
2917    m_primitiveUnitType = CSS_VALUE_ID;
2918    switch (e) {
2919    case TopToBottomWritingMode:
2920        m_value.valueID = CSSValueHorizontalTb;
2921        break;
2922    case RightToLeftWritingMode:
2923        m_value.valueID = CSSValueVerticalRl;
2924        break;
2925    case LeftToRightWritingMode:
2926        m_value.valueID = CSSValueVerticalLr;
2927        break;
2928    case BottomToTopWritingMode:
2929        m_value.valueID = CSSValueHorizontalBt;
2930        break;
2931    }
2932}
2933
2934template<> inline CSSPrimitiveValue::operator WritingMode() const
2935{
2936    ASSERT(isValueID());
2937    switch (m_value.valueID) {
2938    case CSSValueHorizontalTb:
2939        return TopToBottomWritingMode;
2940    case CSSValueVerticalRl:
2941        return RightToLeftWritingMode;
2942    case CSSValueVerticalLr:
2943        return LeftToRightWritingMode;
2944    case CSSValueHorizontalBt:
2945        return BottomToTopWritingMode;
2946    default:
2947        break;
2948    }
2949
2950    ASSERT_NOT_REACHED();
2951    return TopToBottomWritingMode;
2952}
2953
2954template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextCombine e)
2955    : CSSValue(PrimitiveClass)
2956{
2957    m_primitiveUnitType = CSS_VALUE_ID;
2958    switch (e) {
2959    case TextCombineNone:
2960        m_value.valueID = CSSValueNone;
2961        break;
2962    case TextCombineHorizontal:
2963        m_value.valueID = CSSValueHorizontal;
2964        break;
2965    }
2966}
2967
2968template<> inline CSSPrimitiveValue::operator TextCombine() const
2969{
2970    ASSERT(isValueID());
2971    switch (m_value.valueID) {
2972    case CSSValueNone:
2973        return TextCombineNone;
2974    case CSSValueHorizontal:
2975        return TextCombineHorizontal;
2976    default:
2977        break;
2978    }
2979
2980    ASSERT_NOT_REACHED();
2981    return TextCombineNone;
2982}
2983
2984template<> inline CSSPrimitiveValue::CSSPrimitiveValue(RubyPosition position)
2985    : CSSValue(PrimitiveClass)
2986{
2987    m_primitiveUnitType = CSS_VALUE_ID;
2988    switch (position) {
2989    case RubyPositionBefore:
2990        m_value.valueID = CSSValueBefore;
2991        break;
2992    case RubyPositionAfter:
2993        m_value.valueID = CSSValueAfter;
2994        break;
2995    }
2996}
2997
2998template<> inline CSSPrimitiveValue::operator RubyPosition() const
2999{
3000    ASSERT(isValueID());
3001    switch (m_value.valueID) {
3002    case CSSValueBefore:
3003        return RubyPositionBefore;
3004    case CSSValueAfter:
3005        return RubyPositionAfter;
3006    default:
3007        break;
3008    }
3009
3010    ASSERT_NOT_REACHED();
3011    return RubyPositionBefore;
3012}
3013
3014template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextEmphasisPosition position)
3015    : CSSValue(PrimitiveClass)
3016{
3017    m_primitiveUnitType = CSS_VALUE_ID;
3018    switch (position) {
3019    case TextEmphasisPositionOver:
3020        m_value.valueID = CSSValueOver;
3021        break;
3022    case TextEmphasisPositionUnder:
3023        m_value.valueID = CSSValueUnder;
3024        break;
3025    }
3026}
3027
3028template<> inline CSSPrimitiveValue::operator TextEmphasisPosition() const
3029{
3030    ASSERT(isValueID());
3031    switch (m_value.valueID) {
3032    case CSSValueOver:
3033        return TextEmphasisPositionOver;
3034    case CSSValueUnder:
3035        return TextEmphasisPositionUnder;
3036    default:
3037        break;
3038    }
3039
3040    ASSERT_NOT_REACHED();
3041    return TextEmphasisPositionOver;
3042}
3043
3044template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextOverflow overflow)
3045    : CSSValue(PrimitiveClass)
3046{
3047    m_primitiveUnitType = CSS_VALUE_ID;
3048    switch (overflow) {
3049    case TextOverflowClip:
3050        m_value.valueID = CSSValueClip;
3051        break;
3052    case TextOverflowEllipsis:
3053        m_value.valueID = CSSValueEllipsis;
3054        break;
3055    }
3056}
3057
3058template<> inline CSSPrimitiveValue::operator TextOverflow() const
3059{
3060    ASSERT(isValueID());
3061    switch (m_value.valueID) {
3062    case CSSValueClip:
3063        return TextOverflowClip;
3064    case CSSValueEllipsis:
3065        return TextOverflowEllipsis;
3066    default:
3067        break;
3068    }
3069
3070    ASSERT_NOT_REACHED();
3071    return TextOverflowClip;
3072}
3073
3074template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextEmphasisFill fill)
3075    : CSSValue(PrimitiveClass)
3076{
3077    m_primitiveUnitType = CSS_VALUE_ID;
3078    switch (fill) {
3079    case TextEmphasisFillFilled:
3080        m_value.valueID = CSSValueFilled;
3081        break;
3082    case TextEmphasisFillOpen:
3083        m_value.valueID = CSSValueOpen;
3084        break;
3085    }
3086}
3087
3088template<> inline CSSPrimitiveValue::operator TextEmphasisFill() const
3089{
3090    ASSERT(isValueID());
3091    switch (m_value.valueID) {
3092    case CSSValueFilled:
3093        return TextEmphasisFillFilled;
3094    case CSSValueOpen:
3095        return TextEmphasisFillOpen;
3096    default:
3097        break;
3098    }
3099
3100    ASSERT_NOT_REACHED();
3101    return TextEmphasisFillFilled;
3102}
3103
3104template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextEmphasisMark mark)
3105    : CSSValue(PrimitiveClass)
3106{
3107    m_primitiveUnitType = CSS_VALUE_ID;
3108    switch (mark) {
3109    case TextEmphasisMarkDot:
3110        m_value.valueID = CSSValueDot;
3111        break;
3112    case TextEmphasisMarkCircle:
3113        m_value.valueID = CSSValueCircle;
3114        break;
3115    case TextEmphasisMarkDoubleCircle:
3116        m_value.valueID = CSSValueDoubleCircle;
3117        break;
3118    case TextEmphasisMarkTriangle:
3119        m_value.valueID = CSSValueTriangle;
3120        break;
3121    case TextEmphasisMarkSesame:
3122        m_value.valueID = CSSValueSesame;
3123        break;
3124    case TextEmphasisMarkNone:
3125    case TextEmphasisMarkAuto:
3126    case TextEmphasisMarkCustom:
3127        ASSERT_NOT_REACHED();
3128        m_value.valueID = CSSValueNone;
3129        break;
3130    }
3131}
3132
3133template<> inline CSSPrimitiveValue::operator TextEmphasisMark() const
3134{
3135    ASSERT(isValueID());
3136    switch (m_value.valueID) {
3137    case CSSValueNone:
3138        return TextEmphasisMarkNone;
3139    case CSSValueDot:
3140        return TextEmphasisMarkDot;
3141    case CSSValueCircle:
3142        return TextEmphasisMarkCircle;
3143    case CSSValueDoubleCircle:
3144        return TextEmphasisMarkDoubleCircle;
3145    case CSSValueTriangle:
3146        return TextEmphasisMarkTriangle;
3147    case CSSValueSesame:
3148        return TextEmphasisMarkSesame;
3149    default:
3150        break;
3151    }
3152
3153    ASSERT_NOT_REACHED();
3154    return TextEmphasisMarkNone;
3155}
3156
3157template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextOrientation e)
3158    : CSSValue(PrimitiveClass)
3159{
3160    m_primitiveUnitType = CSS_VALUE_ID;
3161    switch (e) {
3162    case TextOrientationSideways:
3163        m_value.valueID = CSSValueSideways;
3164        break;
3165    case TextOrientationSidewaysRight:
3166        m_value.valueID = CSSValueSidewaysRight;
3167        break;
3168    case TextOrientationVerticalRight:
3169        m_value.valueID = CSSValueVerticalRight;
3170        break;
3171    case TextOrientationUpright:
3172        m_value.valueID = CSSValueUpright;
3173        break;
3174    }
3175}
3176
3177template<> inline CSSPrimitiveValue::operator TextOrientation() const
3178{
3179    ASSERT(isValueID());
3180    switch (m_value.valueID) {
3181    case CSSValueSideways:
3182        return TextOrientationSideways;
3183    case CSSValueSidewaysRight:
3184        return TextOrientationSidewaysRight;
3185    case CSSValueVerticalRight:
3186        return TextOrientationVerticalRight;
3187    case CSSValueUpright:
3188        return TextOrientationUpright;
3189    default:
3190        break;
3191    }
3192
3193    ASSERT_NOT_REACHED();
3194    return TextOrientationVerticalRight;
3195}
3196
3197template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EPointerEvents e)
3198    : CSSValue(PrimitiveClass)
3199{
3200    m_primitiveUnitType = CSS_VALUE_ID;
3201    switch (e) {
3202    case PE_NONE:
3203        m_value.valueID = CSSValueNone;
3204        break;
3205    case PE_STROKE:
3206        m_value.valueID = CSSValueStroke;
3207        break;
3208    case PE_FILL:
3209        m_value.valueID = CSSValueFill;
3210        break;
3211    case PE_PAINTED:
3212        m_value.valueID = CSSValuePainted;
3213        break;
3214    case PE_VISIBLE:
3215        m_value.valueID = CSSValueVisible;
3216        break;
3217    case PE_VISIBLE_STROKE:
3218        m_value.valueID = CSSValueVisiblestroke;
3219        break;
3220    case PE_VISIBLE_FILL:
3221        m_value.valueID = CSSValueVisiblefill;
3222        break;
3223    case PE_VISIBLE_PAINTED:
3224        m_value.valueID = CSSValueVisiblepainted;
3225        break;
3226    case PE_AUTO:
3227        m_value.valueID = CSSValueAuto;
3228        break;
3229    case PE_ALL:
3230        m_value.valueID = CSSValueAll;
3231        break;
3232    case PE_BOUNDINGBOX:
3233        m_value.valueID = CSSValueBoundingBox;
3234        break;
3235    }
3236}
3237
3238template<> inline CSSPrimitiveValue::operator EPointerEvents() const
3239{
3240    ASSERT(isValueID());
3241    switch (m_value.valueID) {
3242    case CSSValueAll:
3243        return PE_ALL;
3244    case CSSValueAuto:
3245        return PE_AUTO;
3246    case CSSValueNone:
3247        return PE_NONE;
3248    case CSSValueVisiblepainted:
3249        return PE_VISIBLE_PAINTED;
3250    case CSSValueVisiblefill:
3251        return PE_VISIBLE_FILL;
3252    case CSSValueVisiblestroke:
3253        return PE_VISIBLE_STROKE;
3254    case CSSValueVisible:
3255        return PE_VISIBLE;
3256    case CSSValuePainted:
3257        return PE_PAINTED;
3258    case CSSValueFill:
3259        return PE_FILL;
3260    case CSSValueStroke:
3261        return PE_STROKE;
3262    case CSSValueBoundingBox:
3263        return PE_BOUNDINGBOX;
3264    default:
3265        break;
3266    }
3267
3268    ASSERT_NOT_REACHED();
3269    return PE_ALL;
3270}
3271
3272template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontDescription::Kerning kerning)
3273    : CSSValue(PrimitiveClass)
3274{
3275    m_primitiveUnitType = CSS_VALUE_ID;
3276    switch (kerning) {
3277    case FontDescription::AutoKerning:
3278        m_value.valueID = CSSValueAuto;
3279        return;
3280    case FontDescription::NormalKerning:
3281        m_value.valueID = CSSValueNormal;
3282        return;
3283    case FontDescription::NoneKerning:
3284        m_value.valueID = CSSValueNone;
3285        return;
3286    }
3287
3288    ASSERT_NOT_REACHED();
3289    m_value.valueID = CSSValueAuto;
3290}
3291
3292template<> inline CSSPrimitiveValue::operator FontDescription::Kerning() const
3293{
3294    ASSERT(isValueID());
3295    switch (m_value.valueID) {
3296    case CSSValueAuto:
3297        return FontDescription::AutoKerning;
3298    case CSSValueNormal:
3299        return FontDescription::NormalKerning;
3300    case CSSValueNone:
3301        return FontDescription::NoneKerning;
3302    default:
3303        break;
3304    }
3305
3306    ASSERT_NOT_REACHED();
3307    return FontDescription::AutoKerning;
3308}
3309
3310template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ObjectFit fit)
3311    : CSSValue(PrimitiveClass)
3312{
3313    m_primitiveUnitType = CSS_VALUE_ID;
3314    switch (fit) {
3315    case ObjectFitFill:
3316        m_value.valueID = CSSValueFill;
3317        break;
3318    case ObjectFitContain:
3319        m_value.valueID = CSSValueContain;
3320        break;
3321    case ObjectFitCover:
3322        m_value.valueID = CSSValueCover;
3323        break;
3324    case ObjectFitNone:
3325        m_value.valueID = CSSValueNone;
3326        break;
3327    case ObjectFitScaleDown:
3328        m_value.valueID = CSSValueScaleDown;
3329        break;
3330    }
3331}
3332
3333template<> inline CSSPrimitiveValue::operator ObjectFit() const
3334{
3335    switch (m_value.valueID) {
3336    case CSSValueFill:
3337        return ObjectFitFill;
3338    case CSSValueContain:
3339        return ObjectFitContain;
3340    case CSSValueCover:
3341        return ObjectFitCover;
3342    case CSSValueNone:
3343        return ObjectFitNone;
3344    case CSSValueScaleDown:
3345        return ObjectFitScaleDown;
3346    default:
3347        ASSERT_NOT_REACHED();
3348        return ObjectFitFill;
3349    }
3350}
3351
3352template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EFillSizeType fillSize)
3353    : CSSValue(PrimitiveClass)
3354{
3355    m_primitiveUnitType = CSS_VALUE_ID;
3356    switch (fillSize) {
3357    case Contain:
3358        m_value.valueID = CSSValueContain;
3359        break;
3360    case Cover:
3361        m_value.valueID = CSSValueCover;
3362        break;
3363    case SizeNone:
3364        m_value.valueID = CSSValueNone;
3365        break;
3366    case SizeLength:
3367    default:
3368        ASSERT_NOT_REACHED();
3369    }
3370}
3371
3372template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontSmoothingMode smoothing)
3373    : CSSValue(PrimitiveClass)
3374{
3375    m_primitiveUnitType = CSS_VALUE_ID;
3376    switch (smoothing) {
3377    case AutoSmoothing:
3378        m_value.valueID = CSSValueAuto;
3379        return;
3380    case NoSmoothing:
3381        m_value.valueID = CSSValueNone;
3382        return;
3383    case Antialiased:
3384        m_value.valueID = CSSValueAntialiased;
3385        return;
3386    case SubpixelAntialiased:
3387        m_value.valueID = CSSValueSubpixelAntialiased;
3388        return;
3389    }
3390
3391    ASSERT_NOT_REACHED();
3392    m_value.valueID = CSSValueAuto;
3393}
3394
3395template<> inline CSSPrimitiveValue::operator FontSmoothingMode() const
3396{
3397    ASSERT(isValueID());
3398    switch (m_value.valueID) {
3399    case CSSValueAuto:
3400        return AutoSmoothing;
3401    case CSSValueNone:
3402        return NoSmoothing;
3403    case CSSValueAntialiased:
3404        return Antialiased;
3405    case CSSValueSubpixelAntialiased:
3406        return SubpixelAntialiased;
3407    default:
3408        break;
3409    }
3410
3411    ASSERT_NOT_REACHED();
3412    return AutoSmoothing;
3413}
3414
3415template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontWeight weight)
3416    : CSSValue(PrimitiveClass)
3417{
3418    m_primitiveUnitType = CSS_VALUE_ID;
3419    switch (weight) {
3420    case FontWeight900:
3421        m_value.valueID = CSSValue900;
3422        return;
3423    case FontWeight800:
3424        m_value.valueID = CSSValue800;
3425        return;
3426    case FontWeight700:
3427        m_value.valueID = CSSValue700;
3428        return;
3429    case FontWeight600:
3430        m_value.valueID = CSSValue600;
3431        return;
3432    case FontWeight500:
3433        m_value.valueID = CSSValue500;
3434        return;
3435    case FontWeight400:
3436        m_value.valueID = CSSValue400;
3437        return;
3438    case FontWeight300:
3439        m_value.valueID = CSSValue300;
3440        return;
3441    case FontWeight200:
3442        m_value.valueID = CSSValue200;
3443        return;
3444    case FontWeight100:
3445        m_value.valueID = CSSValue100;
3446        return;
3447    }
3448
3449    ASSERT_NOT_REACHED();
3450    m_value.valueID = CSSValueNormal;
3451}
3452
3453template<> inline CSSPrimitiveValue::operator FontWeight() const
3454{
3455    ASSERT(isValueID());
3456    switch (m_value.valueID) {
3457    case CSSValueBold:
3458        return FontWeightBold;
3459    case CSSValueNormal:
3460        return FontWeightNormal;
3461    case CSSValue900:
3462        return FontWeight900;
3463    case CSSValue800:
3464        return FontWeight800;
3465    case CSSValue700:
3466        return FontWeight700;
3467    case CSSValue600:
3468        return FontWeight600;
3469    case CSSValue500:
3470        return FontWeight500;
3471    case CSSValue400:
3472        return FontWeight400;
3473    case CSSValue300:
3474        return FontWeight300;
3475    case CSSValue200:
3476        return FontWeight200;
3477    case CSSValue100:
3478        return FontWeight100;
3479    default:
3480        break;
3481    }
3482
3483    ASSERT_NOT_REACHED();
3484    return FontWeightNormal;
3485}
3486
3487template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontStyle italic)
3488    : CSSValue(PrimitiveClass)
3489{
3490    m_primitiveUnitType = CSS_VALUE_ID;
3491    switch (italic) {
3492    case FontStyleNormal:
3493        m_value.valueID = CSSValueNormal;
3494        return;
3495    case FontStyleItalic:
3496        m_value.valueID = CSSValueItalic;
3497        return;
3498    }
3499
3500    ASSERT_NOT_REACHED();
3501    m_value.valueID = CSSValueNormal;
3502}
3503
3504template<> inline CSSPrimitiveValue::operator FontStyle() const
3505{
3506    ASSERT(isValueID());
3507    switch (m_value.valueID) {
3508    case CSSValueOblique:
3509    // FIXME: oblique is the same as italic for the moment...
3510    case CSSValueItalic:
3511        return FontStyleItalic;
3512    case CSSValueNormal:
3513        return FontStyleNormal;
3514    default:
3515        break;
3516    }
3517    ASSERT_NOT_REACHED();
3518    return FontStyleNormal;
3519}
3520
3521template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontVariant smallCaps)
3522    : CSSValue(PrimitiveClass)
3523{
3524    m_primitiveUnitType = CSS_VALUE_ID;
3525    switch (smallCaps) {
3526    case FontVariantNormal:
3527        m_value.valueID = CSSValueNormal;
3528        return;
3529    case FontVariantSmallCaps:
3530        m_value.valueID = CSSValueSmallCaps;
3531        return;
3532    }
3533
3534    ASSERT_NOT_REACHED();
3535    m_value.valueID = CSSValueNormal;
3536}
3537
3538template<> inline CSSPrimitiveValue::operator FontVariant() const
3539{
3540    ASSERT(isValueID());
3541    switch (m_value.valueID) {
3542    case CSSValueSmallCaps:
3543        return FontVariantSmallCaps;
3544    case CSSValueNormal:
3545        return FontVariantNormal;
3546    default:
3547        break;
3548    }
3549    ASSERT_NOT_REACHED();
3550    return FontVariantNormal;
3551}
3552
3553template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextRenderingMode e)
3554    : CSSValue(PrimitiveClass)
3555{
3556    m_primitiveUnitType = CSS_VALUE_ID;
3557    switch (e) {
3558    case AutoTextRendering:
3559        m_value.valueID = CSSValueAuto;
3560        break;
3561    case OptimizeSpeed:
3562        m_value.valueID = CSSValueOptimizespeed;
3563        break;
3564    case OptimizeLegibility:
3565        m_value.valueID = CSSValueOptimizelegibility;
3566        break;
3567    case GeometricPrecision:
3568        m_value.valueID = CSSValueGeometricprecision;
3569        break;
3570    }
3571}
3572
3573template<> inline CSSPrimitiveValue::operator TextRenderingMode() const
3574{
3575    ASSERT(isValueID());
3576    switch (m_value.valueID) {
3577    case CSSValueAuto:
3578        return AutoTextRendering;
3579    case CSSValueOptimizespeed:
3580        return OptimizeSpeed;
3581    case CSSValueOptimizelegibility:
3582        return OptimizeLegibility;
3583    case CSSValueGeometricprecision:
3584        return GeometricPrecision;
3585    default:
3586        break;
3587    }
3588
3589    ASSERT_NOT_REACHED();
3590    return AutoTextRendering;
3591}
3592
3593template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ESpeak e)
3594    : CSSValue(PrimitiveClass)
3595{
3596    m_primitiveUnitType = CSS_VALUE_ID;
3597    switch (e) {
3598    case SpeakNone:
3599        m_value.valueID = CSSValueNone;
3600        break;
3601    case SpeakNormal:
3602        m_value.valueID = CSSValueNormal;
3603        break;
3604    case SpeakSpellOut:
3605        m_value.valueID = CSSValueSpellOut;
3606        break;
3607    case SpeakDigits:
3608        m_value.valueID = CSSValueDigits;
3609        break;
3610    case SpeakLiteralPunctuation:
3611        m_value.valueID = CSSValueLiteralPunctuation;
3612        break;
3613    case SpeakNoPunctuation:
3614        m_value.valueID = CSSValueNoPunctuation;
3615        break;
3616    }
3617}
3618
3619template<> inline CSSPrimitiveValue::operator Order() const
3620{
3621    ASSERT(isValueID());
3622    switch (m_value.valueID) {
3623    case CSSValueLogical:
3624        return LogicalOrder;
3625    case CSSValueVisual:
3626        return VisualOrder;
3627    default:
3628        break;
3629    }
3630
3631    ASSERT_NOT_REACHED();
3632    return LogicalOrder;
3633}
3634
3635template<> inline CSSPrimitiveValue::CSSPrimitiveValue(Order e)
3636    : CSSValue(PrimitiveClass)
3637{
3638    m_primitiveUnitType = CSS_VALUE_ID;
3639    switch (e) {
3640    case LogicalOrder:
3641        m_value.valueID = CSSValueLogical;
3642        break;
3643    case VisualOrder:
3644        m_value.valueID = CSSValueVisual;
3645        break;
3646    }
3647}
3648
3649template<> inline CSSPrimitiveValue::operator ESpeak() const
3650{
3651    ASSERT(isValueID());
3652    switch (m_value.valueID) {
3653    case CSSValueNone:
3654        return SpeakNone;
3655    case CSSValueNormal:
3656        return SpeakNormal;
3657    case CSSValueSpellOut:
3658        return SpeakSpellOut;
3659    case CSSValueDigits:
3660        return SpeakDigits;
3661    case CSSValueLiteralPunctuation:
3662        return SpeakLiteralPunctuation;
3663    case CSSValueNoPunctuation:
3664        return SpeakNoPunctuation;
3665    default:
3666        break;
3667    }
3668
3669    ASSERT_NOT_REACHED();
3670    return SpeakNormal;
3671}
3672
3673template<> inline CSSPrimitiveValue::CSSPrimitiveValue(blink::WebBlendMode blendMode)
3674    : CSSValue(PrimitiveClass)
3675{
3676    m_primitiveUnitType = CSS_VALUE_ID;
3677    switch (blendMode) {
3678    case blink::WebBlendModeNormal:
3679        m_value.valueID = CSSValueNormal;
3680        break;
3681    case blink::WebBlendModeMultiply:
3682        m_value.valueID = CSSValueMultiply;
3683        break;
3684    case blink::WebBlendModeScreen:
3685        m_value.valueID = CSSValueScreen;
3686        break;
3687    case blink::WebBlendModeOverlay:
3688        m_value.valueID = CSSValueOverlay;
3689        break;
3690    case blink::WebBlendModeDarken:
3691        m_value.valueID = CSSValueDarken;
3692        break;
3693    case blink::WebBlendModeLighten:
3694        m_value.valueID = CSSValueLighten;
3695        break;
3696    case blink::WebBlendModeColorDodge:
3697        m_value.valueID = CSSValueColorDodge;
3698        break;
3699    case blink::WebBlendModeColorBurn:
3700        m_value.valueID = CSSValueColorBurn;
3701        break;
3702    case blink::WebBlendModeHardLight:
3703        m_value.valueID = CSSValueHardLight;
3704        break;
3705    case blink::WebBlendModeSoftLight:
3706        m_value.valueID = CSSValueSoftLight;
3707        break;
3708    case blink::WebBlendModeDifference:
3709        m_value.valueID = CSSValueDifference;
3710        break;
3711    case blink::WebBlendModeExclusion:
3712        m_value.valueID = CSSValueExclusion;
3713        break;
3714    case blink::WebBlendModeHue:
3715        m_value.valueID = CSSValueHue;
3716        break;
3717    case blink::WebBlendModeSaturation:
3718        m_value.valueID = CSSValueSaturation;
3719        break;
3720    case blink::WebBlendModeColor:
3721        m_value.valueID = CSSValueColor;
3722        break;
3723    case blink::WebBlendModeLuminosity:
3724        m_value.valueID = CSSValueLuminosity;
3725        break;
3726    }
3727}
3728
3729template<> inline CSSPrimitiveValue::operator blink::WebBlendMode() const
3730{
3731    ASSERT(isValueID());
3732    switch (m_value.valueID) {
3733    case CSSValueNormal:
3734        return blink::WebBlendModeNormal;
3735    case CSSValueMultiply:
3736        return blink::WebBlendModeMultiply;
3737    case CSSValueScreen:
3738        return blink::WebBlendModeScreen;
3739    case CSSValueOverlay:
3740        return blink::WebBlendModeOverlay;
3741    case CSSValueDarken:
3742        return blink::WebBlendModeDarken;
3743    case CSSValueLighten:
3744        return blink::WebBlendModeLighten;
3745    case CSSValueColorDodge:
3746        return blink::WebBlendModeColorDodge;
3747    case CSSValueColorBurn:
3748        return blink::WebBlendModeColorBurn;
3749    case CSSValueHardLight:
3750        return blink::WebBlendModeHardLight;
3751    case CSSValueSoftLight:
3752        return blink::WebBlendModeSoftLight;
3753    case CSSValueDifference:
3754        return blink::WebBlendModeDifference;
3755    case CSSValueExclusion:
3756        return blink::WebBlendModeExclusion;
3757    case CSSValueHue:
3758        return blink::WebBlendModeHue;
3759    case CSSValueSaturation:
3760        return blink::WebBlendModeSaturation;
3761    case CSSValueColor:
3762        return blink::WebBlendModeColor;
3763    case CSSValueLuminosity:
3764        return blink::WebBlendModeLuminosity;
3765    default:
3766        break;
3767    }
3768
3769    ASSERT_NOT_REACHED();
3770    return blink::WebBlendModeNormal;
3771}
3772
3773template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineCap e)
3774    : CSSValue(PrimitiveClass)
3775{
3776    m_primitiveUnitType = CSS_VALUE_ID;
3777    switch (e) {
3778    case ButtCap:
3779        m_value.valueID = CSSValueButt;
3780        break;
3781    case RoundCap:
3782        m_value.valueID = CSSValueRound;
3783        break;
3784    case SquareCap:
3785        m_value.valueID = CSSValueSquare;
3786        break;
3787    }
3788}
3789
3790template<> inline CSSPrimitiveValue::operator LineCap() const
3791{
3792    ASSERT(isValueID());
3793    switch (m_value.valueID) {
3794    case CSSValueButt:
3795        return ButtCap;
3796    case CSSValueRound:
3797        return RoundCap;
3798    case CSSValueSquare:
3799        return SquareCap;
3800    default:
3801        break;
3802    }
3803
3804    ASSERT_NOT_REACHED();
3805    return ButtCap;
3806}
3807
3808template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineJoin e)
3809    : CSSValue(PrimitiveClass)
3810{
3811    m_primitiveUnitType = CSS_VALUE_ID;
3812    switch (e) {
3813    case MiterJoin:
3814        m_value.valueID = CSSValueMiter;
3815        break;
3816    case RoundJoin:
3817        m_value.valueID = CSSValueRound;
3818        break;
3819    case BevelJoin:
3820        m_value.valueID = CSSValueBevel;
3821        break;
3822    }
3823}
3824
3825template<> inline CSSPrimitiveValue::operator LineJoin() const
3826{
3827    ASSERT(isValueID());
3828    switch (m_value.valueID) {
3829    case CSSValueMiter:
3830        return MiterJoin;
3831    case CSSValueRound:
3832        return RoundJoin;
3833    case CSSValueBevel:
3834        return BevelJoin;
3835    default:
3836        break;
3837    }
3838
3839    ASSERT_NOT_REACHED();
3840    return MiterJoin;
3841}
3842
3843template<> inline CSSPrimitiveValue::CSSPrimitiveValue(WindRule e)
3844    : CSSValue(PrimitiveClass)
3845{
3846    m_primitiveUnitType = CSS_VALUE_ID;
3847    switch (e) {
3848    case RULE_NONZERO:
3849        m_value.valueID = CSSValueNonzero;
3850        break;
3851    case RULE_EVENODD:
3852        m_value.valueID = CSSValueEvenodd;
3853        break;
3854    }
3855}
3856
3857template<> inline CSSPrimitiveValue::operator WindRule() const
3858{
3859    ASSERT(isValueID());
3860    switch (m_value.valueID) {
3861    case CSSValueNonzero:
3862        return RULE_NONZERO;
3863    case CSSValueEvenodd:
3864        return RULE_EVENODD;
3865    default:
3866        break;
3867    }
3868
3869    ASSERT_NOT_REACHED();
3870    return RULE_NONZERO;
3871}
3872
3873
3874template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EAlignmentBaseline e)
3875    : CSSValue(PrimitiveClass)
3876{
3877    m_primitiveUnitType = CSS_VALUE_ID;
3878    switch (e) {
3879    case AB_AUTO:
3880        m_value.valueID = CSSValueAuto;
3881        break;
3882    case AB_BASELINE:
3883        m_value.valueID = CSSValueBaseline;
3884        break;
3885    case AB_BEFORE_EDGE:
3886        m_value.valueID = CSSValueBeforeEdge;
3887        break;
3888    case AB_TEXT_BEFORE_EDGE:
3889        m_value.valueID = CSSValueTextBeforeEdge;
3890        break;
3891    case AB_MIDDLE:
3892        m_value.valueID = CSSValueMiddle;
3893        break;
3894    case AB_CENTRAL:
3895        m_value.valueID = CSSValueCentral;
3896        break;
3897    case AB_AFTER_EDGE:
3898        m_value.valueID = CSSValueAfterEdge;
3899        break;
3900    case AB_TEXT_AFTER_EDGE:
3901        m_value.valueID = CSSValueTextAfterEdge;
3902        break;
3903    case AB_IDEOGRAPHIC:
3904        m_value.valueID = CSSValueIdeographic;
3905        break;
3906    case AB_ALPHABETIC:
3907        m_value.valueID = CSSValueAlphabetic;
3908        break;
3909    case AB_HANGING:
3910        m_value.valueID = CSSValueHanging;
3911        break;
3912    case AB_MATHEMATICAL:
3913        m_value.valueID = CSSValueMathematical;
3914        break;
3915    }
3916}
3917
3918template<> inline CSSPrimitiveValue::operator EAlignmentBaseline() const
3919{
3920    ASSERT(isValueID());
3921    switch (m_value.valueID) {
3922    case CSSValueAuto:
3923        return AB_AUTO;
3924    case CSSValueBaseline:
3925        return AB_BASELINE;
3926    case CSSValueBeforeEdge:
3927        return AB_BEFORE_EDGE;
3928    case CSSValueTextBeforeEdge:
3929        return AB_TEXT_BEFORE_EDGE;
3930    case CSSValueMiddle:
3931        return AB_MIDDLE;
3932    case CSSValueCentral:
3933        return AB_CENTRAL;
3934    case CSSValueAfterEdge:
3935        return AB_AFTER_EDGE;
3936    case CSSValueTextAfterEdge:
3937        return AB_TEXT_AFTER_EDGE;
3938    case CSSValueIdeographic:
3939        return AB_IDEOGRAPHIC;
3940    case CSSValueAlphabetic:
3941        return AB_ALPHABETIC;
3942    case CSSValueHanging:
3943        return AB_HANGING;
3944    case CSSValueMathematical:
3945        return AB_MATHEMATICAL;
3946    default:
3947        break;
3948    }
3949
3950    ASSERT_NOT_REACHED();
3951    return AB_AUTO;
3952}
3953
3954template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBorderCollapse e)
3955    : CSSValue(PrimitiveClass)
3956{
3957    m_primitiveUnitType = CSS_VALUE_ID;
3958    switch (e) {
3959    case BSEPARATE:
3960        m_value.valueID = CSSValueSeparate;
3961        break;
3962    case BCOLLAPSE:
3963        m_value.valueID = CSSValueCollapse;
3964        break;
3965    }
3966}
3967
3968template<> inline CSSPrimitiveValue::operator EBorderCollapse() const
3969{
3970    ASSERT(isValueID());
3971    switch (m_value.valueID) {
3972    case CSSValueSeparate:
3973        return BSEPARATE;
3974    case CSSValueCollapse:
3975        return BCOLLAPSE;
3976    default:
3977        break;
3978    }
3979
3980    ASSERT_NOT_REACHED();
3981    return BSEPARATE;
3982}
3983
3984template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBorderFit e)
3985    : CSSValue(PrimitiveClass)
3986{
3987    m_primitiveUnitType = CSS_VALUE_ID;
3988    switch (e) {
3989    case BorderFitBorder:
3990        m_value.valueID = CSSValueBorder;
3991        break;
3992    case BorderFitLines:
3993        m_value.valueID = CSSValueLines;
3994        break;
3995    }
3996}
3997
3998template<> inline CSSPrimitiveValue::operator EBorderFit() const
3999{
4000    ASSERT(isValueID());
4001    switch (m_value.valueID) {
4002    case CSSValueBorder:
4003        return BorderFitBorder;
4004    case CSSValueLines:
4005        return BorderFitLines;
4006    default:
4007        break;
4008    }
4009
4010    ASSERT_NOT_REACHED();
4011    return BorderFitLines;
4012}
4013
4014template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EImageRendering e)
4015    : CSSValue(PrimitiveClass)
4016{
4017    m_primitiveUnitType = CSS_VALUE_ID;
4018    switch (e) {
4019    case ImageRenderingAuto:
4020        m_value.valueID = CSSValueAuto;
4021        break;
4022    case ImageRenderingOptimizeSpeed:
4023        m_value.valueID = CSSValueOptimizespeed;
4024        break;
4025    case ImageRenderingOptimizeQuality:
4026        m_value.valueID = CSSValueOptimizequality;
4027        break;
4028    case ImageRenderingOptimizeContrast:
4029        m_value.valueID = CSSValueWebkitOptimizeContrast;
4030        break;
4031    }
4032}
4033
4034template<> inline CSSPrimitiveValue::operator EImageRendering() const
4035{
4036    ASSERT(isValueID());
4037    switch (m_value.valueID) {
4038    case CSSValueAuto:
4039        return ImageRenderingAuto;
4040    case CSSValueOptimizespeed:
4041        return ImageRenderingOptimizeSpeed;
4042    case CSSValueOptimizequality:
4043        return ImageRenderingOptimizeQuality;
4044    case CSSValueWebkitOptimizeContrast:
4045        return ImageRenderingOptimizeContrast;
4046    default:
4047        break;
4048    }
4049
4050    ASSERT_NOT_REACHED();
4051    return ImageRenderingAuto;
4052}
4053
4054template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ETransformStyle3D e)
4055    : CSSValue(PrimitiveClass)
4056{
4057    m_primitiveUnitType = CSS_VALUE_ID;
4058    switch (e) {
4059    case TransformStyle3DFlat:
4060        m_value.valueID = CSSValueFlat;
4061        break;
4062    case TransformStyle3DPreserve3D:
4063        m_value.valueID = CSSValuePreserve3d;
4064        break;
4065    }
4066}
4067
4068template<> inline CSSPrimitiveValue::operator ETransformStyle3D() const
4069{
4070    ASSERT(isValueID());
4071    switch (m_value.valueID) {
4072    case CSSValueFlat:
4073        return TransformStyle3DFlat;
4074    case CSSValuePreserve3d:
4075        return TransformStyle3DPreserve3D;
4076    default:
4077        break;
4078    }
4079
4080    ASSERT_NOT_REACHED();
4081    return TransformStyle3DFlat;
4082}
4083
4084template<> inline CSSPrimitiveValue::CSSPrimitiveValue(WrapFlow wrapFlow)
4085: CSSValue(PrimitiveClass)
4086{
4087    m_primitiveUnitType = CSS_VALUE_ID;
4088    switch (wrapFlow) {
4089    case WrapFlowAuto:
4090        m_value.valueID = CSSValueAuto;
4091        break;
4092    case WrapFlowBoth:
4093        m_value.valueID = CSSValueBoth;
4094        break;
4095    case WrapFlowStart:
4096        m_value.valueID = CSSValueStart;
4097        break;
4098    case WrapFlowEnd:
4099        m_value.valueID = CSSValueEnd;
4100        break;
4101    case WrapFlowMaximum:
4102        m_value.valueID = CSSValueMaximum;
4103        break;
4104    case WrapFlowClear:
4105        m_value.valueID = CSSValueClear;
4106        break;
4107    }
4108}
4109
4110template<> inline CSSPrimitiveValue::operator WrapFlow() const
4111{
4112    ASSERT(isValueID());
4113    switch (m_value.valueID) {
4114    case CSSValueAuto:
4115        return WrapFlowAuto;
4116    case CSSValueBoth:
4117        return WrapFlowBoth;
4118    case CSSValueStart:
4119        return WrapFlowStart;
4120    case CSSValueEnd:
4121        return WrapFlowEnd;
4122    case CSSValueMaximum:
4123        return WrapFlowMaximum;
4124    case CSSValueClear:
4125        return WrapFlowClear;
4126    default:
4127        break;
4128    }
4129
4130    ASSERT_NOT_REACHED();
4131    return WrapFlowAuto;
4132}
4133
4134template<> inline CSSPrimitiveValue::CSSPrimitiveValue(WrapThrough wrapThrough)
4135: CSSValue(PrimitiveClass)
4136{
4137    m_primitiveUnitType = CSS_VALUE_ID;
4138    switch (wrapThrough) {
4139    case WrapThroughWrap:
4140        m_value.valueID = CSSValueWrap;
4141        break;
4142    case WrapThroughNone:
4143        m_value.valueID = CSSValueNone;
4144        break;
4145    }
4146}
4147
4148template<> inline CSSPrimitiveValue::operator WrapThrough() const
4149{
4150    ASSERT(isValueID());
4151    switch (m_value.valueID) {
4152    case CSSValueWrap:
4153        return WrapThroughWrap;
4154    case CSSValueNone:
4155        return WrapThroughNone;
4156    default:
4157        break;
4158    }
4159
4160    ASSERT_NOT_REACHED();
4161    return WrapThroughWrap;
4162}
4163
4164template<> inline CSSPrimitiveValue::operator GridAutoFlow() const
4165{
4166    ASSERT(isValueID());
4167    switch (m_value.valueID) {
4168    case CSSValueNone:
4169        return AutoFlowNone;
4170    case CSSValueColumn:
4171        return AutoFlowColumn;
4172    case CSSValueRow:
4173        return AutoFlowRow;
4174    default:
4175        break;
4176    }
4177
4178    ASSERT_NOT_REACHED();
4179    return AutoFlowNone;
4180
4181}
4182
4183template<> inline CSSPrimitiveValue::CSSPrimitiveValue(GridAutoFlow flow)
4184    : CSSValue(PrimitiveClass)
4185{
4186    m_primitiveUnitType = CSS_VALUE_ID;
4187    switch (flow) {
4188    case AutoFlowNone:
4189        m_value.valueID = CSSValueNone;
4190        break;
4191    case AutoFlowColumn:
4192        m_value.valueID = CSSValueColumn;
4193        break;
4194    case AutoFlowRow:
4195        m_value.valueID = CSSValueRow;
4196        break;
4197    }
4198}
4199
4200enum LengthConversion {
4201    AnyConversion = ~0,
4202    FixedConversion = 1 << 0,
4203    AutoConversion = 1 << 1,
4204    PercentConversion = 1 << 2,
4205};
4206
4207template<int supported> Length CSSPrimitiveValue::convertToLength(const CSSToLengthConversionData& conversionData)
4208{
4209    if ((supported & FixedConversion) && isLength())
4210        return computeLength<Length>(conversionData);
4211    if ((supported & PercentConversion) && isPercentage())
4212        return Length(getDoubleValue(), Percent);
4213    if ((supported & AutoConversion) && getValueID() == CSSValueAuto)
4214        return Length(Auto);
4215    if ((supported & FixedConversion) && (supported & PercentConversion) && isCalculated())
4216        return Length(cssCalcValue()->toCalcValue(conversionData));
4217    ASSERT_NOT_REACHED();
4218    return Length(0, Fixed);
4219}
4220
4221template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBufferedRendering e)
4222    : CSSValue(PrimitiveClass)
4223{
4224    m_primitiveUnitType = CSS_VALUE_ID;
4225    switch (e) {
4226    case BR_AUTO:
4227        m_value.valueID = CSSValueAuto;
4228        break;
4229    case BR_DYNAMIC:
4230        m_value.valueID = CSSValueDynamic;
4231        break;
4232    case BR_STATIC:
4233        m_value.valueID = CSSValueStatic;
4234        break;
4235    }
4236}
4237
4238template<> inline CSSPrimitiveValue::operator EBufferedRendering() const
4239{
4240    ASSERT(isValueID());
4241    switch (m_value.valueID) {
4242    case CSSValueAuto:
4243        return BR_AUTO;
4244    case CSSValueDynamic:
4245        return BR_DYNAMIC;
4246    case CSSValueStatic:
4247        return BR_STATIC;
4248    default:
4249        break;
4250    }
4251
4252    ASSERT_NOT_REACHED();
4253    return BR_AUTO;
4254}
4255
4256template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EColorInterpolation e)
4257    : CSSValue(PrimitiveClass)
4258{
4259    m_primitiveUnitType = CSS_VALUE_ID;
4260    switch (e) {
4261    case CI_AUTO:
4262        m_value.valueID = CSSValueAuto;
4263        break;
4264    case CI_SRGB:
4265        m_value.valueID = CSSValueSrgb;
4266        break;
4267    case CI_LINEARRGB:
4268        m_value.valueID = CSSValueLinearrgb;
4269        break;
4270    }
4271}
4272
4273template<> inline CSSPrimitiveValue::operator EColorInterpolation() const
4274{
4275    ASSERT(isValueID());
4276    switch (m_value.valueID) {
4277    case CSSValueSrgb:
4278        return CI_SRGB;
4279    case CSSValueLinearrgb:
4280        return CI_LINEARRGB;
4281    case CSSValueAuto:
4282        return CI_AUTO;
4283    default:
4284        break;
4285    }
4286
4287    ASSERT_NOT_REACHED();
4288    return CI_AUTO;
4289}
4290
4291template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EColorRendering e)
4292    : CSSValue(PrimitiveClass)
4293{
4294    m_primitiveUnitType = CSS_VALUE_ID;
4295    switch (e) {
4296    case CR_AUTO:
4297        m_value.valueID = CSSValueAuto;
4298        break;
4299    case CR_OPTIMIZESPEED:
4300        m_value.valueID = CSSValueOptimizespeed;
4301        break;
4302    case CR_OPTIMIZEQUALITY:
4303        m_value.valueID = CSSValueOptimizequality;
4304        break;
4305    }
4306}
4307
4308template<> inline CSSPrimitiveValue::operator EColorRendering() const
4309{
4310    ASSERT(isValueID());
4311    switch (m_value.valueID) {
4312    case CSSValueOptimizespeed:
4313        return CR_OPTIMIZESPEED;
4314    case CSSValueOptimizequality:
4315        return CR_OPTIMIZEQUALITY;
4316    case CSSValueAuto:
4317        return CR_AUTO;
4318    default:
4319        break;
4320    }
4321
4322    ASSERT_NOT_REACHED();
4323    return CR_AUTO;
4324}
4325
4326template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EDominantBaseline e)
4327    : CSSValue(PrimitiveClass)
4328{
4329    m_primitiveUnitType = CSS_VALUE_ID;
4330    switch (e) {
4331    case DB_AUTO:
4332        m_value.valueID = CSSValueAuto;
4333        break;
4334    case DB_USE_SCRIPT:
4335        m_value.valueID = CSSValueUseScript;
4336        break;
4337    case DB_NO_CHANGE:
4338        m_value.valueID = CSSValueNoChange;
4339        break;
4340    case DB_RESET_SIZE:
4341        m_value.valueID = CSSValueResetSize;
4342        break;
4343    case DB_CENTRAL:
4344        m_value.valueID = CSSValueCentral;
4345        break;
4346    case DB_MIDDLE:
4347        m_value.valueID = CSSValueMiddle;
4348        break;
4349    case DB_TEXT_BEFORE_EDGE:
4350        m_value.valueID = CSSValueTextBeforeEdge;
4351        break;
4352    case DB_TEXT_AFTER_EDGE:
4353        m_value.valueID = CSSValueTextAfterEdge;
4354        break;
4355    case DB_IDEOGRAPHIC:
4356        m_value.valueID = CSSValueIdeographic;
4357        break;
4358    case DB_ALPHABETIC:
4359        m_value.valueID = CSSValueAlphabetic;
4360        break;
4361    case DB_HANGING:
4362        m_value.valueID = CSSValueHanging;
4363        break;
4364    case DB_MATHEMATICAL:
4365        m_value.valueID = CSSValueMathematical;
4366        break;
4367    }
4368}
4369
4370template<> inline CSSPrimitiveValue::operator EDominantBaseline() const
4371{
4372    ASSERT(isValueID());
4373    switch (m_value.valueID) {
4374    case CSSValueAuto:
4375        return DB_AUTO;
4376    case CSSValueUseScript:
4377        return DB_USE_SCRIPT;
4378    case CSSValueNoChange:
4379        return DB_NO_CHANGE;
4380    case CSSValueResetSize:
4381        return DB_RESET_SIZE;
4382    case CSSValueIdeographic:
4383        return DB_IDEOGRAPHIC;
4384    case CSSValueAlphabetic:
4385        return DB_ALPHABETIC;
4386    case CSSValueHanging:
4387        return DB_HANGING;
4388    case CSSValueMathematical:
4389        return DB_MATHEMATICAL;
4390    case CSSValueCentral:
4391        return DB_CENTRAL;
4392    case CSSValueMiddle:
4393        return DB_MIDDLE;
4394    case CSSValueTextAfterEdge:
4395        return DB_TEXT_AFTER_EDGE;
4396    case CSSValueTextBeforeEdge:
4397        return DB_TEXT_BEFORE_EDGE;
4398    default:
4399        break;
4400    }
4401
4402    ASSERT_NOT_REACHED();
4403    return DB_AUTO;
4404}
4405
4406template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EShapeRendering e)
4407    : CSSValue(PrimitiveClass)
4408{
4409    m_primitiveUnitType = CSS_VALUE_ID;
4410    switch (e) {
4411    case SR_AUTO:
4412        m_value.valueID = CSSValueAuto;
4413        break;
4414    case SR_OPTIMIZESPEED:
4415        m_value.valueID = CSSValueOptimizespeed;
4416        break;
4417    case SR_CRISPEDGES:
4418        m_value.valueID = CSSValueCrispedges;
4419        break;
4420    case SR_GEOMETRICPRECISION:
4421        m_value.valueID = CSSValueGeometricprecision;
4422        break;
4423    }
4424}
4425
4426template<> inline CSSPrimitiveValue::operator EShapeRendering() const
4427{
4428    ASSERT(isValueID());
4429    switch (m_value.valueID) {
4430    case CSSValueAuto:
4431        return SR_AUTO;
4432    case CSSValueOptimizespeed:
4433        return SR_OPTIMIZESPEED;
4434    case CSSValueCrispedges:
4435        return SR_CRISPEDGES;
4436    case CSSValueGeometricprecision:
4437        return SR_GEOMETRICPRECISION;
4438    default:
4439        break;
4440    }
4441
4442    ASSERT_NOT_REACHED();
4443    return SR_AUTO;
4444}
4445
4446template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ETextAnchor e)
4447    : CSSValue(PrimitiveClass)
4448{
4449    m_primitiveUnitType = CSS_VALUE_ID;
4450    switch (e) {
4451    case TA_START:
4452        m_value.valueID = CSSValueStart;
4453        break;
4454    case TA_MIDDLE:
4455        m_value.valueID = CSSValueMiddle;
4456        break;
4457    case TA_END:
4458        m_value.valueID = CSSValueEnd;
4459        break;
4460    }
4461}
4462
4463template<> inline CSSPrimitiveValue::operator ETextAnchor() const
4464{
4465    ASSERT(isValueID());
4466    switch (m_value.valueID) {
4467    case CSSValueStart:
4468        return TA_START;
4469    case CSSValueMiddle:
4470        return TA_MIDDLE;
4471    case CSSValueEnd:
4472        return TA_END;
4473    default:
4474        break;
4475    }
4476
4477    ASSERT_NOT_REACHED();
4478    return TA_START;
4479}
4480
4481template<> inline CSSPrimitiveValue::CSSPrimitiveValue(SVGWritingMode e)
4482    : CSSValue(PrimitiveClass)
4483{
4484    m_primitiveUnitType = CSS_VALUE_ID;
4485    switch (e) {
4486    case WM_LRTB:
4487        m_value.valueID = CSSValueLrTb;
4488        break;
4489    case WM_LR:
4490        m_value.valueID = CSSValueLr;
4491        break;
4492    case WM_RLTB:
4493        m_value.valueID = CSSValueRlTb;
4494        break;
4495    case WM_RL:
4496        m_value.valueID = CSSValueRl;
4497        break;
4498    case WM_TBRL:
4499        m_value.valueID = CSSValueTbRl;
4500        break;
4501    case WM_TB:
4502        m_value.valueID = CSSValueTb;
4503        break;
4504    }
4505}
4506
4507template<> inline CSSPrimitiveValue::operator SVGWritingMode() const
4508{
4509    ASSERT(isValueID());
4510    switch (m_value.valueID) {
4511    case CSSValueLrTb:
4512        return WM_LRTB;
4513    case CSSValueLr:
4514        return WM_LR;
4515    case CSSValueRlTb:
4516        return WM_RLTB;
4517    case CSSValueRl:
4518        return WM_RL;
4519    case CSSValueTbRl:
4520        return WM_TBRL;
4521    case CSSValueTb:
4522        return WM_TB;
4523    default:
4524        break;
4525    }
4526
4527    ASSERT_NOT_REACHED();
4528    return WM_LRTB;
4529}
4530
4531template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EVectorEffect e)
4532    : CSSValue(PrimitiveClass)
4533{
4534    m_primitiveUnitType = CSS_VALUE_ID;
4535    switch (e) {
4536    case VE_NONE:
4537        m_value.valueID = CSSValueNone;
4538        break;
4539    case VE_NON_SCALING_STROKE:
4540        m_value.valueID = CSSValueNonScalingStroke;
4541        break;
4542    }
4543}
4544
4545template<> inline CSSPrimitiveValue::operator EVectorEffect() const
4546{
4547    ASSERT(isValueID());
4548    switch (m_value.valueID) {
4549    case CSSValueNone:
4550        return VE_NONE;
4551    case CSSValueNonScalingStroke:
4552        return VE_NON_SCALING_STROKE;
4553    default:
4554        break;
4555    }
4556
4557    ASSERT_NOT_REACHED();
4558    return VE_NONE;
4559}
4560
4561template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EPaintOrderType e)
4562    : CSSValue(PrimitiveClass)
4563{
4564    m_primitiveUnitType = CSS_VALUE_ID;
4565    switch (e) {
4566    case PT_FILL:
4567        m_value.valueID = CSSValueFill;
4568        break;
4569    case PT_STROKE:
4570        m_value.valueID = CSSValueStroke;
4571        break;
4572    case PT_MARKERS:
4573        m_value.valueID = CSSValueMarkers;
4574        break;
4575    default:
4576        ASSERT_NOT_REACHED();
4577        m_value.valueID = CSSValueFill;
4578        break;
4579    }
4580}
4581
4582template<> inline CSSPrimitiveValue::operator EPaintOrderType() const
4583{
4584    ASSERT(isValueID());
4585    switch (m_value.valueID) {
4586    case CSSValueFill:
4587        return PT_FILL;
4588    case CSSValueStroke:
4589        return PT_STROKE;
4590    case CSSValueMarkers:
4591        return PT_MARKERS;
4592    default:
4593        break;
4594    }
4595
4596    ASSERT_NOT_REACHED();
4597    return PT_NONE;
4598}
4599
4600template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EMaskType e)
4601    : CSSValue(PrimitiveClass)
4602{
4603    m_primitiveUnitType = CSS_VALUE_ID;
4604    switch (e) {
4605    case MT_LUMINANCE:
4606        m_value.valueID = CSSValueLuminance;
4607        break;
4608    case MT_ALPHA:
4609        m_value.valueID = CSSValueAlpha;
4610        break;
4611    }
4612}
4613
4614template<> inline CSSPrimitiveValue::operator EMaskType() const
4615{
4616    ASSERT(isValueID());
4617    switch (m_value.valueID) {
4618    case CSSValueLuminance:
4619        return MT_LUMINANCE;
4620    case CSSValueAlpha:
4621        return MT_ALPHA;
4622    default:
4623        break;
4624    }
4625
4626    ASSERT_NOT_REACHED();
4627    return MT_LUMINANCE;
4628}
4629
4630template<> inline CSSPrimitiveValue::operator TouchAction() const
4631{
4632    ASSERT(isValueID());
4633    switch (m_value.valueID) {
4634    case CSSValueNone:
4635        return TouchActionNone;
4636    case CSSValueAuto:
4637        return TouchActionAuto;
4638    case CSSValuePanX:
4639        return TouchActionPanX;
4640    case CSSValuePanY:
4641        return TouchActionPanY;
4642    case CSSValueManipulation:
4643        return TouchActionPanX | TouchActionPanY | TouchActionPinchZoom;
4644    default:
4645        break;
4646    }
4647
4648    ASSERT_NOT_REACHED();
4649    return TouchActionNone;
4650}
4651
4652template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EIsolation i)
4653    : CSSValue(PrimitiveClass)
4654{
4655    m_primitiveUnitType = CSS_VALUE_ID;
4656    switch (i) {
4657    case IsolationAuto:
4658        m_value.valueID = CSSValueAuto;
4659        break;
4660    case IsolationIsolate:
4661        m_value.valueID = CSSValueIsolate;
4662        break;
4663    }
4664}
4665
4666template<> inline CSSPrimitiveValue::operator EIsolation() const
4667{
4668    ASSERT(isValueID());
4669    switch (m_value.valueID) {
4670    case CSSValueAuto:
4671        return IsolationAuto;
4672    case CSSValueIsolate:
4673        return IsolationIsolate;
4674    default:
4675        break;
4676    }
4677
4678    ASSERT_NOT_REACHED();
4679    return IsolationAuto;
4680}
4681
4682template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TouchActionDelay t)
4683    : CSSValue(PrimitiveClass)
4684{
4685    m_primitiveUnitType = CSS_VALUE_ID;
4686    switch (t) {
4687    case TouchActionDelayNone:
4688        m_value.valueID = CSSValueNone;
4689        break;
4690    case TouchActionDelayScript:
4691        m_value.valueID = CSSValueScript;
4692        break;
4693    }
4694}
4695
4696template<> inline CSSPrimitiveValue::operator TouchActionDelay() const
4697{
4698    switch (m_value.valueID) {
4699    case CSSValueNone:
4700        return TouchActionDelayNone;
4701    case CSSValueScript:
4702        return TouchActionDelayScript;
4703    default:
4704        break;
4705    }
4706
4707    ASSERT_NOT_REACHED();
4708    return TouchActionDelayNone;
4709}
4710
4711template<> inline CSSPrimitiveValue::CSSPrimitiveValue(CSSBoxType cssBox)
4712    : CSSValue(PrimitiveClass)
4713{
4714    m_primitiveUnitType = CSS_VALUE_ID;
4715    switch (cssBox) {
4716    case MarginBox:
4717        m_value.valueID = CSSValueMarginBox;
4718        break;
4719    case BorderBox:
4720        m_value.valueID = CSSValueBorderBox;
4721        break;
4722    case PaddingBox:
4723        m_value.valueID = CSSValuePaddingBox;
4724        break;
4725    case ContentBox:
4726        m_value.valueID = CSSValueContentBox;
4727        break;
4728    case BoxMissing:
4729        // The missing box should convert to a null primitive value.
4730        ASSERT_NOT_REACHED();
4731    }
4732}
4733
4734template<> inline CSSPrimitiveValue::operator CSSBoxType() const
4735{
4736    switch (getValueID()) {
4737    case CSSValueMarginBox:
4738        return MarginBox;
4739    case CSSValueBorderBox:
4740        return BorderBox;
4741    case CSSValuePaddingBox:
4742        return PaddingBox;
4743    case CSSValueContentBox:
4744        return ContentBox;
4745    default:
4746        break;
4747    }
4748    ASSERT_NOT_REACHED();
4749    return ContentBox;
4750}
4751
4752template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ItemPosition itemPosition)
4753    : CSSValue(PrimitiveClass)
4754{
4755    m_primitiveUnitType = CSS_VALUE_ID;
4756    switch (itemPosition) {
4757    case ItemPositionAuto:
4758        m_value.valueID = CSSValueAuto;
4759        break;
4760    case ItemPositionStretch:
4761        m_value.valueID = CSSValueStretch;
4762        break;
4763    case ItemPositionBaseline:
4764        m_value.valueID = CSSValueBaseline;
4765        break;
4766    case ItemPositionCenter:
4767        m_value.valueID = CSSValueCenter;
4768        break;
4769    case ItemPositionStart:
4770        m_value.valueID = CSSValueStart;
4771        break;
4772    case ItemPositionEnd:
4773        m_value.valueID = CSSValueEnd;
4774        break;
4775    case ItemPositionSelfStart:
4776        m_value.valueID = CSSValueSelfStart;
4777        break;
4778    case ItemPositionSelfEnd:
4779        m_value.valueID = CSSValueSelfEnd;
4780        break;
4781    case ItemPositionFlexStart:
4782        m_value.valueID = CSSValueFlexStart;
4783        break;
4784    case ItemPositionFlexEnd:
4785        m_value.valueID = CSSValueFlexEnd;
4786        break;
4787    case ItemPositionLeft:
4788        m_value.valueID = CSSValueLeft;
4789        break;
4790    case ItemPositionRight:
4791        m_value.valueID = CSSValueRight;
4792        break;
4793    }
4794}
4795
4796template<> inline CSSPrimitiveValue::operator ItemPosition() const
4797{
4798    switch (m_value.valueID) {
4799    case CSSValueAuto:
4800        return ItemPositionAuto;
4801    case CSSValueStretch:
4802        return ItemPositionStretch;
4803    case CSSValueBaseline:
4804        return ItemPositionBaseline;
4805    case CSSValueCenter:
4806        return ItemPositionCenter;
4807    case CSSValueStart:
4808        return ItemPositionStart;
4809    case CSSValueEnd:
4810        return ItemPositionEnd;
4811    case CSSValueSelfStart:
4812        return ItemPositionSelfStart;
4813    case CSSValueSelfEnd:
4814        return ItemPositionSelfEnd;
4815    case CSSValueFlexStart:
4816        return ItemPositionFlexStart;
4817    case CSSValueFlexEnd:
4818        return ItemPositionFlexEnd;
4819    case CSSValueLeft:
4820        return ItemPositionLeft;
4821    case CSSValueRight:
4822        return ItemPositionRight;
4823    default:
4824        break;
4825    }
4826    ASSERT_NOT_REACHED();
4827    return ItemPositionAuto;
4828}
4829
4830template<> inline CSSPrimitiveValue::CSSPrimitiveValue(OverflowAlignment overflowAlignment)
4831    : CSSValue(PrimitiveClass)
4832{
4833    m_primitiveUnitType = CSS_VALUE_ID;
4834    switch (overflowAlignment) {
4835    case OverflowAlignmentDefault:
4836        m_value.valueID = CSSValueDefault;
4837        break;
4838    case OverflowAlignmentTrue:
4839        m_value.valueID = CSSValueTrue;
4840        break;
4841    case OverflowAlignmentSafe:
4842        m_value.valueID = CSSValueSafe;
4843        break;
4844    }
4845}
4846
4847template<> inline CSSPrimitiveValue::operator OverflowAlignment() const
4848{
4849    switch (m_value.valueID) {
4850    case CSSValueTrue:
4851        return OverflowAlignmentTrue;
4852    case CSSValueSafe:
4853        return OverflowAlignmentSafe;
4854    default:
4855        break;
4856    }
4857    ASSERT_NOT_REACHED();
4858    return OverflowAlignmentTrue;
4859}
4860
4861template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ScrollBehavior behavior)
4862    : CSSValue(PrimitiveClass)
4863{
4864    m_primitiveUnitType = CSS_VALUE_ID;
4865    switch (behavior) {
4866    case ScrollBehaviorInstant:
4867        m_value.valueID = CSSValueInstant;
4868        break;
4869    case ScrollBehaviorSmooth:
4870        m_value.valueID = CSSValueSmooth;
4871        break;
4872    case ScrollBehaviorAuto:
4873        // Behavior 'auto' is only allowed in ScrollOptions arguments passed to
4874        // CSSOM scroll APIs.
4875        ASSERT_NOT_REACHED();
4876    }
4877}
4878
4879template<> inline CSSPrimitiveValue::operator ScrollBehavior() const
4880{
4881    switch (getValueID()) {
4882    case CSSValueInstant:
4883        return ScrollBehaviorInstant;
4884    case CSSValueSmooth:
4885        return ScrollBehaviorSmooth;
4886    default:
4887        break;
4888    }
4889    ASSERT_NOT_REACHED();
4890    return ScrollBehaviorInstant;
4891}
4892
4893}
4894
4895#endif
4896