[CSS Parser] Unprefix -webkit-writing-mode
[WebKit-https.git] / Source / WebCore / css / SVGCSSComputedStyleDeclaration.cpp
1 /*
2     Copyright (C) 2007 Eric Seidel <eric@webkit.org>
3     Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org>
4
5     This library is free software; you can redistribute it and/or
6     modify it under the terms of the GNU Library General Public
7     License as published by the Free Software Foundation; either
8     version 2 of the License, or (at your option) any later version.
9
10     This library is distributed in the hope that it will be useful,
11     but WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13     Library General Public License for more details.
14
15     You should have received a copy of the GNU Library General Public License
16     along with this library; see the file COPYING.LIB.  If not, write to
17     the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18     Boston, MA 02110-1301, USA.
19  */
20
21 #include "config.h"
22 #include "CSSComputedStyleDeclaration.h"
23
24 #include "CSSPrimitiveValueMappings.h"
25 #include "CSSPropertyNames.h"
26 #include "Document.h"
27 #include "Element.h"
28 #include "RenderStyle.h"
29 #include "SVGPaint.h"
30
31 namespace WebCore {
32
33 static Ref<CSSValue> paintOrder(PaintOrder paintOrder)
34 {
35     Ref<CSSValueList> paintOrderList = CSSValueList::createSpaceSeparated();
36     Ref<CSSValue> fill = CSSPrimitiveValue::createIdentifier(CSSValueFill);
37     Ref<CSSValue> stroke = CSSPrimitiveValue::createIdentifier(CSSValueStroke);
38     Ref<CSSValue> markers = CSSPrimitiveValue::createIdentifier(CSSValueMarkers);
39
40     switch (paintOrder) {
41     case PaintOrderNormal:
42         return CSSPrimitiveValue::createIdentifier(CSSValueNormal);
43     case PaintOrderFill:
44         paintOrderList->append(WTFMove(fill));
45         break;
46     case PaintOrderFillMarkers:
47         paintOrderList->append(WTFMove(fill));
48         paintOrderList->append(WTFMove(markers));
49         break;
50     case PaintOrderStroke:
51         paintOrderList->append(WTFMove(stroke));
52         break;
53     case PaintOrderStrokeMarkers:
54         paintOrderList->append(WTFMove(stroke));
55         paintOrderList->append(WTFMove(markers));
56         break;
57     case PaintOrderMarkers:
58         paintOrderList->append(WTFMove(markers));
59         break;
60     case PaintOrderMarkersStroke:
61         paintOrderList->append(WTFMove(markers));
62         paintOrderList->append(WTFMove(stroke));
63         break;
64     }
65     return WTFMove(paintOrderList);
66 }
67
68 static RefPtr<CSSPrimitiveValue> glyphOrientationToCSSPrimitiveValue(EGlyphOrientation orientation)
69 {
70     switch (orientation) {
71         case GO_0DEG:
72             return CSSPrimitiveValue::create(0.0f, CSSPrimitiveValue::CSS_DEG);
73         case GO_90DEG:
74             return CSSPrimitiveValue::create(90.0f, CSSPrimitiveValue::CSS_DEG);
75         case GO_180DEG:
76             return CSSPrimitiveValue::create(180.0f, CSSPrimitiveValue::CSS_DEG);
77         case GO_270DEG:
78             return CSSPrimitiveValue::create(270.0f, CSSPrimitiveValue::CSS_DEG);
79         default:
80             return nullptr;
81     }
82 }
83
84 static RefPtr<CSSValue> strokeDashArrayToCSSValueList(const Vector<SVGLength>& dashes)
85 {
86     if (dashes.isEmpty())
87         return CSSPrimitiveValue::createIdentifier(CSSValueNone);
88
89     RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
90     const Vector<SVGLength>::const_iterator end = dashes.end();
91     for (Vector<SVGLength>::const_iterator it = dashes.begin(); it != end; ++it)
92         list->append(SVGLength::toCSSPrimitiveValue(*it));
93
94     return list;
95 }
96
97 RefPtr<SVGPaint> ComputedStyleExtractor::adjustSVGPaintForCurrentColor(RefPtr<SVGPaint>&& paint, const RenderStyle* style) const
98 {
99     if (paint->paintType() == SVGPaint::SVG_PAINTTYPE_CURRENTCOLOR || paint->paintType() == SVGPaint::SVG_PAINTTYPE_URI_CURRENTCOLOR)
100         paint->setColor(style->color());
101     return WTFMove(paint);
102 }
103
104 RefPtr<CSSValue> ComputedStyleExtractor::svgPropertyValue(CSSPropertyID propertyID, EUpdateLayout updateLayout)
105 {
106     if (!m_element)
107         return nullptr;
108
109     // Make sure our layout is up to date before we allow a query on these attributes.
110     if (updateLayout)
111         m_element->document().updateLayout();
112
113     auto* style = m_element->computedStyle();
114     if (!style)
115         return nullptr;
116
117     const SVGRenderStyle& svgStyle = style->svgStyle();
118
119     switch (propertyID) {
120         case CSSPropertyClipRule:
121             return CSSPrimitiveValue::create(svgStyle.clipRule());
122         case CSSPropertyFloodOpacity:
123             return CSSPrimitiveValue::create(svgStyle.floodOpacity(), CSSPrimitiveValue::CSS_NUMBER);
124         case CSSPropertyStopOpacity:
125             return CSSPrimitiveValue::create(svgStyle.stopOpacity(), CSSPrimitiveValue::CSS_NUMBER);
126         case CSSPropertyColorInterpolation:
127             return CSSPrimitiveValue::create(svgStyle.colorInterpolation());
128         case CSSPropertyColorInterpolationFilters:
129             return CSSPrimitiveValue::create(svgStyle.colorInterpolationFilters());
130         case CSSPropertyFillOpacity:
131             return CSSPrimitiveValue::create(svgStyle.fillOpacity(), CSSPrimitiveValue::CSS_NUMBER);
132         case CSSPropertyFillRule:
133             return CSSPrimitiveValue::create(svgStyle.fillRule());
134         case CSSPropertyColorRendering:
135             return CSSPrimitiveValue::create(svgStyle.colorRendering());
136         case CSSPropertyShapeRendering:
137             return CSSPrimitiveValue::create(svgStyle.shapeRendering());
138         case CSSPropertyStrokeLinecap:
139             return CSSPrimitiveValue::create(svgStyle.capStyle());
140         case CSSPropertyStrokeLinejoin:
141             return CSSPrimitiveValue::create(svgStyle.joinStyle());
142         case CSSPropertyStrokeMiterlimit:
143             return CSSPrimitiveValue::create(svgStyle.strokeMiterLimit(), CSSPrimitiveValue::CSS_NUMBER);
144         case CSSPropertyStrokeOpacity:
145             return CSSPrimitiveValue::create(svgStyle.strokeOpacity(), CSSPrimitiveValue::CSS_NUMBER);
146         case CSSPropertyAlignmentBaseline:
147             return CSSPrimitiveValue::create(svgStyle.alignmentBaseline());
148         case CSSPropertyDominantBaseline:
149             return CSSPrimitiveValue::create(svgStyle.dominantBaseline());
150         case CSSPropertyTextAnchor:
151             return CSSPrimitiveValue::create(svgStyle.textAnchor());
152         case CSSPropertyClipPath:
153             if (!svgStyle.clipperResource().isEmpty())
154                 return CSSPrimitiveValue::create(svgStyle.clipperResource(), CSSPrimitiveValue::CSS_URI);
155             return CSSPrimitiveValue::createIdentifier(CSSValueNone);
156         case CSSPropertyMask:
157             if (!svgStyle.maskerResource().isEmpty())
158                 return CSSPrimitiveValue::create(svgStyle.maskerResource(), CSSPrimitiveValue::CSS_URI);
159             return CSSPrimitiveValue::createIdentifier(CSSValueNone);
160         case CSSPropertyFloodColor:
161             return currentColorOrValidColor(style, svgStyle.floodColor());
162         case CSSPropertyLightingColor:
163             return currentColorOrValidColor(style, svgStyle.lightingColor());
164         case CSSPropertyStopColor:
165             return currentColorOrValidColor(style, svgStyle.stopColor());
166         case CSSPropertyFill:
167             return adjustSVGPaintForCurrentColor(SVGPaint::create(svgStyle.fillPaintType(), svgStyle.fillPaintUri(), svgStyle.fillPaintColor()), style);
168         case CSSPropertyKerning:
169             return SVGLength::toCSSPrimitiveValue(svgStyle.kerning());
170         case CSSPropertyMarkerEnd:
171             if (!svgStyle.markerEndResource().isEmpty())
172                 return CSSPrimitiveValue::create(svgStyle.markerEndResource(), CSSPrimitiveValue::CSS_URI);
173             return CSSPrimitiveValue::createIdentifier(CSSValueNone);
174         case CSSPropertyMarkerMid:
175             if (!svgStyle.markerMidResource().isEmpty())
176                 return CSSPrimitiveValue::create(svgStyle.markerMidResource(), CSSPrimitiveValue::CSS_URI);
177             return CSSPrimitiveValue::createIdentifier(CSSValueNone);
178         case CSSPropertyMarkerStart:
179             if (!svgStyle.markerStartResource().isEmpty())
180                 return CSSPrimitiveValue::create(svgStyle.markerStartResource(), CSSPrimitiveValue::CSS_URI);
181             return CSSPrimitiveValue::createIdentifier(CSSValueNone);
182         case CSSPropertyStroke:
183             return adjustSVGPaintForCurrentColor(SVGPaint::create(svgStyle.strokePaintType(), svgStyle.strokePaintUri(), svgStyle.strokePaintColor()), style);
184         case CSSPropertyStrokeDasharray:
185             return strokeDashArrayToCSSValueList(svgStyle.strokeDashArray());
186         case CSSPropertyBaselineShift: {
187             switch (svgStyle.baselineShift()) {
188                 case BS_BASELINE:
189                     return CSSPrimitiveValue::createIdentifier(CSSValueBaseline);
190                 case BS_SUPER:
191                     return CSSPrimitiveValue::createIdentifier(CSSValueSuper);
192                 case BS_SUB:
193                     return CSSPrimitiveValue::createIdentifier(CSSValueSub);
194                 case BS_LENGTH:
195                     return SVGLength::toCSSPrimitiveValue(svgStyle.baselineShiftValue());
196             }
197             ASSERT_NOT_REACHED();
198             return nullptr;
199         }
200         case CSSPropertyBufferedRendering:
201             return CSSPrimitiveValue::create(svgStyle.bufferedRendering());
202         case CSSPropertyGlyphOrientationHorizontal:
203             return glyphOrientationToCSSPrimitiveValue(svgStyle.glyphOrientationHorizontal());
204         case CSSPropertyGlyphOrientationVertical: {
205             if (RefPtr<CSSPrimitiveValue> value = glyphOrientationToCSSPrimitiveValue(svgStyle.glyphOrientationVertical()))
206                 return value;
207
208             if (svgStyle.glyphOrientationVertical() == GO_AUTO)
209                 return CSSPrimitiveValue::createIdentifier(CSSValueAuto);
210
211             return nullptr;
212         }
213         case CSSPropertyWebkitSvgShadow:
214             return valueForShadow(svgStyle.shadow(), propertyID, *style);
215         case CSSPropertyVectorEffect:
216             return CSSPrimitiveValue::create(svgStyle.vectorEffect());
217         case CSSPropertyMaskType:
218             return CSSPrimitiveValue::create(svgStyle.maskType());
219         case CSSPropertyPaintOrder:
220             return paintOrder(svgStyle.paintOrder());
221         case CSSPropertyMarker:
222         case CSSPropertyEnableBackground:
223         case CSSPropertyColorProfile:
224             // the above properties are not yet implemented in the engine
225             break;
226     default:
227         // If you crash here, it's because you added a css property and are not handling it
228         // in either this switch statement or the one in CSSComputedStyleDelcaration::getPropertyCSSValue
229         ASSERT_WITH_MESSAGE(0, "unimplemented propertyID: %d", propertyID);
230     }
231     LOG_ERROR("unimplemented propertyID: %d", propertyID);
232     return nullptr;
233 }
234
235 }