1 | /*
|
---|
2 | * Copyright (C) 2004 Zack Rusin <[email protected]>
|
---|
3 | * Copyright (C) 2004-2021 Apple Inc. All rights reserved.
|
---|
4 | * Copyright (C) 2007 Alexey Proskuryakov <[email protected]>
|
---|
5 | * Copyright (C) 2007 Nicholas Shanks <[email protected]>
|
---|
6 | * Copyright (C) 2011 Sencha, Inc. All rights reserved.
|
---|
7 | * Copyright (C) 2013 Adobe Systems Incorporated. All rights reserved.
|
---|
8 | *
|
---|
9 | * This library is free software; you can redistribute it and/or
|
---|
10 | * modify it under the terms of the GNU Lesser General Public
|
---|
11 | * License as published by the Free Software Foundation; either
|
---|
12 | * version 2 of the License, or (at your option) any later version.
|
---|
13 | *
|
---|
14 | * This library is distributed in the hope that it will be useful,
|
---|
15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
---|
16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
---|
17 | * Lesser General Public License for more details.
|
---|
18 | *
|
---|
19 | * You should have received a copy of the GNU Lesser General Public
|
---|
20 | * License along with this library; if not, write to the Free Software
|
---|
21 | * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
---|
22 | * 02110-1301 USA
|
---|
23 | */
|
---|
24 |
|
---|
25 | #include "config.h"
|
---|
26 | #include "CSSComputedStyleDeclaration.h"
|
---|
27 |
|
---|
28 | #include "BasicShapeFunctions.h"
|
---|
29 | #include "CSSBasicShapes.h"
|
---|
30 | #include "CSSBorderImage.h"
|
---|
31 | #include "CSSBorderImageSliceValue.h"
|
---|
32 | #include "CSSFontFeatureValue.h"
|
---|
33 | #include "CSSFontStyleValue.h"
|
---|
34 | #include "CSSFontValue.h"
|
---|
35 | #include "CSSFontVariationValue.h"
|
---|
36 | #include "CSSFunctionValue.h"
|
---|
37 | #include "CSSGridAutoRepeatValue.h"
|
---|
38 | #include "CSSGridIntegerRepeatValue.h"
|
---|
39 | #include "CSSLineBoxContainValue.h"
|
---|
40 | #include "CSSPrimitiveValue.h"
|
---|
41 | #include "CSSPrimitiveValueMappings.h"
|
---|
42 | #include "CSSPropertyAnimation.h"
|
---|
43 | #include "CSSPropertyNames.h"
|
---|
44 | #include "CSSPropertyParser.h"
|
---|
45 | #include "CSSRayValue.h"
|
---|
46 | #include "CSSReflectValue.h"
|
---|
47 | #include "CSSSelector.h"
|
---|
48 | #include "CSSShadowValue.h"
|
---|
49 | #include "CSSTimingFunctionValue.h"
|
---|
50 | #include "CSSValueList.h"
|
---|
51 | #include "CSSValuePool.h"
|
---|
52 | #include "ComposedTreeAncestorIterator.h"
|
---|
53 | #include "ContentData.h"
|
---|
54 | #include "CursorList.h"
|
---|
55 | #include "DeprecatedCSSOMValue.h"
|
---|
56 | #include "Document.h"
|
---|
57 | #include "ElementRareData.h"
|
---|
58 | #include "FontCascade.h"
|
---|
59 | #include "FontSelectionValueInlines.h"
|
---|
60 | #include "FontTaggedSettings.h"
|
---|
61 | #include "NodeRenderStyle.h"
|
---|
62 | #include "Pair.h"
|
---|
63 | #include "QuotesData.h"
|
---|
64 | #include "Rect.h"
|
---|
65 | #include "RenderBlock.h"
|
---|
66 | #include "RenderBox.h"
|
---|
67 | #include "RenderInline.h"
|
---|
68 | #include "RenderStyle.h"
|
---|
69 | #include "SVGElement.h"
|
---|
70 | #include "SVGRenderSupport.h"
|
---|
71 | #include "Settings.h"
|
---|
72 | #include "ShapeValue.h"
|
---|
73 | #include "StyleProperties.h"
|
---|
74 | #include "StylePropertyShorthand.h"
|
---|
75 | #include "StylePropertyShorthandFunctions.h"
|
---|
76 | #include "StyleResolver.h"
|
---|
77 | #include "StyleScope.h"
|
---|
78 | #include "StyleScrollSnapPoints.h"
|
---|
79 | #include "Styleable.h"
|
---|
80 | #include "TouchAction.h"
|
---|
81 | #include "WebKitFontFamilyNames.h"
|
---|
82 | #include "WillChangeData.h"
|
---|
83 | #include <wtf/IsoMallocInlines.h>
|
---|
84 | #include <wtf/NeverDestroyed.h>
|
---|
85 | #include <wtf/text/StringBuilder.h>
|
---|
86 |
|
---|
87 | #include "CSSGridLineNamesValue.h"
|
---|
88 | #include "CSSGridTemplateAreasValue.h"
|
---|
89 | #include "RenderGrid.h"
|
---|
90 |
|
---|
91 | namespace WebCore {
|
---|
92 |
|
---|
93 | WTF_MAKE_ISO_ALLOCATED_IMPL(CSSComputedStyleDeclaration);
|
---|
94 |
|
---|
95 | static CSSValueID valueForRepeatRule(NinePieceImageRule rule)
|
---|
96 | {
|
---|
97 | switch (rule) {
|
---|
98 | case NinePieceImageRule::Repeat:
|
---|
99 | return CSSValueRepeat;
|
---|
100 | case NinePieceImageRule::Round:
|
---|
101 | return CSSValueRound;
|
---|
102 | case NinePieceImageRule::Space:
|
---|
103 | return CSSValueSpace;
|
---|
104 | default:
|
---|
105 | return CSSValueStretch;
|
---|
106 | }
|
---|
107 | }
|
---|
108 |
|
---|
109 | static Ref<CSSPrimitiveValue> valueForImageSliceSide(const Length& length)
|
---|
110 | {
|
---|
111 | // These values can be percentages, numbers, or while an animation of mixed types is in progress,
|
---|
112 | // a calculation that combines a percentage and a number.
|
---|
113 | if (length.isPercent())
|
---|
114 | return CSSValuePool::singleton().createValue(length.percent(), CSSUnitType::CSS_PERCENTAGE);
|
---|
115 | if (length.isAuto() || length.isFixed())
|
---|
116 | return CSSValuePool::singleton().createValue(length.value(), CSSUnitType::CSS_NUMBER);
|
---|
117 |
|
---|
118 | // Calculating the actual length currently in use would require most of the code from RenderBoxModelObject::paintNinePieceImage.
|
---|
119 | // And even if we could do that, it's not clear if that's exactly what we'd want during animation.
|
---|
120 | // FIXME: For now, just return 0.
|
---|
121 | ASSERT(length.isCalculated());
|
---|
122 | return CSSValuePool::singleton().createValue(0, CSSUnitType::CSS_NUMBER);
|
---|
123 | }
|
---|
124 |
|
---|
125 | static Ref<CSSBorderImageSliceValue> valueForNinePieceImageSlice(const NinePieceImage& image)
|
---|
126 | {
|
---|
127 | auto& slices = image.imageSlices();
|
---|
128 |
|
---|
129 | RefPtr<CSSPrimitiveValue> top = valueForImageSliceSide(slices.top());
|
---|
130 |
|
---|
131 | RefPtr<CSSPrimitiveValue> right;
|
---|
132 | RefPtr<CSSPrimitiveValue> bottom;
|
---|
133 | RefPtr<CSSPrimitiveValue> left;
|
---|
134 |
|
---|
135 | if (slices.right() == slices.top() && slices.bottom() == slices.top() && slices.left() == slices.top()) {
|
---|
136 | right = top;
|
---|
137 | bottom = top;
|
---|
138 | left = top;
|
---|
139 | } else {
|
---|
140 | right = valueForImageSliceSide(slices.right());
|
---|
141 |
|
---|
142 | if (slices.bottom() == slices.top() && slices.right() == slices.left()) {
|
---|
143 | bottom = top;
|
---|
144 | left = right;
|
---|
145 | } else {
|
---|
146 | bottom = valueForImageSliceSide(slices.bottom());
|
---|
147 |
|
---|
148 | if (slices.left() == slices.right())
|
---|
149 | left = right;
|
---|
150 | else
|
---|
151 | left = valueForImageSliceSide(slices.left());
|
---|
152 | }
|
---|
153 | }
|
---|
154 |
|
---|
155 | auto quad = Quad::create();
|
---|
156 | quad->setTop(WTFMove(top));
|
---|
157 | quad->setRight(WTFMove(right));
|
---|
158 | quad->setBottom(WTFMove(bottom));
|
---|
159 | quad->setLeft(WTFMove(left));
|
---|
160 |
|
---|
161 | return CSSBorderImageSliceValue::create(CSSValuePool::singleton().createValue(WTFMove(quad)), image.fill());
|
---|
162 | }
|
---|
163 |
|
---|
164 | static Ref<CSSPrimitiveValue> valueForNinePieceImageQuad(const LengthBox& box, const RenderStyle& style)
|
---|
165 | {
|
---|
166 | RefPtr<CSSPrimitiveValue> top;
|
---|
167 | RefPtr<CSSPrimitiveValue> right;
|
---|
168 | RefPtr<CSSPrimitiveValue> bottom;
|
---|
169 | RefPtr<CSSPrimitiveValue> left;
|
---|
170 |
|
---|
171 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
172 |
|
---|
173 | if (box.top().isRelative())
|
---|
174 | top = cssValuePool.createValue(box.top().value(), CSSUnitType::CSS_NUMBER);
|
---|
175 | else
|
---|
176 | top = cssValuePool.createValue(box.top(), style);
|
---|
177 |
|
---|
178 | if (box.right() == box.top() && box.bottom() == box.top() && box.left() == box.top()) {
|
---|
179 | right = top;
|
---|
180 | bottom = top;
|
---|
181 | left = top;
|
---|
182 | } else {
|
---|
183 | if (box.right().isRelative())
|
---|
184 | right = cssValuePool.createValue(box.right().value(), CSSUnitType::CSS_NUMBER);
|
---|
185 | else
|
---|
186 | right = cssValuePool.createValue(box.right(), style);
|
---|
187 |
|
---|
188 | if (box.bottom() == box.top() && box.right() == box.left()) {
|
---|
189 | bottom = top;
|
---|
190 | left = right;
|
---|
191 | } else {
|
---|
192 | if (box.bottom().isRelative())
|
---|
193 | bottom = cssValuePool.createValue(box.bottom().value(), CSSUnitType::CSS_NUMBER);
|
---|
194 | else
|
---|
195 | bottom = cssValuePool.createValue(box.bottom(), style);
|
---|
196 |
|
---|
197 | if (box.left() == box.right())
|
---|
198 | left = right;
|
---|
199 | else {
|
---|
200 | if (box.left().isRelative())
|
---|
201 | left = cssValuePool.createValue(box.left().value(), CSSUnitType::CSS_NUMBER);
|
---|
202 | else
|
---|
203 | left = cssValuePool.createValue(box.left(), style);
|
---|
204 | }
|
---|
205 | }
|
---|
206 | }
|
---|
207 |
|
---|
208 | auto quad = Quad::create();
|
---|
209 | quad->setTop(WTFMove(top));
|
---|
210 | quad->setRight(WTFMove(right));
|
---|
211 | quad->setBottom(WTFMove(bottom));
|
---|
212 | quad->setLeft(WTFMove(left));
|
---|
213 |
|
---|
214 | return cssValuePool.createValue(WTFMove(quad));
|
---|
215 | }
|
---|
216 |
|
---|
217 | static Ref<CSSValue> valueForNinePieceImageRepeat(const NinePieceImage& image)
|
---|
218 | {
|
---|
219 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
220 | auto horizontalRepeat = cssValuePool.createIdentifierValue(valueForRepeatRule(image.horizontalRule()));
|
---|
221 | RefPtr<CSSPrimitiveValue> verticalRepeat;
|
---|
222 | if (image.horizontalRule() == image.verticalRule())
|
---|
223 | verticalRepeat = horizontalRepeat.copyRef();
|
---|
224 | else
|
---|
225 | verticalRepeat = cssValuePool.createIdentifierValue(valueForRepeatRule(image.verticalRule()));
|
---|
226 | return cssValuePool.createValue(Pair::create(WTFMove(horizontalRepeat), WTFMove(verticalRepeat)));
|
---|
227 | }
|
---|
228 |
|
---|
229 | static RefPtr<CSSValue> valueForNinePieceImage(CSSPropertyID propertyID, const NinePieceImage& image, const RenderStyle& style)
|
---|
230 | {
|
---|
231 | if (!image.hasImage())
|
---|
232 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
233 |
|
---|
234 | RefPtr<CSSValue> imageValue;
|
---|
235 | if (image.image())
|
---|
236 | imageValue = image.image()->cssValue();
|
---|
237 |
|
---|
238 | // -webkit-border-image has a legacy behavior that makes fixed border slices also set the border widths.
|
---|
239 | const LengthBox& slices = image.borderSlices();
|
---|
240 | bool overridesBorderWidths = propertyID == CSSPropertyWebkitBorderImage && (slices.top().isFixed() || slices.right().isFixed() || slices.bottom().isFixed() || slices.left().isFixed());
|
---|
241 | if (overridesBorderWidths != image.overridesBorderWidths())
|
---|
242 | return nullptr;
|
---|
243 |
|
---|
244 | auto imageSlices = valueForNinePieceImageSlice(image);
|
---|
245 | auto borderSlices = valueForNinePieceImageQuad(slices, style);
|
---|
246 | auto outset = valueForNinePieceImageQuad(image.outset(), style);
|
---|
247 | auto repeat = valueForNinePieceImageRepeat(image);
|
---|
248 |
|
---|
249 | return createBorderImageValue(WTFMove(imageValue), WTFMove(imageSlices), WTFMove(borderSlices), WTFMove(outset), WTFMove(repeat));
|
---|
250 | }
|
---|
251 |
|
---|
252 | inline static Ref<CSSPrimitiveValue> zoomAdjustedPixelValue(double value, const RenderStyle& style)
|
---|
253 | {
|
---|
254 | return CSSValuePool::singleton().createValue(adjustFloatForAbsoluteZoom(value, style), CSSUnitType::CSS_PX);
|
---|
255 | }
|
---|
256 |
|
---|
257 | inline static Ref<CSSPrimitiveValue> zoomAdjustedNumberValue(double value, const RenderStyle& style)
|
---|
258 | {
|
---|
259 | return CSSValuePool::singleton().createValue(value / style.effectiveZoom(), CSSUnitType::CSS_NUMBER);
|
---|
260 | }
|
---|
261 |
|
---|
262 | static Ref<CSSPrimitiveValue> zoomAdjustedPixelValueForLength(const Length& length, const RenderStyle& style)
|
---|
263 | {
|
---|
264 | if (length.isFixed())
|
---|
265 | return zoomAdjustedPixelValue(length.value(), style);
|
---|
266 | return CSSValuePool::singleton().createValue(length, style);
|
---|
267 | }
|
---|
268 |
|
---|
269 | static Ref<CSSValue> valueForReflection(const StyleReflection* reflection, const RenderStyle& style)
|
---|
270 | {
|
---|
271 | if (!reflection)
|
---|
272 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
273 |
|
---|
274 | RefPtr<CSSPrimitiveValue> offset;
|
---|
275 | if (reflection->offset().isPercentOrCalculated())
|
---|
276 | offset = CSSValuePool::singleton().createValue(reflection->offset().percent(), CSSUnitType::CSS_PERCENTAGE);
|
---|
277 | else
|
---|
278 | offset = zoomAdjustedPixelValue(reflection->offset().value(), style);
|
---|
279 |
|
---|
280 | RefPtr<CSSPrimitiveValue> direction;
|
---|
281 | switch (reflection->direction()) {
|
---|
282 | case ReflectionDirection::Below:
|
---|
283 | direction = CSSValuePool::singleton().createIdentifierValue(CSSValueBelow);
|
---|
284 | break;
|
---|
285 | case ReflectionDirection::Above:
|
---|
286 | direction = CSSValuePool::singleton().createIdentifierValue(CSSValueAbove);
|
---|
287 | break;
|
---|
288 | case ReflectionDirection::Left:
|
---|
289 | direction = CSSValuePool::singleton().createIdentifierValue(CSSValueLeft);
|
---|
290 | break;
|
---|
291 | case ReflectionDirection::Right:
|
---|
292 | direction = CSSValuePool::singleton().createIdentifierValue(CSSValueRight);
|
---|
293 | break;
|
---|
294 | }
|
---|
295 |
|
---|
296 | return CSSReflectValue::create(direction.releaseNonNull(), offset.releaseNonNull(), valueForNinePieceImage(CSSPropertyWebkitBoxReflect, reflection->mask(), style));
|
---|
297 | }
|
---|
298 |
|
---|
299 | static Ref<CSSValueList> createPositionListForLayer(CSSPropertyID propertyID, const FillLayer& layer, const RenderStyle& style)
|
---|
300 | {
|
---|
301 | auto list = CSSValueList::createSpaceSeparated();
|
---|
302 | if (layer.isBackgroundXOriginSet() && layer.backgroundXOrigin() != Edge::Left) {
|
---|
303 | ASSERT_UNUSED(propertyID, propertyID == CSSPropertyBackgroundPosition || propertyID == CSSPropertyMaskPosition || propertyID == CSSPropertyWebkitMaskPosition);
|
---|
304 | list->append(CSSValuePool::singleton().createValue(layer.backgroundXOrigin()));
|
---|
305 | }
|
---|
306 | list->append(zoomAdjustedPixelValueForLength(layer.xPosition(), style));
|
---|
307 | if (layer.isBackgroundYOriginSet() && layer.backgroundYOrigin() != Edge::Top) {
|
---|
308 | ASSERT(propertyID == CSSPropertyBackgroundPosition || propertyID == CSSPropertyMaskPosition || propertyID == CSSPropertyWebkitMaskPosition);
|
---|
309 | list->append(CSSValuePool::singleton().createValue(layer.backgroundYOrigin()));
|
---|
310 | }
|
---|
311 | list->append(zoomAdjustedPixelValueForLength(layer.yPosition(), style));
|
---|
312 | return list;
|
---|
313 | }
|
---|
314 |
|
---|
315 | static Ref<CSSValue> createSingleAxisPositionValueForLayer(CSSPropertyID propertyID, const FillLayer& layer, const RenderStyle& style)
|
---|
316 | {
|
---|
317 | if (propertyID == CSSPropertyBackgroundPositionX || propertyID == CSSPropertyWebkitMaskPositionX) {
|
---|
318 | if (!layer.isBackgroundXOriginSet() || layer.backgroundXOrigin() == Edge::Left)
|
---|
319 | return zoomAdjustedPixelValueForLength(layer.xPosition(), style);
|
---|
320 |
|
---|
321 | auto list = CSSValueList::createSpaceSeparated();
|
---|
322 | list->append(CSSValuePool::singleton().createValue(layer.backgroundXOrigin()));
|
---|
323 | list->append(zoomAdjustedPixelValueForLength(layer.xPosition(), style));
|
---|
324 | return list;
|
---|
325 | }
|
---|
326 |
|
---|
327 | if (!layer.isBackgroundYOriginSet() || layer.backgroundYOrigin() == Edge::Top)
|
---|
328 | return zoomAdjustedPixelValueForLength(layer.yPosition(), style);
|
---|
329 |
|
---|
330 | auto list = CSSValueList::createSpaceSeparated();
|
---|
331 | list->append(CSSValuePool::singleton().createValue(layer.backgroundYOrigin()));
|
---|
332 | list->append(zoomAdjustedPixelValueForLength(layer.yPosition(), style));
|
---|
333 | return list;
|
---|
334 | }
|
---|
335 |
|
---|
336 | static Length getOffsetComputedLength(const RenderStyle& style, CSSPropertyID propertyID)
|
---|
337 | {
|
---|
338 | // If specified as a length, the corresponding absolute length; if specified as
|
---|
339 | // a percentage, the specified value; otherwise, 'auto'. Hence, we can just
|
---|
340 | // return the value in the style.
|
---|
341 | //
|
---|
342 | // See http://www.w3.org/TR/CSS21/cascade.html#computed-value
|
---|
343 | switch (propertyID) {
|
---|
344 | case CSSPropertyLeft:
|
---|
345 | return style.left();
|
---|
346 | case CSSPropertyRight:
|
---|
347 | return style.right();
|
---|
348 | case CSSPropertyTop:
|
---|
349 | return style.top();
|
---|
350 | case CSSPropertyBottom:
|
---|
351 | return style.bottom();
|
---|
352 | default:
|
---|
353 | ASSERT_NOT_REACHED();
|
---|
354 | }
|
---|
355 |
|
---|
356 | return { };
|
---|
357 | }
|
---|
358 |
|
---|
359 | static LayoutUnit getOffsetUsedStyleRelative(RenderBox& box, CSSPropertyID propertyID)
|
---|
360 | {
|
---|
361 | // For relatively positioned boxes, the offset is with respect to the top edges
|
---|
362 | // of the box itself. This ties together top/bottom and left/right to be
|
---|
363 | // opposites of each other.
|
---|
364 | //
|
---|
365 | // See http://www.w3.org/TR/CSS2/visuren.html#relative-positioning
|
---|
366 | //
|
---|
367 | // Specifically;
|
---|
368 | // Since boxes are not split or stretched as a result of 'left' or
|
---|
369 | // 'right', the used values are always: left = -right.
|
---|
370 | // and
|
---|
371 | // Since boxes are not split or stretched as a result of 'top' or
|
---|
372 | // 'bottom', the used values are always: top = -bottom.
|
---|
373 | switch (propertyID) {
|
---|
374 | case CSSPropertyTop:
|
---|
375 | return box.relativePositionOffset().height();
|
---|
376 | case CSSPropertyBottom:
|
---|
377 | return -(box.relativePositionOffset().height());
|
---|
378 | case CSSPropertyLeft:
|
---|
379 | return box.relativePositionOffset().width();
|
---|
380 | case CSSPropertyRight:
|
---|
381 | return -(box.relativePositionOffset().width());
|
---|
382 | default:
|
---|
383 | ASSERT_NOT_REACHED();
|
---|
384 | }
|
---|
385 |
|
---|
386 | return 0;
|
---|
387 | }
|
---|
388 |
|
---|
389 | static LayoutUnit getOffsetUsedStyleOutOfFlowPositioned(RenderBlock& container, RenderBox& box, CSSPropertyID propertyID)
|
---|
390 | {
|
---|
391 | // For out-of-flow positioned boxes, the offset is how far an box's margin
|
---|
392 | // edge is offset below the edge of the box's containing block.
|
---|
393 | // See http://www.w3.org/TR/CSS2/visuren.html#position-props
|
---|
394 |
|
---|
395 | // Margins are included in offsetTop/offsetLeft so we need to remove them here.
|
---|
396 | switch (propertyID) {
|
---|
397 | case CSSPropertyTop:
|
---|
398 | return box.offsetTop() - box.marginTop();
|
---|
399 | case CSSPropertyBottom:
|
---|
400 | return container.clientHeight() - (box.offsetTop() + box.offsetHeight()) - box.marginBottom();
|
---|
401 | case CSSPropertyLeft:
|
---|
402 | return box.offsetLeft() - box.marginLeft();
|
---|
403 | case CSSPropertyRight:
|
---|
404 | return container.clientWidth() - (box.offsetLeft() + box.offsetWidth()) - box.marginRight();
|
---|
405 | default:
|
---|
406 | ASSERT_NOT_REACHED();
|
---|
407 | }
|
---|
408 |
|
---|
409 | return 0;
|
---|
410 | }
|
---|
411 |
|
---|
412 | static RefPtr<CSSValue> positionOffsetValue(const RenderStyle& style, CSSPropertyID propertyID, RenderObject* renderer)
|
---|
413 | {
|
---|
414 | auto offset = getOffsetComputedLength(style, propertyID);
|
---|
415 |
|
---|
416 | // If the element is not displayed; return the "computed value".
|
---|
417 | if (!renderer || !renderer->isBox())
|
---|
418 | return zoomAdjustedPixelValueForLength(offset, style);
|
---|
419 |
|
---|
420 | auto& box = downcast<RenderBox>(*renderer);
|
---|
421 | auto* containingBlock = box.containingBlock();
|
---|
422 |
|
---|
423 | // Resolve a "computed value" percentage if the element is positioned.
|
---|
424 | if (containingBlock && offset.isPercentOrCalculated() && box.isPositioned()) {
|
---|
425 | bool isVerticalProperty;
|
---|
426 | if (propertyID == CSSPropertyTop || propertyID == CSSPropertyBottom)
|
---|
427 | isVerticalProperty = true;
|
---|
428 | else {
|
---|
429 | ASSERT(propertyID == CSSPropertyLeft || propertyID == CSSPropertyRight);
|
---|
430 | isVerticalProperty = false;
|
---|
431 | }
|
---|
432 | LayoutUnit containingBlockSize;
|
---|
433 | if (box.isStickilyPositioned()) {
|
---|
434 | auto& enclosingClippingBox = box.enclosingClippingBoxForStickyPosition().first;
|
---|
435 | if (isVerticalProperty == enclosingClippingBox.isHorizontalWritingMode())
|
---|
436 | containingBlockSize = enclosingClippingBox.contentLogicalHeight();
|
---|
437 | else
|
---|
438 | containingBlockSize = enclosingClippingBox.contentLogicalWidth();
|
---|
439 | } else {
|
---|
440 | if (isVerticalProperty == containingBlock->isHorizontalWritingMode()) {
|
---|
441 | containingBlockSize = box.isOutOfFlowPositioned()
|
---|
442 | ? box.containingBlockLogicalHeightForPositioned(*containingBlock, false)
|
---|
443 | : box.containingBlockLogicalHeightForContent(ExcludeMarginBorderPadding);
|
---|
444 | } else {
|
---|
445 | containingBlockSize = box.isOutOfFlowPositioned()
|
---|
446 | ? box.containingBlockLogicalWidthForPositioned(*containingBlock, nullptr, false)
|
---|
447 | : box.containingBlockLogicalWidthForContent();
|
---|
448 | }
|
---|
449 | }
|
---|
450 | return zoomAdjustedPixelValue(floatValueForLength(offset, containingBlockSize), style);
|
---|
451 | }
|
---|
452 |
|
---|
453 | // Return a "computed value" length.
|
---|
454 | if (!offset.isAuto())
|
---|
455 | return zoomAdjustedPixelValueForLength(offset, style);
|
---|
456 |
|
---|
457 | // The property won't be overconstrained if its computed value is "auto", so the "used value" can be returned.
|
---|
458 | if (box.isRelativelyPositioned())
|
---|
459 | return zoomAdjustedPixelValue(getOffsetUsedStyleRelative(box, propertyID), style);
|
---|
460 |
|
---|
461 | if (containingBlock && box.isOutOfFlowPositioned())
|
---|
462 | return zoomAdjustedPixelValue(getOffsetUsedStyleOutOfFlowPositioned(*containingBlock, box, propertyID), style);
|
---|
463 |
|
---|
464 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
465 | }
|
---|
466 |
|
---|
467 | Ref<CSSPrimitiveValue> ComputedStyleExtractor::currentColorOrValidColor(const RenderStyle* style, const Color& color) const
|
---|
468 | {
|
---|
469 | // This function does NOT look at visited information, so that computed style doesn't expose that.
|
---|
470 | if (!color.isValid())
|
---|
471 | return CSSValuePool::singleton().createColorValue(style->color());
|
---|
472 | return CSSValuePool::singleton().createColorValue(color);
|
---|
473 | }
|
---|
474 |
|
---|
475 | static Ref<CSSPrimitiveValue> percentageOrZoomAdjustedValue(Length length, const RenderStyle& style)
|
---|
476 | {
|
---|
477 | if (length.isPercent())
|
---|
478 | return CSSValuePool::singleton().createValue(length.percent(), CSSUnitType::CSS_PERCENTAGE);
|
---|
479 |
|
---|
480 | return zoomAdjustedPixelValueForLength(length, style);
|
---|
481 | }
|
---|
482 |
|
---|
483 | static Ref<CSSPrimitiveValue> autoOrZoomAdjustedValue(Length length, const RenderStyle& style)
|
---|
484 | {
|
---|
485 | if (length.isAuto())
|
---|
486 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
487 |
|
---|
488 | return zoomAdjustedPixelValueForLength(length, style);
|
---|
489 | }
|
---|
490 |
|
---|
491 | static Ref<CSSValueList> borderRadiusCornerValues(const LengthSize& radius, const RenderStyle& style)
|
---|
492 | {
|
---|
493 | auto list = CSSValueList::createSpaceSeparated();
|
---|
494 | list->append(percentageOrZoomAdjustedValue(radius.width, style));
|
---|
495 | list->append(percentageOrZoomAdjustedValue(radius.height, style));
|
---|
496 | return list;
|
---|
497 | }
|
---|
498 |
|
---|
499 | static Ref<CSSValue> valueForQuotes(const QuotesData* quotes)
|
---|
500 | {
|
---|
501 | if (!quotes)
|
---|
502 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
503 | unsigned size = quotes->size();
|
---|
504 | if (!size)
|
---|
505 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
506 | auto list = CSSValueList::createSpaceSeparated();
|
---|
507 | for (unsigned i = 0; i < size; ++i) {
|
---|
508 | list->append(CSSValuePool::singleton().createValue(quotes->openQuote(i), CSSUnitType::CSS_STRING));
|
---|
509 | list->append(CSSValuePool::singleton().createValue(quotes->closeQuote(i), CSSUnitType::CSS_STRING));
|
---|
510 | }
|
---|
511 | return list;
|
---|
512 | }
|
---|
513 |
|
---|
514 | static Ref<CSSValue> borderRadiusCornerValue(const LengthSize& radius, const RenderStyle& style)
|
---|
515 | {
|
---|
516 | if (radius.width == radius.height)
|
---|
517 | return percentageOrZoomAdjustedValue(radius.width, style);
|
---|
518 | return borderRadiusCornerValues(radius, style);
|
---|
519 | }
|
---|
520 |
|
---|
521 | static Ref<CSSValueList> borderRadiusShorthandValue(const RenderStyle& style)
|
---|
522 | {
|
---|
523 | auto list = CSSValueList::createSlashSeparated();
|
---|
524 | bool showHorizontalBottomLeft = style.borderTopRightRadius().width != style.borderBottomLeftRadius().width;
|
---|
525 | bool showHorizontalBottomRight = showHorizontalBottomLeft || (style.borderBottomRightRadius().width != style.borderTopLeftRadius().width);
|
---|
526 | bool showHorizontalTopRight = showHorizontalBottomRight || (style.borderTopRightRadius().width != style.borderTopLeftRadius().width);
|
---|
527 |
|
---|
528 | bool showVerticalBottomLeft = style.borderTopRightRadius().height != style.borderBottomLeftRadius().height;
|
---|
529 | bool showVerticalBottomRight = showVerticalBottomLeft || (style.borderBottomRightRadius().height != style.borderTopLeftRadius().height);
|
---|
530 | bool showVerticalTopRight = showVerticalBottomRight || (style.borderTopRightRadius().height != style.borderTopLeftRadius().height);
|
---|
531 |
|
---|
532 | auto topLeftRadius = borderRadiusCornerValues(style.borderTopLeftRadius(), style);
|
---|
533 | auto topRightRadius = borderRadiusCornerValues(style.borderTopRightRadius(), style);
|
---|
534 | auto bottomRightRadius = borderRadiusCornerValues(style.borderBottomRightRadius(), style);
|
---|
535 | auto bottomLeftRadius = borderRadiusCornerValues(style.borderBottomLeftRadius(), style);
|
---|
536 |
|
---|
537 | auto horizontalRadii = CSSValueList::createSpaceSeparated();
|
---|
538 | horizontalRadii->append(*topLeftRadius->item(0));
|
---|
539 | if (showHorizontalTopRight)
|
---|
540 | horizontalRadii->append(*topRightRadius->item(0));
|
---|
541 | if (showHorizontalBottomRight)
|
---|
542 | horizontalRadii->append(*bottomRightRadius->item(0));
|
---|
543 | if (showHorizontalBottomLeft)
|
---|
544 | horizontalRadii->append(*bottomLeftRadius->item(0));
|
---|
545 |
|
---|
546 | list->append(WTFMove(horizontalRadii));
|
---|
547 |
|
---|
548 | auto verticalRadiiList = CSSValueList::createSpaceSeparated();
|
---|
549 | verticalRadiiList->append(*topLeftRadius->item(1));
|
---|
550 | if (showVerticalTopRight)
|
---|
551 | verticalRadiiList->append(*topRightRadius->item(1));
|
---|
552 | if (showVerticalBottomRight)
|
---|
553 | verticalRadiiList->append(*bottomRightRadius->item(1));
|
---|
554 | if (showVerticalBottomLeft)
|
---|
555 | verticalRadiiList->append(*bottomLeftRadius->item(1));
|
---|
556 |
|
---|
557 | if (!verticalRadiiList->equals(downcast<CSSValueList>(*list->item(0))))
|
---|
558 | list->append(WTFMove(verticalRadiiList));
|
---|
559 |
|
---|
560 | return list;
|
---|
561 | }
|
---|
562 |
|
---|
563 | static LayoutRect sizingBox(RenderObject& renderer)
|
---|
564 | {
|
---|
565 | if (!is<RenderBox>(renderer))
|
---|
566 | return LayoutRect();
|
---|
567 |
|
---|
568 | auto& box = downcast<RenderBox>(renderer);
|
---|
569 | return box.style().boxSizing() == BoxSizing::BorderBox ? box.borderBoxRect() : box.computedCSSContentBoxRect();
|
---|
570 | }
|
---|
571 |
|
---|
572 | static Ref<CSSFunctionValue> matrixTransformValue(const TransformationMatrix& transform, const RenderStyle& style)
|
---|
573 | {
|
---|
574 | RefPtr<CSSFunctionValue> transformValue;
|
---|
575 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
576 | if (transform.isAffine()) {
|
---|
577 | transformValue = CSSFunctionValue::create(CSSValueMatrix);
|
---|
578 |
|
---|
579 | transformValue->append(cssValuePool.createValue(transform.a(), CSSUnitType::CSS_NUMBER));
|
---|
580 | transformValue->append(cssValuePool.createValue(transform.b(), CSSUnitType::CSS_NUMBER));
|
---|
581 | transformValue->append(cssValuePool.createValue(transform.c(), CSSUnitType::CSS_NUMBER));
|
---|
582 | transformValue->append(cssValuePool.createValue(transform.d(), CSSUnitType::CSS_NUMBER));
|
---|
583 | transformValue->append(zoomAdjustedNumberValue(transform.e(), style));
|
---|
584 | transformValue->append(zoomAdjustedNumberValue(transform.f(), style));
|
---|
585 | } else {
|
---|
586 | transformValue = CSSFunctionValue::create(CSSValueMatrix3d);
|
---|
587 |
|
---|
588 | transformValue->append(cssValuePool.createValue(transform.m11(), CSSUnitType::CSS_NUMBER));
|
---|
589 | transformValue->append(cssValuePool.createValue(transform.m12(), CSSUnitType::CSS_NUMBER));
|
---|
590 | transformValue->append(cssValuePool.createValue(transform.m13(), CSSUnitType::CSS_NUMBER));
|
---|
591 | transformValue->append(cssValuePool.createValue(transform.m14(), CSSUnitType::CSS_NUMBER));
|
---|
592 |
|
---|
593 | transformValue->append(cssValuePool.createValue(transform.m21(), CSSUnitType::CSS_NUMBER));
|
---|
594 | transformValue->append(cssValuePool.createValue(transform.m22(), CSSUnitType::CSS_NUMBER));
|
---|
595 | transformValue->append(cssValuePool.createValue(transform.m23(), CSSUnitType::CSS_NUMBER));
|
---|
596 | transformValue->append(cssValuePool.createValue(transform.m24(), CSSUnitType::CSS_NUMBER));
|
---|
597 |
|
---|
598 | transformValue->append(cssValuePool.createValue(transform.m31(), CSSUnitType::CSS_NUMBER));
|
---|
599 | transformValue->append(cssValuePool.createValue(transform.m32(), CSSUnitType::CSS_NUMBER));
|
---|
600 | transformValue->append(cssValuePool.createValue(transform.m33(), CSSUnitType::CSS_NUMBER));
|
---|
601 | transformValue->append(cssValuePool.createValue(transform.m34(), CSSUnitType::CSS_NUMBER));
|
---|
602 |
|
---|
603 | transformValue->append(zoomAdjustedNumberValue(transform.m41(), style));
|
---|
604 | transformValue->append(zoomAdjustedNumberValue(transform.m42(), style));
|
---|
605 | transformValue->append(zoomAdjustedNumberValue(transform.m43(), style));
|
---|
606 | transformValue->append(cssValuePool.createValue(transform.m44(), CSSUnitType::CSS_NUMBER));
|
---|
607 | }
|
---|
608 |
|
---|
609 | return transformValue.releaseNonNull();
|
---|
610 | }
|
---|
611 |
|
---|
612 | static bool rendererCanBeTransformed(RenderObject* renderer)
|
---|
613 | {
|
---|
614 | // Inline renderers do not support transforms.
|
---|
615 | return renderer && !is<RenderInline>(*renderer);
|
---|
616 | }
|
---|
617 |
|
---|
618 | static Ref<CSSValue> computedTransform(RenderElement* renderer, const RenderStyle& style)
|
---|
619 | {
|
---|
620 | if (!rendererCanBeTransformed(renderer) || !style.hasTransform())
|
---|
621 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
622 |
|
---|
623 | TransformationMatrix transform;
|
---|
624 | style.applyTransform(transform, renderer->transformReferenceBoxRect(style), { });
|
---|
625 |
|
---|
626 | // Note that this does not flatten to an affine transform if ENABLE(3D_TRANSFORMS) is off, by design.
|
---|
627 |
|
---|
628 | // FIXME: Need to print out individual functions (https://bugs.webkit.org/show_bug.cgi?id=23924)
|
---|
629 | auto list = CSSValueList::createSpaceSeparated();
|
---|
630 | list->append(matrixTransformValue(transform, style));
|
---|
631 | return list;
|
---|
632 | }
|
---|
633 |
|
---|
634 | // https://drafts.csswg.org/css-transforms-2/#propdef-translate
|
---|
635 | // Computed value: the keyword none or a pair of computed <length-percentage> values and an absolute length
|
---|
636 | static Ref<CSSValue> computedTranslate(RenderObject* renderer, const RenderStyle& style)
|
---|
637 | {
|
---|
638 | auto* translate = style.translate();
|
---|
639 | if (!translate || !rendererCanBeTransformed(renderer) || translate->isIdentity())
|
---|
640 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
641 |
|
---|
642 | auto list = CSSValueList::createSpaceSeparated();
|
---|
643 | list->append(zoomAdjustedPixelValueForLength(translate->x(), style));
|
---|
644 |
|
---|
645 | if (!translate->y().isZero() || !translate->z().isZero())
|
---|
646 | list->append(zoomAdjustedPixelValueForLength(translate->y(), style));
|
---|
647 |
|
---|
648 | if (!translate->z().isZero())
|
---|
649 | list->append(zoomAdjustedPixelValueForLength(translate->z(), style));
|
---|
650 |
|
---|
651 | return list;
|
---|
652 | }
|
---|
653 |
|
---|
654 | static Ref<CSSValue> computedScale(RenderObject* renderer, const RenderStyle& style)
|
---|
655 | {
|
---|
656 | auto* scale = style.scale();
|
---|
657 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
658 | if (!scale || !rendererCanBeTransformed(renderer) || scale->isIdentity())
|
---|
659 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
660 |
|
---|
661 | auto list = CSSValueList::createSpaceSeparated();
|
---|
662 | list->append(cssValuePool.createValue(scale->x(), CSSUnitType::CSS_NUMBER));
|
---|
663 | if (scale->z() != 1) {
|
---|
664 | list->append(cssValuePool.createValue(scale->y(), CSSUnitType::CSS_NUMBER));
|
---|
665 | list->append(cssValuePool.createValue(scale->z(), CSSUnitType::CSS_NUMBER));
|
---|
666 | } else if (scale->x() != scale->y())
|
---|
667 | list->append(cssValuePool.createValue(scale->y(), CSSUnitType::CSS_NUMBER));
|
---|
668 | return list;
|
---|
669 | }
|
---|
670 |
|
---|
671 | static Ref<CSSValue> computedRotate(RenderObject* renderer, const RenderStyle& style)
|
---|
672 | {
|
---|
673 | auto* rotate = style.rotate();
|
---|
674 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
675 | if (!rotate || !rendererCanBeTransformed(renderer) || rotate->isIdentity())
|
---|
676 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
677 |
|
---|
678 | if (!rotate->is3DOperation() || (!rotate->x() && !rotate->y() && rotate->z()))
|
---|
679 | return cssValuePool.createValue(rotate->angle(), CSSUnitType::CSS_DEG);
|
---|
680 |
|
---|
681 | auto list = CSSValueList::createSpaceSeparated();
|
---|
682 |
|
---|
683 | if (rotate->x() && !rotate->y() && !rotate->z())
|
---|
684 | list->append(cssValuePool.createIdentifierValue(CSSValueX));
|
---|
685 | else if (!rotate->x() && rotate->y() && !rotate->z())
|
---|
686 | list->append(cssValuePool.createIdentifierValue(CSSValueY));
|
---|
687 | else {
|
---|
688 | list->append(cssValuePool.createValue(rotate->x(), CSSUnitType::CSS_NUMBER));
|
---|
689 | list->append(cssValuePool.createValue(rotate->y(), CSSUnitType::CSS_NUMBER));
|
---|
690 | list->append(cssValuePool.createValue(rotate->z(), CSSUnitType::CSS_NUMBER));
|
---|
691 | }
|
---|
692 |
|
---|
693 | list->append(cssValuePool.createValue(rotate->angle(), CSSUnitType::CSS_DEG));
|
---|
694 |
|
---|
695 | return list;
|
---|
696 | }
|
---|
697 |
|
---|
698 | static inline Ref<CSSPrimitiveValue> adjustLengthForZoom(double length, const RenderStyle& style, AdjustPixelValuesForComputedStyle adjust)
|
---|
699 | {
|
---|
700 | return adjust == AdjustPixelValues ? zoomAdjustedPixelValue(length, style) : CSSValuePool::singleton().createValue(length, CSSUnitType::CSS_PX);
|
---|
701 | }
|
---|
702 |
|
---|
703 | static inline Ref<CSSPrimitiveValue> adjustLengthForZoom(const Length& length, const RenderStyle& style, AdjustPixelValuesForComputedStyle adjust)
|
---|
704 | {
|
---|
705 | return adjust == AdjustPixelValues ? zoomAdjustedPixelValue(length.value(), style) : CSSValuePool::singleton().createValue(length);
|
---|
706 | }
|
---|
707 |
|
---|
708 | Ref<CSSValue> ComputedStyleExtractor::valueForShadow(const ShadowData* shadow, CSSPropertyID propertyID, const RenderStyle& style, AdjustPixelValuesForComputedStyle adjust)
|
---|
709 | {
|
---|
710 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
711 | if (!shadow)
|
---|
712 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
713 |
|
---|
714 | auto list = CSSValueList::createCommaSeparated();
|
---|
715 | for (const ShadowData* currShadowData = shadow; currShadowData; currShadowData = currShadowData->next()) {
|
---|
716 | auto x = adjustLengthForZoom(currShadowData->x(), style, adjust);
|
---|
717 | auto y = adjustLengthForZoom(currShadowData->y(), style, adjust);
|
---|
718 | auto blur = adjustLengthForZoom(currShadowData->radius(), style, adjust);
|
---|
719 | auto spread = propertyID == CSSPropertyTextShadow ? RefPtr<CSSPrimitiveValue>() : adjustLengthForZoom(currShadowData->spread(), style, adjust);
|
---|
720 | auto style = propertyID == CSSPropertyTextShadow || currShadowData->style() == ShadowStyle::Normal ? RefPtr<CSSPrimitiveValue>() : cssValuePool.createIdentifierValue(CSSValueInset);
|
---|
721 | auto color = cssValuePool.createColorValue(currShadowData->color());
|
---|
722 | list->prepend(CSSShadowValue::create(WTFMove(x), WTFMove(y), WTFMove(blur), WTFMove(spread), WTFMove(style), WTFMove(color)));
|
---|
723 | }
|
---|
724 | return list;
|
---|
725 | }
|
---|
726 |
|
---|
727 | Ref<CSSValue> ComputedStyleExtractor::valueForFilter(const RenderStyle& style, const FilterOperations& filterOperations, AdjustPixelValuesForComputedStyle adjust)
|
---|
728 | {
|
---|
729 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
730 | if (filterOperations.operations().isEmpty())
|
---|
731 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
732 |
|
---|
733 | auto list = CSSValueList::createSpaceSeparated();
|
---|
734 |
|
---|
735 | Vector<RefPtr<FilterOperation>>::const_iterator end = filterOperations.operations().end();
|
---|
736 | for (Vector<RefPtr<FilterOperation>>::const_iterator it = filterOperations.operations().begin(); it != end; ++it) {
|
---|
737 | FilterOperation& filterOperation = **it;
|
---|
738 |
|
---|
739 | if (filterOperation.type() == FilterOperation::REFERENCE) {
|
---|
740 | ReferenceFilterOperation& referenceOperation = downcast<ReferenceFilterOperation>(filterOperation);
|
---|
741 | list->append(cssValuePool.createValue(referenceOperation.url(), CSSUnitType::CSS_URI));
|
---|
742 | } else {
|
---|
743 | RefPtr<CSSFunctionValue> filterValue;
|
---|
744 | switch (filterOperation.type()) {
|
---|
745 | case FilterOperation::GRAYSCALE: {
|
---|
746 | filterValue = CSSFunctionValue::create(CSSValueGrayscale);
|
---|
747 | filterValue->append(cssValuePool.createValue(downcast<BasicColorMatrixFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
748 | break;
|
---|
749 | }
|
---|
750 | case FilterOperation::SEPIA: {
|
---|
751 | filterValue = CSSFunctionValue::create(CSSValueSepia);
|
---|
752 | filterValue->append(cssValuePool.createValue(downcast<BasicColorMatrixFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
753 | break;
|
---|
754 | }
|
---|
755 | case FilterOperation::SATURATE: {
|
---|
756 | filterValue = CSSFunctionValue::create(CSSValueSaturate);
|
---|
757 | filterValue->append(cssValuePool.createValue(downcast<BasicColorMatrixFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
758 | break;
|
---|
759 | }
|
---|
760 | case FilterOperation::HUE_ROTATE: {
|
---|
761 | filterValue = CSSFunctionValue::create(CSSValueHueRotate);
|
---|
762 | filterValue->append(cssValuePool.createValue(downcast<BasicColorMatrixFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_DEG));
|
---|
763 | break;
|
---|
764 | }
|
---|
765 | case FilterOperation::INVERT: {
|
---|
766 | filterValue = CSSFunctionValue::create(CSSValueInvert);
|
---|
767 | filterValue->append(cssValuePool.createValue(downcast<BasicComponentTransferFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
768 | break;
|
---|
769 | }
|
---|
770 | case FilterOperation::APPLE_INVERT_LIGHTNESS: {
|
---|
771 | filterValue = CSSFunctionValue::create(CSSValueAppleInvertLightness);
|
---|
772 | break;
|
---|
773 | }
|
---|
774 | case FilterOperation::OPACITY: {
|
---|
775 | filterValue = CSSFunctionValue::create(CSSValueOpacity);
|
---|
776 | filterValue->append(cssValuePool.createValue(downcast<BasicComponentTransferFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
777 | break;
|
---|
778 | }
|
---|
779 | case FilterOperation::BRIGHTNESS: {
|
---|
780 | filterValue = CSSFunctionValue::create(CSSValueBrightness);
|
---|
781 | filterValue->append(cssValuePool.createValue(downcast<BasicComponentTransferFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
782 | break;
|
---|
783 | }
|
---|
784 | case FilterOperation::CONTRAST: {
|
---|
785 | filterValue = CSSFunctionValue::create(CSSValueContrast);
|
---|
786 | filterValue->append(cssValuePool.createValue(downcast<BasicComponentTransferFilterOperation>(filterOperation).amount(), CSSUnitType::CSS_NUMBER));
|
---|
787 | break;
|
---|
788 | }
|
---|
789 | case FilterOperation::BLUR: {
|
---|
790 | filterValue = CSSFunctionValue::create(CSSValueBlur);
|
---|
791 | filterValue->append(adjustLengthForZoom(downcast<BlurFilterOperation>(filterOperation).stdDeviation(), style, adjust));
|
---|
792 | break;
|
---|
793 | }
|
---|
794 | case FilterOperation::DROP_SHADOW: {
|
---|
795 | DropShadowFilterOperation& dropShadowOperation = downcast<DropShadowFilterOperation>(filterOperation);
|
---|
796 | filterValue = CSSFunctionValue::create(CSSValueDropShadow);
|
---|
797 | // We want our computed style to look like that of a text shadow (has neither spread nor inset style).
|
---|
798 | ShadowData shadowData = ShadowData({ Length(dropShadowOperation.location().x(), LengthType::Fixed), Length(dropShadowOperation.location().y(), LengthType::Fixed) }, Length(dropShadowOperation.stdDeviation(), LengthType::Fixed), Length(0, LengthType::Fixed), ShadowStyle::Normal, false, dropShadowOperation.color());
|
---|
799 | filterValue->append(valueForShadow(&shadowData, CSSPropertyTextShadow, style, adjust));
|
---|
800 | break;
|
---|
801 | }
|
---|
802 | default:
|
---|
803 | ASSERT_NOT_REACHED();
|
---|
804 | filterValue = CSSFunctionValue::create(CSSValueInvalid);
|
---|
805 | break;
|
---|
806 | }
|
---|
807 | list->append(filterValue.releaseNonNull());
|
---|
808 | }
|
---|
809 | }
|
---|
810 | return list;
|
---|
811 | }
|
---|
812 |
|
---|
813 | static Ref<CSSValue> specifiedValueForGridTrackBreadth(const GridLength& trackBreadth, const RenderStyle& style)
|
---|
814 | {
|
---|
815 | if (!trackBreadth.isLength())
|
---|
816 | return CSSValuePool::singleton().createValue(trackBreadth.flex(), CSSUnitType::CSS_FR);
|
---|
817 |
|
---|
818 | const Length& trackBreadthLength = trackBreadth.length();
|
---|
819 | if (trackBreadthLength.isAuto())
|
---|
820 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
821 | return zoomAdjustedPixelValueForLength(trackBreadthLength, style);
|
---|
822 | }
|
---|
823 |
|
---|
824 | static Ref<CSSValue> specifiedValueForGridTrackSize(const GridTrackSize& trackSize, const RenderStyle& style)
|
---|
825 | {
|
---|
826 | switch (trackSize.type()) {
|
---|
827 | case LengthTrackSizing:
|
---|
828 | return specifiedValueForGridTrackBreadth(trackSize.minTrackBreadth(), style);
|
---|
829 | case FitContentTrackSizing: {
|
---|
830 | auto fitContentTrackSize = CSSFunctionValue::create(CSSValueFitContent);
|
---|
831 | fitContentTrackSize->append(zoomAdjustedPixelValueForLength(trackSize.fitContentTrackBreadth().length(), style));
|
---|
832 | return fitContentTrackSize;
|
---|
833 | }
|
---|
834 | default:
|
---|
835 | ASSERT(trackSize.type() == MinMaxTrackSizing);
|
---|
836 | if (trackSize.minTrackBreadth().isAuto() && trackSize.maxTrackBreadth().isFlex())
|
---|
837 | return CSSValuePool::singleton().createValue(trackSize.maxTrackBreadth().flex(), CSSUnitType::CSS_FR);
|
---|
838 |
|
---|
839 | auto minMaxTrackBreadths = CSSFunctionValue::create(CSSValueMinmax);
|
---|
840 | minMaxTrackBreadths->append(specifiedValueForGridTrackBreadth(trackSize.minTrackBreadth(), style));
|
---|
841 | minMaxTrackBreadths->append(specifiedValueForGridTrackBreadth(trackSize.maxTrackBreadth(), style));
|
---|
842 | return minMaxTrackBreadths;
|
---|
843 | }
|
---|
844 | }
|
---|
845 |
|
---|
846 | class OrderedNamedLinesCollector {
|
---|
847 | WTF_MAKE_NONCOPYABLE(OrderedNamedLinesCollector);
|
---|
848 | public:
|
---|
849 | OrderedNamedLinesCollector(const RenderStyle& style, bool isRowAxis)
|
---|
850 | : m_orderedNamedGridLines(isRowAxis ? style.orderedNamedGridColumnLines() : style.orderedNamedGridRowLines())
|
---|
851 | , m_orderedNamedAutoRepeatGridLines(isRowAxis ? style.autoRepeatOrderedNamedGridColumnLines() : style.autoRepeatOrderedNamedGridRowLines())
|
---|
852 | {
|
---|
853 | }
|
---|
854 | virtual ~OrderedNamedLinesCollector() = default;
|
---|
855 |
|
---|
856 | bool isEmpty() const { return m_orderedNamedGridLines.isEmpty() && m_orderedNamedAutoRepeatGridLines.isEmpty(); }
|
---|
857 | virtual void collectLineNamesForIndex(CSSGridLineNamesValue&, unsigned index) const = 0;
|
---|
858 |
|
---|
859 | virtual int namedGridLineCount() const { return m_orderedNamedGridLines.size(); }
|
---|
860 |
|
---|
861 | protected:
|
---|
862 |
|
---|
863 | enum NamedLinesType { NamedLines, AutoRepeatNamedLines };
|
---|
864 | void appendLines(CSSGridLineNamesValue&, unsigned index, NamedLinesType) const;
|
---|
865 |
|
---|
866 | const OrderedNamedGridLinesMap& m_orderedNamedGridLines;
|
---|
867 | const OrderedNamedGridLinesMap& m_orderedNamedAutoRepeatGridLines;
|
---|
868 | };
|
---|
869 |
|
---|
870 | class OrderedNamedLinesCollectorInGridLayout : public OrderedNamedLinesCollector {
|
---|
871 | public:
|
---|
872 | OrderedNamedLinesCollectorInGridLayout(const RenderStyle& style, bool isRowAxis, unsigned autoRepeatTracksCount, unsigned autoRepeatTrackListLength)
|
---|
873 | : OrderedNamedLinesCollector(style, isRowAxis)
|
---|
874 | , m_insertionPoint(isRowAxis ? style.gridAutoRepeatColumnsInsertionPoint() : style.gridAutoRepeatRowsInsertionPoint())
|
---|
875 | , m_autoRepeatTotalTracks(autoRepeatTracksCount)
|
---|
876 | , m_autoRepeatTrackListLength(autoRepeatTrackListLength)
|
---|
877 | {
|
---|
878 | }
|
---|
879 |
|
---|
880 | void collectLineNamesForIndex(CSSGridLineNamesValue&, unsigned index) const override;
|
---|
881 |
|
---|
882 | private:
|
---|
883 | unsigned m_insertionPoint;
|
---|
884 | unsigned m_autoRepeatTotalTracks;
|
---|
885 | unsigned m_autoRepeatTrackListLength;
|
---|
886 | };
|
---|
887 |
|
---|
888 | class OrderedNamedLinesCollectorInSubgridLayout : public OrderedNamedLinesCollector {
|
---|
889 | public:
|
---|
890 | OrderedNamedLinesCollectorInSubgridLayout(const RenderStyle& style, bool isRowAxis, unsigned totalTracksCount)
|
---|
891 | : OrderedNamedLinesCollector(style, isRowAxis)
|
---|
892 | , m_insertionPoint(isRowAxis ? style.gridAutoRepeatColumnsInsertionPoint() : style.gridAutoRepeatRowsInsertionPoint())
|
---|
893 | , m_autoRepeatLineSetListLength((isRowAxis ? style.autoRepeatOrderedNamedGridColumnLines() : style.autoRepeatOrderedNamedGridRowLines()).size())
|
---|
894 | , m_totalLines(totalTracksCount + 1)
|
---|
895 | {
|
---|
896 | if (!m_autoRepeatLineSetListLength) {
|
---|
897 | m_autoRepeatTotalLineSets = 0;
|
---|
898 | return;
|
---|
899 | }
|
---|
900 | unsigned named = (isRowAxis ? style.orderedNamedGridColumnLines() : style.orderedNamedGridRowLines()).size();
|
---|
901 | if (named >= m_totalLines) {
|
---|
902 | m_autoRepeatTotalLineSets = 0;
|
---|
903 | return;
|
---|
904 | }
|
---|
905 | m_autoRepeatTotalLineSets = (m_totalLines - named) / m_autoRepeatLineSetListLength;
|
---|
906 | m_autoRepeatTotalLineSets *= m_autoRepeatLineSetListLength;
|
---|
907 | }
|
---|
908 |
|
---|
909 | void collectLineNamesForIndex(CSSGridLineNamesValue&, unsigned index) const override;
|
---|
910 |
|
---|
911 | int namedGridLineCount() const override { return m_totalLines; }
|
---|
912 | private:
|
---|
913 | unsigned m_insertionPoint;
|
---|
914 | unsigned m_autoRepeatTotalLineSets;
|
---|
915 | unsigned m_autoRepeatLineSetListLength;
|
---|
916 | unsigned m_totalLines;
|
---|
917 | };
|
---|
918 |
|
---|
919 | void OrderedNamedLinesCollector::appendLines(CSSGridLineNamesValue& lineNamesValue, unsigned index, NamedLinesType type) const
|
---|
920 | {
|
---|
921 | auto iter = type == NamedLines ? m_orderedNamedGridLines.find(index) : m_orderedNamedAutoRepeatGridLines.find(index);
|
---|
922 | auto endIter = type == NamedLines ? m_orderedNamedGridLines.end() : m_orderedNamedAutoRepeatGridLines.end();
|
---|
923 | if (iter == endIter)
|
---|
924 | return;
|
---|
925 |
|
---|
926 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
927 | for (const auto& lineName : iter->value)
|
---|
928 | lineNamesValue.append(cssValuePool.createCustomIdent(lineName));
|
---|
929 | }
|
---|
930 |
|
---|
931 | void OrderedNamedLinesCollectorInGridLayout::collectLineNamesForIndex(CSSGridLineNamesValue& lineNamesValue, unsigned i) const
|
---|
932 | {
|
---|
933 | ASSERT(!isEmpty());
|
---|
934 | if (!m_autoRepeatTrackListLength || i < m_insertionPoint) {
|
---|
935 | appendLines(lineNamesValue, i, NamedLines);
|
---|
936 | return;
|
---|
937 | }
|
---|
938 |
|
---|
939 | ASSERT(m_autoRepeatTotalTracks);
|
---|
940 |
|
---|
941 | if (i > m_insertionPoint + m_autoRepeatTotalTracks) {
|
---|
942 | appendLines(lineNamesValue, i - (m_autoRepeatTotalTracks - 1), NamedLines);
|
---|
943 | return;
|
---|
944 | }
|
---|
945 |
|
---|
946 | if (i == m_insertionPoint) {
|
---|
947 | appendLines(lineNamesValue, i, NamedLines);
|
---|
948 | appendLines(lineNamesValue, 0, AutoRepeatNamedLines);
|
---|
949 | return;
|
---|
950 | }
|
---|
951 |
|
---|
952 | if (i == m_insertionPoint + m_autoRepeatTotalTracks) {
|
---|
953 | appendLines(lineNamesValue, m_autoRepeatTrackListLength, AutoRepeatNamedLines);
|
---|
954 | appendLines(lineNamesValue, m_insertionPoint + 1, NamedLines);
|
---|
955 | return;
|
---|
956 | }
|
---|
957 |
|
---|
958 | unsigned autoRepeatIndexInFirstRepetition = (i - m_insertionPoint) % m_autoRepeatTrackListLength;
|
---|
959 | if (!autoRepeatIndexInFirstRepetition && i > m_insertionPoint)
|
---|
960 | appendLines(lineNamesValue, m_autoRepeatTrackListLength, AutoRepeatNamedLines);
|
---|
961 | appendLines(lineNamesValue, autoRepeatIndexInFirstRepetition, AutoRepeatNamedLines);
|
---|
962 | }
|
---|
963 |
|
---|
964 | void OrderedNamedLinesCollectorInSubgridLayout::collectLineNamesForIndex(CSSGridLineNamesValue& lineNamesValue, unsigned i) const
|
---|
965 | {
|
---|
966 | if (!m_autoRepeatLineSetListLength || i < m_insertionPoint) {
|
---|
967 | appendLines(lineNamesValue, i, NamedLines);
|
---|
968 | return;
|
---|
969 | }
|
---|
970 |
|
---|
971 | if (i >= m_insertionPoint + m_autoRepeatTotalLineSets) {
|
---|
972 | appendLines(lineNamesValue, i - m_autoRepeatTotalLineSets, NamedLines);
|
---|
973 | return;
|
---|
974 | }
|
---|
975 |
|
---|
976 | unsigned autoRepeatIndexInFirstRepetition = (i - m_insertionPoint) % m_autoRepeatLineSetListLength;
|
---|
977 | appendLines(lineNamesValue, autoRepeatIndexInFirstRepetition, AutoRepeatNamedLines);
|
---|
978 | }
|
---|
979 |
|
---|
980 | static void addValuesForNamedGridLinesAtIndex(OrderedNamedLinesCollector& collector, unsigned i, CSSValueList& list, bool renderEmpty = false)
|
---|
981 | {
|
---|
982 | if (collector.isEmpty() && !renderEmpty)
|
---|
983 | return;
|
---|
984 |
|
---|
985 | auto lineNames = CSSGridLineNamesValue::create();
|
---|
986 | collector.collectLineNamesForIndex(lineNames.get(), i);
|
---|
987 | if (lineNames->length() || renderEmpty)
|
---|
988 | list.append(WTFMove(lineNames));
|
---|
989 | }
|
---|
990 |
|
---|
991 | static Ref<CSSValueList> valueForGridTrackSizeList(GridTrackSizingDirection direction, const RenderStyle& style)
|
---|
992 | {
|
---|
993 | auto& autoTrackSizes = direction == ForColumns ? style.gridAutoColumns() : style.gridAutoRows();
|
---|
994 |
|
---|
995 | auto list = CSSValueList::createSpaceSeparated();
|
---|
996 | for (auto& trackSize : autoTrackSizes)
|
---|
997 | list->append(specifiedValueForGridTrackSize(trackSize, style));
|
---|
998 | return list;
|
---|
999 | }
|
---|
1000 |
|
---|
1001 | template <typename T, typename F>
|
---|
1002 | void populateGridTrackList(CSSValueList& list, OrderedNamedLinesCollector& collector, const Vector<T>& tracks, F getTrackSize, int offset = 0)
|
---|
1003 | {
|
---|
1004 | int start = 0;
|
---|
1005 | int end = tracks.size();
|
---|
1006 | ASSERT(start <= end);
|
---|
1007 | ASSERT(static_cast<unsigned>(end) <= tracks.size());
|
---|
1008 | for (int i = start; i < end; ++i) {
|
---|
1009 | if (i + offset >= 0)
|
---|
1010 | addValuesForNamedGridLinesAtIndex(collector, i + offset, list);
|
---|
1011 | list.append(getTrackSize(tracks[i]));
|
---|
1012 | }
|
---|
1013 | if (end + offset >= 0)
|
---|
1014 | addValuesForNamedGridLinesAtIndex(collector, end + offset, list);
|
---|
1015 | }
|
---|
1016 |
|
---|
1017 | static void populateSubgridLineNameList(CSSValueList& list, OrderedNamedLinesCollector& collector)
|
---|
1018 | {
|
---|
1019 | for (int i = 0; i < collector.namedGridLineCount(); i++)
|
---|
1020 | addValuesForNamedGridLinesAtIndex(collector, i, list, true);
|
---|
1021 | }
|
---|
1022 |
|
---|
1023 | static Ref<CSSValue> valueForGridTrackList(GridTrackSizingDirection direction, RenderObject* renderer, const RenderStyle& style)
|
---|
1024 | {
|
---|
1025 | bool isRowAxis = direction == ForColumns;
|
---|
1026 | bool isRenderGrid = is<RenderGrid>(renderer);
|
---|
1027 | bool isSubgrid = isRowAxis ? style.gridSubgridColumns() : style.gridSubgridRows();
|
---|
1028 | auto& trackSizes = isRowAxis ? style.gridColumns() : style.gridRows();
|
---|
1029 | auto& autoRepeatTrackSizes = isRowAxis ? style.gridAutoRepeatColumns() : style.gridAutoRepeatRows();
|
---|
1030 |
|
---|
1031 | // Handle the 'none' case.
|
---|
1032 | bool trackListIsEmpty = trackSizes.isEmpty() && autoRepeatTrackSizes.isEmpty();
|
---|
1033 | if (isRenderGrid && trackListIsEmpty) {
|
---|
1034 | // For grids we should consider every listed track, whether implicitly or explicitly
|
---|
1035 | // created. Empty grids have a sole grid line per axis.
|
---|
1036 | auto& grid = downcast<RenderGrid>(*renderer);
|
---|
1037 | auto& positions = isRowAxis ? grid.columnPositions() : grid.rowPositions();
|
---|
1038 | trackListIsEmpty = positions.size() == 1;
|
---|
1039 | }
|
---|
1040 |
|
---|
1041 | if (trackListIsEmpty && !isSubgrid)
|
---|
1042 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
1043 |
|
---|
1044 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1045 |
|
---|
1046 | // If the element is a grid container, the resolved value is the used value,
|
---|
1047 | // specifying track sizes in pixels and expanding the repeat() notation.
|
---|
1048 | // If subgrid was specified, but the element isn't a subgrid (due to not having
|
---|
1049 | // an appropriate grid parent), then we fall back to using the specified value.
|
---|
1050 | if (isRenderGrid && (!isSubgrid || downcast<RenderGrid>(renderer)->isSubgrid(direction))) {
|
---|
1051 | auto* grid = downcast<RenderGrid>(renderer);
|
---|
1052 | if (isSubgrid) {
|
---|
1053 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSubgrid));
|
---|
1054 |
|
---|
1055 | OrderedNamedLinesCollectorInSubgridLayout collector(style, isRowAxis, grid->numTracks(direction));
|
---|
1056 | populateSubgridLineNameList(list.get(), collector);
|
---|
1057 | return list;
|
---|
1058 | }
|
---|
1059 | OrderedNamedLinesCollectorInGridLayout collector(style, isRowAxis, grid->autoRepeatCountForDirection(direction), autoRepeatTrackSizes.size());
|
---|
1060 | // Named grid line indices are relative to the explicit grid, but we are including all tracks.
|
---|
1061 | // So we need to subtract the number of leading implicit tracks in order to get the proper line index.
|
---|
1062 | int offset = -grid->explicitGridStartForDirection(direction);
|
---|
1063 | populateGridTrackList(list.get(), collector, grid->trackSizesForComputedStyle(direction), [&](const LayoutUnit& v) {
|
---|
1064 | return zoomAdjustedPixelValue(v, style);
|
---|
1065 | }, offset);
|
---|
1066 | return list;
|
---|
1067 | }
|
---|
1068 |
|
---|
1069 | // Otherwise, the resolved value is the computed value, preserving repeat().
|
---|
1070 | const GridTrackList& computedTracks = isRowAxis ? style.gridColumnList() : style.gridRowList();
|
---|
1071 |
|
---|
1072 | auto repeatVisitor = [&](CSSValueList& dest, const RepeatEntry& entry) {
|
---|
1073 | if (std::holds_alternative<Vector<String>>(entry)) {
|
---|
1074 | const auto& names = std::get<Vector<String>>(entry);
|
---|
1075 | if (names.isEmpty() && !isSubgrid)
|
---|
1076 | return;
|
---|
1077 | auto lineNamesValue = CSSGridLineNamesValue::create();
|
---|
1078 | for (const auto& name : names)
|
---|
1079 | lineNamesValue->append(CSSValuePool::singleton().createCustomIdent(name));
|
---|
1080 | dest.append(lineNamesValue);
|
---|
1081 | } else {
|
---|
1082 | dest.append(specifiedValueForGridTrackSize(std::get<GridTrackSize>(entry), style));
|
---|
1083 | }
|
---|
1084 | };
|
---|
1085 |
|
---|
1086 | auto trackEntryVisitor = WTF::makeVisitor([&](const GridTrackSize& size) {
|
---|
1087 | list->append(specifiedValueForGridTrackSize(size, style));
|
---|
1088 | }, [&](const Vector<String>& names) {
|
---|
1089 | // Subgrids don't have track sizes specified, so empty line names sets
|
---|
1090 | // need to be serialized, as they are meaningful placeholders.
|
---|
1091 | if (names.isEmpty() && !isSubgrid)
|
---|
1092 | return;
|
---|
1093 |
|
---|
1094 | auto lineNamesValue = CSSGridLineNamesValue::create();
|
---|
1095 | for (const auto& name : names)
|
---|
1096 | lineNamesValue->append(CSSValuePool::singleton().createCustomIdent(name));
|
---|
1097 | list->append(lineNamesValue);
|
---|
1098 | }, [&](const GridTrackEntryRepeat& repeat) {
|
---|
1099 | auto repeatedValues = CSSGridIntegerRepeatValue::create(repeat.repeats);
|
---|
1100 | for (const auto& entry : repeat.list)
|
---|
1101 | repeatVisitor(repeatedValues, entry);
|
---|
1102 | list->append(repeatedValues);
|
---|
1103 | }, [&](const GridTrackEntryAutoRepeat& repeat) {
|
---|
1104 | auto repeatedValues = CSSGridAutoRepeatValue::create(repeat.type == AutoRepeatType::Fill ? CSSValueAutoFill : CSSValueAutoFit);
|
---|
1105 | for (const auto& entry : repeat.list)
|
---|
1106 | repeatVisitor(repeatedValues, entry);
|
---|
1107 | list->append(repeatedValues);
|
---|
1108 | }, [&](const GridTrackEntrySubgrid&) {
|
---|
1109 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSubgrid));
|
---|
1110 | });
|
---|
1111 |
|
---|
1112 | for (const auto& entry : computedTracks)
|
---|
1113 | std::visit(trackEntryVisitor, entry);
|
---|
1114 |
|
---|
1115 | return list;
|
---|
1116 | }
|
---|
1117 |
|
---|
1118 | static Ref<CSSValue> valueForGridPosition(const GridPosition& position)
|
---|
1119 | {
|
---|
1120 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1121 | if (position.isAuto())
|
---|
1122 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
1123 |
|
---|
1124 | if (position.isNamedGridArea())
|
---|
1125 | return cssValuePool.createCustomIdent(position.namedGridLine());
|
---|
1126 |
|
---|
1127 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1128 | if (position.isSpan()) {
|
---|
1129 | list->append(cssValuePool.createIdentifierValue(CSSValueSpan));
|
---|
1130 | list->append(cssValuePool.createValue(position.spanPosition(), CSSUnitType::CSS_INTEGER));
|
---|
1131 | } else
|
---|
1132 | list->append(cssValuePool.createValue(position.integerPosition(), CSSUnitType::CSS_INTEGER));
|
---|
1133 |
|
---|
1134 | if (!position.namedGridLine().isNull())
|
---|
1135 | list->append(cssValuePool.createCustomIdent(position.namedGridLine()));
|
---|
1136 | return list;
|
---|
1137 | }
|
---|
1138 |
|
---|
1139 | static Ref<CSSValue> createTransitionPropertyValue(const Animation& animation)
|
---|
1140 | {
|
---|
1141 | switch (animation.property().mode) {
|
---|
1142 | case Animation::TransitionMode::None:
|
---|
1143 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
1144 | case Animation::TransitionMode::All:
|
---|
1145 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAll);
|
---|
1146 | case Animation::TransitionMode::SingleProperty:
|
---|
1147 | return CSSValuePool::singleton().createCustomIdent(getPropertyNameString(animation.property().id));
|
---|
1148 | case Animation::TransitionMode::UnknownProperty:
|
---|
1149 | return CSSValuePool::singleton().createCustomIdent(animation.unknownProperty());
|
---|
1150 | }
|
---|
1151 | ASSERT_NOT_REACHED();
|
---|
1152 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
1153 | }
|
---|
1154 |
|
---|
1155 | static Ref<CSSValueList> valueForScrollSnapType(const ScrollSnapType& type)
|
---|
1156 | {
|
---|
1157 | auto value = CSSValueList::createSpaceSeparated();
|
---|
1158 | if (type.strictness == ScrollSnapStrictness::None)
|
---|
1159 | value->append(CSSValuePool::singleton().createValue(CSSValueNone));
|
---|
1160 | else {
|
---|
1161 | value->append(CSSPrimitiveValue::create(type.axis));
|
---|
1162 | if (type.strictness != ScrollSnapStrictness::Proximity)
|
---|
1163 | value->append(CSSPrimitiveValue::create(type.strictness));
|
---|
1164 | }
|
---|
1165 | return value;
|
---|
1166 | }
|
---|
1167 |
|
---|
1168 | static Ref<CSSValueList> valueForScrollSnapAlignment(const ScrollSnapAlign& alignment)
|
---|
1169 | {
|
---|
1170 | auto value = CSSValueList::createSpaceSeparated();
|
---|
1171 | value->append(CSSPrimitiveValue::create(alignment.blockAlign));
|
---|
1172 | if (alignment.inlineAlign != alignment.blockAlign)
|
---|
1173 | value->append(CSSPrimitiveValue::create(alignment.inlineAlign));
|
---|
1174 | return value;
|
---|
1175 | }
|
---|
1176 |
|
---|
1177 | static Ref<CSSValue> willChangePropertyValue(const WillChangeData* willChangeData)
|
---|
1178 | {
|
---|
1179 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1180 | if (!willChangeData || !willChangeData->numFeatures())
|
---|
1181 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
1182 |
|
---|
1183 | auto list = CSSValueList::createCommaSeparated();
|
---|
1184 | for (size_t i = 0; i < willChangeData->numFeatures(); ++i) {
|
---|
1185 | WillChangeData::FeaturePropertyPair feature = willChangeData->featureAt(i);
|
---|
1186 | switch (feature.first) {
|
---|
1187 | case WillChangeData::ScrollPosition:
|
---|
1188 | list->append(cssValuePool.createIdentifierValue(CSSValueScrollPosition));
|
---|
1189 | break;
|
---|
1190 | case WillChangeData::Contents:
|
---|
1191 | list->append(cssValuePool.createIdentifierValue(CSSValueContents));
|
---|
1192 | break;
|
---|
1193 | case WillChangeData::Property:
|
---|
1194 | list->append(cssValuePool.createIdentifierValue(feature.second));
|
---|
1195 | break;
|
---|
1196 | case WillChangeData::Invalid:
|
---|
1197 | ASSERT_NOT_REACHED();
|
---|
1198 | break;
|
---|
1199 | }
|
---|
1200 | }
|
---|
1201 |
|
---|
1202 | return list;
|
---|
1203 | }
|
---|
1204 |
|
---|
1205 | static inline void appendLigaturesValue(CSSValueList& list, FontVariantLigatures value, CSSValueID yesValue, CSSValueID noValue)
|
---|
1206 | {
|
---|
1207 | switch (value) {
|
---|
1208 | case FontVariantLigatures::Normal:
|
---|
1209 | return;
|
---|
1210 | case FontVariantLigatures::No:
|
---|
1211 | list.append(CSSValuePool::singleton().createIdentifierValue(noValue));
|
---|
1212 | return;
|
---|
1213 | case FontVariantLigatures::Yes:
|
---|
1214 | list.append(CSSValuePool::singleton().createIdentifierValue(yesValue));
|
---|
1215 | return;
|
---|
1216 | }
|
---|
1217 | ASSERT_NOT_REACHED();
|
---|
1218 | }
|
---|
1219 |
|
---|
1220 | static Ref<CSSValue> fontVariantLigaturesPropertyValue(FontVariantLigatures common, FontVariantLigatures discretionary, FontVariantLigatures historical, FontVariantLigatures contextualAlternates)
|
---|
1221 | {
|
---|
1222 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1223 | if (common == FontVariantLigatures::No && discretionary == FontVariantLigatures::No && historical == FontVariantLigatures::No && contextualAlternates == FontVariantLigatures::No)
|
---|
1224 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1225 | if (common == FontVariantLigatures::Normal && discretionary == FontVariantLigatures::Normal && historical == FontVariantLigatures::Normal && contextualAlternates == FontVariantLigatures::Normal)
|
---|
1226 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
1227 |
|
---|
1228 | auto valueList = CSSValueList::createSpaceSeparated();
|
---|
1229 | appendLigaturesValue(valueList, common, CSSValueCommonLigatures, CSSValueNoCommonLigatures);
|
---|
1230 | appendLigaturesValue(valueList, discretionary, CSSValueDiscretionaryLigatures, CSSValueNoDiscretionaryLigatures);
|
---|
1231 | appendLigaturesValue(valueList, historical, CSSValueHistoricalLigatures, CSSValueNoHistoricalLigatures);
|
---|
1232 | appendLigaturesValue(valueList, contextualAlternates, CSSValueContextual, CSSValueNoContextual);
|
---|
1233 | return valueList;
|
---|
1234 | }
|
---|
1235 |
|
---|
1236 | static Ref<CSSValue> fontVariantPositionPropertyValue(FontVariantPosition position)
|
---|
1237 | {
|
---|
1238 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1239 | CSSValueID valueID = CSSValueNormal;
|
---|
1240 | switch (position) {
|
---|
1241 | case FontVariantPosition::Normal:
|
---|
1242 | break;
|
---|
1243 | case FontVariantPosition::Subscript:
|
---|
1244 | valueID = CSSValueSub;
|
---|
1245 | break;
|
---|
1246 | case FontVariantPosition::Superscript:
|
---|
1247 | valueID = CSSValueSuper;
|
---|
1248 | break;
|
---|
1249 | }
|
---|
1250 | return cssValuePool.createIdentifierValue(valueID);
|
---|
1251 | }
|
---|
1252 |
|
---|
1253 | static Ref<CSSValue> fontVariantCapsPropertyValue(FontVariantCaps caps)
|
---|
1254 | {
|
---|
1255 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1256 | CSSValueID valueID = CSSValueNormal;
|
---|
1257 | switch (caps) {
|
---|
1258 | case FontVariantCaps::Normal:
|
---|
1259 | break;
|
---|
1260 | case FontVariantCaps::Small:
|
---|
1261 | valueID = CSSValueSmallCaps;
|
---|
1262 | break;
|
---|
1263 | case FontVariantCaps::AllSmall:
|
---|
1264 | valueID = CSSValueAllSmallCaps;
|
---|
1265 | break;
|
---|
1266 | case FontVariantCaps::Petite:
|
---|
1267 | valueID = CSSValuePetiteCaps;
|
---|
1268 | break;
|
---|
1269 | case FontVariantCaps::AllPetite:
|
---|
1270 | valueID = CSSValueAllPetiteCaps;
|
---|
1271 | break;
|
---|
1272 | case FontVariantCaps::Unicase:
|
---|
1273 | valueID = CSSValueUnicase;
|
---|
1274 | break;
|
---|
1275 | case FontVariantCaps::Titling:
|
---|
1276 | valueID = CSSValueTitlingCaps;
|
---|
1277 | break;
|
---|
1278 | }
|
---|
1279 | return cssValuePool.createIdentifierValue(valueID);
|
---|
1280 | }
|
---|
1281 |
|
---|
1282 | static Ref<CSSValue> fontVariantNumericPropertyValue(FontVariantNumericFigure figure, FontVariantNumericSpacing spacing, FontVariantNumericFraction fraction, FontVariantNumericOrdinal ordinal, FontVariantNumericSlashedZero slashedZero)
|
---|
1283 | {
|
---|
1284 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1285 | if (figure == FontVariantNumericFigure::Normal && spacing == FontVariantNumericSpacing::Normal && fraction == FontVariantNumericFraction::Normal && ordinal == FontVariantNumericOrdinal::Normal && slashedZero == FontVariantNumericSlashedZero::Normal)
|
---|
1286 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
1287 |
|
---|
1288 | auto valueList = CSSValueList::createSpaceSeparated();
|
---|
1289 | switch (figure) {
|
---|
1290 | case FontVariantNumericFigure::Normal:
|
---|
1291 | break;
|
---|
1292 | case FontVariantNumericFigure::LiningNumbers:
|
---|
1293 | valueList->append(cssValuePool.createIdentifierValue(CSSValueLiningNums));
|
---|
1294 | break;
|
---|
1295 | case FontVariantNumericFigure::OldStyleNumbers:
|
---|
1296 | valueList->append(cssValuePool.createIdentifierValue(CSSValueOldstyleNums));
|
---|
1297 | break;
|
---|
1298 | }
|
---|
1299 |
|
---|
1300 | switch (spacing) {
|
---|
1301 | case FontVariantNumericSpacing::Normal:
|
---|
1302 | break;
|
---|
1303 | case FontVariantNumericSpacing::ProportionalNumbers:
|
---|
1304 | valueList->append(cssValuePool.createIdentifierValue(CSSValueProportionalNums));
|
---|
1305 | break;
|
---|
1306 | case FontVariantNumericSpacing::TabularNumbers:
|
---|
1307 | valueList->append(cssValuePool.createIdentifierValue(CSSValueTabularNums));
|
---|
1308 | break;
|
---|
1309 | }
|
---|
1310 |
|
---|
1311 | switch (fraction) {
|
---|
1312 | case FontVariantNumericFraction::Normal:
|
---|
1313 | break;
|
---|
1314 | case FontVariantNumericFraction::DiagonalFractions:
|
---|
1315 | valueList->append(cssValuePool.createIdentifierValue(CSSValueDiagonalFractions));
|
---|
1316 | break;
|
---|
1317 | case FontVariantNumericFraction::StackedFractions:
|
---|
1318 | valueList->append(cssValuePool.createIdentifierValue(CSSValueStackedFractions));
|
---|
1319 | break;
|
---|
1320 | }
|
---|
1321 |
|
---|
1322 | if (ordinal == FontVariantNumericOrdinal::Yes)
|
---|
1323 | valueList->append(cssValuePool.createIdentifierValue(CSSValueOrdinal));
|
---|
1324 | if (slashedZero == FontVariantNumericSlashedZero::Yes)
|
---|
1325 | valueList->append(cssValuePool.createIdentifierValue(CSSValueSlashedZero));
|
---|
1326 |
|
---|
1327 | return valueList;
|
---|
1328 | }
|
---|
1329 |
|
---|
1330 | static Ref<CSSValue> fontVariantAlternatesPropertyValue(FontVariantAlternates alternates)
|
---|
1331 | {
|
---|
1332 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1333 | CSSValueID valueID = CSSValueNormal;
|
---|
1334 | switch (alternates) {
|
---|
1335 | case FontVariantAlternates::Normal:
|
---|
1336 | break;
|
---|
1337 | case FontVariantAlternates::HistoricalForms:
|
---|
1338 | valueID = CSSValueHistoricalForms;
|
---|
1339 | break;
|
---|
1340 | }
|
---|
1341 | return cssValuePool.createIdentifierValue(valueID);
|
---|
1342 | }
|
---|
1343 |
|
---|
1344 | static Ref<CSSValue> fontVariantEastAsianPropertyValue(FontVariantEastAsianVariant variant, FontVariantEastAsianWidth width, FontVariantEastAsianRuby ruby)
|
---|
1345 | {
|
---|
1346 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1347 | if (variant == FontVariantEastAsianVariant::Normal && width == FontVariantEastAsianWidth::Normal && ruby == FontVariantEastAsianRuby::Normal)
|
---|
1348 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
1349 |
|
---|
1350 | auto valueList = CSSValueList::createSpaceSeparated();
|
---|
1351 | switch (variant) {
|
---|
1352 | case FontVariantEastAsianVariant::Normal:
|
---|
1353 | break;
|
---|
1354 | case FontVariantEastAsianVariant::Jis78:
|
---|
1355 | valueList->append(cssValuePool.createIdentifierValue(CSSValueJis78));
|
---|
1356 | break;
|
---|
1357 | case FontVariantEastAsianVariant::Jis83:
|
---|
1358 | valueList->append(cssValuePool.createIdentifierValue(CSSValueJis83));
|
---|
1359 | break;
|
---|
1360 | case FontVariantEastAsianVariant::Jis90:
|
---|
1361 | valueList->append(cssValuePool.createIdentifierValue(CSSValueJis90));
|
---|
1362 | break;
|
---|
1363 | case FontVariantEastAsianVariant::Jis04:
|
---|
1364 | valueList->append(cssValuePool.createIdentifierValue(CSSValueJis04));
|
---|
1365 | break;
|
---|
1366 | case FontVariantEastAsianVariant::Simplified:
|
---|
1367 | valueList->append(cssValuePool.createIdentifierValue(CSSValueSimplified));
|
---|
1368 | break;
|
---|
1369 | case FontVariantEastAsianVariant::Traditional:
|
---|
1370 | valueList->append(cssValuePool.createIdentifierValue(CSSValueTraditional));
|
---|
1371 | break;
|
---|
1372 | }
|
---|
1373 |
|
---|
1374 | switch (width) {
|
---|
1375 | case FontVariantEastAsianWidth::Normal:
|
---|
1376 | break;
|
---|
1377 | case FontVariantEastAsianWidth::Full:
|
---|
1378 | valueList->append(cssValuePool.createIdentifierValue(CSSValueFullWidth));
|
---|
1379 | break;
|
---|
1380 | case FontVariantEastAsianWidth::Proportional:
|
---|
1381 | valueList->append(cssValuePool.createIdentifierValue(CSSValueProportionalWidth));
|
---|
1382 | break;
|
---|
1383 | }
|
---|
1384 |
|
---|
1385 | if (ruby == FontVariantEastAsianRuby::Yes)
|
---|
1386 | valueList->append(cssValuePool.createIdentifierValue(CSSValueRuby));
|
---|
1387 |
|
---|
1388 | return valueList;
|
---|
1389 | }
|
---|
1390 |
|
---|
1391 | static Ref<CSSPrimitiveValue> valueForAnimationDuration(double duration)
|
---|
1392 | {
|
---|
1393 | return CSSValuePool::singleton().createValue(duration, CSSUnitType::CSS_S);
|
---|
1394 | }
|
---|
1395 |
|
---|
1396 | static Ref<CSSPrimitiveValue> valueForAnimationDelay(double delay)
|
---|
1397 | {
|
---|
1398 | return CSSValuePool::singleton().createValue(delay, CSSUnitType::CSS_S);
|
---|
1399 | }
|
---|
1400 |
|
---|
1401 | static Ref<CSSPrimitiveValue> valueForAnimationIterationCount(double iterationCount)
|
---|
1402 | {
|
---|
1403 | if (iterationCount == Animation::IterationCountInfinite)
|
---|
1404 | return CSSValuePool::singleton().createIdentifierValue(CSSValueInfinite);
|
---|
1405 | return CSSValuePool::singleton().createValue(iterationCount, CSSUnitType::CSS_NUMBER);
|
---|
1406 | }
|
---|
1407 |
|
---|
1408 | static Ref<CSSPrimitiveValue> valueForAnimationDirection(Animation::AnimationDirection direction)
|
---|
1409 | {
|
---|
1410 | switch (direction) {
|
---|
1411 | case Animation::AnimationDirectionNormal:
|
---|
1412 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNormal);
|
---|
1413 | case Animation::AnimationDirectionAlternate:
|
---|
1414 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAlternate);
|
---|
1415 | case Animation::AnimationDirectionReverse:
|
---|
1416 | return CSSValuePool::singleton().createIdentifierValue(CSSValueReverse);
|
---|
1417 | case Animation::AnimationDirectionAlternateReverse:
|
---|
1418 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAlternateReverse);
|
---|
1419 | }
|
---|
1420 | RELEASE_ASSERT_NOT_REACHED();
|
---|
1421 | }
|
---|
1422 |
|
---|
1423 | static Ref<CSSPrimitiveValue> valueForAnimationFillMode(AnimationFillMode fillMode)
|
---|
1424 | {
|
---|
1425 | switch (fillMode) {
|
---|
1426 | case AnimationFillMode::None:
|
---|
1427 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
1428 | case AnimationFillMode::Forwards:
|
---|
1429 | return CSSValuePool::singleton().createIdentifierValue(CSSValueForwards);
|
---|
1430 | case AnimationFillMode::Backwards:
|
---|
1431 | return CSSValuePool::singleton().createIdentifierValue(CSSValueBackwards);
|
---|
1432 | case AnimationFillMode::Both:
|
---|
1433 | return CSSValuePool::singleton().createIdentifierValue(CSSValueBoth);
|
---|
1434 | }
|
---|
1435 | RELEASE_ASSERT_NOT_REACHED();
|
---|
1436 | }
|
---|
1437 |
|
---|
1438 | static Ref<CSSPrimitiveValue> valueForAnimationComposition(CompositeOperation operation)
|
---|
1439 | {
|
---|
1440 | switch (operation) {
|
---|
1441 | case CompositeOperation::Add:
|
---|
1442 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAdd);
|
---|
1443 | case CompositeOperation::Accumulate:
|
---|
1444 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAccumulate);
|
---|
1445 | case CompositeOperation::Replace:
|
---|
1446 | return CSSValuePool::singleton().createIdentifierValue(CSSValueReplace);
|
---|
1447 | }
|
---|
1448 | RELEASE_ASSERT_NOT_REACHED();
|
---|
1449 | }
|
---|
1450 |
|
---|
1451 | static Ref<CSSPrimitiveValue> valueForAnimationPlayState(AnimationPlayState playState)
|
---|
1452 | {
|
---|
1453 | switch (playState) {
|
---|
1454 | case AnimationPlayState::Playing:
|
---|
1455 | return CSSValuePool::singleton().createIdentifierValue(CSSValueRunning);
|
---|
1456 | case AnimationPlayState::Paused:
|
---|
1457 | return CSSValuePool::singleton().createIdentifierValue(CSSValuePaused);
|
---|
1458 | }
|
---|
1459 | RELEASE_ASSERT_NOT_REACHED();
|
---|
1460 | }
|
---|
1461 |
|
---|
1462 | static Ref<CSSPrimitiveValue> valueForAnimationName(const Animation::Name& name)
|
---|
1463 | {
|
---|
1464 | if (name.isIdentifier)
|
---|
1465 | return CSSValuePool::singleton().createCustomIdent(name.string);
|
---|
1466 | return CSSValuePool::singleton().createValue(name.string, CSSUnitType::CSS_STRING);
|
---|
1467 | }
|
---|
1468 |
|
---|
1469 | static Ref<CSSValue> valueForAnimationTimingFunction(const TimingFunction& timingFunction)
|
---|
1470 | {
|
---|
1471 | switch (timingFunction.type()) {
|
---|
1472 | case TimingFunction::CubicBezierFunction: {
|
---|
1473 | auto& function = downcast<CubicBezierTimingFunction>(timingFunction);
|
---|
1474 | if (function.timingFunctionPreset() != CubicBezierTimingFunction::Custom) {
|
---|
1475 | CSSValueID valueId = CSSValueInvalid;
|
---|
1476 | switch (function.timingFunctionPreset()) {
|
---|
1477 | case CubicBezierTimingFunction::Ease:
|
---|
1478 | valueId = CSSValueEase;
|
---|
1479 | break;
|
---|
1480 | case CubicBezierTimingFunction::EaseIn:
|
---|
1481 | valueId = CSSValueEaseIn;
|
---|
1482 | break;
|
---|
1483 | case CubicBezierTimingFunction::EaseOut:
|
---|
1484 | valueId = CSSValueEaseOut;
|
---|
1485 | break;
|
---|
1486 | default:
|
---|
1487 | ASSERT(function.timingFunctionPreset() == CubicBezierTimingFunction::EaseInOut);
|
---|
1488 | valueId = CSSValueEaseInOut;
|
---|
1489 | break;
|
---|
1490 | }
|
---|
1491 | return CSSValuePool::singleton().createIdentifierValue(valueId);
|
---|
1492 | }
|
---|
1493 | return CSSCubicBezierTimingFunctionValue::create(function.x1(), function.y1(), function.x2(), function.y2());
|
---|
1494 | }
|
---|
1495 | case TimingFunction::StepsFunction: {
|
---|
1496 | auto& function = downcast<StepsTimingFunction>(timingFunction);
|
---|
1497 | return CSSStepsTimingFunctionValue::create(function.numberOfSteps(), function.stepPosition());
|
---|
1498 | }
|
---|
1499 | case TimingFunction::SpringFunction: {
|
---|
1500 | auto& function = downcast<SpringTimingFunction>(timingFunction);
|
---|
1501 | return CSSSpringTimingFunctionValue::create(function.mass(), function.stiffness(), function.damping(), function.initialVelocity());
|
---|
1502 | }
|
---|
1503 | default:
|
---|
1504 | ASSERT(timingFunction.type() == TimingFunction::LinearFunction);
|
---|
1505 | return CSSValuePool::singleton().createIdentifierValue(CSSValueLinear);
|
---|
1506 | }
|
---|
1507 | }
|
---|
1508 |
|
---|
1509 | void ComputedStyleExtractor::addValueForAnimationPropertyToList(CSSValueList& list, CSSPropertyID property, const Animation* animation)
|
---|
1510 | {
|
---|
1511 | if (property == CSSPropertyAnimationDuration || property == CSSPropertyTransitionDuration) {
|
---|
1512 | if (!animation || !animation->isDurationFilled())
|
---|
1513 | list.append(valueForAnimationDuration(animation ? animation->duration() : Animation::initialDuration()));
|
---|
1514 | } else if (property == CSSPropertyAnimationDelay || property == CSSPropertyTransitionDelay) {
|
---|
1515 | if (!animation || !animation->isDelayFilled())
|
---|
1516 | list.append(valueForAnimationDelay(animation ? animation->delay() : Animation::initialDelay()));
|
---|
1517 | } else if (property == CSSPropertyAnimationIterationCount) {
|
---|
1518 | if (!animation || !animation->isIterationCountFilled())
|
---|
1519 | list.append(valueForAnimationIterationCount(animation ? animation->iterationCount() : Animation::initialIterationCount()));
|
---|
1520 | } else if (property == CSSPropertyAnimationDirection) {
|
---|
1521 | if (!animation || !animation->isDirectionFilled())
|
---|
1522 | list.append(valueForAnimationDirection(animation ? animation->direction() : Animation::initialDirection()));
|
---|
1523 | } else if (property == CSSPropertyAnimationFillMode) {
|
---|
1524 | if (!animation || !animation->isFillModeFilled())
|
---|
1525 | list.append(valueForAnimationFillMode(animation ? animation->fillMode() : Animation::initialFillMode()));
|
---|
1526 | } else if (property == CSSPropertyAnimationPlayState) {
|
---|
1527 | if (!animation || !animation->isPlayStateFilled())
|
---|
1528 | list.append(valueForAnimationPlayState(animation ? animation->playState() : Animation::initialPlayState()));
|
---|
1529 | } else if (property == CSSPropertyAnimationName)
|
---|
1530 | list.append(valueForAnimationName(animation ? animation->name() : Animation::initialName()));
|
---|
1531 | else if (property == CSSPropertyAnimationComposition) {
|
---|
1532 | if (!animation || !animation->isCompositeOperationFilled())
|
---|
1533 | list.append(valueForAnimationComposition(animation ? animation->compositeOperation() : Animation::initialCompositeOperation()));
|
---|
1534 | } else if (property == CSSPropertyTransitionProperty) {
|
---|
1535 | if (animation) {
|
---|
1536 | if (!animation->isPropertyFilled())
|
---|
1537 | list.append(createTransitionPropertyValue(*animation));
|
---|
1538 | } else
|
---|
1539 | list.append(CSSValuePool::singleton().createIdentifierValue(CSSValueAll));
|
---|
1540 | } else if (property == CSSPropertyAnimationTimingFunction || property == CSSPropertyTransitionTimingFunction) {
|
---|
1541 | if (animation) {
|
---|
1542 | if (!animation->isTimingFunctionFilled())
|
---|
1543 | list.append(valueForAnimationTimingFunction(*animation->timingFunction()));
|
---|
1544 | } else
|
---|
1545 | list.append(valueForAnimationTimingFunction(CubicBezierTimingFunction::defaultTimingFunction()));
|
---|
1546 | } else
|
---|
1547 | ASSERT_NOT_REACHED();
|
---|
1548 | }
|
---|
1549 |
|
---|
1550 | static Ref<CSSValueList> valueListForAnimationOrTransitionProperty(CSSPropertyID property, const AnimationList* animationList)
|
---|
1551 | {
|
---|
1552 | auto list = CSSValueList::createCommaSeparated();
|
---|
1553 | if (animationList) {
|
---|
1554 | for (const auto& animation : *animationList)
|
---|
1555 | ComputedStyleExtractor::addValueForAnimationPropertyToList(list.get(), property, animation.ptr());
|
---|
1556 | } else
|
---|
1557 | ComputedStyleExtractor::addValueForAnimationPropertyToList(list.get(), property, nullptr);
|
---|
1558 | return list;
|
---|
1559 | }
|
---|
1560 |
|
---|
1561 | static Ref<CSSValueList> animationShorthandValue(CSSPropertyID property, const AnimationList* animationList)
|
---|
1562 | {
|
---|
1563 | auto parentList = CSSValueList::createCommaSeparated();
|
---|
1564 |
|
---|
1565 | auto addAnimation = [&](Ref<Animation> animation) {
|
---|
1566 | auto childList = CSSValueList::createSpaceSeparated();
|
---|
1567 | for (auto longhand : shorthandForProperty(property))
|
---|
1568 | ComputedStyleExtractor::addValueForAnimationPropertyToList(childList.get(), longhand, animation.ptr());
|
---|
1569 | parentList->append(childList);
|
---|
1570 | };
|
---|
1571 |
|
---|
1572 | if (animationList && !animationList->isEmpty()) {
|
---|
1573 | for (const auto& animation : *animationList)
|
---|
1574 | addAnimation(animation);
|
---|
1575 | } else
|
---|
1576 | addAnimation(Animation::create());
|
---|
1577 |
|
---|
1578 | return parentList;
|
---|
1579 | }
|
---|
1580 |
|
---|
1581 | static Ref<CSSValue> createLineBoxContainValue(OptionSet<LineBoxContain> lineBoxContain)
|
---|
1582 | {
|
---|
1583 | if (!lineBoxContain)
|
---|
1584 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
1585 | return CSSLineBoxContainValue::create(lineBoxContain);
|
---|
1586 | }
|
---|
1587 |
|
---|
1588 | static Element* styleElementForNode(Node* node)
|
---|
1589 | {
|
---|
1590 | if (!node)
|
---|
1591 | return nullptr;
|
---|
1592 | if (is<Element>(*node))
|
---|
1593 | return downcast<Element>(node);
|
---|
1594 | return composedTreeAncestors(*node).first();
|
---|
1595 | }
|
---|
1596 |
|
---|
1597 | static Ref<CSSValue> valueForPosition(const RenderStyle& style, const LengthPoint& position)
|
---|
1598 | {
|
---|
1599 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1600 | list->append(zoomAdjustedPixelValueForLength(position.x(), style));
|
---|
1601 | list->append(zoomAdjustedPixelValueForLength(position.y(), style));
|
---|
1602 | return list;
|
---|
1603 | }
|
---|
1604 |
|
---|
1605 | static Ref<CSSValue> valueForPositionOrAuto(const RenderStyle& style, const LengthPoint& position)
|
---|
1606 | {
|
---|
1607 | if (position.x().isAuto() && position.y().isAuto())
|
---|
1608 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
1609 |
|
---|
1610 | return valueForPosition(style, position);
|
---|
1611 | }
|
---|
1612 |
|
---|
1613 | static CSSValueID valueIDForRaySize(RayPathOperation::Size size)
|
---|
1614 | {
|
---|
1615 | switch (size) {
|
---|
1616 | case RayPathOperation::Size::ClosestCorner:
|
---|
1617 | return CSSValueClosestCorner;
|
---|
1618 | case RayPathOperation::Size::ClosestSide:
|
---|
1619 | return CSSValueClosestSide;
|
---|
1620 | case RayPathOperation::Size::FarthestCorner:
|
---|
1621 | return CSSValueFarthestCorner;
|
---|
1622 | case RayPathOperation::Size::FarthestSide:
|
---|
1623 | return CSSValueFarthestSide;
|
---|
1624 | case RayPathOperation::Size::Sides:
|
---|
1625 | return CSSValueSides;
|
---|
1626 | }
|
---|
1627 |
|
---|
1628 | ASSERT_NOT_REACHED();
|
---|
1629 | return CSSValueInvalid;
|
---|
1630 | }
|
---|
1631 |
|
---|
1632 | static Ref<CSSValue> valueForPathOperation(const RenderStyle& style, const PathOperation* operation, SVGPathConversion conversion = SVGPathConversion::None)
|
---|
1633 | {
|
---|
1634 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1635 |
|
---|
1636 | if (!operation)
|
---|
1637 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1638 |
|
---|
1639 | switch (operation->type()) {
|
---|
1640 | case PathOperation::Reference:
|
---|
1641 | return CSSPrimitiveValue::create(downcast<ReferencePathOperation>(*operation).url(), CSSUnitType::CSS_URI);
|
---|
1642 |
|
---|
1643 | case PathOperation::Shape: {
|
---|
1644 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1645 |
|
---|
1646 | auto& shapeOperation = downcast<ShapePathOperation>(*operation);
|
---|
1647 | list->append(valueForBasicShape(style, shapeOperation.basicShape(), conversion));
|
---|
1648 |
|
---|
1649 | if (shapeOperation.referenceBox() != CSSBoxType::BoxMissing)
|
---|
1650 | list->append(cssValuePool.createValue(shapeOperation.referenceBox()));
|
---|
1651 |
|
---|
1652 | return list;
|
---|
1653 | }
|
---|
1654 |
|
---|
1655 | case PathOperation::Box:
|
---|
1656 | return cssValuePool.createValue(downcast<BoxPathOperation>(*operation).referenceBox());
|
---|
1657 |
|
---|
1658 | case PathOperation::Ray: {
|
---|
1659 | auto& ray = downcast<RayPathOperation>(*operation);
|
---|
1660 |
|
---|
1661 | auto angle = cssValuePool.createValue(ray.angle(), CSSUnitType::CSS_DEG);
|
---|
1662 | auto size = cssValuePool.createIdentifierValue(valueIDForRaySize(ray.size()));
|
---|
1663 |
|
---|
1664 | return CSSRayValue::create(WTFMove(angle), WTFMove(size), ray.isContaining());
|
---|
1665 | }
|
---|
1666 | }
|
---|
1667 |
|
---|
1668 | ASSERT_NOT_REACHED();
|
---|
1669 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1670 | }
|
---|
1671 |
|
---|
1672 | static Ref<CSSValue> valueForContainIntrinsicSize(const RenderStyle& style, const ContainIntrinsicSizeType& type, const std::optional<Length> containIntrinsicLength)
|
---|
1673 | {
|
---|
1674 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1675 |
|
---|
1676 | switch (type) {
|
---|
1677 | case ContainIntrinsicSizeType::None:
|
---|
1678 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1679 | case ContainIntrinsicSizeType::Length: {
|
---|
1680 | ASSERT(containIntrinsicLength.has_value());
|
---|
1681 | return zoomAdjustedPixelValueForLength(containIntrinsicLength.value(), style);
|
---|
1682 | }
|
---|
1683 | case ContainIntrinsicSizeType::AutoAndLength: {
|
---|
1684 | auto autoValue = cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
1685 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1686 | list->append(autoValue);
|
---|
1687 | ASSERT(containIntrinsicLength.has_value());
|
---|
1688 | list->append(zoomAdjustedPixelValueForLength(containIntrinsicLength.value(), style));
|
---|
1689 | return list;
|
---|
1690 | }
|
---|
1691 | }
|
---|
1692 | RELEASE_ASSERT_NOT_REACHED();
|
---|
1693 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1694 | }
|
---|
1695 |
|
---|
1696 | ComputedStyleExtractor::ComputedStyleExtractor(Node* node, bool allowVisitedStyle, PseudoId pseudoElementSpecifier)
|
---|
1697 | : m_element(styleElementForNode(node))
|
---|
1698 | , m_pseudoElementSpecifier(pseudoElementSpecifier)
|
---|
1699 | , m_allowVisitedStyle(allowVisitedStyle)
|
---|
1700 | {
|
---|
1701 | }
|
---|
1702 |
|
---|
1703 | ComputedStyleExtractor::ComputedStyleExtractor(Element* element, bool allowVisitedStyle, PseudoId pseudoElementSpecifier)
|
---|
1704 | : m_element(element)
|
---|
1705 | , m_pseudoElementSpecifier(pseudoElementSpecifier)
|
---|
1706 | , m_allowVisitedStyle(allowVisitedStyle)
|
---|
1707 | {
|
---|
1708 | }
|
---|
1709 |
|
---|
1710 | CSSComputedStyleDeclaration::CSSComputedStyleDeclaration(Element& element, bool allowVisitedStyle, StringView pseudoElementName)
|
---|
1711 | : m_element(element)
|
---|
1712 | , m_allowVisitedStyle(allowVisitedStyle)
|
---|
1713 | {
|
---|
1714 | StringView name = pseudoElementName;
|
---|
1715 | if (name.startsWith(':'))
|
---|
1716 | name = name.substring(1);
|
---|
1717 | if (name.startsWith(':'))
|
---|
1718 | name = name.substring(1);
|
---|
1719 | m_pseudoElementSpecifier = CSSSelector::pseudoId(CSSSelector::parsePseudoElementType(name));
|
---|
1720 | }
|
---|
1721 |
|
---|
1722 | CSSComputedStyleDeclaration::~CSSComputedStyleDeclaration() = default;
|
---|
1723 |
|
---|
1724 | Ref<CSSComputedStyleDeclaration> CSSComputedStyleDeclaration::create(Element& element, bool allowVisitedStyle, StringView pseudoElementName)
|
---|
1725 | {
|
---|
1726 | return adoptRef(*new CSSComputedStyleDeclaration(element, allowVisitedStyle, pseudoElementName));
|
---|
1727 | }
|
---|
1728 |
|
---|
1729 | void CSSComputedStyleDeclaration::ref()
|
---|
1730 | {
|
---|
1731 | ++m_refCount;
|
---|
1732 | }
|
---|
1733 |
|
---|
1734 | void CSSComputedStyleDeclaration::deref()
|
---|
1735 | {
|
---|
1736 | ASSERT(m_refCount);
|
---|
1737 | if (!--m_refCount)
|
---|
1738 | delete this;
|
---|
1739 | }
|
---|
1740 |
|
---|
1741 | String CSSComputedStyleDeclaration::cssText() const
|
---|
1742 | {
|
---|
1743 | return emptyString();
|
---|
1744 | }
|
---|
1745 |
|
---|
1746 | ExceptionOr<void> CSSComputedStyleDeclaration::setCssText(const String&)
|
---|
1747 | {
|
---|
1748 | return Exception { NoModificationAllowedError };
|
---|
1749 | }
|
---|
1750 |
|
---|
1751 | RefPtr<CSSPrimitiveValue> ComputedStyleExtractor::getFontSizeCSSValuePreferringKeyword()
|
---|
1752 | {
|
---|
1753 | if (!m_element)
|
---|
1754 | return nullptr;
|
---|
1755 |
|
---|
1756 | m_element->document().updateLayoutIgnorePendingStylesheets();
|
---|
1757 |
|
---|
1758 | auto* style = m_element->computedStyle(m_pseudoElementSpecifier);
|
---|
1759 | if (!style)
|
---|
1760 | return nullptr;
|
---|
1761 |
|
---|
1762 | if (CSSValueID sizeIdentifier = style->fontDescription().keywordSizeAsIdentifier())
|
---|
1763 | return CSSValuePool::singleton().createIdentifierValue(sizeIdentifier);
|
---|
1764 |
|
---|
1765 | return zoomAdjustedPixelValue(style->fontDescription().computedSize(), *style);
|
---|
1766 | }
|
---|
1767 |
|
---|
1768 | bool ComputedStyleExtractor::useFixedFontDefaultSize()
|
---|
1769 | {
|
---|
1770 | if (!m_element)
|
---|
1771 | return false;
|
---|
1772 | auto* style = m_element->computedStyle(m_pseudoElementSpecifier);
|
---|
1773 | if (!style)
|
---|
1774 | return false;
|
---|
1775 |
|
---|
1776 | return style->fontDescription().useFixedDefaultSize();
|
---|
1777 | }
|
---|
1778 |
|
---|
1779 | static CSSValueID identifierForFamily(const AtomString& family)
|
---|
1780 | {
|
---|
1781 | if (family == cursiveFamily)
|
---|
1782 | return CSSValueCursive;
|
---|
1783 | if (family == fantasyFamily)
|
---|
1784 | return CSSValueFantasy;
|
---|
1785 | if (family == monospaceFamily)
|
---|
1786 | return CSSValueMonospace;
|
---|
1787 | if (family == pictographFamily)
|
---|
1788 | return CSSValueWebkitPictograph;
|
---|
1789 | if (family == sansSerifFamily)
|
---|
1790 | return CSSValueSansSerif;
|
---|
1791 | if (family == serifFamily)
|
---|
1792 | return CSSValueSerif;
|
---|
1793 | if (family == systemUiFamily)
|
---|
1794 | return CSSValueSystemUi;
|
---|
1795 | return CSSValueInvalid;
|
---|
1796 | }
|
---|
1797 |
|
---|
1798 | static Ref<CSSPrimitiveValue> valueForFamily(const AtomString& family)
|
---|
1799 | {
|
---|
1800 | if (CSSValueID familyIdentifier = identifierForFamily(family))
|
---|
1801 | return CSSValuePool::singleton().createIdentifierValue(familyIdentifier);
|
---|
1802 | return CSSValuePool::singleton().createFontFamilyValue(family);
|
---|
1803 | }
|
---|
1804 |
|
---|
1805 | static Ref<CSSValue> touchActionFlagsToCSSValue(OptionSet<TouchAction> touchActions)
|
---|
1806 | {
|
---|
1807 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1808 |
|
---|
1809 | if (touchActions & TouchAction::Auto)
|
---|
1810 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
1811 | if (touchActions & TouchAction::None)
|
---|
1812 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1813 | if (touchActions & TouchAction::Manipulation)
|
---|
1814 | return cssValuePool.createIdentifierValue(CSSValueManipulation);
|
---|
1815 |
|
---|
1816 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1817 | if (touchActions & TouchAction::PanX)
|
---|
1818 | list->append(cssValuePool.createIdentifierValue(CSSValuePanX));
|
---|
1819 | if (touchActions & TouchAction::PanY)
|
---|
1820 | list->append(cssValuePool.createIdentifierValue(CSSValuePanY));
|
---|
1821 | if (touchActions & TouchAction::PinchZoom)
|
---|
1822 | list->append(cssValuePool.createIdentifierValue(CSSValuePinchZoom));
|
---|
1823 |
|
---|
1824 | if (!list->length())
|
---|
1825 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
1826 | return list;
|
---|
1827 | }
|
---|
1828 |
|
---|
1829 | static Ref<CSSValue> renderTextDecorationLineFlagsToCSSValue(OptionSet<TextDecorationLine> textDecorationLine)
|
---|
1830 | {
|
---|
1831 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1832 | // Blink value is ignored.
|
---|
1833 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1834 | if (textDecorationLine & TextDecorationLine::Underline)
|
---|
1835 | list->append(cssValuePool.createIdentifierValue(CSSValueUnderline));
|
---|
1836 | if (textDecorationLine & TextDecorationLine::Overline)
|
---|
1837 | list->append(cssValuePool.createIdentifierValue(CSSValueOverline));
|
---|
1838 | if (textDecorationLine & TextDecorationLine::LineThrough)
|
---|
1839 | list->append(cssValuePool.createIdentifierValue(CSSValueLineThrough));
|
---|
1840 |
|
---|
1841 | if (!list->length())
|
---|
1842 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1843 | return list;
|
---|
1844 | }
|
---|
1845 |
|
---|
1846 | static Ref<CSSValue> renderTextDecorationStyleFlagsToCSSValue(TextDecorationStyle textDecorationStyle)
|
---|
1847 | {
|
---|
1848 | switch (textDecorationStyle) {
|
---|
1849 | case TextDecorationStyle::Solid:
|
---|
1850 | return CSSValuePool::singleton().createIdentifierValue(CSSValueSolid);
|
---|
1851 | case TextDecorationStyle::Double:
|
---|
1852 | return CSSValuePool::singleton().createIdentifierValue(CSSValueDouble);
|
---|
1853 | case TextDecorationStyle::Dotted:
|
---|
1854 | return CSSValuePool::singleton().createIdentifierValue(CSSValueDotted);
|
---|
1855 | case TextDecorationStyle::Dashed:
|
---|
1856 | return CSSValuePool::singleton().createIdentifierValue(CSSValueDashed);
|
---|
1857 | case TextDecorationStyle::Wavy:
|
---|
1858 | return CSSValuePool::singleton().createIdentifierValue(CSSValueWavy);
|
---|
1859 | }
|
---|
1860 |
|
---|
1861 | ASSERT_NOT_REACHED();
|
---|
1862 | return CSSValuePool::singleton().createIdentifierValue(CSSValueInitial);
|
---|
1863 | }
|
---|
1864 |
|
---|
1865 | static RefPtr<CSSValue> renderTextDecorationSkipToCSSValue(TextDecorationSkipInk textDecorationSkipInk)
|
---|
1866 | {
|
---|
1867 | switch (textDecorationSkipInk) {
|
---|
1868 | case TextDecorationSkipInk::None:
|
---|
1869 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
1870 | case TextDecorationSkipInk::Auto:
|
---|
1871 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
1872 | case TextDecorationSkipInk::All:
|
---|
1873 | return nullptr;
|
---|
1874 | }
|
---|
1875 |
|
---|
1876 | ASSERT_NOT_REACHED();
|
---|
1877 | return CSSValuePool::singleton().createIdentifierValue(CSSValueInitial);
|
---|
1878 | }
|
---|
1879 |
|
---|
1880 | static Ref<CSSValue> textUnderlineOffsetToCSSValue(const TextUnderlineOffset& textUnderlineOffset)
|
---|
1881 | {
|
---|
1882 | if (textUnderlineOffset.isAuto())
|
---|
1883 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
1884 | ASSERT(textUnderlineOffset.isLength());
|
---|
1885 | return CSSValuePool::singleton().createValue(textUnderlineOffset.lengthValue(), CSSUnitType::CSS_PX);
|
---|
1886 | }
|
---|
1887 |
|
---|
1888 | static Ref<CSSValue> textDecorationThicknessToCSSValue(const TextDecorationThickness& textDecorationThickness)
|
---|
1889 | {
|
---|
1890 | if (textDecorationThickness.isAuto())
|
---|
1891 | return CSSValuePool::singleton().createIdentifierValue(CSSValueAuto);
|
---|
1892 | if (textDecorationThickness.isFromFont())
|
---|
1893 | return CSSValuePool::singleton().createIdentifierValue(CSSValueFromFont);
|
---|
1894 | ASSERT(textDecorationThickness.isLength());
|
---|
1895 | return CSSValuePool::singleton().createValue(textDecorationThickness.lengthValue(), CSSUnitType::CSS_PX);
|
---|
1896 | }
|
---|
1897 |
|
---|
1898 | static Ref<CSSValue> renderEmphasisPositionFlagsToCSSValue(OptionSet<TextEmphasisPosition> textEmphasisPosition)
|
---|
1899 | {
|
---|
1900 | ASSERT(!((textEmphasisPosition & TextEmphasisPosition::Over) && (textEmphasisPosition & TextEmphasisPosition::Under)));
|
---|
1901 | ASSERT(!((textEmphasisPosition & TextEmphasisPosition::Left) && (textEmphasisPosition & TextEmphasisPosition::Right)));
|
---|
1902 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1903 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1904 | if (textEmphasisPosition & TextEmphasisPosition::Over)
|
---|
1905 | list->append(cssValuePool.createIdentifierValue(CSSValueOver));
|
---|
1906 | if (textEmphasisPosition & TextEmphasisPosition::Under)
|
---|
1907 | list->append(cssValuePool.createIdentifierValue(CSSValueUnder));
|
---|
1908 | if (textEmphasisPosition & TextEmphasisPosition::Left)
|
---|
1909 | list->append(cssValuePool.createIdentifierValue(CSSValueLeft));
|
---|
1910 | if (textEmphasisPosition & TextEmphasisPosition::Right)
|
---|
1911 | list->append(cssValuePool.createIdentifierValue(CSSValueRight));
|
---|
1912 | if (!list->length())
|
---|
1913 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1914 | return list;
|
---|
1915 | }
|
---|
1916 |
|
---|
1917 | static Ref<CSSValue> valueForTextEmphasisStyle(const RenderStyle& style)
|
---|
1918 | {
|
---|
1919 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1920 | switch (style.textEmphasisMark()) {
|
---|
1921 | case TextEmphasisMark::None:
|
---|
1922 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1923 | case TextEmphasisMark::Custom:
|
---|
1924 | return cssValuePool.createValue(style.textEmphasisCustomMark(), CSSUnitType::CSS_STRING);
|
---|
1925 | case TextEmphasisMark::Auto:
|
---|
1926 | ASSERT_NOT_REACHED();
|
---|
1927 | #if !ASSERT_ENABLED
|
---|
1928 | FALLTHROUGH;
|
---|
1929 | #endif
|
---|
1930 | case TextEmphasisMark::Dot:
|
---|
1931 | case TextEmphasisMark::Circle:
|
---|
1932 | case TextEmphasisMark::DoubleCircle:
|
---|
1933 | case TextEmphasisMark::Triangle:
|
---|
1934 | case TextEmphasisMark::Sesame:
|
---|
1935 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1936 | if (style.textEmphasisFill() != TextEmphasisFill::Filled)
|
---|
1937 | list->append(cssValuePool.createValue(style.textEmphasisFill()));
|
---|
1938 | list->append(cssValuePool.createValue(style.textEmphasisMark()));
|
---|
1939 | return list;
|
---|
1940 | }
|
---|
1941 | RELEASE_ASSERT_NOT_REACHED();
|
---|
1942 | }
|
---|
1943 |
|
---|
1944 | static Ref<CSSValue> speakAsToCSSValue(OptionSet<SpeakAs> speakAs)
|
---|
1945 | {
|
---|
1946 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1947 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1948 | if (speakAs & SpeakAs::SpellOut)
|
---|
1949 | list->append(cssValuePool.createIdentifierValue(CSSValueSpellOut));
|
---|
1950 | if (speakAs & SpeakAs::Digits)
|
---|
1951 | list->append(cssValuePool.createIdentifierValue(CSSValueDigits));
|
---|
1952 | if (speakAs & SpeakAs::LiteralPunctuation)
|
---|
1953 | list->append(cssValuePool.createIdentifierValue(CSSValueLiteralPunctuation));
|
---|
1954 | if (speakAs & SpeakAs::NoPunctuation)
|
---|
1955 | list->append(cssValuePool.createIdentifierValue(CSSValueNoPunctuation));
|
---|
1956 | if (!list->length())
|
---|
1957 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
1958 | return list;
|
---|
1959 | }
|
---|
1960 |
|
---|
1961 | static Ref<CSSValue> hangingPunctuationToCSSValue(OptionSet<HangingPunctuation> hangingPunctuation)
|
---|
1962 | {
|
---|
1963 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1964 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1965 | if (hangingPunctuation & HangingPunctuation::First)
|
---|
1966 | list->append(cssValuePool.createIdentifierValue(CSSValueFirst));
|
---|
1967 | if (hangingPunctuation & HangingPunctuation::AllowEnd)
|
---|
1968 | list->append(cssValuePool.createIdentifierValue(CSSValueAllowEnd));
|
---|
1969 | if (hangingPunctuation & HangingPunctuation::ForceEnd)
|
---|
1970 | list->append(cssValuePool.createIdentifierValue(CSSValueForceEnd));
|
---|
1971 | if (hangingPunctuation & HangingPunctuation::Last)
|
---|
1972 | list->append(cssValuePool.createIdentifierValue(CSSValueLast));
|
---|
1973 | if (!list->length())
|
---|
1974 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
1975 | return list;
|
---|
1976 | }
|
---|
1977 |
|
---|
1978 | static Ref<CSSValue> fillRepeatToCSSValue(FillRepeat xRepeat, FillRepeat yRepeat)
|
---|
1979 | {
|
---|
1980 | // For backwards compatibility, if both values are equal, just return one of them. And
|
---|
1981 | // if the two values are equivalent to repeat-x or repeat-y, just return the shorthand.
|
---|
1982 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
1983 | if (xRepeat == yRepeat)
|
---|
1984 | return cssValuePool.createValue(xRepeat);
|
---|
1985 | if (xRepeat == FillRepeat::Repeat && yRepeat == FillRepeat::NoRepeat)
|
---|
1986 | return cssValuePool.createIdentifierValue(CSSValueRepeatX);
|
---|
1987 | if (xRepeat == FillRepeat::NoRepeat && yRepeat == FillRepeat::Repeat)
|
---|
1988 | return cssValuePool.createIdentifierValue(CSSValueRepeatY);
|
---|
1989 |
|
---|
1990 | auto list = CSSValueList::createSpaceSeparated();
|
---|
1991 | list->append(cssValuePool.createValue(xRepeat));
|
---|
1992 | list->append(cssValuePool.createValue(yRepeat));
|
---|
1993 | return list;
|
---|
1994 | }
|
---|
1995 |
|
---|
1996 | static Ref<CSSValue> maskSourceTypeToCSSValue(MaskMode type)
|
---|
1997 | {
|
---|
1998 | switch (type) {
|
---|
1999 | case MaskMode::Alpha:
|
---|
2000 | return CSSValuePool::singleton().createValue(CSSValueAlpha);
|
---|
2001 | case MaskMode::Luminance:
|
---|
2002 | ASSERT(type == MaskMode::Luminance);
|
---|
2003 | return CSSValuePool::singleton().createValue(CSSValueLuminance);
|
---|
2004 | case MaskMode::MatchSource:
|
---|
2005 | // MatchSource is only available in the mask-mode property.
|
---|
2006 | return CSSValuePool::singleton().createValue(CSSValueAlpha);
|
---|
2007 | }
|
---|
2008 | ASSERT_NOT_REACHED();
|
---|
2009 | return CSSValuePool::singleton().createValue(CSSValueAlpha);
|
---|
2010 | }
|
---|
2011 |
|
---|
2012 | static Ref<CSSValue> maskModeToCSSValue(MaskMode type)
|
---|
2013 | {
|
---|
2014 | switch (type) {
|
---|
2015 | case MaskMode::Alpha:
|
---|
2016 | return CSSValuePool::singleton().createValue(CSSValueAlpha);
|
---|
2017 | case MaskMode::Luminance:
|
---|
2018 | return CSSValuePool::singleton().createValue(CSSValueLuminance);
|
---|
2019 | case MaskMode::MatchSource:
|
---|
2020 | return CSSValuePool::singleton().createValue(CSSValueMatchSource);
|
---|
2021 | }
|
---|
2022 | ASSERT_NOT_REACHED();
|
---|
2023 | return CSSValuePool::singleton().createValue(CSSValueMatchSource);
|
---|
2024 | }
|
---|
2025 |
|
---|
2026 | static Ref<CSSValue> fillSizeToCSSValue(const FillSize& fillSize, const RenderStyle& style)
|
---|
2027 | {
|
---|
2028 | if (fillSize.type == FillSizeType::Contain)
|
---|
2029 | return CSSValuePool::singleton().createIdentifierValue(CSSValueContain);
|
---|
2030 |
|
---|
2031 | if (fillSize.type == FillSizeType::Cover)
|
---|
2032 | return CSSValuePool::singleton().createIdentifierValue(CSSValueCover);
|
---|
2033 |
|
---|
2034 | if (fillSize.size.height.isAuto())
|
---|
2035 | return zoomAdjustedPixelValueForLength(fillSize.size.width, style);
|
---|
2036 |
|
---|
2037 | auto list = CSSValueList::createSpaceSeparated();
|
---|
2038 | list->append(zoomAdjustedPixelValueForLength(fillSize.size.width, style));
|
---|
2039 | list->append(zoomAdjustedPixelValueForLength(fillSize.size.height, style));
|
---|
2040 | return list;
|
---|
2041 | }
|
---|
2042 |
|
---|
2043 | static Ref<CSSValue> altTextToCSSValue(const RenderStyle& style)
|
---|
2044 | {
|
---|
2045 | return CSSValuePool::singleton().createValue(style.contentAltText(), CSSUnitType::CSS_STRING);
|
---|
2046 | }
|
---|
2047 |
|
---|
2048 | static Ref<CSSValueList> contentToCSSValue(const RenderStyle& style)
|
---|
2049 | {
|
---|
2050 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
2051 | auto list = CSSValueList::createSpaceSeparated();
|
---|
2052 | for (auto* contentData = style.contentData(); contentData; contentData = contentData->next()) {
|
---|
2053 | if (is<CounterContentData>(*contentData))
|
---|
2054 | list->append(cssValuePool.createValue(downcast<CounterContentData>(*contentData).counter().identifier(), CSSUnitType::CSS_COUNTER_NAME));
|
---|
2055 | else if (is<ImageContentData>(*contentData))
|
---|
2056 | list->append(downcast<ImageContentData>(*contentData).image().cssValue());
|
---|
2057 | else if (is<TextContentData>(*contentData))
|
---|
2058 | list->append(cssValuePool.createValue(downcast<TextContentData>(*contentData).text(), CSSUnitType::CSS_STRING));
|
---|
2059 | }
|
---|
2060 | if (!list->length())
|
---|
2061 | list->append(cssValuePool.createIdentifierValue(style.hasEffectiveContentNone() ? CSSValueNone : CSSValueNormal));
|
---|
2062 | return list;
|
---|
2063 | }
|
---|
2064 |
|
---|
2065 | static Ref<CSSValue> counterToCSSValue(const RenderStyle& style, CSSPropertyID propertyID)
|
---|
2066 | {
|
---|
2067 | auto* map = style.counterDirectives();
|
---|
2068 | if (!map)
|
---|
2069 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
2070 |
|
---|
2071 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
2072 | auto list = CSSValueList::createSpaceSeparated();
|
---|
2073 | for (auto& keyValue : *map) {
|
---|
2074 | if (auto number = (propertyID == CSSPropertyCounterIncrement ? keyValue.value.incrementValue : keyValue.value.resetValue)) {
|
---|
2075 | list->append(cssValuePool.createCustomIdent(keyValue.key));
|
---|
2076 | list->append(cssValuePool.createValue(*number, CSSUnitType::CSS_INTEGER));
|
---|
2077 | }
|
---|
2078 | }
|
---|
2079 |
|
---|
2080 | if (list->length())
|
---|
2081 | return list;
|
---|
2082 |
|
---|
2083 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
2084 | }
|
---|
2085 |
|
---|
2086 | static Ref<CSSValueList> fontFamilyListFromStyle(const RenderStyle& style)
|
---|
2087 | {
|
---|
2088 | auto list = CSSValueList::createCommaSeparated();
|
---|
2089 | for (unsigned i = 0; i < style.fontCascade().familyCount(); ++i)
|
---|
2090 | list->append(valueForFamily(style.fontCascade().familyAt(i)));
|
---|
2091 | return list;
|
---|
2092 | }
|
---|
2093 |
|
---|
2094 | static Ref<CSSValue> fontFamilyFromStyle(const RenderStyle& style)
|
---|
2095 | {
|
---|
2096 | if (style.fontCascade().familyCount() == 1)
|
---|
2097 | return valueForFamily(style.fontCascade().familyAt(0));
|
---|
2098 | return fontFamilyListFromStyle(style);
|
---|
2099 | }
|
---|
2100 |
|
---|
2101 | static Ref<CSSPrimitiveValue> lineHeightFromStyle(const RenderStyle& style)
|
---|
2102 | {
|
---|
2103 | Length length = style.lineHeight();
|
---|
2104 | if (length.isNegative())
|
---|
2105 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNormal);
|
---|
2106 | if (length.isPercent()) {
|
---|
2107 | // This is imperfect, because it doesn't include the zoom factor and the real computation
|
---|
2108 | // for how high to be in pixels does include things like minimum font size and the zoom factor.
|
---|
2109 | // On the other hand, since font-size doesn't include the zoom factor, we really can't do
|
---|
2110 | // that here either.
|
---|
2111 | return zoomAdjustedPixelValue(static_cast<double>(length.percent() * style.fontDescription().computedSize()) / 100, style);
|
---|
2112 | }
|
---|
2113 | return zoomAdjustedPixelValue(floatValueForLength(length, 0), style);
|
---|
2114 | }
|
---|
2115 |
|
---|
2116 | static Ref<CSSPrimitiveValue> fontSizeFromStyle(const RenderStyle& style)
|
---|
2117 | {
|
---|
2118 | return zoomAdjustedPixelValue(style.fontDescription().computedSize(), style);
|
---|
2119 | }
|
---|
2120 |
|
---|
2121 | static Ref<CSSPrimitiveValue> fontPaletteFromStyle(const RenderStyle& style)
|
---|
2122 | {
|
---|
2123 | auto fontPalette = style.fontDescription().fontPalette();
|
---|
2124 | switch (fontPalette.type) {
|
---|
2125 | case FontPalette::Type::Normal:
|
---|
2126 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNormal);
|
---|
2127 | case FontPalette::Type::Light:
|
---|
2128 | return CSSValuePool::singleton().createIdentifierValue(CSSValueLight);
|
---|
2129 | case FontPalette::Type::Dark:
|
---|
2130 | return CSSValuePool::singleton().createIdentifierValue(CSSValueDark);
|
---|
2131 | case FontPalette::Type::Custom:
|
---|
2132 | return CSSValuePool::singleton().createCustomIdent(fontPalette.identifier);
|
---|
2133 | }
|
---|
2134 | RELEASE_ASSERT_NOT_REACHED();
|
---|
2135 | }
|
---|
2136 |
|
---|
2137 | Ref<CSSPrimitiveValue> ComputedStyleExtractor::fontNonKeywordWeightFromStyleValue(FontSelectionValue weight)
|
---|
2138 | {
|
---|
2139 | return CSSValuePool::singleton().createValue(static_cast<float>(weight), CSSUnitType::CSS_NUMBER);
|
---|
2140 | }
|
---|
2141 |
|
---|
2142 | static Ref<CSSPrimitiveValue> fontNonKeywordWeightFromStyle(const RenderStyle& style)
|
---|
2143 | {
|
---|
2144 | return ComputedStyleExtractor::fontNonKeywordWeightFromStyleValue(style.fontDescription().weight());
|
---|
2145 | }
|
---|
2146 |
|
---|
2147 | Ref<CSSPrimitiveValue> ComputedStyleExtractor::fontWeightFromStyleValue(FontSelectionValue weight)
|
---|
2148 | {
|
---|
2149 | if (auto value = fontWeightKeyword(weight))
|
---|
2150 | return CSSValuePool::singleton().createIdentifierValue(value.value());
|
---|
2151 | return fontNonKeywordWeightFromStyleValue(weight);
|
---|
2152 | }
|
---|
2153 |
|
---|
2154 | Ref<CSSPrimitiveValue> ComputedStyleExtractor::fontNonKeywordStretchFromStyleValue(FontSelectionValue stretch)
|
---|
2155 | {
|
---|
2156 | return CSSValuePool::singleton().createValue(static_cast<float>(stretch), CSSUnitType::CSS_PERCENTAGE);
|
---|
2157 | }
|
---|
2158 |
|
---|
2159 | Ref<CSSPrimitiveValue> ComputedStyleExtractor::fontStretchFromStyleValue(FontSelectionValue stretch)
|
---|
2160 | {
|
---|
2161 | if (auto keyword = fontStretchKeyword(stretch))
|
---|
2162 | return CSSValuePool::singleton().createIdentifierValue(keyword.value());
|
---|
2163 | return fontNonKeywordStretchFromStyleValue(stretch);
|
---|
2164 | }
|
---|
2165 |
|
---|
2166 | static Ref<CSSPrimitiveValue> fontStretchFromStyle(const RenderStyle& style)
|
---|
2167 | {
|
---|
2168 | return ComputedStyleExtractor::fontStretchFromStyleValue(style.fontDescription().stretch());
|
---|
2169 | }
|
---|
2170 |
|
---|
2171 | Ref<CSSFontStyleValue> ComputedStyleExtractor::fontNonKeywordStyleFromStyleValue(FontSelectionValue italic)
|
---|
2172 | {
|
---|
2173 | return CSSFontStyleValue::create(CSSValuePool::singleton().createIdentifierValue(CSSValueOblique), CSSValuePool::singleton().createValue(static_cast<float>(italic), CSSUnitType::CSS_DEG));
|
---|
2174 | }
|
---|
2175 |
|
---|
2176 | Ref<CSSFontStyleValue> ComputedStyleExtractor::fontStyleFromStyleValue(std::optional<FontSelectionValue> italic, FontStyleAxis fontStyleAxis)
|
---|
2177 | {
|
---|
2178 | if (auto keyword = fontStyleKeyword(italic, fontStyleAxis))
|
---|
2179 | return CSSFontStyleValue::create(CSSValuePool::singleton().createIdentifierValue(keyword.value()));
|
---|
2180 | return fontNonKeywordStyleFromStyleValue(italic.value());
|
---|
2181 | }
|
---|
2182 |
|
---|
2183 | static Ref<CSSFontStyleValue> fontStyleFromStyle(const RenderStyle& style)
|
---|
2184 | {
|
---|
2185 | return ComputedStyleExtractor::fontStyleFromStyleValue(style.fontDescription().italic(), style.fontDescription().fontStyleAxis());
|
---|
2186 | }
|
---|
2187 |
|
---|
2188 | static Ref<CSSValue> fontVariantFromStyle(const RenderStyle& style)
|
---|
2189 | {
|
---|
2190 | if (style.fontDescription().variantSettings().isAllNormal())
|
---|
2191 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNormal);
|
---|
2192 |
|
---|
2193 | auto list = CSSValueList::createSpaceSeparated();
|
---|
2194 |
|
---|
2195 | switch (style.fontDescription().variantCommonLigatures()) {
|
---|
2196 | case FontVariantLigatures::Normal:
|
---|
2197 | break;
|
---|
2198 | case FontVariantLigatures::Yes:
|
---|
2199 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueCommonLigatures));
|
---|
2200 | break;
|
---|
2201 | case FontVariantLigatures::No:
|
---|
2202 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueNoCommonLigatures));
|
---|
2203 | break;
|
---|
2204 | }
|
---|
2205 |
|
---|
2206 | switch (style.fontDescription().variantDiscretionaryLigatures()) {
|
---|
2207 | case FontVariantLigatures::Normal:
|
---|
2208 | break;
|
---|
2209 | case FontVariantLigatures::Yes:
|
---|
2210 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueDiscretionaryLigatures));
|
---|
2211 | break;
|
---|
2212 | case FontVariantLigatures::No:
|
---|
2213 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueNoDiscretionaryLigatures));
|
---|
2214 | break;
|
---|
2215 | }
|
---|
2216 |
|
---|
2217 | switch (style.fontDescription().variantHistoricalLigatures()) {
|
---|
2218 | case FontVariantLigatures::Normal:
|
---|
2219 | break;
|
---|
2220 | case FontVariantLigatures::Yes:
|
---|
2221 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueHistoricalLigatures));
|
---|
2222 | break;
|
---|
2223 | case FontVariantLigatures::No:
|
---|
2224 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueNoHistoricalLigatures));
|
---|
2225 | break;
|
---|
2226 | }
|
---|
2227 |
|
---|
2228 | switch (style.fontDescription().variantContextualAlternates()) {
|
---|
2229 | case FontVariantLigatures::Normal:
|
---|
2230 | break;
|
---|
2231 | case FontVariantLigatures::Yes:
|
---|
2232 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueContextual));
|
---|
2233 | break;
|
---|
2234 | case FontVariantLigatures::No:
|
---|
2235 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueNoContextual));
|
---|
2236 | break;
|
---|
2237 | }
|
---|
2238 |
|
---|
2239 | switch (style.fontDescription().variantPosition()) {
|
---|
2240 | case FontVariantPosition::Normal:
|
---|
2241 | break;
|
---|
2242 | case FontVariantPosition::Subscript:
|
---|
2243 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSub));
|
---|
2244 | break;
|
---|
2245 | case FontVariantPosition::Superscript:
|
---|
2246 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSuper));
|
---|
2247 | break;
|
---|
2248 | }
|
---|
2249 |
|
---|
2250 | switch (style.fontDescription().variantCaps()) {
|
---|
2251 | case FontVariantCaps::Normal:
|
---|
2252 | break;
|
---|
2253 | case FontVariantCaps::Small:
|
---|
2254 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSmallCaps));
|
---|
2255 | break;
|
---|
2256 | case FontVariantCaps::AllSmall:
|
---|
2257 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueAllSmallCaps));
|
---|
2258 | break;
|
---|
2259 | case FontVariantCaps::Petite:
|
---|
2260 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValuePetiteCaps));
|
---|
2261 | break;
|
---|
2262 | case FontVariantCaps::AllPetite:
|
---|
2263 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueAllPetiteCaps));
|
---|
2264 | break;
|
---|
2265 | case FontVariantCaps::Unicase:
|
---|
2266 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueUnicase));
|
---|
2267 | break;
|
---|
2268 | case FontVariantCaps::Titling:
|
---|
2269 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueTitlingCaps));
|
---|
2270 | break;
|
---|
2271 | }
|
---|
2272 |
|
---|
2273 | switch (style.fontDescription().variantNumericFigure()) {
|
---|
2274 | case FontVariantNumericFigure::Normal:
|
---|
2275 | break;
|
---|
2276 | case FontVariantNumericFigure::LiningNumbers:
|
---|
2277 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueLiningNums));
|
---|
2278 | break;
|
---|
2279 | case FontVariantNumericFigure::OldStyleNumbers:
|
---|
2280 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueOldstyleNums));
|
---|
2281 | break;
|
---|
2282 | }
|
---|
2283 |
|
---|
2284 | switch (style.fontDescription().variantNumericSpacing()) {
|
---|
2285 | case FontVariantNumericSpacing::Normal:
|
---|
2286 | break;
|
---|
2287 | case FontVariantNumericSpacing::ProportionalNumbers:
|
---|
2288 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueProportionalNums));
|
---|
2289 | break;
|
---|
2290 | case FontVariantNumericSpacing::TabularNumbers:
|
---|
2291 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueTabularNums));
|
---|
2292 | break;
|
---|
2293 | }
|
---|
2294 |
|
---|
2295 | switch (style.fontDescription().variantNumericFraction()) {
|
---|
2296 | case FontVariantNumericFraction::Normal:
|
---|
2297 | break;
|
---|
2298 | case FontVariantNumericFraction::DiagonalFractions:
|
---|
2299 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueDiagonalFractions));
|
---|
2300 | break;
|
---|
2301 | case FontVariantNumericFraction::StackedFractions:
|
---|
2302 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueStackedFractions));
|
---|
2303 | break;
|
---|
2304 | }
|
---|
2305 |
|
---|
2306 | switch (style.fontDescription().variantNumericOrdinal()) {
|
---|
2307 | case FontVariantNumericOrdinal::Normal:
|
---|
2308 | break;
|
---|
2309 | case FontVariantNumericOrdinal::Yes:
|
---|
2310 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueOrdinal));
|
---|
2311 | break;
|
---|
2312 | }
|
---|
2313 |
|
---|
2314 | switch (style.fontDescription().variantNumericSlashedZero()) {
|
---|
2315 | case FontVariantNumericSlashedZero::Normal:
|
---|
2316 | break;
|
---|
2317 | case FontVariantNumericSlashedZero::Yes:
|
---|
2318 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSlashedZero));
|
---|
2319 | break;
|
---|
2320 | }
|
---|
2321 |
|
---|
2322 | switch (style.fontDescription().variantAlternates()) {
|
---|
2323 | case FontVariantAlternates::Normal:
|
---|
2324 | break;
|
---|
2325 | case FontVariantAlternates::HistoricalForms:
|
---|
2326 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueHistoricalForms));
|
---|
2327 | break;
|
---|
2328 | }
|
---|
2329 |
|
---|
2330 | switch (style.fontDescription().variantEastAsianVariant()) {
|
---|
2331 | case FontVariantEastAsianVariant::Normal:
|
---|
2332 | break;
|
---|
2333 | case FontVariantEastAsianVariant::Jis78:
|
---|
2334 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueJis78));
|
---|
2335 | break;
|
---|
2336 | case FontVariantEastAsianVariant::Jis83:
|
---|
2337 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueJis83));
|
---|
2338 | break;
|
---|
2339 | case FontVariantEastAsianVariant::Jis90:
|
---|
2340 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueJis90));
|
---|
2341 | break;
|
---|
2342 | case FontVariantEastAsianVariant::Jis04:
|
---|
2343 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueJis04));
|
---|
2344 | break;
|
---|
2345 | case FontVariantEastAsianVariant::Simplified:
|
---|
2346 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSimplified));
|
---|
2347 | break;
|
---|
2348 | case FontVariantEastAsianVariant::Traditional:
|
---|
2349 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueTraditional));
|
---|
2350 | break;
|
---|
2351 | }
|
---|
2352 |
|
---|
2353 | switch (style.fontDescription().variantEastAsianWidth()) {
|
---|
2354 | case FontVariantEastAsianWidth::Normal:
|
---|
2355 | break;
|
---|
2356 | case FontVariantEastAsianWidth::Full:
|
---|
2357 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueFullWidth));
|
---|
2358 | break;
|
---|
2359 | case FontVariantEastAsianWidth::Proportional:
|
---|
2360 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueProportionalWidth));
|
---|
2361 | break;
|
---|
2362 | }
|
---|
2363 |
|
---|
2364 | switch (style.fontDescription().variantEastAsianRuby()) {
|
---|
2365 | case FontVariantEastAsianRuby::Normal:
|
---|
2366 | break;
|
---|
2367 | case FontVariantEastAsianRuby::Yes:
|
---|
2368 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueRuby));
|
---|
2369 | break;
|
---|
2370 | }
|
---|
2371 |
|
---|
2372 | return list;
|
---|
2373 | }
|
---|
2374 |
|
---|
2375 | static Ref<CSSValue> fontSynthesisFromStyle(const RenderStyle& style)
|
---|
2376 | {
|
---|
2377 | if (style.fontDescription().fontSynthesis() == FontSynthesisNone)
|
---|
2378 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
2379 |
|
---|
2380 | auto list = CSSValueList::createSpaceSeparated();
|
---|
2381 | if (style.fontDescription().fontSynthesis() & FontSynthesisWeight)
|
---|
2382 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueWeight));
|
---|
2383 | if (style.fontDescription().fontSynthesis() & FontSynthesisStyle)
|
---|
2384 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueStyle));
|
---|
2385 | if (style.fontDescription().fontSynthesis() & FontSynthesisSmallCaps)
|
---|
2386 | list->append(CSSValuePool::singleton().createIdentifierValue(CSSValueSmallCaps));
|
---|
2387 | return list;
|
---|
2388 | }
|
---|
2389 |
|
---|
2390 | typedef const Length& (RenderStyle::*RenderStyleLengthGetter)() const;
|
---|
2391 | typedef LayoutUnit (RenderBoxModelObject::*RenderBoxComputedCSSValueGetter)() const;
|
---|
2392 |
|
---|
2393 | template<RenderStyleLengthGetter lengthGetter, RenderBoxComputedCSSValueGetter computedCSSValueGetter>
|
---|
2394 | static RefPtr<CSSValue> zoomAdjustedPaddingOrMarginPixelValue(const RenderStyle& style, RenderObject* renderer)
|
---|
2395 | {
|
---|
2396 | Length unzoomzedLength = (style.*lengthGetter)();
|
---|
2397 | if (!is<RenderBox>(renderer) || unzoomzedLength.isFixed())
|
---|
2398 | return zoomAdjustedPixelValueForLength(unzoomzedLength, style);
|
---|
2399 | return zoomAdjustedPixelValue((downcast<RenderBox>(*renderer).*computedCSSValueGetter)(), style);
|
---|
2400 | }
|
---|
2401 |
|
---|
2402 | template<RenderStyleLengthGetter lengthGetter>
|
---|
2403 | static bool paddingOrMarginIsRendererDependent(const RenderStyle* style, RenderObject* renderer)
|
---|
2404 | {
|
---|
2405 | return renderer && style && renderer->isBox() && !(style->*lengthGetter)().isFixed();
|
---|
2406 | }
|
---|
2407 |
|
---|
2408 | static bool positionOffsetValueIsRendererDependent(const RenderStyle* style, RenderObject* renderer)
|
---|
2409 | {
|
---|
2410 | return renderer && style && renderer->isBox();
|
---|
2411 | }
|
---|
2412 |
|
---|
2413 | static CSSValueID convertToPageBreak(BreakBetween value)
|
---|
2414 | {
|
---|
2415 | if (value == BreakBetween::Page || value == BreakBetween::LeftPage || value == BreakBetween::RightPage
|
---|
2416 | || value == BreakBetween::RectoPage || value == BreakBetween::VersoPage)
|
---|
2417 | return CSSValueAlways; // CSS 2.1 allows us to map these to always.
|
---|
2418 | if (value == BreakBetween::Avoid || value == BreakBetween::AvoidPage)
|
---|
2419 | return CSSValueAvoid;
|
---|
2420 | return CSSValueAuto;
|
---|
2421 | }
|
---|
2422 |
|
---|
2423 | static CSSValueID convertToColumnBreak(BreakBetween value)
|
---|
2424 | {
|
---|
2425 | if (value == BreakBetween::Column)
|
---|
2426 | return CSSValueAlways;
|
---|
2427 | if (value == BreakBetween::Avoid || value == BreakBetween::AvoidColumn)
|
---|
2428 | return CSSValueAvoid;
|
---|
2429 | return CSSValueAuto;
|
---|
2430 | }
|
---|
2431 |
|
---|
2432 | static CSSValueID convertToPageBreak(BreakInside value)
|
---|
2433 | {
|
---|
2434 | if (value == BreakInside::Avoid || value == BreakInside::AvoidPage)
|
---|
2435 | return CSSValueAvoid;
|
---|
2436 | return CSSValueAuto;
|
---|
2437 | }
|
---|
2438 |
|
---|
2439 | static CSSValueID convertToColumnBreak(BreakInside value)
|
---|
2440 | {
|
---|
2441 | if (value == BreakInside::Avoid || value == BreakInside::AvoidColumn)
|
---|
2442 | return CSSValueAvoid;
|
---|
2443 | return CSSValueAuto;
|
---|
2444 | }
|
---|
2445 |
|
---|
2446 | static inline bool isNonReplacedInline(RenderObject& renderer)
|
---|
2447 | {
|
---|
2448 | return renderer.isInline() && !renderer.isReplacedOrInlineBlock();
|
---|
2449 | }
|
---|
2450 |
|
---|
2451 | static bool isLayoutDependent(CSSPropertyID propertyID, const RenderStyle* style, RenderObject* renderer)
|
---|
2452 | {
|
---|
2453 | switch (propertyID) {
|
---|
2454 | case CSSPropertyTop:
|
---|
2455 | case CSSPropertyBottom:
|
---|
2456 | case CSSPropertyLeft:
|
---|
2457 | case CSSPropertyRight:
|
---|
2458 | case CSSPropertyInsetBlockStart:
|
---|
2459 | case CSSPropertyInsetBlockEnd:
|
---|
2460 | case CSSPropertyInsetInlineStart:
|
---|
2461 | case CSSPropertyInsetInlineEnd:
|
---|
2462 | return positionOffsetValueIsRendererDependent(style, renderer);
|
---|
2463 | case CSSPropertyWidth:
|
---|
2464 | case CSSPropertyHeight:
|
---|
2465 | case CSSPropertyInlineSize:
|
---|
2466 | case CSSPropertyBlockSize:
|
---|
2467 | return renderer && !renderer->isRenderOrLegacyRenderSVGModelObject() && !isNonReplacedInline(*renderer);
|
---|
2468 | case CSSPropertyPerspectiveOrigin:
|
---|
2469 | case CSSPropertyTransformOrigin:
|
---|
2470 | case CSSPropertyTransform:
|
---|
2471 | case CSSPropertyFilter: // Why are filters layout-dependent?
|
---|
2472 | #if ENABLE(FILTERS_LEVEL_2)
|
---|
2473 | case CSSPropertyWebkitBackdropFilter: // Ditto for backdrop-filter.
|
---|
2474 | #endif
|
---|
2475 | return true;
|
---|
2476 | case CSSPropertyMargin: {
|
---|
2477 | if (!renderer || !renderer->isBox())
|
---|
2478 | return false;
|
---|
2479 | return !(style && style->marginTop().isFixed() && style->marginRight().isFixed()
|
---|
2480 | && style->marginBottom().isFixed() && style->marginLeft().isFixed());
|
---|
2481 | }
|
---|
2482 | case CSSPropertyMarginTop:
|
---|
2483 | return paddingOrMarginIsRendererDependent<&RenderStyle::marginTop>(style, renderer);
|
---|
2484 | case CSSPropertyMarginRight:
|
---|
2485 | return paddingOrMarginIsRendererDependent<&RenderStyle::marginRight>(style, renderer);
|
---|
2486 | case CSSPropertyMarginBottom:
|
---|
2487 | return paddingOrMarginIsRendererDependent<&RenderStyle::marginBottom>(style, renderer);
|
---|
2488 | case CSSPropertyMarginLeft:
|
---|
2489 | return paddingOrMarginIsRendererDependent<&RenderStyle::marginLeft>(style, renderer);
|
---|
2490 | case CSSPropertyPadding: {
|
---|
2491 | if (!renderer || !renderer->isBox())
|
---|
2492 | return false;
|
---|
2493 | return !(style && style->paddingTop().isFixed() && style->paddingRight().isFixed()
|
---|
2494 | && style->paddingBottom().isFixed() && style->paddingLeft().isFixed());
|
---|
2495 | }
|
---|
2496 | case CSSPropertyPaddingTop:
|
---|
2497 | return paddingOrMarginIsRendererDependent<&RenderStyle::paddingTop>(style, renderer);
|
---|
2498 | case CSSPropertyPaddingRight:
|
---|
2499 | return paddingOrMarginIsRendererDependent<&RenderStyle::paddingRight>(style, renderer);
|
---|
2500 | case CSSPropertyPaddingBottom:
|
---|
2501 | return paddingOrMarginIsRendererDependent<&RenderStyle::paddingBottom>(style, renderer);
|
---|
2502 | case CSSPropertyPaddingLeft:
|
---|
2503 | return paddingOrMarginIsRendererDependent<&RenderStyle::paddingLeft>(style, renderer);
|
---|
2504 | case CSSPropertyGridTemplateColumns:
|
---|
2505 | case CSSPropertyGridTemplateRows:
|
---|
2506 | case CSSPropertyGridTemplate:
|
---|
2507 | case CSSPropertyGrid:
|
---|
2508 | return renderer && renderer->isRenderGrid();
|
---|
2509 | default:
|
---|
2510 | return false;
|
---|
2511 | }
|
---|
2512 | }
|
---|
2513 |
|
---|
2514 | RenderElement* ComputedStyleExtractor::styledRenderer() const
|
---|
2515 | {
|
---|
2516 | if (!m_element)
|
---|
2517 | return nullptr;
|
---|
2518 | if (m_pseudoElementSpecifier != PseudoId::None)
|
---|
2519 | return Styleable(*m_element, m_pseudoElementSpecifier).renderer();
|
---|
2520 | if (m_element->hasDisplayContents())
|
---|
2521 | return nullptr;
|
---|
2522 | return m_element->renderer();
|
---|
2523 | }
|
---|
2524 |
|
---|
2525 | static bool isImplicitlyInheritedGridOrFlexProperty(CSSPropertyID propertyID)
|
---|
2526 | {
|
---|
2527 | // It would be nice if grid and flex worked within normal CSS mechanisms and not invented their own inheritance system.
|
---|
2528 | switch (propertyID) {
|
---|
2529 | case CSSPropertyAlignSelf:
|
---|
2530 | case CSSPropertyJustifySelf:
|
---|
2531 | case CSSPropertyJustifyItems:
|
---|
2532 | // FIXME: In StyleResolver::adjustRenderStyle z-index is adjusted based on the parent display property for grid/flex.
|
---|
2533 | case CSSPropertyZIndex:
|
---|
2534 | return true;
|
---|
2535 | default:
|
---|
2536 | return false;
|
---|
2537 | }
|
---|
2538 | }
|
---|
2539 |
|
---|
2540 | static bool nonInheritedColorPropertyHasValueCurrentColor(CSSPropertyID propertyID, const RenderStyle* style)
|
---|
2541 | {
|
---|
2542 | if (CSSProperty::isInheritedProperty(propertyID) || !CSSProperty::isColorProperty(propertyID))
|
---|
2543 | return false;
|
---|
2544 |
|
---|
2545 | if (!style)
|
---|
2546 | return true;
|
---|
2547 |
|
---|
2548 | return RenderStyle::isCurrentColor(style->unresolvedColorForProperty(propertyID));
|
---|
2549 | }
|
---|
2550 |
|
---|
2551 | // In CSS 2.1 the returned object should actually contain the "used values"
|
---|
2552 | // rather then the "computed values" (despite the name saying otherwise).
|
---|
2553 | //
|
---|
2554 | // See;
|
---|
2555 | // http://www.w3.org/TR/CSS21/cascade.html#used-value
|
---|
2556 | // http://www.w3.org/TR/DOM-Level-2-Style/css.html#CSS-CSSStyleDeclaration
|
---|
2557 | // https://developer.mozilla.org/en-US/docs/Web/API/Window/getComputedStyle#Notes
|
---|
2558 | RefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropertyID propertyID, EUpdateLayout updateLayout) const
|
---|
2559 | {
|
---|
2560 | return ComputedStyleExtractor(m_element.ptr(), m_allowVisitedStyle, m_pseudoElementSpecifier).propertyValue(propertyID, updateLayout);
|
---|
2561 | }
|
---|
2562 |
|
---|
2563 | Ref<MutableStyleProperties> CSSComputedStyleDeclaration::copyProperties() const
|
---|
2564 | {
|
---|
2565 | return ComputedStyleExtractor(m_element.ptr(), m_allowVisitedStyle, m_pseudoElementSpecifier).copyProperties();
|
---|
2566 | }
|
---|
2567 |
|
---|
2568 | const Settings* CSSComputedStyleDeclaration::settings() const
|
---|
2569 | {
|
---|
2570 | return &m_element->document().settings();
|
---|
2571 | }
|
---|
2572 |
|
---|
2573 | static inline bool hasValidStyleForProperty(Element& element, CSSPropertyID propertyID)
|
---|
2574 | {
|
---|
2575 | if (element.styleValidity() != Style::Validity::Valid)
|
---|
2576 | return false;
|
---|
2577 | if (element.document().hasPendingFullStyleRebuild())
|
---|
2578 | return false;
|
---|
2579 | if (!element.document().childNeedsStyleRecalc())
|
---|
2580 | return true;
|
---|
2581 |
|
---|
2582 | auto isQueryContainer = [&](Element& element) {
|
---|
2583 | auto* style = element.renderStyle();
|
---|
2584 | return style && style->containerType() != ContainerType::None;
|
---|
2585 | };
|
---|
2586 |
|
---|
2587 | bool isInherited = CSSProperty::isInheritedProperty(propertyID) || isImplicitlyInheritedGridOrFlexProperty(propertyID);
|
---|
2588 | bool maybeExplicitlyInherited = !isInherited;
|
---|
2589 |
|
---|
2590 | if (isQueryContainer(element))
|
---|
2591 | return false;
|
---|
2592 |
|
---|
2593 | const auto* currentElement = &element;
|
---|
2594 | for (auto& ancestor : composedTreeAncestors(element)) {
|
---|
2595 | if (ancestor.styleValidity() >= Style::Validity::SubtreeInvalid)
|
---|
2596 | return false;
|
---|
2597 |
|
---|
2598 | if (isQueryContainer(ancestor))
|
---|
2599 | return false;
|
---|
2600 |
|
---|
2601 | if (maybeExplicitlyInherited) {
|
---|
2602 | auto* style = currentElement->renderStyle();
|
---|
2603 | // While most color properties are not inherited, the value 'currentcolor' resolves to the value of the inherited 'color' property.
|
---|
2604 | if (nonInheritedColorPropertyHasValueCurrentColor(propertyID, style))
|
---|
2605 | isInherited = true;
|
---|
2606 |
|
---|
2607 | maybeExplicitlyInherited = !style || style->hasExplicitlyInheritedProperties();
|
---|
2608 | }
|
---|
2609 |
|
---|
2610 | if ((isInherited || maybeExplicitlyInherited) && ancestor.styleValidity() == Style::Validity::ElementInvalid)
|
---|
2611 | return false;
|
---|
2612 |
|
---|
2613 | if (ancestor.directChildNeedsStyleRecalc() && currentElement->styleIsAffectedByPreviousSibling())
|
---|
2614 | return false;
|
---|
2615 |
|
---|
2616 | currentElement = &ancestor;
|
---|
2617 | }
|
---|
2618 |
|
---|
2619 | return true;
|
---|
2620 | }
|
---|
2621 |
|
---|
2622 | static bool updateStyleIfNeededForProperty(Element& element, CSSPropertyID propertyID)
|
---|
2623 | {
|
---|
2624 | auto& document = element.document();
|
---|
2625 |
|
---|
2626 | document.styleScope().flushPendingUpdate();
|
---|
2627 |
|
---|
2628 | auto hasValidStyle = [&] {
|
---|
2629 | auto shorthand = shorthandForProperty(propertyID);
|
---|
2630 | if (shorthand.length()) {
|
---|
2631 | for (auto longhand : shorthand) {
|
---|
2632 | if (!hasValidStyleForProperty(element, longhand))
|
---|
2633 | return false;
|
---|
2634 | }
|
---|
2635 | return true;
|
---|
2636 | }
|
---|
2637 | return hasValidStyleForProperty(element, propertyID);
|
---|
2638 | }();
|
---|
2639 |
|
---|
2640 | if (hasValidStyle)
|
---|
2641 | return false;
|
---|
2642 |
|
---|
2643 | document.updateStyleIfNeeded();
|
---|
2644 | return true;
|
---|
2645 | }
|
---|
2646 |
|
---|
2647 | static inline const RenderStyle* computeRenderStyleForProperty(Element& element, PseudoId pseudoElementSpecifier, CSSPropertyID propertyID, std::unique_ptr<RenderStyle>& ownedStyle, WeakPtr<RenderElement> renderer)
|
---|
2648 | {
|
---|
2649 | if (!renderer)
|
---|
2650 | renderer = element.renderer();
|
---|
2651 |
|
---|
2652 | if (renderer && renderer->isComposited() && CSSPropertyAnimation::animationOfPropertyIsAccelerated(propertyID)) {
|
---|
2653 | ownedStyle = renderer->animatedStyle();
|
---|
2654 | if (pseudoElementSpecifier != PseudoId::None) {
|
---|
2655 | // FIXME: This cached pseudo style will only exist if the animation has been run at least once.
|
---|
2656 | return ownedStyle->getCachedPseudoStyle(pseudoElementSpecifier);
|
---|
2657 | }
|
---|
2658 | return ownedStyle.get();
|
---|
2659 | }
|
---|
2660 |
|
---|
2661 | return element.computedStyle(pseudoElementSpecifier);
|
---|
2662 | }
|
---|
2663 |
|
---|
2664 | static Ref<CSSValue> shapePropertyValue(const RenderStyle& style, const ShapeValue* shapeValue)
|
---|
2665 | {
|
---|
2666 | if (!shapeValue)
|
---|
2667 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
2668 |
|
---|
2669 | if (shapeValue->type() == ShapeValue::Type::Box)
|
---|
2670 | return CSSValuePool::singleton().createValue(shapeValue->cssBox());
|
---|
2671 |
|
---|
2672 | if (shapeValue->type() == ShapeValue::Type::Image) {
|
---|
2673 | if (shapeValue->image())
|
---|
2674 | return shapeValue->image()->cssValue();
|
---|
2675 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
2676 | }
|
---|
2677 |
|
---|
2678 | ASSERT(shapeValue->type() == ShapeValue::Type::Shape);
|
---|
2679 |
|
---|
2680 | auto list = CSSValueList::createSpaceSeparated();
|
---|
2681 | list->append(valueForBasicShape(style, *shapeValue->shape()));
|
---|
2682 | if (shapeValue->cssBox() != CSSBoxType::BoxMissing)
|
---|
2683 | list->append(CSSValuePool::singleton().createValue(shapeValue->cssBox()));
|
---|
2684 | return list;
|
---|
2685 | }
|
---|
2686 |
|
---|
2687 | static Ref<CSSValueList> valueForItemPositionWithOverflowAlignment(const StyleSelfAlignmentData& data)
|
---|
2688 | {
|
---|
2689 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
2690 | auto result = CSSValueList::createSpaceSeparated();
|
---|
2691 | if (data.positionType() == ItemPositionType::Legacy)
|
---|
2692 | result->append(cssValuePool.createIdentifierValue(CSSValueLegacy));
|
---|
2693 | if (data.position() == ItemPosition::Baseline)
|
---|
2694 | result->append(cssValuePool.createIdentifierValue(CSSValueBaseline));
|
---|
2695 | else if (data.position() == ItemPosition::LastBaseline) {
|
---|
2696 | result->append(cssValuePool.createIdentifierValue(CSSValueLast));
|
---|
2697 | result->append(cssValuePool.createIdentifierValue(CSSValueBaseline));
|
---|
2698 | } else {
|
---|
2699 | if (data.position() >= ItemPosition::Center && data.overflow() != OverflowAlignment::Default)
|
---|
2700 | result->append(cssValuePool.createValue(data.overflow()));
|
---|
2701 | if (data.position() == ItemPosition::Legacy)
|
---|
2702 | result->append(cssValuePool.createIdentifierValue(CSSValueNormal));
|
---|
2703 | else
|
---|
2704 | result->append(cssValuePool.createValue(data.position()));
|
---|
2705 | }
|
---|
2706 | ASSERT(result->length() <= 2);
|
---|
2707 | return result;
|
---|
2708 | }
|
---|
2709 |
|
---|
2710 | static Ref<CSSValueList> valueForContentPositionAndDistributionWithOverflowAlignment(const StyleContentAlignmentData& data)
|
---|
2711 | {
|
---|
2712 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
2713 | auto result = CSSValueList::createSpaceSeparated();
|
---|
2714 | // Handle content-distribution values
|
---|
2715 | if (data.distribution() != ContentDistribution::Default)
|
---|
2716 | result->append(cssValuePool.createValue(data.distribution()));
|
---|
2717 |
|
---|
2718 | // Handle content-position values (either as fallback or actual value)
|
---|
2719 | switch (data.position()) {
|
---|
2720 | case ContentPosition::Normal:
|
---|
2721 | // Handle 'normal' value, not valid as content-distribution fallback.
|
---|
2722 | if (data.distribution() == ContentDistribution::Default)
|
---|
2723 | result->append(cssValuePool.createIdentifierValue(CSSValueNormal));
|
---|
2724 | break;
|
---|
2725 | case ContentPosition::LastBaseline:
|
---|
2726 | result->append(cssValuePool.createIdentifierValue(CSSValueLast));
|
---|
2727 | result->append(cssValuePool.createIdentifierValue(CSSValueBaseline));
|
---|
2728 | break;
|
---|
2729 | default:
|
---|
2730 | // Handle overflow-alignment (only allowed for content-position values)
|
---|
2731 | if ((data.position() >= ContentPosition::Center || data.distribution() != ContentDistribution::Default) && data.overflow() != OverflowAlignment::Default)
|
---|
2732 | result->append(cssValuePool.createValue(data.overflow()));
|
---|
2733 | result->append(cssValuePool.createValue(data.position()));
|
---|
2734 | }
|
---|
2735 |
|
---|
2736 | ASSERT(result->length() > 0);
|
---|
2737 | ASSERT(result->length() <= 3);
|
---|
2738 | return result;
|
---|
2739 | }
|
---|
2740 |
|
---|
2741 | static Ref<CSSValueList> valueForOffsetRotate(const OffsetRotation& rotation)
|
---|
2742 | {
|
---|
2743 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
2744 |
|
---|
2745 | auto result = CSSValueList::createSpaceSeparated();
|
---|
2746 |
|
---|
2747 | if (rotation.hasAuto())
|
---|
2748 | result->append(cssValuePool.createIdentifierValue(CSSValueAuto));
|
---|
2749 | result->append(cssValuePool.createValue(rotation.angle(), CSSUnitType::CSS_DEG));
|
---|
2750 |
|
---|
2751 | return result;
|
---|
2752 | }
|
---|
2753 |
|
---|
2754 | static Ref<CSSValue> valueForOffsetShorthand(const RenderStyle& style)
|
---|
2755 | {
|
---|
2756 | // offset is serialized as follow:
|
---|
2757 | // [offset-position] [offset-path] [offset-distance] [offset-rotate] / [offset-anchor]
|
---|
2758 | // The first four elements are serialized in a space separated CSSValueList.
|
---|
2759 | // This is then combined with offset-anchor in a slash separated CSSValueList.
|
---|
2760 |
|
---|
2761 | auto outerList = CSSValueList::createSlashSeparated();
|
---|
2762 | auto innerList = CSSValueList::createSpaceSeparated();
|
---|
2763 | innerList->append(valueForPositionOrAuto(style, style.offsetPosition()));
|
---|
2764 | innerList->append(valueForPathOperation(style, style.offsetPath(), SVGPathConversion::ForceAbsolute));
|
---|
2765 | innerList->append(CSSValuePool::singleton().createValue(style.offsetDistance(), style));
|
---|
2766 | innerList->append(valueForOffsetRotate(style.offsetRotate()));
|
---|
2767 | outerList->append(WTFMove(innerList));
|
---|
2768 | outerList->append(valueForPositionOrAuto(style, style.offsetAnchor()));
|
---|
2769 | return outerList;
|
---|
2770 | }
|
---|
2771 |
|
---|
2772 | static Ref<CSSValue> paintOrder(PaintOrder paintOrder)
|
---|
2773 | {
|
---|
2774 | if (paintOrder == PaintOrder::Normal)
|
---|
2775 | return CSSPrimitiveValue::createIdentifier(CSSValueNormal);
|
---|
2776 |
|
---|
2777 | auto paintOrderList = CSSValueList::createSpaceSeparated();
|
---|
2778 | switch (paintOrder) {
|
---|
2779 | case PaintOrder::Normal:
|
---|
2780 | ASSERT_NOT_REACHED();
|
---|
2781 | break;
|
---|
2782 | case PaintOrder::Fill:
|
---|
2783 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueFill));
|
---|
2784 | break;
|
---|
2785 | case PaintOrder::FillMarkers:
|
---|
2786 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueFill));
|
---|
2787 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueMarkers));
|
---|
2788 | break;
|
---|
2789 | case PaintOrder::Stroke:
|
---|
2790 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueStroke));
|
---|
2791 | break;
|
---|
2792 | case PaintOrder::StrokeMarkers:
|
---|
2793 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueStroke));
|
---|
2794 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueMarkers));
|
---|
2795 | break;
|
---|
2796 | case PaintOrder::Markers:
|
---|
2797 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueMarkers));
|
---|
2798 | break;
|
---|
2799 | case PaintOrder::MarkersStroke:
|
---|
2800 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueMarkers));
|
---|
2801 | paintOrderList->append(CSSPrimitiveValue::createIdentifier(CSSValueStroke));
|
---|
2802 | break;
|
---|
2803 | }
|
---|
2804 | return paintOrderList;
|
---|
2805 | }
|
---|
2806 |
|
---|
2807 | inline static bool isFlexOrGridItem(RenderObject* renderer)
|
---|
2808 | {
|
---|
2809 | if (!renderer || !renderer->isBox())
|
---|
2810 | return false;
|
---|
2811 | auto& box = downcast<RenderBox>(*renderer);
|
---|
2812 | return box.isFlexItem() || box.isGridItem();
|
---|
2813 | }
|
---|
2814 |
|
---|
2815 | RefPtr<CSSValue> ComputedStyleExtractor::customPropertyValue(const AtomString& propertyName)
|
---|
2816 | {
|
---|
2817 | Element* styledElement = m_element.get();
|
---|
2818 | if (!styledElement)
|
---|
2819 | return nullptr;
|
---|
2820 |
|
---|
2821 | updateStyleIfNeededForProperty(*styledElement, CSSPropertyCustom);
|
---|
2822 |
|
---|
2823 | std::unique_ptr<RenderStyle> ownedStyle;
|
---|
2824 | auto* style = computeRenderStyleForProperty(*styledElement, m_pseudoElementSpecifier, CSSPropertyCustom, ownedStyle, nullptr);
|
---|
2825 | if (!style)
|
---|
2826 | return nullptr;
|
---|
2827 |
|
---|
2828 | auto* value = style->getCustomProperty(propertyName);
|
---|
2829 | if (!value) {
|
---|
2830 | auto registered = styledElement->document().getCSSRegisteredCustomPropertySet().get(propertyName);
|
---|
2831 | return registered ? registered->initialValueCopy() : nullptr;
|
---|
2832 | }
|
---|
2833 |
|
---|
2834 | return WTF::switchOn(value->value(), [&](const Length& value) -> Ref<CSSValue> {
|
---|
2835 | return zoomAdjustedPixelValueForLength(value, *style);
|
---|
2836 | }, [&](auto&) -> Ref<CSSValue> {
|
---|
2837 | return CSSCustomPropertyValue::create(*value);
|
---|
2838 | });
|
---|
2839 | }
|
---|
2840 |
|
---|
2841 | String ComputedStyleExtractor::customPropertyText(const AtomString& propertyName)
|
---|
2842 | {
|
---|
2843 | RefPtr<CSSValue> propertyValue = customPropertyValue(propertyName);
|
---|
2844 | return propertyValue ? propertyValue->cssText() : emptyString();
|
---|
2845 | }
|
---|
2846 |
|
---|
2847 | static Ref<CSSFontValue> fontShorthandValueForSelectionProperties(const FontDescription& fontDescription)
|
---|
2848 | {
|
---|
2849 | auto computedFont = CSSFontValue::create();
|
---|
2850 |
|
---|
2851 | auto variantCaps = fontDescription.variantCaps();
|
---|
2852 | if (variantCaps == FontVariantCaps::Small)
|
---|
2853 | computedFont->variant = CSSValuePool::singleton().createIdentifierValue(CSSValueSmallCaps);
|
---|
2854 | else if (variantCaps == FontVariantCaps::Normal)
|
---|
2855 | computedFont->variant = CSSValuePool::singleton().createIdentifierValue(CSSValueNormal);
|
---|
2856 | else
|
---|
2857 | return CSSFontValue::create();
|
---|
2858 |
|
---|
2859 | auto weight = fontDescription.weight();
|
---|
2860 | if (auto value = fontWeightKeyword(weight))
|
---|
2861 | computedFont->weight = CSSValuePool::singleton().createIdentifierValue(value.value());
|
---|
2862 | else if (isCSS21Weight(weight))
|
---|
2863 | computedFont->weight = CSSValuePool::singleton().createValue(static_cast<float>(weight), CSSUnitType::CSS_NUMBER);
|
---|
2864 | else
|
---|
2865 | return CSSFontValue::create();
|
---|
2866 |
|
---|
2867 | if (auto keyword = fontStretchKeyword(fontDescription.stretch()))
|
---|
2868 | computedFont->stretch = CSSValuePool::singleton().createIdentifierValue(keyword.value());
|
---|
2869 | else
|
---|
2870 | return CSSFontValue::create();
|
---|
2871 |
|
---|
2872 | if (auto italic = fontStyleKeyword(fontDescription.italic(), fontDescription.fontStyleAxis()))
|
---|
2873 | computedFont->style = CSSFontStyleValue::create(CSSValuePool::singleton().createIdentifierValue(italic.value()));
|
---|
2874 | else
|
---|
2875 | return CSSFontValue::create();
|
---|
2876 |
|
---|
2877 | return computedFont;
|
---|
2878 | }
|
---|
2879 |
|
---|
2880 | RefPtr<CSSValue> ComputedStyleExtractor::propertyValue(CSSPropertyID propertyID, EUpdateLayout updateLayout, PropertyValueType valueType)
|
---|
2881 | {
|
---|
2882 | auto* styledElement = m_element.get();
|
---|
2883 | if (!styledElement)
|
---|
2884 | return nullptr;
|
---|
2885 |
|
---|
2886 | std::unique_ptr<RenderStyle> ownedStyle;
|
---|
2887 | const RenderStyle* style = nullptr;
|
---|
2888 | bool forceFullLayout = false;
|
---|
2889 | if (updateLayout) {
|
---|
2890 | Document& document = m_element->document();
|
---|
2891 |
|
---|
2892 | updateStyleIfNeededForProperty(*styledElement, propertyID);
|
---|
2893 | if (propertyID == CSSPropertyDisplay && !styledRenderer() && is<SVGElement>(*styledElement) && !downcast<SVGElement>(*styledElement).isValid())
|
---|
2894 | return nullptr;
|
---|
2895 |
|
---|
2896 | style = computeRenderStyleForProperty(*styledElement, m_pseudoElementSpecifier, propertyID, ownedStyle, styledRenderer());
|
---|
2897 |
|
---|
2898 | forceFullLayout = [&] {
|
---|
2899 | // FIXME: Some of these cases could be narrowed down or optimized better.
|
---|
2900 | if (isLayoutDependent(propertyID, style, styledRenderer()))
|
---|
2901 | return true;
|
---|
2902 | // FIXME: Why?
|
---|
2903 | if (styledElement->isInShadowTree())
|
---|
2904 | return true;
|
---|
2905 | if (!document.ownerElement())
|
---|
2906 | return false;
|
---|
2907 | if (!document.styleScope().resolverIfExists())
|
---|
2908 | return false;
|
---|
2909 | auto& ruleSets = document.styleScope().resolverIfExists()->ruleSets();
|
---|
2910 | return ruleSets.hasViewportDependentMediaQueries() || ruleSets.hasContainerQueries();
|
---|
2911 | }();
|
---|
2912 |
|
---|
2913 | if (forceFullLayout)
|
---|
2914 | document.updateLayoutIgnorePendingStylesheets();
|
---|
2915 | }
|
---|
2916 |
|
---|
2917 | if (!updateLayout || forceFullLayout)
|
---|
2918 | style = computeRenderStyleForProperty(*styledElement, m_pseudoElementSpecifier, propertyID, ownedStyle, styledRenderer());
|
---|
2919 |
|
---|
2920 | if (!style)
|
---|
2921 | return nullptr;
|
---|
2922 |
|
---|
2923 | return valueForPropertyInStyle(*style, propertyID, valueType == PropertyValueType::Resolved ? styledRenderer() : nullptr);
|
---|
2924 | }
|
---|
2925 |
|
---|
2926 | RefPtr<CSSValue> ComputedStyleExtractor::valueForPropertyInStyle(const RenderStyle& style, CSSPropertyID propertyID, RenderElement* renderer)
|
---|
2927 | {
|
---|
2928 | auto& cssValuePool = CSSValuePool::singleton();
|
---|
2929 | propertyID = CSSProperty::resolveDirectionAwareProperty(propertyID, style.direction(), style.writingMode());
|
---|
2930 |
|
---|
2931 | switch (propertyID) {
|
---|
2932 | case CSSPropertyInvalid:
|
---|
2933 | #if ENABLE(TEXT_AUTOSIZING)
|
---|
2934 | case CSSPropertyInternalTextAutosizingStatus:
|
---|
2935 | #endif
|
---|
2936 | break;
|
---|
2937 | case CSSPropertyAccentColor: {
|
---|
2938 | if (!m_element->document().settings().accentColorEnabled())
|
---|
2939 | return nullptr;
|
---|
2940 | if (style.hasAutoAccentColor())
|
---|
2941 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
2942 | return currentColorOrValidColor(&style, style.accentColor());
|
---|
2943 | }
|
---|
2944 | case CSSPropertyBackgroundColor:
|
---|
2945 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyBackgroundColor)) : currentColorOrValidColor(&style, style.backgroundColor());
|
---|
2946 | case CSSPropertyBackgroundImage:
|
---|
2947 | case CSSPropertyMaskImage: {
|
---|
2948 | auto& layers = propertyID == CSSPropertyMaskImage ? style.maskLayers() : style.backgroundLayers();
|
---|
2949 | if (!layers.next()) {
|
---|
2950 | if (layers.image())
|
---|
2951 | return layers.image()->cssValue();
|
---|
2952 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
2953 | }
|
---|
2954 | auto list = CSSValueList::createCommaSeparated();
|
---|
2955 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next()) {
|
---|
2956 | if (currLayer->image())
|
---|
2957 | list->append(currLayer->image()->cssValue());
|
---|
2958 | else
|
---|
2959 | list->append(cssValuePool.createIdentifierValue(CSSValueNone));
|
---|
2960 | }
|
---|
2961 | return list;
|
---|
2962 | }
|
---|
2963 | case CSSPropertyBackgroundSize:
|
---|
2964 | case CSSPropertyWebkitBackgroundSize:
|
---|
2965 | case CSSPropertyMaskSize: {
|
---|
2966 | auto& layers = propertyID == CSSPropertyMaskSize ? style.maskLayers() : style.backgroundLayers();
|
---|
2967 | if (!layers.next())
|
---|
2968 | return fillSizeToCSSValue(layers.size(), style);
|
---|
2969 | auto list = CSSValueList::createCommaSeparated();
|
---|
2970 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
2971 | list->append(fillSizeToCSSValue(currLayer->size(), style));
|
---|
2972 | return list;
|
---|
2973 | }
|
---|
2974 | case CSSPropertyBackgroundRepeat:
|
---|
2975 | case CSSPropertyMaskRepeat: {
|
---|
2976 | auto& layers = propertyID == CSSPropertyMaskRepeat ? style.maskLayers() : style.backgroundLayers();
|
---|
2977 | if (!layers.next())
|
---|
2978 | return fillRepeatToCSSValue(layers.repeatX(), layers.repeatY());
|
---|
2979 | auto list = CSSValueList::createCommaSeparated();
|
---|
2980 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
2981 | list->append(fillRepeatToCSSValue(currLayer->repeatX(), currLayer->repeatY()));
|
---|
2982 | return list;
|
---|
2983 | }
|
---|
2984 | case CSSPropertyWebkitMaskSourceType: {
|
---|
2985 | auto& layers = style.maskLayers();
|
---|
2986 | if (!layers.next())
|
---|
2987 | return maskSourceTypeToCSSValue(layers.maskMode());
|
---|
2988 | auto list = CSSValueList::createCommaSeparated();
|
---|
2989 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
2990 | list->append(maskSourceTypeToCSSValue(currLayer->maskMode()));
|
---|
2991 | return list;
|
---|
2992 | }
|
---|
2993 | case CSSPropertyMaskMode: {
|
---|
2994 | auto& layers = style.maskLayers();
|
---|
2995 | if (!layers.next())
|
---|
2996 | return maskModeToCSSValue(layers.maskMode());
|
---|
2997 | auto list = CSSValueList::createCommaSeparated();
|
---|
2998 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
2999 | list->append(maskModeToCSSValue(currLayer->maskMode()));
|
---|
3000 | return list;
|
---|
3001 | }
|
---|
3002 | case CSSPropertyWebkitMaskComposite:
|
---|
3003 | case CSSPropertyMaskComposite: {
|
---|
3004 | auto& layers = style.maskLayers();
|
---|
3005 | if (!layers.next())
|
---|
3006 | return cssValuePool.createValue(layers.composite(), propertyID);
|
---|
3007 | auto list = CSSValueList::createCommaSeparated();
|
---|
3008 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
3009 | list->append(cssValuePool.createValue(currLayer->composite(), propertyID));
|
---|
3010 | return list;
|
---|
3011 | }
|
---|
3012 | case CSSPropertyBackgroundAttachment: {
|
---|
3013 | auto& layers = style.backgroundLayers();
|
---|
3014 | if (!layers.next())
|
---|
3015 | return cssValuePool.createValue(layers.attachment());
|
---|
3016 | auto list = CSSValueList::createCommaSeparated();
|
---|
3017 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
3018 | list->append(cssValuePool.createValue(currLayer->attachment()));
|
---|
3019 | return list;
|
---|
3020 | }
|
---|
3021 | case CSSPropertyBackgroundClip:
|
---|
3022 | case CSSPropertyBackgroundOrigin:
|
---|
3023 | case CSSPropertyWebkitBackgroundClip:
|
---|
3024 | case CSSPropertyWebkitBackgroundOrigin:
|
---|
3025 | case CSSPropertyMaskClip:
|
---|
3026 | case CSSPropertyWebkitMaskClip:
|
---|
3027 | case CSSPropertyMaskOrigin: {
|
---|
3028 | auto& layers = (propertyID == CSSPropertyMaskClip || propertyID == CSSPropertyWebkitMaskClip || propertyID == CSSPropertyMaskOrigin) ? style.maskLayers() : style.backgroundLayers();
|
---|
3029 | bool isClip = propertyID == CSSPropertyBackgroundClip || propertyID == CSSPropertyWebkitBackgroundClip || propertyID == CSSPropertyMaskClip || propertyID == CSSPropertyWebkitMaskClip;
|
---|
3030 | if (!layers.next())
|
---|
3031 | return cssValuePool.createValue(isClip ? layers.clip() : layers.origin());
|
---|
3032 | auto list = CSSValueList::createCommaSeparated();
|
---|
3033 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
3034 | list->append(cssValuePool.createValue(isClip ? currLayer->clip() : currLayer->origin()));
|
---|
3035 | return list;
|
---|
3036 | }
|
---|
3037 | case CSSPropertyBackgroundPosition:
|
---|
3038 | case CSSPropertyWebkitMaskPosition:
|
---|
3039 | case CSSPropertyMaskPosition: {
|
---|
3040 | auto& layers = propertyID == CSSPropertyBackgroundPosition ? style.backgroundLayers() : style.maskLayers();
|
---|
3041 | if (!layers.next())
|
---|
3042 | return createPositionListForLayer(propertyID, layers, style);
|
---|
3043 |
|
---|
3044 | auto list = CSSValueList::createCommaSeparated();
|
---|
3045 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
3046 | list->append(createPositionListForLayer(propertyID, *currLayer, style));
|
---|
3047 | return list;
|
---|
3048 | }
|
---|
3049 | case CSSPropertyBackgroundPositionX:
|
---|
3050 | case CSSPropertyWebkitMaskPositionX: {
|
---|
3051 | auto& layers = propertyID == CSSPropertyWebkitMaskPositionX ? style.maskLayers() : style.backgroundLayers();
|
---|
3052 | if (!layers.next())
|
---|
3053 | return createSingleAxisPositionValueForLayer(propertyID, layers, style);
|
---|
3054 |
|
---|
3055 | auto list = CSSValueList::createCommaSeparated();
|
---|
3056 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
3057 | list->append(createSingleAxisPositionValueForLayer(propertyID, *currLayer, style));
|
---|
3058 |
|
---|
3059 | return list;
|
---|
3060 | }
|
---|
3061 | case CSSPropertyBackgroundPositionY:
|
---|
3062 | case CSSPropertyWebkitMaskPositionY: {
|
---|
3063 | auto& layers = propertyID == CSSPropertyWebkitMaskPositionY ? style.maskLayers() : style.backgroundLayers();
|
---|
3064 | if (!layers.next())
|
---|
3065 | return createSingleAxisPositionValueForLayer(propertyID, layers, style);
|
---|
3066 |
|
---|
3067 | auto list = CSSValueList::createCommaSeparated();
|
---|
3068 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
3069 | list->append(createSingleAxisPositionValueForLayer(propertyID, *currLayer, style));
|
---|
3070 |
|
---|
3071 | return list;
|
---|
3072 | }
|
---|
3073 | case CSSPropertyBorderCollapse:
|
---|
3074 | if (style.borderCollapse() == BorderCollapse::Collapse)
|
---|
3075 | return cssValuePool.createIdentifierValue(CSSValueCollapse);
|
---|
3076 | return cssValuePool.createIdentifierValue(CSSValueSeparate);
|
---|
3077 | case CSSPropertyBorderSpacing: {
|
---|
3078 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3079 | list->append(zoomAdjustedPixelValue(style.horizontalBorderSpacing(), style));
|
---|
3080 | list->append(zoomAdjustedPixelValue(style.verticalBorderSpacing(), style));
|
---|
3081 | return list;
|
---|
3082 | }
|
---|
3083 | case CSSPropertyWebkitBorderHorizontalSpacing:
|
---|
3084 | return zoomAdjustedPixelValue(style.horizontalBorderSpacing(), style);
|
---|
3085 | case CSSPropertyWebkitBorderVerticalSpacing:
|
---|
3086 | return zoomAdjustedPixelValue(style.verticalBorderSpacing(), style);
|
---|
3087 | case CSSPropertyBorderImageSource:
|
---|
3088 | if (style.borderImageSource())
|
---|
3089 | return style.borderImageSource()->cssValue();
|
---|
3090 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3091 | case CSSPropertyBorderTopColor:
|
---|
3092 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyBorderTopColor)) : currentColorOrValidColor(&style, style.borderTopColor());
|
---|
3093 | case CSSPropertyBorderRightColor:
|
---|
3094 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyBorderRightColor)) : currentColorOrValidColor(&style, style.borderRightColor());
|
---|
3095 | case CSSPropertyBorderBottomColor:
|
---|
3096 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyBorderBottomColor)) : currentColorOrValidColor(&style, style.borderBottomColor());
|
---|
3097 | case CSSPropertyBorderLeftColor:
|
---|
3098 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyBorderLeftColor)) : currentColorOrValidColor(&style, style.borderLeftColor());
|
---|
3099 | case CSSPropertyBorderTopStyle:
|
---|
3100 | return cssValuePool.createValue(style.borderTopStyle());
|
---|
3101 | case CSSPropertyBorderRightStyle:
|
---|
3102 | return cssValuePool.createValue(style.borderRightStyle());
|
---|
3103 | case CSSPropertyBorderBottomStyle:
|
---|
3104 | return cssValuePool.createValue(style.borderBottomStyle());
|
---|
3105 | case CSSPropertyBorderLeftStyle:
|
---|
3106 | return cssValuePool.createValue(style.borderLeftStyle());
|
---|
3107 | case CSSPropertyBorderTopWidth:
|
---|
3108 | return zoomAdjustedPixelValue(style.borderTopWidth(), style);
|
---|
3109 | case CSSPropertyBorderRightWidth:
|
---|
3110 | return zoomAdjustedPixelValue(style.borderRightWidth(), style);
|
---|
3111 | case CSSPropertyBorderBottomWidth:
|
---|
3112 | return zoomAdjustedPixelValue(style.borderBottomWidth(), style);
|
---|
3113 | case CSSPropertyBorderLeftWidth:
|
---|
3114 | return zoomAdjustedPixelValue(style.borderLeftWidth(), style);
|
---|
3115 | case CSSPropertyBottom:
|
---|
3116 | return positionOffsetValue(style, CSSPropertyBottom, renderer);
|
---|
3117 | case CSSPropertyWebkitBoxAlign:
|
---|
3118 | return cssValuePool.createValue(style.boxAlign());
|
---|
3119 | #if ENABLE(CSS_BOX_DECORATION_BREAK)
|
---|
3120 | case CSSPropertyWebkitBoxDecorationBreak:
|
---|
3121 | if (style.boxDecorationBreak() == BoxDecorationBreak::Slice)
|
---|
3122 | return cssValuePool.createIdentifierValue(CSSValueSlice);
|
---|
3123 | return cssValuePool.createIdentifierValue(CSSValueClone);
|
---|
3124 | #endif
|
---|
3125 | case CSSPropertyWebkitBoxDirection:
|
---|
3126 | return cssValuePool.createValue(style.boxDirection());
|
---|
3127 | case CSSPropertyWebkitBoxFlex:
|
---|
3128 | return cssValuePool.createValue(style.boxFlex(), CSSUnitType::CSS_NUMBER);
|
---|
3129 | case CSSPropertyWebkitBoxFlexGroup:
|
---|
3130 | return cssValuePool.createValue(style.boxFlexGroup(), CSSUnitType::CSS_INTEGER);
|
---|
3131 | case CSSPropertyWebkitBoxLines:
|
---|
3132 | return cssValuePool.createValue(style.boxLines());
|
---|
3133 | case CSSPropertyWebkitBoxOrdinalGroup:
|
---|
3134 | return cssValuePool.createValue(style.boxOrdinalGroup(), CSSUnitType::CSS_INTEGER);
|
---|
3135 | case CSSPropertyWebkitBoxOrient:
|
---|
3136 | return cssValuePool.createValue(style.boxOrient());
|
---|
3137 | case CSSPropertyWebkitBoxPack:
|
---|
3138 | return cssValuePool.createValue(style.boxPack());
|
---|
3139 | case CSSPropertyWebkitBoxReflect:
|
---|
3140 | return valueForReflection(style.boxReflect(), style);
|
---|
3141 | case CSSPropertyBoxShadow:
|
---|
3142 | case CSSPropertyWebkitBoxShadow:
|
---|
3143 | return valueForShadow(style.boxShadow(), propertyID, style);
|
---|
3144 | case CSSPropertyCaptionSide:
|
---|
3145 | return cssValuePool.createValue(style.captionSide());
|
---|
3146 | case CSSPropertyCaretColor:
|
---|
3147 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyCaretColor)) : currentColorOrValidColor(&style, style.caretColor());
|
---|
3148 | case CSSPropertyClear:
|
---|
3149 | return cssValuePool.createValue(style.clear());
|
---|
3150 | case CSSPropertyColor:
|
---|
3151 | return cssValuePool.createColorValue(m_allowVisitedStyle ? style.visitedDependentColor(CSSPropertyColor) : style.color());
|
---|
3152 | case CSSPropertyPrintColorAdjust:
|
---|
3153 | return cssValuePool.createValue(style.printColorAdjust());
|
---|
3154 | case CSSPropertyWebkitColumnAxis:
|
---|
3155 | return cssValuePool.createValue(style.columnAxis());
|
---|
3156 | case CSSPropertyColumnCount:
|
---|
3157 | if (style.hasAutoColumnCount())
|
---|
3158 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3159 | return cssValuePool.createValue(style.columnCount(), CSSUnitType::CSS_NUMBER);
|
---|
3160 | case CSSPropertyColumnFill:
|
---|
3161 | return cssValuePool.createValue(style.columnFill());
|
---|
3162 | case CSSPropertyColumnGap:
|
---|
3163 | if (style.columnGap().isNormal())
|
---|
3164 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
3165 | return zoomAdjustedPixelValueForLength(style.columnGap().length(), style);
|
---|
3166 | case CSSPropertyRowGap:
|
---|
3167 | if (style.rowGap().isNormal())
|
---|
3168 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
3169 | return zoomAdjustedPixelValueForLength(style.rowGap().length(), style);
|
---|
3170 | case CSSPropertyWebkitColumnProgression:
|
---|
3171 | return cssValuePool.createValue(style.columnProgression());
|
---|
3172 | case CSSPropertyColumnRuleColor:
|
---|
3173 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyOutlineColor)) : currentColorOrValidColor(&style, style.columnRuleColor());
|
---|
3174 | case CSSPropertyColumnRuleStyle:
|
---|
3175 | return cssValuePool.createValue(style.columnRuleStyle());
|
---|
3176 | case CSSPropertyColumnRuleWidth:
|
---|
3177 | return zoomAdjustedPixelValue(style.columnRuleWidth(), style);
|
---|
3178 | case CSSPropertyColumnSpan:
|
---|
3179 | return cssValuePool.createIdentifierValue(style.columnSpan() == ColumnSpan::All ? CSSValueAll : CSSValueNone);
|
---|
3180 | case CSSPropertyWebkitColumnBreakAfter:
|
---|
3181 | return cssValuePool.createValue(convertToColumnBreak(style.breakAfter()));
|
---|
3182 | case CSSPropertyWebkitColumnBreakBefore:
|
---|
3183 | return cssValuePool.createValue(convertToColumnBreak(style.breakBefore()));
|
---|
3184 | case CSSPropertyWebkitColumnBreakInside:
|
---|
3185 | return cssValuePool.createValue(convertToColumnBreak(style.breakInside()));
|
---|
3186 | case CSSPropertyColumnWidth:
|
---|
3187 | if (style.hasAutoColumnWidth())
|
---|
3188 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3189 | return zoomAdjustedPixelValue(style.columnWidth(), style);
|
---|
3190 | case CSSPropertyTabSize:
|
---|
3191 | return cssValuePool.createValue(style.tabSize().widthInPixels(1.0), style.tabSize().isSpaces() ? CSSUnitType::CSS_NUMBER : CSSUnitType::CSS_PX);
|
---|
3192 | case CSSPropertyCursor: {
|
---|
3193 | RefPtr<CSSValueList> list;
|
---|
3194 | auto* cursors = style.cursors();
|
---|
3195 | if (cursors && cursors->size() > 0) {
|
---|
3196 | list = CSSValueList::createCommaSeparated();
|
---|
3197 | for (unsigned i = 0; i < cursors->size(); ++i)
|
---|
3198 | if (StyleImage* image = cursors->at(i).image())
|
---|
3199 | list->append(image->cssValue());
|
---|
3200 | }
|
---|
3201 | auto value = cssValuePool.createValue(style.cursor());
|
---|
3202 | if (list) {
|
---|
3203 | list->append(WTFMove(value));
|
---|
3204 | return list;
|
---|
3205 | }
|
---|
3206 | return value;
|
---|
3207 | }
|
---|
3208 | #if ENABLE(CURSOR_VISIBILITY)
|
---|
3209 | case CSSPropertyWebkitCursorVisibility:
|
---|
3210 | return cssValuePool.createValue(style.cursorVisibility());
|
---|
3211 | #endif
|
---|
3212 | case CSSPropertyDirection:
|
---|
3213 | return cssValuePool.createValue(style.direction());
|
---|
3214 | case CSSPropertyDisplay:
|
---|
3215 | return cssValuePool.createValue(style.display());
|
---|
3216 | case CSSPropertyEmptyCells:
|
---|
3217 | return cssValuePool.createValue(style.emptyCells());
|
---|
3218 | case CSSPropertyAlignContent:
|
---|
3219 | return valueForContentPositionAndDistributionWithOverflowAlignment(style.alignContent());
|
---|
3220 | case CSSPropertyAlignItems:
|
---|
3221 | return valueForItemPositionWithOverflowAlignment(style.alignItems());
|
---|
3222 | case CSSPropertyAlignSelf:
|
---|
3223 | return valueForItemPositionWithOverflowAlignment(style.alignSelf());
|
---|
3224 | case CSSPropertyFlex:
|
---|
3225 | return getCSSPropertyValuesForShorthandProperties(flexShorthand());
|
---|
3226 | case CSSPropertyFlexBasis:
|
---|
3227 | return cssValuePool.createValue(style.flexBasis(), style);
|
---|
3228 | case CSSPropertyFlexDirection:
|
---|
3229 | return cssValuePool.createValue(style.flexDirection());
|
---|
3230 | case CSSPropertyFlexFlow:
|
---|
3231 | return getCSSPropertyValuesForShorthandProperties(flexFlowShorthand());
|
---|
3232 | case CSSPropertyFlexGrow:
|
---|
3233 | return cssValuePool.createValue(style.flexGrow());
|
---|
3234 | case CSSPropertyFlexShrink:
|
---|
3235 | return cssValuePool.createValue(style.flexShrink());
|
---|
3236 | case CSSPropertyFlexWrap:
|
---|
3237 | return cssValuePool.createValue(style.flexWrap());
|
---|
3238 | case CSSPropertyJustifyContent:
|
---|
3239 | return valueForContentPositionAndDistributionWithOverflowAlignment(style.justifyContent());
|
---|
3240 | case CSSPropertyJustifyItems:
|
---|
3241 | return valueForItemPositionWithOverflowAlignment(style.justifyItems());
|
---|
3242 | case CSSPropertyJustifySelf:
|
---|
3243 | return valueForItemPositionWithOverflowAlignment(style.justifySelf());
|
---|
3244 | case CSSPropertyPlaceContent:
|
---|
3245 | return getCSSPropertyValuesForShorthandProperties(placeContentShorthand());
|
---|
3246 | case CSSPropertyPlaceItems:
|
---|
3247 | return getCSSPropertyValuesForShorthandProperties(placeItemsShorthand());
|
---|
3248 | case CSSPropertyPlaceSelf:
|
---|
3249 | return getCSSPropertyValuesForShorthandProperties(placeSelfShorthand());
|
---|
3250 | case CSSPropertyOrder:
|
---|
3251 | return cssValuePool.createValue(style.order(), CSSUnitType::CSS_INTEGER);
|
---|
3252 | case CSSPropertyFloat:
|
---|
3253 | if (style.display() != DisplayType::None && style.hasOutOfFlowPosition())
|
---|
3254 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3255 | return cssValuePool.createValue(style.floating());
|
---|
3256 | case CSSPropertyFont: {
|
---|
3257 | auto computedFont = fontShorthandValueForSelectionProperties(style.fontDescription());
|
---|
3258 | computedFont->size = fontSizeFromStyle(style);
|
---|
3259 | computedFont->lineHeight = lineHeightFromStyle(style);
|
---|
3260 | computedFont->family = fontFamilyListFromStyle(style);
|
---|
3261 | return computedFont;
|
---|
3262 | }
|
---|
3263 | case CSSPropertyFontFamily:
|
---|
3264 | return fontFamilyFromStyle(style);
|
---|
3265 | case CSSPropertyFontSize:
|
---|
3266 | return fontSizeFromStyle(style);
|
---|
3267 | case CSSPropertyFontStyle:
|
---|
3268 | return fontStyleFromStyle(style);
|
---|
3269 | case CSSPropertyFontStretch:
|
---|
3270 | return fontStretchFromStyle(style);
|
---|
3271 | case CSSPropertyFontVariant:
|
---|
3272 | return fontVariantFromStyle(style);
|
---|
3273 | case CSSPropertyFontWeight:
|
---|
3274 | return fontNonKeywordWeightFromStyle(style);
|
---|
3275 | case CSSPropertyFontPalette:
|
---|
3276 | return fontPaletteFromStyle(style);
|
---|
3277 | case CSSPropertyFontSynthesis:
|
---|
3278 | return fontSynthesisFromStyle(style);
|
---|
3279 | case CSSPropertyFontFeatureSettings: {
|
---|
3280 | const FontFeatureSettings& featureSettings = style.fontDescription().featureSettings();
|
---|
3281 | if (!featureSettings.size())
|
---|
3282 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
3283 | auto list = CSSValueList::createCommaSeparated();
|
---|
3284 | for (auto& feature : featureSettings)
|
---|
3285 | list->append(CSSFontFeatureValue::create(FontTag(feature.tag()), feature.value()));
|
---|
3286 | return list;
|
---|
3287 | }
|
---|
3288 | #if ENABLE(VARIATION_FONTS)
|
---|
3289 | case CSSPropertyFontVariationSettings: {
|
---|
3290 | const FontVariationSettings& variationSettings = style.fontDescription().variationSettings();
|
---|
3291 | if (variationSettings.isEmpty())
|
---|
3292 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
3293 | auto list = CSSValueList::createCommaSeparated();
|
---|
3294 | for (auto& feature : variationSettings)
|
---|
3295 | list->append(CSSFontVariationValue::create(feature.tag(), feature.value()));
|
---|
3296 | return list;
|
---|
3297 | }
|
---|
3298 | case CSSPropertyFontOpticalSizing:
|
---|
3299 | return cssValuePool.createValue(style.fontDescription().opticalSizing());
|
---|
3300 | #endif
|
---|
3301 | case CSSPropertyGridAutoFlow: {
|
---|
3302 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3303 | ASSERT(style.isGridAutoFlowDirectionRow() || style.isGridAutoFlowDirectionColumn());
|
---|
3304 | if (style.isGridAutoFlowDirectionColumn())
|
---|
3305 | list->append(cssValuePool.createIdentifierValue(CSSValueColumn));
|
---|
3306 | else if (!style.isGridAutoFlowAlgorithmDense())
|
---|
3307 | list->append(cssValuePool.createIdentifierValue(CSSValueRow));
|
---|
3308 |
|
---|
3309 | if (style.isGridAutoFlowAlgorithmDense())
|
---|
3310 | list->append(cssValuePool.createIdentifierValue(CSSValueDense));
|
---|
3311 |
|
---|
3312 | return list;
|
---|
3313 | }
|
---|
3314 |
|
---|
3315 | // Specs mention that getComputedStyle() should return the used value of the property instead of the computed
|
---|
3316 | // one for grid-template-{rows|columns} but not for the grid-auto-{rows|columns} as things like
|
---|
3317 | // grid-auto-columns: 2fr; cannot be resolved to a value in pixels as the '2fr' means very different things
|
---|
3318 | // depending on the size of the explicit grid or the number of implicit tracks added to the grid. See
|
---|
3319 | // http://lists.w3.org/Archives/Public/www-style/2013Nov/0014.html
|
---|
3320 | case CSSPropertyGridAutoColumns:
|
---|
3321 | return valueForGridTrackSizeList(ForColumns, style);
|
---|
3322 | case CSSPropertyGridAutoRows:
|
---|
3323 | return valueForGridTrackSizeList(ForRows, style);
|
---|
3324 |
|
---|
3325 | case CSSPropertyGridTemplateColumns:
|
---|
3326 | return valueForGridTrackList(ForColumns, renderer, style);
|
---|
3327 | case CSSPropertyGridTemplateRows:
|
---|
3328 | return valueForGridTrackList(ForRows, renderer, style);
|
---|
3329 |
|
---|
3330 | case CSSPropertyGridColumnStart:
|
---|
3331 | return valueForGridPosition(style.gridItemColumnStart());
|
---|
3332 | case CSSPropertyGridColumnEnd:
|
---|
3333 | return valueForGridPosition(style.gridItemColumnEnd());
|
---|
3334 | case CSSPropertyGridRowStart:
|
---|
3335 | return valueForGridPosition(style.gridItemRowStart());
|
---|
3336 | case CSSPropertyGridRowEnd:
|
---|
3337 | return valueForGridPosition(style.gridItemRowEnd());
|
---|
3338 | case CSSPropertyGridArea:
|
---|
3339 | return getCSSPropertyValuesForGridShorthand(gridAreaShorthand());
|
---|
3340 | case CSSPropertyGridTemplate:
|
---|
3341 | return getCSSPropertyValuesForGridShorthand(gridTemplateShorthand());
|
---|
3342 | case CSSPropertyGrid:
|
---|
3343 | return getCSSPropertyValuesForGridShorthand(gridShorthand());
|
---|
3344 | case CSSPropertyGridColumn:
|
---|
3345 | return getCSSPropertyValuesForGridShorthand(gridColumnShorthand());
|
---|
3346 | case CSSPropertyGridRow:
|
---|
3347 | return getCSSPropertyValuesForGridShorthand(gridRowShorthand());
|
---|
3348 | case CSSPropertyGridTemplateAreas:
|
---|
3349 | if (!style.namedGridAreaRowCount()) {
|
---|
3350 | ASSERT(!style.namedGridAreaColumnCount());
|
---|
3351 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3352 | }
|
---|
3353 | return CSSGridTemplateAreasValue::create(style.namedGridArea(), style.namedGridAreaRowCount(), style.namedGridAreaColumnCount());
|
---|
3354 | case CSSPropertyGap:
|
---|
3355 | return getCSSPropertyValuesForShorthandProperties(gapShorthand());
|
---|
3356 | case CSSPropertyHeight:
|
---|
3357 | if (renderer && !renderer->isRenderOrLegacyRenderSVGModelObject()) {
|
---|
3358 | // According to http://www.w3.org/TR/CSS2/visudet.html#the-height-property,
|
---|
3359 | // the "height" property does not apply for non-replaced inline elements.
|
---|
3360 | if (!isNonReplacedInline(*renderer))
|
---|
3361 | return zoomAdjustedPixelValue(sizingBox(*renderer).height(), style);
|
---|
3362 | }
|
---|
3363 | return zoomAdjustedPixelValueForLength(style.height(), style);
|
---|
3364 | case CSSPropertyWebkitHyphens:
|
---|
3365 | return cssValuePool.createValue(style.hyphens());
|
---|
3366 | case CSSPropertyWebkitHyphenateCharacter:
|
---|
3367 | if (style.hyphenationString().isNull())
|
---|
3368 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3369 | return cssValuePool.createValue(style.hyphenationString(), CSSUnitType::CSS_STRING);
|
---|
3370 | case CSSPropertyWebkitHyphenateLimitAfter:
|
---|
3371 | if (style.hyphenationLimitAfter() < 0)
|
---|
3372 | return CSSPrimitiveValue::createIdentifier(CSSValueAuto);
|
---|
3373 | return CSSPrimitiveValue::create(style.hyphenationLimitAfter(), CSSUnitType::CSS_NUMBER);
|
---|
3374 | case CSSPropertyWebkitHyphenateLimitBefore:
|
---|
3375 | if (style.hyphenationLimitBefore() < 0)
|
---|
3376 | return CSSPrimitiveValue::createIdentifier(CSSValueAuto);
|
---|
3377 | return CSSPrimitiveValue::create(style.hyphenationLimitBefore(), CSSUnitType::CSS_NUMBER);
|
---|
3378 | case CSSPropertyWebkitHyphenateLimitLines:
|
---|
3379 | if (style.hyphenationLimitLines() < 0)
|
---|
3380 | return CSSPrimitiveValue::createIdentifier(CSSValueNoLimit);
|
---|
3381 | return CSSPrimitiveValue::create(style.hyphenationLimitLines(), CSSUnitType::CSS_NUMBER);
|
---|
3382 | case CSSPropertyImageOrientation:
|
---|
3383 | if (style.imageOrientation() == ImageOrientation::FromImage)
|
---|
3384 | return cssValuePool.createIdentifierValue(CSSValueFromImage);
|
---|
3385 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3386 | case CSSPropertyImageRendering:
|
---|
3387 | return CSSPrimitiveValue::create(style.imageRendering());
|
---|
3388 | #if ENABLE(CSS_IMAGE_RESOLUTION)
|
---|
3389 | case CSSPropertyImageResolution:
|
---|
3390 | return cssValuePool.createValue(style.imageResolution(), CSSUnitType::CSS_DPPX);
|
---|
3391 | #endif
|
---|
3392 | case CSSPropertyInputSecurity:
|
---|
3393 | if (!m_element->document().settings().cssInputSecurityEnabled())
|
---|
3394 | return nullptr;
|
---|
3395 | return cssValuePool.createValue(style.inputSecurity());
|
---|
3396 | case CSSPropertyLeft:
|
---|
3397 | return positionOffsetValue(style, CSSPropertyLeft, renderer);
|
---|
3398 | case CSSPropertyLetterSpacing:
|
---|
3399 | if (!style.letterSpacing())
|
---|
3400 | return cssValuePool.createIdentifierValue(CSSValueNormal);
|
---|
3401 | return zoomAdjustedPixelValue(style.letterSpacing(), style);
|
---|
3402 | case CSSPropertyWebkitLineClamp:
|
---|
3403 | if (style.lineClamp().isNone())
|
---|
3404 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3405 | return cssValuePool.createValue(style.lineClamp().value(), style.lineClamp().isPercentage() ? CSSUnitType::CSS_PERCENTAGE : CSSUnitType::CSS_INTEGER);
|
---|
3406 | case CSSPropertyLineHeight:
|
---|
3407 | return lineHeightFromStyle(style);
|
---|
3408 | case CSSPropertyListStyleImage:
|
---|
3409 | if (style.listStyleImage())
|
---|
3410 | return style.listStyleImage()->cssValue();
|
---|
3411 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3412 | case CSSPropertyListStylePosition:
|
---|
3413 | return cssValuePool.createValue(style.listStylePosition());
|
---|
3414 | case CSSPropertyListStyleType:
|
---|
3415 | if (style.listStyleType() == ListStyleType::String)
|
---|
3416 | return cssValuePool.createValue(style.listStyleStringValue(), CSSUnitType::CSS_STRING);
|
---|
3417 | return cssValuePool.createValue(style.listStyleType());
|
---|
3418 | case CSSPropertyWebkitLocale:
|
---|
3419 | if (style.specifiedLocale().isNull())
|
---|
3420 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3421 | return cssValuePool.createCustomIdent(style.specifiedLocale());
|
---|
3422 | case CSSPropertyMarginTop:
|
---|
3423 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::marginTop, &RenderBoxModelObject::marginTop>(style, renderer);
|
---|
3424 | case CSSPropertyMarginRight: {
|
---|
3425 | Length marginRight = style.marginRight();
|
---|
3426 | if (marginRight.isFixed() || !is<RenderBox>(renderer))
|
---|
3427 | return zoomAdjustedPixelValueForLength(marginRight, style);
|
---|
3428 | float value;
|
---|
3429 | if (marginRight.isPercentOrCalculated()) {
|
---|
3430 | // RenderBox gives a marginRight() that is the distance between the right-edge of the child box
|
---|
3431 | // and the right-edge of the containing box, when display == DisplayType::Block. Let's calculate the absolute
|
---|
3432 | // value of the specified margin-right % instead of relying on RenderBox's marginRight() value.
|
---|
3433 | value = minimumValueForLength(marginRight, downcast<RenderBox>(*renderer).containingBlockLogicalWidthForContent());
|
---|
3434 | } else
|
---|
3435 | value = downcast<RenderBox>(*renderer).marginRight();
|
---|
3436 | return zoomAdjustedPixelValue(value, style);
|
---|
3437 | }
|
---|
3438 | case CSSPropertyMarginBottom:
|
---|
3439 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::marginBottom, &RenderBoxModelObject::marginBottom>(style, renderer);
|
---|
3440 | case CSSPropertyMarginLeft:
|
---|
3441 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::marginLeft, &RenderBoxModelObject::marginLeft>(style, renderer);
|
---|
3442 | case CSSPropertyWebkitUserModify:
|
---|
3443 | return cssValuePool.createValue(style.userModify());
|
---|
3444 | case CSSPropertyMaxHeight: {
|
---|
3445 | const Length& maxHeight = style.maxHeight();
|
---|
3446 | if (maxHeight.isUndefined())
|
---|
3447 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3448 | return zoomAdjustedPixelValueForLength(maxHeight, style);
|
---|
3449 | }
|
---|
3450 | case CSSPropertyMaxWidth: {
|
---|
3451 | const Length& maxWidth = style.maxWidth();
|
---|
3452 | if (maxWidth.isUndefined())
|
---|
3453 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3454 | return zoomAdjustedPixelValueForLength(maxWidth, style);
|
---|
3455 | }
|
---|
3456 | case CSSPropertyMinHeight:
|
---|
3457 | if (style.minHeight().isAuto()) {
|
---|
3458 | if (isFlexOrGridItem(renderer))
|
---|
3459 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3460 | return zoomAdjustedPixelValue(0, style);
|
---|
3461 | }
|
---|
3462 | return zoomAdjustedPixelValueForLength(style.minHeight(), style);
|
---|
3463 | case CSSPropertyMinWidth:
|
---|
3464 | if (style.minWidth().isAuto()) {
|
---|
3465 | if (isFlexOrGridItem(renderer))
|
---|
3466 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3467 | return zoomAdjustedPixelValue(0, style);
|
---|
3468 | }
|
---|
3469 | return zoomAdjustedPixelValueForLength(style.minWidth(), style);
|
---|
3470 | case CSSPropertyObjectFit:
|
---|
3471 | return cssValuePool.createValue(style.objectFit());
|
---|
3472 | case CSSPropertyObjectPosition:
|
---|
3473 | return valueForPosition(style, style.objectPosition());
|
---|
3474 | case CSSPropertyOffsetPath:
|
---|
3475 | // The computed value of offset-path must only contain absolute draw commands.
|
---|
3476 | // https://github.com/w3c/fxtf-drafts/issues/225#issuecomment-334322738
|
---|
3477 | if (!m_element->document().settings().cssMotionPathEnabled())
|
---|
3478 | return nullptr;
|
---|
3479 | return valueForPathOperation(style, style.offsetPath(), SVGPathConversion::ForceAbsolute);
|
---|
3480 | case CSSPropertyOffsetDistance:
|
---|
3481 | if (!m_element->document().settings().cssMotionPathEnabled())
|
---|
3482 | return nullptr;
|
---|
3483 | return cssValuePool.createValue(style.offsetDistance(), style);
|
---|
3484 | case CSSPropertyOffsetPosition:
|
---|
3485 | if (!m_element->document().settings().cssMotionPathEnabled())
|
---|
3486 | return nullptr;
|
---|
3487 | return valueForPositionOrAuto(style, style.offsetPosition());
|
---|
3488 | case CSSPropertyOffsetAnchor:
|
---|
3489 | if (!m_element->document().settings().cssMotionPathEnabled())
|
---|
3490 | return nullptr;
|
---|
3491 | return valueForPositionOrAuto(style, style.offsetAnchor());
|
---|
3492 | case CSSPropertyOffsetRotate:
|
---|
3493 | if (!m_element->document().settings().cssMotionPathEnabled())
|
---|
3494 | return nullptr;
|
---|
3495 | return valueForOffsetRotate(style.offsetRotate());
|
---|
3496 | case CSSPropertyOffset:
|
---|
3497 | if (!m_element->document().settings().cssMotionPathEnabled())
|
---|
3498 | return nullptr;
|
---|
3499 | return valueForOffsetShorthand(style);
|
---|
3500 | case CSSPropertyOpacity:
|
---|
3501 | return cssValuePool.createValue(style.opacity(), CSSUnitType::CSS_NUMBER);
|
---|
3502 | case CSSPropertyOrphans:
|
---|
3503 | if (style.hasAutoOrphans())
|
---|
3504 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3505 | return cssValuePool.createValue(style.orphans(), CSSUnitType::CSS_INTEGER);
|
---|
3506 | case CSSPropertyOutlineColor:
|
---|
3507 | return m_allowVisitedStyle ? cssValuePool.createColorValue(style.visitedDependentColor(CSSPropertyOutlineColor)) : currentColorOrValidColor(&style, style.outlineColor());
|
---|
3508 | case CSSPropertyOutlineOffset:
|
---|
3509 | return zoomAdjustedPixelValue(style.outlineOffset(), style);
|
---|
3510 | case CSSPropertyOutlineStyle:
|
---|
3511 | if (style.outlineStyleIsAuto() == OutlineIsAuto::On)
|
---|
3512 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3513 | return cssValuePool.createValue(style.outlineStyle());
|
---|
3514 | case CSSPropertyOutlineWidth:
|
---|
3515 | return zoomAdjustedPixelValue(style.outlineWidth(), style);
|
---|
3516 | case CSSPropertyOverflow:
|
---|
3517 | return getCSSPropertyValuesFor2SidesShorthand(overflowShorthand());
|
---|
3518 | case CSSPropertyOverflowWrap:
|
---|
3519 | return cssValuePool.createValue(style.overflowWrap());
|
---|
3520 | case CSSPropertyOverflowX:
|
---|
3521 | return cssValuePool.createValue(style.overflowX());
|
---|
3522 | case CSSPropertyOverflowY:
|
---|
3523 | return cssValuePool.createValue(style.overflowY());
|
---|
3524 | case CSSPropertyOverscrollBehavior:
|
---|
3525 | if (!m_element->document().settings().overscrollBehaviorEnabled())
|
---|
3526 | return nullptr;
|
---|
3527 | return cssValuePool.createValue(std::max(style.overscrollBehaviorX(), style.overscrollBehaviorY()));
|
---|
3528 | case CSSPropertyOverscrollBehaviorX:
|
---|
3529 | if (!m_element->document().settings().overscrollBehaviorEnabled())
|
---|
3530 | return nullptr;
|
---|
3531 | return cssValuePool.createValue(style.overscrollBehaviorX());
|
---|
3532 | case CSSPropertyOverscrollBehaviorY:
|
---|
3533 | if (!m_element->document().settings().overscrollBehaviorEnabled())
|
---|
3534 | return nullptr;
|
---|
3535 | return cssValuePool.createValue(style.overscrollBehaviorY());
|
---|
3536 | case CSSPropertyPaddingTop:
|
---|
3537 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::paddingTop, &RenderBoxModelObject::computedCSSPaddingTop>(style, renderer);
|
---|
3538 | case CSSPropertyPaddingRight:
|
---|
3539 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::paddingRight, &RenderBoxModelObject::computedCSSPaddingRight>(style, renderer);
|
---|
3540 | case CSSPropertyPaddingBottom:
|
---|
3541 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::paddingBottom, &RenderBoxModelObject::computedCSSPaddingBottom>(style, renderer);
|
---|
3542 | case CSSPropertyPaddingLeft:
|
---|
3543 | return zoomAdjustedPaddingOrMarginPixelValue<&RenderStyle::paddingLeft, &RenderBoxModelObject::computedCSSPaddingLeft>(style, renderer);
|
---|
3544 | case CSSPropertyPageBreakAfter:
|
---|
3545 | return cssValuePool.createValue(convertToPageBreak(style.breakAfter()));
|
---|
3546 | case CSSPropertyPageBreakBefore:
|
---|
3547 | return cssValuePool.createValue(convertToPageBreak(style.breakBefore()));
|
---|
3548 | case CSSPropertyPageBreakInside:
|
---|
3549 | return cssValuePool.createValue(convertToPageBreak(style.breakInside()));
|
---|
3550 | case CSSPropertyBreakAfter:
|
---|
3551 | return cssValuePool.createValue(style.breakAfter());
|
---|
3552 | case CSSPropertyBreakBefore:
|
---|
3553 | return cssValuePool.createValue(style.breakBefore());
|
---|
3554 | case CSSPropertyBreakInside:
|
---|
3555 | return cssValuePool.createValue(style.breakInside());
|
---|
3556 | case CSSPropertyHangingPunctuation:
|
---|
3557 | return hangingPunctuationToCSSValue(style.hangingPunctuation());
|
---|
3558 | case CSSPropertyPosition:
|
---|
3559 | return cssValuePool.createValue(style.position());
|
---|
3560 | case CSSPropertyRight:
|
---|
3561 | return positionOffsetValue(style, CSSPropertyRight, renderer);
|
---|
3562 | case CSSPropertyWebkitRubyPosition:
|
---|
3563 | return cssValuePool.createValue(style.rubyPosition());
|
---|
3564 | case CSSPropertyTableLayout:
|
---|
3565 | return cssValuePool.createValue(style.tableLayout());
|
---|
3566 | case CSSPropertyTextAlign:
|
---|
3567 | return cssValuePool.createValue(style.textAlign());
|
---|
3568 | case CSSPropertyTextAlignLast:
|
---|
3569 | if (!m_element->document().settings().cssTextAlignLastEnabled())
|
---|
3570 | return nullptr;
|
---|
3571 | return cssValuePool.createValue(style.textAlignLast());
|
---|
3572 | case CSSPropertyTextDecoration:
|
---|
3573 | return renderTextDecorationLineFlagsToCSSValue(style.textDecorationLine());
|
---|
3574 | case CSSPropertyTextJustify:
|
---|
3575 | if (!m_element->document().settings().cssTextJustifyEnabled())
|
---|
3576 | return nullptr;
|
---|
3577 | return cssValuePool.createValue(style.textJustify());
|
---|
3578 | case CSSPropertyWebkitTextDecoration:
|
---|
3579 | return getCSSPropertyValuesForShorthandProperties(webkitTextDecorationShorthand());
|
---|
3580 | case CSSPropertyTextDecorationLine:
|
---|
3581 | return renderTextDecorationLineFlagsToCSSValue(style.textDecorationLine());
|
---|
3582 | case CSSPropertyTextDecorationStyle:
|
---|
3583 | return renderTextDecorationStyleFlagsToCSSValue(style.textDecorationStyle());
|
---|
3584 | case CSSPropertyTextDecorationColor:
|
---|
3585 | return currentColorOrValidColor(&style, style.textDecorationColor());
|
---|
3586 | case CSSPropertyTextDecorationSkip:
|
---|
3587 | return renderTextDecorationSkipToCSSValue(style.textDecorationSkipInk());
|
---|
3588 | case CSSPropertyTextDecorationSkipInk:
|
---|
3589 | return cssValuePool.createValue(style.textDecorationSkipInk());
|
---|
3590 | case CSSPropertyTextUnderlinePosition:
|
---|
3591 | return cssValuePool.createValue(style.textUnderlinePosition());
|
---|
3592 | case CSSPropertyTextUnderlineOffset:
|
---|
3593 | return textUnderlineOffsetToCSSValue(style.textUnderlineOffset());
|
---|
3594 | case CSSPropertyTextDecorationThickness:
|
---|
3595 | return textDecorationThicknessToCSSValue(style.textDecorationThickness());
|
---|
3596 | case CSSPropertyWebkitTextDecorationsInEffect:
|
---|
3597 | return renderTextDecorationLineFlagsToCSSValue(style.textDecorationsInEffect());
|
---|
3598 | case CSSPropertyWebkitTextFillColor:
|
---|
3599 | return currentColorOrValidColor(&style, style.textFillColor());
|
---|
3600 | case CSSPropertyTextEmphasisColor:
|
---|
3601 | return currentColorOrValidColor(&style, style.textEmphasisColor());
|
---|
3602 | case CSSPropertyTextEmphasisPosition:
|
---|
3603 | return renderEmphasisPositionFlagsToCSSValue(style.textEmphasisPosition());
|
---|
3604 | case CSSPropertyTextEmphasisStyle:
|
---|
3605 | return valueForTextEmphasisStyle(style);
|
---|
3606 | case CSSPropertyTextEmphasis: {
|
---|
3607 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3608 | list->append(valueForTextEmphasisStyle(style));
|
---|
3609 | list->append(currentColorOrValidColor(&style, style.textEmphasisColor()));
|
---|
3610 | return list;
|
---|
3611 | }
|
---|
3612 | case CSSPropertyTextIndent: {
|
---|
3613 | auto textIndent = zoomAdjustedPixelValueForLength(style.textIndent(), style);
|
---|
3614 | if (style.textIndentLine() == TextIndentLine::EachLine || style.textIndentType() == TextIndentType::Hanging) {
|
---|
3615 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3616 | list->append(WTFMove(textIndent));
|
---|
3617 | if (style.textIndentType() == TextIndentType::Hanging)
|
---|
3618 | list->append(cssValuePool.createIdentifierValue(CSSValueHanging));
|
---|
3619 | if (style.textIndentLine() == TextIndentLine::EachLine)
|
---|
3620 | list->append(cssValuePool.createIdentifierValue(CSSValueEachLine));
|
---|
3621 | return list;
|
---|
3622 | }
|
---|
3623 | return textIndent;
|
---|
3624 | }
|
---|
3625 | case CSSPropertyTextShadow:
|
---|
3626 | return valueForShadow(style.textShadow(), propertyID, style);
|
---|
3627 | case CSSPropertyTextRendering:
|
---|
3628 | return cssValuePool.createValue(style.fontDescription().textRenderingMode());
|
---|
3629 | case CSSPropertyTextOverflow:
|
---|
3630 | if (style.textOverflow() == TextOverflow::Ellipsis)
|
---|
3631 | return cssValuePool.createIdentifierValue(CSSValueEllipsis);
|
---|
3632 | return cssValuePool.createIdentifierValue(CSSValueClip);
|
---|
3633 | case CSSPropertyWebkitTextSecurity:
|
---|
3634 | return cssValuePool.createValue(style.textSecurity());
|
---|
3635 | #if ENABLE(TEXT_AUTOSIZING)
|
---|
3636 | case CSSPropertyWebkitTextSizeAdjust:
|
---|
3637 | if (style.textSizeAdjust().isAuto())
|
---|
3638 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3639 | if (style.textSizeAdjust().isNone())
|
---|
3640 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3641 | return CSSPrimitiveValue::create(style.textSizeAdjust().percentage(), CSSUnitType::CSS_PERCENTAGE);
|
---|
3642 | #endif
|
---|
3643 | case CSSPropertyWebkitTextStrokeColor:
|
---|
3644 | return currentColorOrValidColor(&style, style.textStrokeColor());
|
---|
3645 | case CSSPropertyWebkitTextStrokeWidth:
|
---|
3646 | return zoomAdjustedPixelValue(style.textStrokeWidth(), style);
|
---|
3647 | case CSSPropertyTextTransform:
|
---|
3648 | return cssValuePool.createValue(style.textTransform());
|
---|
3649 | case CSSPropertyTop:
|
---|
3650 | return positionOffsetValue(style, CSSPropertyTop, renderer);
|
---|
3651 | case CSSPropertyUnicodeBidi:
|
---|
3652 | return cssValuePool.createValue(style.unicodeBidi());
|
---|
3653 | case CSSPropertyVerticalAlign:
|
---|
3654 | switch (style.verticalAlign()) {
|
---|
3655 | case VerticalAlign::Baseline:
|
---|
3656 | return cssValuePool.createIdentifierValue(CSSValueBaseline);
|
---|
3657 | case VerticalAlign::Middle:
|
---|
3658 | return cssValuePool.createIdentifierValue(CSSValueMiddle);
|
---|
3659 | case VerticalAlign::Sub:
|
---|
3660 | return cssValuePool.createIdentifierValue(CSSValueSub);
|
---|
3661 | case VerticalAlign::Super:
|
---|
3662 | return cssValuePool.createIdentifierValue(CSSValueSuper);
|
---|
3663 | case VerticalAlign::TextTop:
|
---|
3664 | return cssValuePool.createIdentifierValue(CSSValueTextTop);
|
---|
3665 | case VerticalAlign::TextBottom:
|
---|
3666 | return cssValuePool.createIdentifierValue(CSSValueTextBottom);
|
---|
3667 | case VerticalAlign::Top:
|
---|
3668 | return cssValuePool.createIdentifierValue(CSSValueTop);
|
---|
3669 | case VerticalAlign::Bottom:
|
---|
3670 | return cssValuePool.createIdentifierValue(CSSValueBottom);
|
---|
3671 | case VerticalAlign::BaselineMiddle:
|
---|
3672 | return cssValuePool.createIdentifierValue(CSSValueWebkitBaselineMiddle);
|
---|
3673 | case VerticalAlign::Length:
|
---|
3674 | return cssValuePool.createValue(style.verticalAlignLength(), style);
|
---|
3675 | }
|
---|
3676 | ASSERT_NOT_REACHED();
|
---|
3677 | return nullptr;
|
---|
3678 | case CSSPropertyVisibility:
|
---|
3679 | return cssValuePool.createValue(style.visibility());
|
---|
3680 | case CSSPropertyWhiteSpace:
|
---|
3681 | return cssValuePool.createValue(style.whiteSpace());
|
---|
3682 | case CSSPropertyWidows:
|
---|
3683 | if (style.hasAutoWidows())
|
---|
3684 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3685 | return cssValuePool.createValue(style.widows(), CSSUnitType::CSS_INTEGER);
|
---|
3686 | case CSSPropertyWidth:
|
---|
3687 | if (renderer && !renderer->isRenderOrLegacyRenderSVGModelObject()) {
|
---|
3688 | // According to http://www.w3.org/TR/CSS2/visudet.html#the-width-property,
|
---|
3689 | // the "width" property does not apply for non-replaced inline elements.
|
---|
3690 | if (!isNonReplacedInline(*renderer))
|
---|
3691 | return zoomAdjustedPixelValue(sizingBox(*renderer).width(), style);
|
---|
3692 | }
|
---|
3693 | return zoomAdjustedPixelValueForLength(style.width(), style);
|
---|
3694 | case CSSPropertyWillChange:
|
---|
3695 | return willChangePropertyValue(style.willChange());
|
---|
3696 | case CSSPropertyWordBreak:
|
---|
3697 | return cssValuePool.createValue(style.wordBreak());
|
---|
3698 | case CSSPropertyWordSpacing:
|
---|
3699 | return zoomAdjustedPixelValue(style.fontCascade().wordSpacing(), style);
|
---|
3700 | case CSSPropertyLineBreak:
|
---|
3701 | return cssValuePool.createValue(style.lineBreak());
|
---|
3702 | case CSSPropertyWebkitNbspMode:
|
---|
3703 | return cssValuePool.createValue(style.nbspMode());
|
---|
3704 | case CSSPropertyResize:
|
---|
3705 | return cssValuePool.createValue(style.resize());
|
---|
3706 | case CSSPropertyFontKerning:
|
---|
3707 | return cssValuePool.createValue(style.fontDescription().kerning());
|
---|
3708 | case CSSPropertyWebkitFontSmoothing:
|
---|
3709 | return cssValuePool.createValue(style.fontDescription().fontSmoothing());
|
---|
3710 | case CSSPropertyFontVariantLigatures:
|
---|
3711 | return fontVariantLigaturesPropertyValue(style.fontDescription().variantCommonLigatures(), style.fontDescription().variantDiscretionaryLigatures(), style.fontDescription().variantHistoricalLigatures(), style.fontDescription().variantContextualAlternates());
|
---|
3712 | case CSSPropertyFontVariantPosition:
|
---|
3713 | return fontVariantPositionPropertyValue(style.fontDescription().variantPosition());
|
---|
3714 | case CSSPropertyFontVariantCaps:
|
---|
3715 | return fontVariantCapsPropertyValue(style.fontDescription().variantCaps());
|
---|
3716 | case CSSPropertyFontVariantNumeric:
|
---|
3717 | return fontVariantNumericPropertyValue(style.fontDescription().variantNumericFigure(), style.fontDescription().variantNumericSpacing(), style.fontDescription().variantNumericFraction(), style.fontDescription().variantNumericOrdinal(), style.fontDescription().variantNumericSlashedZero());
|
---|
3718 | case CSSPropertyFontVariantAlternates:
|
---|
3719 | return fontVariantAlternatesPropertyValue(style.fontDescription().variantAlternates());
|
---|
3720 | case CSSPropertyFontVariantEastAsian:
|
---|
3721 | return fontVariantEastAsianPropertyValue(style.fontDescription().variantEastAsianVariant(), style.fontDescription().variantEastAsianWidth(), style.fontDescription().variantEastAsianRuby());
|
---|
3722 | case CSSPropertyZIndex:
|
---|
3723 | if (style.hasAutoSpecifiedZIndex())
|
---|
3724 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3725 | return cssValuePool.createValue(style.specifiedZIndex(), CSSUnitType::CSS_INTEGER);
|
---|
3726 | case CSSPropertyZoom:
|
---|
3727 | return cssValuePool.createValue(style.zoom(), CSSUnitType::CSS_NUMBER);
|
---|
3728 | case CSSPropertyBoxSizing:
|
---|
3729 | if (style.boxSizing() == BoxSizing::ContentBox)
|
---|
3730 | return cssValuePool.createIdentifierValue(CSSValueContentBox);
|
---|
3731 | return cssValuePool.createIdentifierValue(CSSValueBorderBox);
|
---|
3732 | case CSSPropertyAnimation:
|
---|
3733 | return animationShorthandValue(propertyID, style.animations());
|
---|
3734 | case CSSPropertyAnimationComposition:
|
---|
3735 | case CSSPropertyAnimationDelay:
|
---|
3736 | case CSSPropertyAnimationDirection:
|
---|
3737 | case CSSPropertyAnimationDuration:
|
---|
3738 | case CSSPropertyAnimationFillMode:
|
---|
3739 | case CSSPropertyAnimationIterationCount:
|
---|
3740 | case CSSPropertyAnimationName:
|
---|
3741 | case CSSPropertyAnimationPlayState:
|
---|
3742 | case CSSPropertyAnimationTimingFunction:
|
---|
3743 | return valueListForAnimationOrTransitionProperty(propertyID, style.animations());
|
---|
3744 | case CSSPropertyAppearance:
|
---|
3745 | return cssValuePool.createValue(style.appearance());
|
---|
3746 | case CSSPropertyAspectRatio:
|
---|
3747 | if (!m_element->document().settings().aspectRatioEnabled())
|
---|
3748 | return nullptr;
|
---|
3749 | switch (style.aspectRatioType()) {
|
---|
3750 | case AspectRatioType::Auto:
|
---|
3751 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3752 | case AspectRatioType::AutoZero:
|
---|
3753 | case AspectRatioType::AutoAndRatio:
|
---|
3754 | case AspectRatioType::Ratio: {
|
---|
3755 | auto ratioList = CSSValueList::createSlashSeparated();
|
---|
3756 | ratioList->append(cssValuePool.createValue(style.aspectRatioWidth(), CSSUnitType::CSS_NUMBER));
|
---|
3757 | ratioList->append(cssValuePool.createValue(style.aspectRatioHeight(), CSSUnitType::CSS_NUMBER));
|
---|
3758 | if (style.aspectRatioType() != AspectRatioType::AutoAndRatio)
|
---|
3759 | return ratioList;
|
---|
3760 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3761 | list->append(cssValuePool.createIdentifierValue(CSSValueAuto));
|
---|
3762 | list->append(ratioList);
|
---|
3763 | return list;
|
---|
3764 | }
|
---|
3765 | }
|
---|
3766 | ASSERT_NOT_REACHED();
|
---|
3767 | return nullptr;
|
---|
3768 | case CSSPropertyContain: {
|
---|
3769 | if (!m_element->document().settings().cssContainmentEnabled())
|
---|
3770 | return nullptr;
|
---|
3771 | auto containment = style.contain();
|
---|
3772 | if (!containment)
|
---|
3773 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3774 | if (containment == RenderStyle::strictContainment())
|
---|
3775 | return cssValuePool.createIdentifierValue(CSSValueStrict);
|
---|
3776 | if (containment == RenderStyle::contentContainment())
|
---|
3777 | return cssValuePool.createIdentifierValue(CSSValueContent);
|
---|
3778 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3779 | if (containment & Containment::Size)
|
---|
3780 | list->append(cssValuePool.createIdentifierValue(CSSValueSize));
|
---|
3781 | if (containment & Containment::Layout)
|
---|
3782 | list->append(cssValuePool.createIdentifierValue(CSSValueLayout));
|
---|
3783 | if (containment & Containment::Style)
|
---|
3784 | list->append(cssValuePool.createIdentifierValue(CSSValueStyle));
|
---|
3785 | if (containment & Containment::Paint)
|
---|
3786 | list->append(cssValuePool.createIdentifierValue(CSSValuePaint));
|
---|
3787 | if (containment & Containment::InlineSize)
|
---|
3788 | list->append(cssValuePool.createIdentifierValue(CSSValueInlineSize));
|
---|
3789 | return list;
|
---|
3790 | }
|
---|
3791 | case CSSPropertyContainer: {
|
---|
3792 | auto list = CSSValueList::createSlashSeparated();
|
---|
3793 | if (style.containerNames().isEmpty())
|
---|
3794 | list->append(cssValuePool.createIdentifierValue(CSSValueNone));
|
---|
3795 | else
|
---|
3796 | list->append(propertyValue(CSSPropertyContainerName, DoNotUpdateLayout).releaseNonNull());
|
---|
3797 | if (style.containerType() != ContainerType::None)
|
---|
3798 | list->append(propertyValue(CSSPropertyContainerType, DoNotUpdateLayout).releaseNonNull());
|
---|
3799 | return list;
|
---|
3800 | }
|
---|
3801 | case CSSPropertyContainerType:
|
---|
3802 | return CSSPrimitiveValue::create(style.containerType());
|
---|
3803 | case CSSPropertyContainerName: {
|
---|
3804 | if (style.containerNames().isEmpty())
|
---|
3805 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3806 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3807 | for (auto& name : style.containerNames())
|
---|
3808 | list->append(cssValuePool.createCustomIdent(name));
|
---|
3809 | return list;
|
---|
3810 | }
|
---|
3811 | case CSSPropertyContainIntrinsicSize: {
|
---|
3812 | if (!m_element->document().settings().cssContainIntrinsicSizeEnabled())
|
---|
3813 | return nullptr;
|
---|
3814 | return getCSSPropertyValuesFor2SidesShorthand(containIntrinsicSizeShorthand());
|
---|
3815 | }
|
---|
3816 | case CSSPropertyContainIntrinsicWidth: {
|
---|
3817 | if (!m_element->document().settings().cssContainIntrinsicSizeEnabled())
|
---|
3818 | return nullptr;
|
---|
3819 | return valueForContainIntrinsicSize(style, style.containIntrinsicWidthType(), style.containIntrinsicWidth());
|
---|
3820 | }
|
---|
3821 | case CSSPropertyContainIntrinsicHeight: {
|
---|
3822 | if (!m_element->document().settings().cssContainIntrinsicSizeEnabled())
|
---|
3823 | return nullptr;
|
---|
3824 | return valueForContainIntrinsicSize(style, style.containIntrinsicHeightType(), style.containIntrinsicHeight());
|
---|
3825 | }
|
---|
3826 | case CSSPropertyBackfaceVisibility:
|
---|
3827 | return cssValuePool.createIdentifierValue((style.backfaceVisibility() == BackfaceVisibility::Hidden) ? CSSValueHidden : CSSValueVisible);
|
---|
3828 | case CSSPropertyBorderImage:
|
---|
3829 | case CSSPropertyWebkitBorderImage:
|
---|
3830 | return valueForNinePieceImage(propertyID, style.borderImage(), style);
|
---|
3831 | case CSSPropertyBorderImageOutset:
|
---|
3832 | return valueForNinePieceImageQuad(style.borderImage().outset(), style);
|
---|
3833 | case CSSPropertyBorderImageRepeat:
|
---|
3834 | return valueForNinePieceImageRepeat(style.borderImage());
|
---|
3835 | case CSSPropertyBorderImageSlice:
|
---|
3836 | return valueForNinePieceImageSlice(style.borderImage());
|
---|
3837 | case CSSPropertyBorderImageWidth:
|
---|
3838 | if (style.borderImage().overridesBorderWidths())
|
---|
3839 | return nullptr;
|
---|
3840 | return valueForNinePieceImageQuad(style.borderImage().borderSlices(), style);
|
---|
3841 | case CSSPropertyWebkitMaskBoxImage:
|
---|
3842 | return valueForNinePieceImage(propertyID, style.maskBoxImage(), style);
|
---|
3843 | case CSSPropertyWebkitMaskBoxImageOutset:
|
---|
3844 | return valueForNinePieceImageQuad(style.maskBoxImage().outset(), style);
|
---|
3845 | case CSSPropertyWebkitMaskBoxImageRepeat:
|
---|
3846 | return valueForNinePieceImageRepeat(style.maskBoxImage());
|
---|
3847 | case CSSPropertyWebkitMaskBoxImageSlice:
|
---|
3848 | return valueForNinePieceImageSlice(style.maskBoxImage());
|
---|
3849 | case CSSPropertyWebkitMaskBoxImageWidth:
|
---|
3850 | return valueForNinePieceImageQuad(style.maskBoxImage().borderSlices(), style);
|
---|
3851 | case CSSPropertyWebkitMaskBoxImageSource:
|
---|
3852 | if (style.maskBoxImageSource())
|
---|
3853 | return style.maskBoxImageSource()->cssValue();
|
---|
3854 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3855 | case CSSPropertyWebkitFontSizeDelta:
|
---|
3856 | // Not a real style property -- used by the editing engine -- so has no computed value.
|
---|
3857 | break;
|
---|
3858 | case CSSPropertyWebkitInitialLetter: {
|
---|
3859 | auto drop = !style.initialLetterDrop() ? cssValuePool.createIdentifierValue(CSSValueNormal) : cssValuePool.createValue(style.initialLetterDrop(), CSSUnitType::CSS_NUMBER);
|
---|
3860 | auto size = !style.initialLetterHeight() ? cssValuePool.createIdentifierValue(CSSValueNormal) : cssValuePool.createValue(style.initialLetterHeight(), CSSUnitType::CSS_NUMBER);
|
---|
3861 | return cssValuePool.createValue(Pair::create(WTFMove(drop), WTFMove(size)));
|
---|
3862 | }
|
---|
3863 | #if ENABLE(OVERFLOW_SCROLLING_TOUCH)
|
---|
3864 | case CSSPropertyWebkitOverflowScrolling:
|
---|
3865 | if (!style.useTouchOverflowScrolling())
|
---|
3866 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3867 | return cssValuePool.createIdentifierValue(CSSValueTouch);
|
---|
3868 | #endif
|
---|
3869 | case CSSPropertyScrollBehavior:
|
---|
3870 | if (!style.useSmoothScrolling())
|
---|
3871 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3872 | return cssValuePool.createIdentifierValue(CSSValueSmooth);
|
---|
3873 | case CSSPropertyPerspective:
|
---|
3874 | case CSSPropertyWebkitPerspective:
|
---|
3875 | if (!style.hasPerspective())
|
---|
3876 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3877 | return zoomAdjustedPixelValue(style.perspective(), style);
|
---|
3878 | case CSSPropertyPerspectiveOrigin: {
|
---|
3879 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3880 | if (renderer) {
|
---|
3881 | auto box = renderer->transformReferenceBoxRect(style);
|
---|
3882 | list->append(zoomAdjustedPixelValue(minimumValueForLength(style.perspectiveOriginX(), box.width()), style));
|
---|
3883 | list->append(zoomAdjustedPixelValue(minimumValueForLength(style.perspectiveOriginY(), box.height()), style));
|
---|
3884 | } else {
|
---|
3885 | list->append(zoomAdjustedPixelValueForLength(style.perspectiveOriginX(), style));
|
---|
3886 | list->append(zoomAdjustedPixelValueForLength(style.perspectiveOriginY(), style));
|
---|
3887 | }
|
---|
3888 | return list;
|
---|
3889 | }
|
---|
3890 | case CSSPropertyWebkitRtlOrdering:
|
---|
3891 | return cssValuePool.createIdentifierValue(style.rtlOrdering() == Order::Visual ? CSSValueVisual : CSSValueLogical);
|
---|
3892 | #if ENABLE(TOUCH_EVENTS)
|
---|
3893 | case CSSPropertyWebkitTapHighlightColor:
|
---|
3894 | return currentColorOrValidColor(&style, style.tapHighlightColor());
|
---|
3895 | #endif
|
---|
3896 | case CSSPropertyTouchAction:
|
---|
3897 | return touchActionFlagsToCSSValue(style.touchActions());
|
---|
3898 | #if PLATFORM(IOS_FAMILY)
|
---|
3899 | case CSSPropertyWebkitTouchCallout:
|
---|
3900 | return cssValuePool.createIdentifierValue(style.touchCalloutEnabled() ? CSSValueDefault : CSSValueNone);
|
---|
3901 | #endif
|
---|
3902 | case CSSPropertyWebkitUserDrag:
|
---|
3903 | return cssValuePool.createValue(style.userDrag());
|
---|
3904 | case CSSPropertyUserSelect:
|
---|
3905 | return cssValuePool.createValue(style.userSelect());
|
---|
3906 | case CSSPropertyBorderBottomLeftRadius:
|
---|
3907 | return borderRadiusCornerValue(style.borderBottomLeftRadius(), style);
|
---|
3908 | case CSSPropertyBorderBottomRightRadius:
|
---|
3909 | return borderRadiusCornerValue(style.borderBottomRightRadius(), style);
|
---|
3910 | case CSSPropertyBorderTopLeftRadius:
|
---|
3911 | return borderRadiusCornerValue(style.borderTopLeftRadius(), style);
|
---|
3912 | case CSSPropertyBorderTopRightRadius:
|
---|
3913 | return borderRadiusCornerValue(style.borderTopRightRadius(), style);
|
---|
3914 | case CSSPropertyClip: {
|
---|
3915 | if (!style.hasClip())
|
---|
3916 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3917 | if (style.clip().top().isAuto() && style.clip().right().isAuto()
|
---|
3918 | && style.clip().top().isAuto() && style.clip().right().isAuto())
|
---|
3919 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
3920 |
|
---|
3921 | auto rect = Rect::create();
|
---|
3922 | rect->setTop(autoOrZoomAdjustedValue(style.clip().top(), style));
|
---|
3923 | rect->setRight(autoOrZoomAdjustedValue(style.clip().right(), style));
|
---|
3924 | rect->setBottom(autoOrZoomAdjustedValue(style.clip().bottom(), style));
|
---|
3925 | rect->setLeft(autoOrZoomAdjustedValue(style.clip().left(), style));
|
---|
3926 | return cssValuePool.createValue(WTFMove(rect));
|
---|
3927 | }
|
---|
3928 | case CSSPropertySpeakAs:
|
---|
3929 | return speakAsToCSSValue(style.speakAs());
|
---|
3930 | case CSSPropertyTransform:
|
---|
3931 | return computedTransform(renderer, style);
|
---|
3932 | case CSSPropertyTransformBox:
|
---|
3933 | return CSSPrimitiveValue::create(style.transformBox());
|
---|
3934 | case CSSPropertyTransformOrigin: {
|
---|
3935 | auto list = CSSValueList::createSpaceSeparated();
|
---|
3936 | if (renderer) {
|
---|
3937 | auto box = renderer->transformReferenceBoxRect(style);
|
---|
3938 | list->append(zoomAdjustedPixelValue(minimumValueForLength(style.transformOriginX(), box.width()), style));
|
---|
3939 | list->append(zoomAdjustedPixelValue(minimumValueForLength(style.transformOriginY(), box.height()), style));
|
---|
3940 | if (style.transformOriginZ())
|
---|
3941 | list->append(zoomAdjustedPixelValue(style.transformOriginZ(), style));
|
---|
3942 | } else {
|
---|
3943 | list->append(zoomAdjustedPixelValueForLength(style.transformOriginX(), style));
|
---|
3944 | list->append(zoomAdjustedPixelValueForLength(style.transformOriginY(), style));
|
---|
3945 | if (style.transformOriginZ())
|
---|
3946 | list->append(zoomAdjustedPixelValue(style.transformOriginZ(), style));
|
---|
3947 | }
|
---|
3948 | return list;
|
---|
3949 | }
|
---|
3950 | case CSSPropertyTransformStyle:
|
---|
3951 | switch (style.transformStyle3D()) {
|
---|
3952 | case TransformStyle3D::Flat:
|
---|
3953 | return cssValuePool.createIdentifierValue(CSSValueFlat);
|
---|
3954 | case TransformStyle3D::Preserve3D:
|
---|
3955 | return cssValuePool.createIdentifierValue(CSSValuePreserve3d);
|
---|
3956 | #if ENABLE(CSS_TRANSFORM_STYLE_OPTIMIZED_3D)
|
---|
3957 | case TransformStyle3D::Optimized3D:
|
---|
3958 | return cssValuePool.createIdentifierValue(CSSValueOptimized3d);
|
---|
3959 | #endif
|
---|
3960 | }
|
---|
3961 | ASSERT_NOT_REACHED();
|
---|
3962 | return nullptr;
|
---|
3963 | case CSSPropertyTranslate:
|
---|
3964 | if (!m_element->document().settings().cssIndividualTransformPropertiesEnabled())
|
---|
3965 | return nullptr;
|
---|
3966 | return computedTranslate(renderer, style);
|
---|
3967 | case CSSPropertyScale:
|
---|
3968 | if (!m_element->document().settings().cssIndividualTransformPropertiesEnabled())
|
---|
3969 | return nullptr;
|
---|
3970 | return computedScale(renderer, style);
|
---|
3971 | case CSSPropertyRotate:
|
---|
3972 | if (!m_element->document().settings().cssIndividualTransformPropertiesEnabled())
|
---|
3973 | return nullptr;
|
---|
3974 | return computedRotate(renderer, style);
|
---|
3975 | case CSSPropertyTransitionDelay:
|
---|
3976 | case CSSPropertyTransitionDuration:
|
---|
3977 | case CSSPropertyTransitionTimingFunction:
|
---|
3978 | case CSSPropertyTransitionProperty:
|
---|
3979 | return valueListForAnimationOrTransitionProperty(propertyID, style.transitions());
|
---|
3980 | case CSSPropertyTransition:
|
---|
3981 | return animationShorthandValue(propertyID, style.transitions());
|
---|
3982 | case CSSPropertyPointerEvents:
|
---|
3983 | return cssValuePool.createValue(style.pointerEvents());
|
---|
3984 | case CSSPropertyWebkitLineGrid:
|
---|
3985 | if (style.lineGrid().isNull())
|
---|
3986 | return cssValuePool.createIdentifierValue(CSSValueNone);
|
---|
3987 | return cssValuePool.createCustomIdent(style.lineGrid());
|
---|
3988 | case CSSPropertyWebkitLineSnap:
|
---|
3989 | return CSSPrimitiveValue::create(style.lineSnap());
|
---|
3990 | case CSSPropertyWebkitLineAlign:
|
---|
3991 | return CSSPrimitiveValue::create(style.lineAlign());
|
---|
3992 | case CSSPropertyWritingMode:
|
---|
3993 | return cssValuePool.createValue(style.writingMode());
|
---|
3994 | case CSSPropertyWebkitTextCombine:
|
---|
3995 | if (style.textCombine() == TextCombine::All)
|
---|
3996 | return CSSPrimitiveValue::createIdentifier(CSSValueHorizontal);
|
---|
3997 | return cssValuePool.createValue(style.textCombine());
|
---|
3998 | case CSSPropertyTextCombineUpright:
|
---|
3999 | return cssValuePool.createValue(style.textCombine());
|
---|
4000 | case CSSPropertyWebkitTextOrientation:
|
---|
4001 | return CSSPrimitiveValue::create(style.textOrientation());
|
---|
4002 | case CSSPropertyTextOrientation:
|
---|
4003 | return CSSPrimitiveValue::create(style.textOrientation());
|
---|
4004 | case CSSPropertyWebkitLineBoxContain:
|
---|
4005 | return createLineBoxContainValue(style.lineBoxContain());
|
---|
4006 | case CSSPropertyAlt:
|
---|
4007 | return altTextToCSSValue(style);
|
---|
4008 | case CSSPropertyContent:
|
---|
4009 | return contentToCSSValue(style);
|
---|
4010 | case CSSPropertyCounterIncrement:
|
---|
4011 | return counterToCSSValue(style, propertyID);
|
---|
4012 | case CSSPropertyCounterReset:
|
---|
4013 | return counterToCSSValue(style, propertyID);
|
---|
4014 | case CSSPropertyClipPath:
|
---|
4015 | return valueForPathOperation(style, style.clipPath());
|
---|
4016 | case CSSPropertyShapeMargin:
|
---|
4017 | return cssValuePool.createValue(style.shapeMargin(), style);
|
---|
4018 | case CSSPropertyShapeImageThreshold:
|
---|
4019 | return cssValuePool.createValue(style.shapeImageThreshold(), CSSUnitType::CSS_NUMBER);
|
---|
4020 | case CSSPropertyShapeOutside:
|
---|
4021 | return shapePropertyValue(style, style.shapeOutside());
|
---|
4022 | case CSSPropertyFilter:
|
---|
4023 | return valueForFilter(style, style.filter());
|
---|
4024 | case CSSPropertyAppleColorFilter:
|
---|
4025 | return valueForFilter(style, style.appleColorFilter());
|
---|
4026 | #if ENABLE(FILTERS_LEVEL_2)
|
---|
4027 | case CSSPropertyWebkitBackdropFilter:
|
---|
4028 | return valueForFilter(style, style.backdropFilter());
|
---|
4029 | #endif
|
---|
4030 | case CSSPropertyMathStyle:
|
---|
4031 | return cssValuePool.createValue(style.mathStyle());
|
---|
4032 | #if ENABLE(CSS_COMPOSITING)
|
---|
4033 | case CSSPropertyMixBlendMode:
|
---|
4034 | return cssValuePool.createValue(style.blendMode());
|
---|
4035 | case CSSPropertyIsolation:
|
---|
4036 | return cssValuePool.createValue(style.isolation());
|
---|
4037 | #endif
|
---|
4038 | case CSSPropertyBackgroundBlendMode: {
|
---|
4039 | auto& layers = style.backgroundLayers();
|
---|
4040 | if (!layers.next())
|
---|
4041 | return cssValuePool.createValue(layers.blendMode());
|
---|
4042 | auto list = CSSValueList::createCommaSeparated();
|
---|
4043 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
4044 | list->append(cssValuePool.createValue(currLayer->blendMode()));
|
---|
4045 | return list;
|
---|
4046 | }
|
---|
4047 | case CSSPropertyBackground:
|
---|
4048 | return getBackgroundShorthandValue();
|
---|
4049 | case CSSPropertyMask:
|
---|
4050 | return getMaskShorthandValue();
|
---|
4051 | case CSSPropertyBorder: {
|
---|
4052 | auto value = propertyValue(CSSPropertyBorderTop, DoNotUpdateLayout);
|
---|
4053 | const CSSPropertyID properties[3] = { CSSPropertyBorderRight, CSSPropertyBorderBottom, CSSPropertyBorderLeft };
|
---|
4054 | for (auto& property : properties) {
|
---|
4055 | if (!compareCSSValuePtr<CSSValue>(value, propertyValue(property, DoNotUpdateLayout)))
|
---|
4056 | return nullptr;
|
---|
4057 | }
|
---|
4058 | return value;
|
---|
4059 | }
|
---|
4060 | case CSSPropertyBorderBlock: {
|
---|
4061 | auto value = propertyValue(CSSPropertyBorderBlockStart, DoNotUpdateLayout);
|
---|
4062 | if (!compareCSSValuePtr<CSSValue>(value, propertyValue(CSSPropertyBorderBlockEnd, DoNotUpdateLayout)))
|
---|
4063 | return nullptr;
|
---|
4064 | return value;
|
---|
4065 | }
|
---|
4066 | case CSSPropertyBorderBlockColor:
|
---|
4067 | return getCSSPropertyValuesFor2SidesShorthand(borderBlockColorShorthand());
|
---|
4068 | case CSSPropertyBorderBlockEnd:
|
---|
4069 | return getCSSPropertyValuesForShorthandProperties(borderBlockEndShorthand());
|
---|
4070 | case CSSPropertyBorderBlockStart:
|
---|
4071 | return getCSSPropertyValuesForShorthandProperties(borderBlockStartShorthand());
|
---|
4072 | case CSSPropertyBorderBlockStyle:
|
---|
4073 | return getCSSPropertyValuesFor2SidesShorthand(borderBlockStyleShorthand());
|
---|
4074 | case CSSPropertyBorderBlockWidth:
|
---|
4075 | return getCSSPropertyValuesFor2SidesShorthand(borderBlockWidthShorthand());
|
---|
4076 | case CSSPropertyBorderBottom:
|
---|
4077 | return getCSSPropertyValuesForShorthandProperties(borderBottomShorthand());
|
---|
4078 | case CSSPropertyBorderColor:
|
---|
4079 | return getCSSPropertyValuesFor4SidesShorthand(borderColorShorthand());
|
---|
4080 | case CSSPropertyBorderLeft:
|
---|
4081 | return getCSSPropertyValuesForShorthandProperties(borderLeftShorthand());
|
---|
4082 | case CSSPropertyBorderInline: {
|
---|
4083 | auto value = propertyValue(CSSPropertyBorderInlineStart, DoNotUpdateLayout);
|
---|
4084 | if (!compareCSSValuePtr<CSSValue>(value, propertyValue(CSSPropertyBorderInlineEnd, DoNotUpdateLayout)))
|
---|
4085 | return nullptr;
|
---|
4086 | return value;
|
---|
4087 | }
|
---|
4088 | case CSSPropertyBorderInlineColor:
|
---|
4089 | return getCSSPropertyValuesFor2SidesShorthand(borderInlineColorShorthand());
|
---|
4090 | case CSSPropertyBorderInlineEnd:
|
---|
4091 | return getCSSPropertyValuesForShorthandProperties(borderInlineEndShorthand());
|
---|
4092 | case CSSPropertyBorderInlineStart:
|
---|
4093 | return getCSSPropertyValuesForShorthandProperties(borderInlineStartShorthand());
|
---|
4094 | case CSSPropertyBorderInlineStyle:
|
---|
4095 | return getCSSPropertyValuesFor2SidesShorthand(borderInlineStyleShorthand());
|
---|
4096 | case CSSPropertyBorderInlineWidth:
|
---|
4097 | return getCSSPropertyValuesFor2SidesShorthand(borderInlineWidthShorthand());
|
---|
4098 | case CSSPropertyBorderRadius:
|
---|
4099 | return borderRadiusShorthandValue(style);
|
---|
4100 | case CSSPropertyBorderRight:
|
---|
4101 | return getCSSPropertyValuesForShorthandProperties(borderRightShorthand());
|
---|
4102 | case CSSPropertyBorderStyle:
|
---|
4103 | return getCSSPropertyValuesFor4SidesShorthand(borderStyleShorthand());
|
---|
4104 | case CSSPropertyBorderTop:
|
---|
4105 | return getCSSPropertyValuesForShorthandProperties(borderTopShorthand());
|
---|
4106 | case CSSPropertyBorderWidth:
|
---|
4107 | return getCSSPropertyValuesFor4SidesShorthand(borderWidthShorthand());
|
---|
4108 | case CSSPropertyColumnRule:
|
---|
4109 | return getCSSPropertyValuesForShorthandProperties(columnRuleShorthand());
|
---|
4110 | case CSSPropertyColumns:
|
---|
4111 | return getCSSPropertyValuesForShorthandProperties(columnsShorthand());
|
---|
4112 | case CSSPropertyInset:
|
---|
4113 | return getCSSPropertyValuesFor4SidesShorthand(insetShorthand());
|
---|
4114 | case CSSPropertyInsetBlock:
|
---|
4115 | return getCSSPropertyValuesFor2SidesShorthand(insetBlockShorthand());
|
---|
4116 | case CSSPropertyInsetInline:
|
---|
4117 | return getCSSPropertyValuesFor2SidesShorthand(insetInlineShorthand());
|
---|
4118 | case CSSPropertyListStyle:
|
---|
4119 | return getCSSPropertyValuesForShorthandProperties(listStyleShorthand());
|
---|
4120 | case CSSPropertyMargin:
|
---|
4121 | return getCSSPropertyValuesFor4SidesShorthand(marginShorthand());
|
---|
4122 | case CSSPropertyMarginBlock:
|
---|
4123 | return getCSSPropertyValuesFor2SidesShorthand(marginBlockShorthand());
|
---|
4124 | case CSSPropertyMarginInline:
|
---|
4125 | return getCSSPropertyValuesFor2SidesShorthand(marginInlineShorthand());
|
---|
4126 | case CSSPropertyOutline:
|
---|
4127 | return getCSSPropertyValuesForShorthandProperties(outlineShorthand());
|
---|
4128 | case CSSPropertyPadding:
|
---|
4129 | return getCSSPropertyValuesFor4SidesShorthand(paddingShorthand());
|
---|
4130 | case CSSPropertyPaddingBlock:
|
---|
4131 | return getCSSPropertyValuesFor2SidesShorthand(paddingBlockShorthand());
|
---|
4132 | case CSSPropertyPaddingInline:
|
---|
4133 | return getCSSPropertyValuesFor2SidesShorthand(paddingInlineShorthand());
|
---|
4134 | case CSSPropertyScrollMargin:
|
---|
4135 | return getCSSPropertyValuesFor4SidesShorthand(scrollMarginShorthand());
|
---|
4136 | case CSSPropertyScrollMarginBottom:
|
---|
4137 | return zoomAdjustedPixelValueForLength(style.scrollMarginBottom(), style);
|
---|
4138 | case CSSPropertyScrollMarginTop:
|
---|
4139 | return zoomAdjustedPixelValueForLength(style.scrollMarginTop(), style);
|
---|
4140 | case CSSPropertyScrollMarginRight:
|
---|
4141 | return zoomAdjustedPixelValueForLength(style.scrollMarginRight(), style);
|
---|
4142 | case CSSPropertyScrollMarginLeft:
|
---|
4143 | return zoomAdjustedPixelValueForLength(style.scrollMarginLeft(), style);
|
---|
4144 | case CSSPropertyScrollMarginBlock:
|
---|
4145 | return getCSSPropertyValuesFor2SidesShorthand(scrollMarginBlockShorthand());
|
---|
4146 | case CSSPropertyScrollMarginInline:
|
---|
4147 | return getCSSPropertyValuesFor2SidesShorthand(scrollMarginInlineShorthand());
|
---|
4148 | case CSSPropertyScrollPadding:
|
---|
4149 | return getCSSPropertyValuesFor4SidesShorthand(scrollPaddingShorthand());
|
---|
4150 | case CSSPropertyScrollPaddingBottom:
|
---|
4151 | return zoomAdjustedPixelValueForLength(style.scrollPaddingBottom(), style);
|
---|
4152 | case CSSPropertyScrollPaddingTop:
|
---|
4153 | return zoomAdjustedPixelValueForLength(style.scrollPaddingTop(), style);
|
---|
4154 | case CSSPropertyScrollPaddingRight:
|
---|
4155 | return zoomAdjustedPixelValueForLength(style.scrollPaddingRight(), style);
|
---|
4156 | case CSSPropertyScrollPaddingLeft:
|
---|
4157 | return zoomAdjustedPixelValueForLength(style.scrollPaddingLeft(), style);
|
---|
4158 | case CSSPropertyScrollPaddingBlock:
|
---|
4159 | return getCSSPropertyValuesFor2SidesShorthand(scrollPaddingBlockShorthand());
|
---|
4160 | case CSSPropertyScrollPaddingInline:
|
---|
4161 | return getCSSPropertyValuesFor2SidesShorthand(scrollPaddingInlineShorthand());
|
---|
4162 | case CSSPropertyScrollSnapAlign:
|
---|
4163 | return valueForScrollSnapAlignment(style.scrollSnapAlign());
|
---|
4164 | case CSSPropertyScrollSnapStop:
|
---|
4165 | return CSSPrimitiveValue::create(style.scrollSnapStop());
|
---|
4166 | case CSSPropertyScrollSnapType:
|
---|
4167 | return valueForScrollSnapType(style.scrollSnapType());
|
---|
4168 |
|
---|
4169 | #if ENABLE(CSS_TRAILING_WORD)
|
---|
4170 | case CSSPropertyAppleTrailingWord:
|
---|
4171 | return cssValuePool.createValue(style.trailingWord());
|
---|
4172 | #endif
|
---|
4173 |
|
---|
4174 | #if ENABLE(APPLE_PAY)
|
---|
4175 | case CSSPropertyApplePayButtonStyle:
|
---|
4176 | return cssValuePool.createValue(style.applePayButtonStyle());
|
---|
4177 | case CSSPropertyApplePayButtonType:
|
---|
4178 | return cssValuePool.createValue(style.applePayButtonType());
|
---|
4179 | #endif
|
---|
4180 |
|
---|
4181 | #if ENABLE(DARK_MODE_CSS)
|
---|
4182 | case CSSPropertyColorScheme: {
|
---|
4183 | auto colorScheme = style.colorScheme();
|
---|
4184 | if (colorScheme.isAuto())
|
---|
4185 | return cssValuePool.createIdentifierValue(CSSValueAuto);
|
---|
4186 |
|
---|
4187 | auto list = CSSValueList::createSpaceSeparated();
|
---|
4188 | if (colorScheme.contains(ColorScheme::Light))
|
---|
4189 | list->append(cssValuePool.createIdentifierValue(CSSValueLight));
|
---|
4190 | if (colorScheme.contains(ColorScheme::Dark))
|
---|
4191 | list->append(cssValuePool.createIdentifierValue(CSSValueDark));
|
---|
4192 | if (!colorScheme.allowsTransformations())
|
---|
4193 | list->append(cssValuePool.createIdentifierValue(CSSValueOnly));
|
---|
4194 | ASSERT(list->length());
|
---|
4195 | return list;
|
---|
4196 | }
|
---|
4197 | #endif
|
---|
4198 |
|
---|
4199 | /* Individual properties not part of the spec */
|
---|
4200 | case CSSPropertyBackgroundRepeatX:
|
---|
4201 | case CSSPropertyBackgroundRepeatY:
|
---|
4202 | break;
|
---|
4203 |
|
---|
4204 | // Length properties for SVG.
|
---|
4205 | case CSSPropertyCx:
|
---|
4206 | return zoomAdjustedPixelValueForLength(style.svgStyle().cx(), style);
|
---|
4207 | case CSSPropertyCy:
|
---|
4208 | return zoomAdjustedPixelValueForLength(style.svgStyle().cy(), style);
|
---|
4209 | case CSSPropertyR:
|
---|
4210 | return zoomAdjustedPixelValueForLength(style.svgStyle().r(), style);
|
---|
4211 | case CSSPropertyRx:
|
---|
4212 | return zoomAdjustedPixelValueForLength(style.svgStyle().rx(), style);
|
---|
4213 | case CSSPropertyRy:
|
---|
4214 | return zoomAdjustedPixelValueForLength(style.svgStyle().ry(), style);
|
---|
4215 | case CSSPropertyStrokeDashoffset:
|
---|
4216 | return zoomAdjustedPixelValueForLength(style.svgStyle().strokeDashOffset(), style);
|
---|
4217 | case CSSPropertyX:
|
---|
4218 | return zoomAdjustedPixelValueForLength(style.svgStyle().x(), style);
|
---|
4219 | case CSSPropertyY:
|
---|
4220 | return zoomAdjustedPixelValueForLength(style.svgStyle().y(), style);
|
---|
4221 | case CSSPropertyWebkitTextZoom:
|
---|
4222 | return cssValuePool.createValue(style.textZoom());
|
---|
4223 |
|
---|
4224 | case CSSPropertyPaintOrder:
|
---|
4225 | return paintOrder(style.paintOrder());
|
---|
4226 | case CSSPropertyStrokeLinecap:
|
---|
4227 | return CSSPrimitiveValue::create(style.capStyle());
|
---|
4228 | case CSSPropertyStrokeLinejoin:
|
---|
4229 | return CSSPrimitiveValue::create(style.joinStyle());
|
---|
4230 | case CSSPropertyStrokeWidth:
|
---|
4231 | return zoomAdjustedPixelValueForLength(style.strokeWidth(), style);
|
---|
4232 | case CSSPropertyStrokeColor:
|
---|
4233 | return currentColorOrValidColor(&style, style.strokeColor());
|
---|
4234 | case CSSPropertyStrokeMiterlimit:
|
---|
4235 | return CSSPrimitiveValue::create(style.strokeMiterLimit(), CSSUnitType::CSS_NUMBER);
|
---|
4236 |
|
---|
4237 | case CSSPropertyQuotes:
|
---|
4238 | return valueForQuotes(style.quotes());
|
---|
4239 |
|
---|
4240 | /* Unimplemented CSS 3 properties (including CSS3 shorthand properties) */
|
---|
4241 | case CSSPropertyAll:
|
---|
4242 | break;
|
---|
4243 |
|
---|
4244 | /* Directional properties are resolved by resolveDirectionAwareProperty() before the switch. */
|
---|
4245 | case CSSPropertyBorderBlockEndColor:
|
---|
4246 | case CSSPropertyBorderBlockEndStyle:
|
---|
4247 | case CSSPropertyBorderBlockEndWidth:
|
---|
4248 | case CSSPropertyBorderBlockStartColor:
|
---|
4249 | case CSSPropertyBorderBlockStartStyle:
|
---|
4250 | case CSSPropertyBorderBlockStartWidth:
|
---|
4251 | case CSSPropertyBorderEndEndRadius:
|
---|
4252 | case CSSPropertyBorderEndStartRadius:
|
---|
4253 | case CSSPropertyBorderInlineEndColor:
|
---|
4254 | case CSSPropertyBorderInlineEndStyle:
|
---|
4255 | case CSSPropertyBorderInlineEndWidth:
|
---|
4256 | case CSSPropertyBorderInlineStartColor:
|
---|
4257 | case CSSPropertyBorderInlineStartStyle:
|
---|
4258 | case CSSPropertyBorderInlineStartWidth:
|
---|
4259 | case CSSPropertyBorderStartEndRadius:
|
---|
4260 | case CSSPropertyBorderStartStartRadius:
|
---|
4261 | case CSSPropertyInsetBlockEnd:
|
---|
4262 | case CSSPropertyInsetBlockStart:
|
---|
4263 | case CSSPropertyInsetInlineEnd:
|
---|
4264 | case CSSPropertyInsetInlineStart:
|
---|
4265 | case CSSPropertyMarginBlockEnd:
|
---|
4266 | case CSSPropertyMarginBlockStart:
|
---|
4267 | case CSSPropertyMarginInlineEnd:
|
---|
4268 | case CSSPropertyMarginInlineStart:
|
---|
4269 | case CSSPropertyOverscrollBehaviorInline:
|
---|
4270 | case CSSPropertyOverscrollBehaviorBlock:
|
---|
4271 | case CSSPropertyPaddingBlockEnd:
|
---|
4272 | case CSSPropertyPaddingBlockStart:
|
---|
4273 | case CSSPropertyPaddingInlineEnd:
|
---|
4274 | case CSSPropertyPaddingInlineStart:
|
---|
4275 | case CSSPropertyBlockSize:
|
---|
4276 | case CSSPropertyInlineSize:
|
---|
4277 | case CSSPropertyMaxBlockSize:
|
---|
4278 | case CSSPropertyMaxInlineSize:
|
---|
4279 | case CSSPropertyMinBlockSize:
|
---|
4280 | case CSSPropertyMinInlineSize:
|
---|
4281 | case CSSPropertyScrollMarginBlockEnd:
|
---|
4282 | case CSSPropertyScrollMarginBlockStart:
|
---|
4283 | case CSSPropertyScrollMarginInlineEnd:
|
---|
4284 | case CSSPropertyScrollMarginInlineStart:
|
---|
4285 | case CSSPropertyScrollPaddingBlockEnd:
|
---|
4286 | case CSSPropertyScrollPaddingBlockStart:
|
---|
4287 | case CSSPropertyScrollPaddingInlineEnd:
|
---|
4288 | case CSSPropertyScrollPaddingInlineStart:
|
---|
4289 | case CSSPropertyContainIntrinsicBlockSize:
|
---|
4290 | case CSSPropertyContainIntrinsicInlineSize:
|
---|
4291 | ASSERT_NOT_REACHED();
|
---|
4292 | break;
|
---|
4293 |
|
---|
4294 | // These are intentionally unimplemented because they are actually descriptors for @counter-style.
|
---|
4295 | case CSSPropertySystem:
|
---|
4296 | case CSSPropertyNegative:
|
---|
4297 | case CSSPropertyPrefix:
|
---|
4298 | case CSSPropertySuffix:
|
---|
4299 | case CSSPropertyRange:
|
---|
4300 | case CSSPropertyPad:
|
---|
4301 | case CSSPropertyFallback:
|
---|
4302 | case CSSPropertySymbols:
|
---|
4303 | case CSSPropertyAdditiveSymbols:
|
---|
4304 | break;
|
---|
4305 |
|
---|
4306 | /* Unimplemented @font-face properties */
|
---|
4307 | case CSSPropertySrc:
|
---|
4308 | case CSSPropertyUnicodeRange:
|
---|
4309 | case CSSPropertyFontDisplay:
|
---|
4310 | break;
|
---|
4311 |
|
---|
4312 | // Unimplemented @font-palette-values properties
|
---|
4313 | case CSSPropertyBasePalette:
|
---|
4314 | case CSSPropertyOverrideColors:
|
---|
4315 | break;
|
---|
4316 |
|
---|
4317 | /* Other unimplemented properties */
|
---|
4318 | case CSSPropertyPage: // for @page
|
---|
4319 | case CSSPropertySize: // for @page
|
---|
4320 | break;
|
---|
4321 |
|
---|
4322 | /* Unimplemented -webkit- properties */
|
---|
4323 | case CSSPropertyWebkitBorderRadius:
|
---|
4324 | case CSSPropertyWebkitMarqueeDirection:
|
---|
4325 | case CSSPropertyWebkitMarqueeIncrement:
|
---|
4326 | case CSSPropertyWebkitMarqueeRepetition:
|
---|
4327 | case CSSPropertyWebkitMarqueeStyle:
|
---|
4328 | case CSSPropertyWebkitMarqueeSpeed:
|
---|
4329 | case CSSPropertyWebkitMask:
|
---|
4330 | case CSSPropertyMaskRepeatX:
|
---|
4331 | case CSSPropertyMaskRepeatY:
|
---|
4332 | case CSSPropertyPerspectiveOriginX:
|
---|
4333 | case CSSPropertyPerspectiveOriginY:
|
---|
4334 | case CSSPropertyWebkitTextStroke:
|
---|
4335 | case CSSPropertyTransformOriginX:
|
---|
4336 | case CSSPropertyTransformOriginY:
|
---|
4337 | case CSSPropertyTransformOriginZ:
|
---|
4338 | break;
|
---|
4339 |
|
---|
4340 | case CSSPropertyBufferedRendering:
|
---|
4341 | case CSSPropertyClipRule:
|
---|
4342 | case CSSPropertyFloodColor:
|
---|
4343 | case CSSPropertyFloodOpacity:
|
---|
4344 | case CSSPropertyLightingColor:
|
---|
4345 | case CSSPropertyStopColor:
|
---|
4346 | case CSSPropertyStopOpacity:
|
---|
4347 | case CSSPropertyColorInterpolation:
|
---|
4348 | case CSSPropertyColorInterpolationFilters:
|
---|
4349 | case CSSPropertyFill:
|
---|
4350 | case CSSPropertyFillOpacity:
|
---|
4351 | case CSSPropertyFillRule:
|
---|
4352 | case CSSPropertyMarker:
|
---|
4353 | case CSSPropertyMarkerEnd:
|
---|
4354 | case CSSPropertyMarkerMid:
|
---|
4355 | case CSSPropertyMarkerStart:
|
---|
4356 | case CSSPropertyMaskType:
|
---|
4357 | case CSSPropertyShapeRendering:
|
---|
4358 | case CSSPropertyStroke:
|
---|
4359 | case CSSPropertyStrokeDasharray:
|
---|
4360 | case CSSPropertyStrokeOpacity:
|
---|
4361 | case CSSPropertyAlignmentBaseline:
|
---|
4362 | case CSSPropertyBaselineShift:
|
---|
4363 | case CSSPropertyDominantBaseline:
|
---|
4364 | case CSSPropertyGlyphOrientationHorizontal:
|
---|
4365 | case CSSPropertyGlyphOrientationVertical:
|
---|
4366 | case CSSPropertyKerning:
|
---|
4367 | case CSSPropertyTextAnchor:
|
---|
4368 | case CSSPropertyVectorEffect:
|
---|
4369 | return svgPropertyValue(propertyID);
|
---|
4370 | case CSSPropertyCustom:
|
---|
4371 | ASSERT_NOT_REACHED();
|
---|
4372 | return nullptr;
|
---|
4373 | }
|
---|
4374 |
|
---|
4375 | return nullptr;
|
---|
4376 | }
|
---|
4377 |
|
---|
4378 | String CSSComputedStyleDeclaration::getPropertyValue(CSSPropertyID propertyID) const
|
---|
4379 | {
|
---|
4380 | auto value = getPropertyCSSValue(propertyID);
|
---|
4381 | if (!value)
|
---|
4382 | return emptyString(); // FIXME: Should this be null instead, as it is in StyleProperties::getPropertyValue?
|
---|
4383 | return value->cssText();
|
---|
4384 | }
|
---|
4385 |
|
---|
4386 | unsigned CSSComputedStyleDeclaration::length() const
|
---|
4387 | {
|
---|
4388 | updateStyleIfNeededForProperty(m_element.get(), CSSPropertyCustom);
|
---|
4389 |
|
---|
4390 | auto* style = m_element->computedStyle(m_pseudoElementSpecifier);
|
---|
4391 | if (!style)
|
---|
4392 | return 0;
|
---|
4393 |
|
---|
4394 | return numComputedPropertyIDs + style->inheritedCustomProperties().size() + style->nonInheritedCustomProperties().size();
|
---|
4395 | }
|
---|
4396 |
|
---|
4397 | String CSSComputedStyleDeclaration::item(unsigned i) const
|
---|
4398 | {
|
---|
4399 | if (i >= length())
|
---|
4400 | return String();
|
---|
4401 |
|
---|
4402 | if (i < numComputedPropertyIDs)
|
---|
4403 | return getPropertyNameString(computedPropertyIDs[i]);
|
---|
4404 |
|
---|
4405 | auto* style = m_element->computedStyle(m_pseudoElementSpecifier);
|
---|
4406 | if (!style)
|
---|
4407 | return String();
|
---|
4408 |
|
---|
4409 | const auto& inheritedCustomProperties = style->inheritedCustomProperties();
|
---|
4410 |
|
---|
4411 | if (i < numComputedPropertyIDs + inheritedCustomProperties.size()) {
|
---|
4412 | auto results = copyToVector(inheritedCustomProperties.keys());
|
---|
4413 | return results.at(i - numComputedPropertyIDs);
|
---|
4414 | }
|
---|
4415 |
|
---|
4416 | const auto& nonInheritedCustomProperties = style->nonInheritedCustomProperties();
|
---|
4417 | auto results = copyToVector(nonInheritedCustomProperties.keys());
|
---|
4418 | return results.at(i - inheritedCustomProperties.size() - numComputedPropertyIDs);
|
---|
4419 | }
|
---|
4420 |
|
---|
4421 | bool ComputedStyleExtractor::propertyMatches(CSSPropertyID propertyID, const CSSValue* value)
|
---|
4422 | {
|
---|
4423 | if (!m_element)
|
---|
4424 | return false;
|
---|
4425 | if (propertyID == CSSPropertyFontSize && is<CSSPrimitiveValue>(*value)) {
|
---|
4426 | m_element->document().updateLayoutIgnorePendingStylesheets();
|
---|
4427 | if (auto* style = m_element->computedStyle(m_pseudoElementSpecifier)) {
|
---|
4428 | if (CSSValueID sizeIdentifier = style->fontDescription().keywordSizeAsIdentifier()) {
|
---|
4429 | auto& primitiveValue = downcast<CSSPrimitiveValue>(*value);
|
---|
4430 | if (primitiveValue.isValueID() && primitiveValue.valueID() == sizeIdentifier)
|
---|
4431 | return true;
|
---|
4432 | }
|
---|
4433 | }
|
---|
4434 | }
|
---|
4435 | RefPtr<CSSValue> computedValue = propertyValue(propertyID);
|
---|
4436 | return computedValue && value && computedValue->equals(*value);
|
---|
4437 | }
|
---|
4438 |
|
---|
4439 | Ref<CSSValueList> ComputedStyleExtractor::getCSSPropertyValuesForShorthandProperties(const StylePropertyShorthand& shorthand)
|
---|
4440 | {
|
---|
4441 | auto list = CSSValueList::createSpaceSeparated();
|
---|
4442 | for (size_t i = 0; i < shorthand.length(); ++i)
|
---|
4443 | list->append(propertyValue(shorthand.properties()[i], DoNotUpdateLayout).releaseNonNull());
|
---|
4444 | return list;
|
---|
4445 | }
|
---|
4446 |
|
---|
4447 | RefPtr<CSSValueList> ComputedStyleExtractor::getCSSPropertyValuesFor2SidesShorthand(const StylePropertyShorthand& shorthand)
|
---|
4448 | {
|
---|
4449 | auto list = CSSValueList::createSpaceSeparated();
|
---|
4450 |
|
---|
4451 | // Assume the properties are in the usual order start, end.
|
---|
4452 | auto startValue = propertyValue(shorthand.properties()[0], DoNotUpdateLayout);
|
---|
4453 | auto endValue = propertyValue(shorthand.properties()[1], DoNotUpdateLayout);
|
---|
4454 |
|
---|
4455 | // All 2 properties must be specified.
|
---|
4456 | if (!startValue || !endValue)
|
---|
4457 | return nullptr;
|
---|
4458 |
|
---|
4459 | bool showEnd = !compareCSSValuePtr(startValue, endValue);
|
---|
4460 |
|
---|
4461 | list->append(startValue.releaseNonNull());
|
---|
4462 | if (showEnd)
|
---|
4463 | list->append(endValue.releaseNonNull());
|
---|
4464 |
|
---|
4465 | return list;
|
---|
4466 | }
|
---|
4467 |
|
---|
4468 | RefPtr<CSSValueList> ComputedStyleExtractor::getCSSPropertyValuesFor4SidesShorthand(const StylePropertyShorthand& shorthand)
|
---|
4469 | {
|
---|
4470 | auto list = CSSValueList::createSpaceSeparated();
|
---|
4471 |
|
---|
4472 | // Assume the properties are in the usual order top, right, bottom, left.
|
---|
4473 | auto topValue = propertyValue(shorthand.properties()[0], DoNotUpdateLayout);
|
---|
4474 | auto rightValue = propertyValue(shorthand.properties()[1], DoNotUpdateLayout);
|
---|
4475 | auto bottomValue = propertyValue(shorthand.properties()[2], DoNotUpdateLayout);
|
---|
4476 | auto leftValue = propertyValue(shorthand.properties()[3], DoNotUpdateLayout);
|
---|
4477 |
|
---|
4478 | // All 4 properties must be specified.
|
---|
4479 | if (!topValue || !rightValue || !bottomValue || !leftValue)
|
---|
4480 | return nullptr;
|
---|
4481 |
|
---|
4482 | bool showLeft = !compareCSSValuePtr(rightValue, leftValue);
|
---|
4483 | bool showBottom = !compareCSSValuePtr(topValue, bottomValue) || showLeft;
|
---|
4484 | bool showRight = !compareCSSValuePtr(topValue, rightValue) || showBottom;
|
---|
4485 |
|
---|
4486 | list->append(topValue.releaseNonNull());
|
---|
4487 | if (showRight)
|
---|
4488 | list->append(rightValue.releaseNonNull());
|
---|
4489 | if (showBottom)
|
---|
4490 | list->append(bottomValue.releaseNonNull());
|
---|
4491 | if (showLeft)
|
---|
4492 | list->append(leftValue.releaseNonNull());
|
---|
4493 |
|
---|
4494 | return list;
|
---|
4495 | }
|
---|
4496 |
|
---|
4497 | Ref<CSSValueList> ComputedStyleExtractor::getCSSPropertyValuesForGridShorthand(const StylePropertyShorthand& shorthand)
|
---|
4498 | {
|
---|
4499 | auto list = CSSValueList::createSlashSeparated();
|
---|
4500 | for (size_t i = 0; i < shorthand.length(); ++i)
|
---|
4501 | list->append(propertyValue(shorthand.properties()[i], DoNotUpdateLayout).releaseNonNull());
|
---|
4502 | return list;
|
---|
4503 | }
|
---|
4504 |
|
---|
4505 | Ref<MutableStyleProperties> ComputedStyleExtractor::copyPropertiesInSet(const CSSPropertyID* set, unsigned length)
|
---|
4506 | {
|
---|
4507 | Vector<CSSProperty> list;
|
---|
4508 | list.reserveInitialCapacity(length);
|
---|
4509 | for (unsigned i = 0; i < length; ++i) {
|
---|
4510 | if (auto value = propertyValue(set[i]))
|
---|
4511 | list.uncheckedAppend(CSSProperty(set[i], WTFMove(value), false));
|
---|
4512 | }
|
---|
4513 | list.shrinkToFit();
|
---|
4514 | return MutableStyleProperties::create(WTFMove(list));
|
---|
4515 | }
|
---|
4516 |
|
---|
4517 | Ref<MutableStyleProperties> ComputedStyleExtractor::copyProperties()
|
---|
4518 | {
|
---|
4519 | Vector<CSSProperty> list;
|
---|
4520 | list.reserveInitialCapacity(numCSSProperties);
|
---|
4521 | for (unsigned i = firstCSSProperty; i < lastCSSProperty; ++i) {
|
---|
4522 | auto propertyID = convertToCSSPropertyID(i);
|
---|
4523 | if (auto value = propertyValue(propertyID))
|
---|
4524 | list.append(CSSProperty(propertyID, WTFMove(value)));
|
---|
4525 | }
|
---|
4526 | list.shrinkToFit();
|
---|
4527 | return MutableStyleProperties::create(WTFMove(list));
|
---|
4528 | }
|
---|
4529 |
|
---|
4530 | CSSRule* CSSComputedStyleDeclaration::parentRule() const
|
---|
4531 | {
|
---|
4532 | return nullptr;
|
---|
4533 | }
|
---|
4534 |
|
---|
4535 | RefPtr<DeprecatedCSSOMValue> CSSComputedStyleDeclaration::getPropertyCSSValue(const String& propertyName)
|
---|
4536 | {
|
---|
4537 | if (isCustomPropertyName(propertyName)) {
|
---|
4538 | auto value = ComputedStyleExtractor(m_element.ptr(), m_allowVisitedStyle, m_pseudoElementSpecifier).customPropertyValue(AtomString { propertyName });
|
---|
4539 | if (!value)
|
---|
4540 | return nullptr;
|
---|
4541 | return value->createDeprecatedCSSOMWrapper(*this);
|
---|
4542 | }
|
---|
4543 |
|
---|
4544 | CSSPropertyID propertyID = cssPropertyID(propertyName);
|
---|
4545 | if (!propertyID)
|
---|
4546 | return nullptr;
|
---|
4547 | auto value = getPropertyCSSValue(propertyID);
|
---|
4548 | if (!value)
|
---|
4549 | return nullptr;
|
---|
4550 | return value->createDeprecatedCSSOMWrapper(*this);
|
---|
4551 | }
|
---|
4552 |
|
---|
4553 | String CSSComputedStyleDeclaration::getPropertyValue(const String &propertyName)
|
---|
4554 | {
|
---|
4555 | if (isCustomPropertyName(propertyName))
|
---|
4556 | return ComputedStyleExtractor(m_element.ptr(), m_allowVisitedStyle, m_pseudoElementSpecifier).customPropertyText(AtomString { propertyName });
|
---|
4557 |
|
---|
4558 | CSSPropertyID propertyID = cssPropertyID(propertyName);
|
---|
4559 | if (!propertyID)
|
---|
4560 | return String();
|
---|
4561 | return getPropertyValue(propertyID);
|
---|
4562 | }
|
---|
4563 |
|
---|
4564 | String CSSComputedStyleDeclaration::getPropertyPriority(const String&)
|
---|
4565 | {
|
---|
4566 | // All computed styles have a priority of not "important".
|
---|
4567 | return emptyString();
|
---|
4568 | }
|
---|
4569 |
|
---|
4570 | String CSSComputedStyleDeclaration::getPropertyShorthand(const String&)
|
---|
4571 | {
|
---|
4572 | return emptyString(); // FIXME: Should this sometimes be null instead of empty, to match a normal style declaration?
|
---|
4573 | }
|
---|
4574 |
|
---|
4575 | bool CSSComputedStyleDeclaration::isPropertyImplicit(const String&)
|
---|
4576 | {
|
---|
4577 | return false;
|
---|
4578 | }
|
---|
4579 |
|
---|
4580 | ExceptionOr<void> CSSComputedStyleDeclaration::setProperty(const String&, const String&, const String&)
|
---|
4581 | {
|
---|
4582 | return Exception { NoModificationAllowedError };
|
---|
4583 | }
|
---|
4584 |
|
---|
4585 | ExceptionOr<String> CSSComputedStyleDeclaration::removeProperty(const String&)
|
---|
4586 | {
|
---|
4587 | return Exception { NoModificationAllowedError };
|
---|
4588 | }
|
---|
4589 |
|
---|
4590 | RefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValueInternal(CSSPropertyID propertyID)
|
---|
4591 | {
|
---|
4592 | return getPropertyCSSValue(propertyID);
|
---|
4593 | }
|
---|
4594 |
|
---|
4595 | String CSSComputedStyleDeclaration::getPropertyValueInternal(CSSPropertyID propertyID)
|
---|
4596 | {
|
---|
4597 | return getPropertyValue(propertyID);
|
---|
4598 | }
|
---|
4599 |
|
---|
4600 | ExceptionOr<void> CSSComputedStyleDeclaration::setPropertyInternal(CSSPropertyID, const String&, bool)
|
---|
4601 | {
|
---|
4602 | return Exception { NoModificationAllowedError };
|
---|
4603 | }
|
---|
4604 |
|
---|
4605 | size_t ComputedStyleExtractor::getLayerCount(CSSPropertyID property)
|
---|
4606 | {
|
---|
4607 | ASSERT(property == CSSPropertyBackground || property == CSSPropertyMask);
|
---|
4608 | if (!m_element)
|
---|
4609 | return 0;
|
---|
4610 |
|
---|
4611 | std::unique_ptr<RenderStyle> ownedStyle;
|
---|
4612 | const RenderStyle* style = computeRenderStyleForProperty(*m_element, m_pseudoElementSpecifier, property, ownedStyle, nullptr);
|
---|
4613 | if (!style)
|
---|
4614 | return 0;
|
---|
4615 |
|
---|
4616 | auto& layers = property == CSSPropertyMask ? style->maskLayers() : style->backgroundLayers();
|
---|
4617 |
|
---|
4618 | size_t layerCount = 0;
|
---|
4619 | for (auto* currLayer = &layers; currLayer; currLayer = currLayer->next())
|
---|
4620 | layerCount++;
|
---|
4621 | if (layerCount == 1 && property == CSSPropertyMask && !layers.image())
|
---|
4622 | return 0;
|
---|
4623 | return layerCount;
|
---|
4624 | }
|
---|
4625 |
|
---|
4626 | Ref<CSSValue> ComputedStyleExtractor::getFillLayerPropertyShorthandValue(CSSPropertyID property, const StylePropertyShorthand& propertiesBeforeSlashSeparator, const StylePropertyShorthand& propertiesAfterSlashSeparator, CSSPropertyID lastLayerProperty)
|
---|
4627 | {
|
---|
4628 | ASSERT(property == CSSPropertyBackground || property == CSSPropertyMask);
|
---|
4629 | size_t layerCount = getLayerCount(property);
|
---|
4630 | if (!layerCount) {
|
---|
4631 | ASSERT(property == CSSPropertyMask);
|
---|
4632 | return CSSValuePool::singleton().createIdentifierValue(CSSValueNone);
|
---|
4633 | }
|
---|
4634 |
|
---|
4635 | auto lastValue = lastLayerProperty != CSSPropertyInvalid ? propertyValue(lastLayerProperty, DoNotUpdateLayout) : nullptr;
|
---|
4636 | auto before = getCSSPropertyValuesForShorthandProperties(propertiesBeforeSlashSeparator);
|
---|
4637 | auto after = getCSSPropertyValuesForShorthandProperties(propertiesAfterSlashSeparator);
|
---|
4638 |
|
---|
4639 | // The computed properties are returned as lists of properties, with a list of layers in each.
|
---|
4640 | // We want to swap that around to have a list of layers, with a list of properties in each.
|
---|
4641 |
|
---|
4642 | auto layers = CSSValueList::createCommaSeparated();
|
---|
4643 |
|
---|
4644 | for (size_t i = 0; i < layerCount; i++) {
|
---|
4645 | auto list = CSSValueList::createSlashSeparated();
|
---|
4646 | auto beforeList = CSSValueList::createSpaceSeparated();
|
---|
4647 |
|
---|
4648 | if (i == layerCount - 1 && lastValue)
|
---|
4649 | beforeList->append(*lastValue);
|
---|
4650 |
|
---|
4651 | for (size_t j = 0; j < propertiesBeforeSlashSeparator.length(); j++) {
|
---|
4652 | auto& value = *before->item(j);
|
---|
4653 | beforeList->append(layerCount == 1 ? value : *downcast<CSSValueList>(value).item(i));
|
---|
4654 | }
|
---|
4655 | list->append(beforeList);
|
---|
4656 |
|
---|
4657 | auto afterList = CSSValueList::createSpaceSeparated();
|
---|
4658 | for (size_t j = 0; j < propertiesAfterSlashSeparator.length(); j++) {
|
---|
4659 | auto& value = *after->item(j);
|
---|
4660 | afterList->append(layerCount == 1 ? value : *downcast<CSSValueList>(value).item(i));
|
---|
4661 | }
|
---|
4662 | list->append(afterList);
|
---|
4663 |
|
---|
4664 | if (layerCount == 1)
|
---|
4665 | return list;
|
---|
4666 |
|
---|
4667 | layers->append(list);
|
---|
4668 | }
|
---|
4669 |
|
---|
4670 | return layers;
|
---|
4671 | }
|
---|
4672 |
|
---|
4673 |
|
---|
4674 | Ref<CSSValue> ComputedStyleExtractor::getBackgroundShorthandValue()
|
---|
4675 | {
|
---|
4676 | static const CSSPropertyID propertiesBeforeSlashSeparator[] = { CSSPropertyBackgroundImage, CSSPropertyBackgroundRepeat, CSSPropertyBackgroundAttachment, CSSPropertyBackgroundPosition };
|
---|
4677 | static const CSSPropertyID propertiesAfterSlashSeparator[] = { CSSPropertyBackgroundSize, CSSPropertyBackgroundOrigin, CSSPropertyBackgroundClip };
|
---|
4678 |
|
---|
4679 | return getFillLayerPropertyShorthandValue(CSSPropertyBackground, StylePropertyShorthand(CSSPropertyBackground, propertiesBeforeSlashSeparator), StylePropertyShorthand(CSSPropertyBackground, propertiesAfterSlashSeparator), CSSPropertyBackgroundColor);
|
---|
4680 | }
|
---|
4681 |
|
---|
4682 | Ref<CSSValue> ComputedStyleExtractor::getMaskShorthandValue()
|
---|
4683 | {
|
---|
4684 | static const CSSPropertyID propertiesBeforeSlashSeperator[2] = { CSSPropertyMaskImage, CSSPropertyMaskPosition };
|
---|
4685 | static const CSSPropertyID propertiesAfterSlashSeperator[6] = { CSSPropertyMaskSize, CSSPropertyMaskRepeat, CSSPropertyMaskOrigin, CSSPropertyMaskClip, CSSPropertyMaskComposite, CSSPropertyMaskMode };
|
---|
4686 |
|
---|
4687 | return getFillLayerPropertyShorthandValue(CSSPropertyMask, StylePropertyShorthand(CSSPropertyMask, propertiesBeforeSlashSeperator), StylePropertyShorthand(CSSPropertyMask, propertiesAfterSlashSeperator), CSSPropertyInvalid);
|
---|
4688 | }
|
---|
4689 |
|
---|
4690 | } // namespace WebCore
|
---|