OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) | 2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) |
3 * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com) | 3 * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com) |
4 * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com) | 4 * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com) |
5 * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All r
ights reserved. | 5 * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All r
ights reserved. |
6 * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org> | 6 * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org> |
7 * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org> | 7 * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org> |
8 * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.t
orchmobile.com/) | 8 * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.t
orchmobile.com/) |
9 * Copyright (c) 2011, Code Aurora Forum. All rights reserved. | 9 * Copyright (c) 2011, Code Aurora Forum. All rights reserved. |
10 * Copyright (C) Research In Motion Limited 2011. All rights reserved. | 10 * Copyright (C) Research In Motion Limited 2011. All rights reserved. |
(...skipping 14 matching lines...) Expand all Loading... |
25 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, | 25 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, |
26 * Boston, MA 02110-1301, USA. | 26 * Boston, MA 02110-1301, USA. |
27 */ | 27 */ |
28 | 28 |
29 #include "config.h" | 29 #include "config.h" |
30 #include "core/css/RuleFeature.h" | 30 #include "core/css/RuleFeature.h" |
31 | 31 |
32 #include "core/HTMLNames.h" | 32 #include "core/HTMLNames.h" |
33 #include "core/css/CSSSelector.h" | 33 #include "core/css/CSSSelector.h" |
34 #include "core/css/CSSSelectorList.h" | 34 #include "core/css/CSSSelectorList.h" |
| 35 #include "core/css/CSSValueList.h" |
35 #include "core/css/RuleSet.h" | 36 #include "core/css/RuleSet.h" |
| 37 #include "core/css/StylePropertySet.h" |
36 #include "core/css/StyleRule.h" | 38 #include "core/css/StyleRule.h" |
37 #include "core/css/invalidation/DescendantInvalidationSet.h" | 39 #include "core/css/invalidation/DescendantInvalidationSet.h" |
38 #include "core/dom/Element.h" | 40 #include "core/dom/Element.h" |
39 #include "core/dom/Node.h" | 41 #include "core/dom/Node.h" |
40 #include "core/inspector/InspectorTraceEvents.h" | 42 #include "core/inspector/InspectorTraceEvents.h" |
41 #include "wtf/BitVector.h" | 43 #include "wtf/BitVector.h" |
42 | 44 |
43 namespace blink { | 45 namespace blink { |
44 | 46 |
45 #if ENABLE(ASSERT) | 47 #if ENABLE(ASSERT) |
(...skipping 168 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
214 if (selector.match() == CSSSelector::Tag && selector.tagQName().localName()
!= starAtom) | 216 if (selector.match() == CSSSelector::Tag && selector.tagQName().localName()
!= starAtom) |
215 features.tagName = selector.tagQName().localName(); | 217 features.tagName = selector.tagQName().localName(); |
216 else if (selector.match() == CSSSelector::Id) | 218 else if (selector.match() == CSSSelector::Id) |
217 features.id = selector.value(); | 219 features.id = selector.value(); |
218 else if (selector.match() == CSSSelector::Class) | 220 else if (selector.match() == CSSSelector::Class) |
219 features.classes.append(selector.value()); | 221 features.classes.append(selector.value()); |
220 else if (selector.isAttributeSelector()) | 222 else if (selector.isAttributeSelector()) |
221 features.attributes.append(selector.attribute().localName()); | 223 features.attributes.append(selector.attribute().localName()); |
222 else if (selector.isCustomPseudoElement()) | 224 else if (selector.isCustomPseudoElement()) |
223 features.customPseudoElement = true; | 225 features.customPseudoElement = true; |
| 226 else if (selector.pseudoType() == CSSSelector::PseudoBefore || selector.pseu
doType() == CSSSelector::PseudoAfter) |
| 227 features.hasBeforeOrAfter = true; |
224 else | 228 else |
225 return false; | 229 return false; |
226 return true; | 230 return true; |
227 } | 231 } |
228 | 232 |
229 RuleFeatureSet::RuleFeatureSet() | 233 RuleFeatureSet::RuleFeatureSet() |
230 { | 234 { |
231 } | 235 } |
232 | 236 |
233 RuleFeatureSet::~RuleFeatureSet() | 237 RuleFeatureSet::~RuleFeatureSet() |
(...skipping 27 matching lines...) Expand all Loading... |
261 case CSSSelector::PseudoIndeterminate: | 265 case CSSSelector::PseudoIndeterminate: |
262 case CSSSelector::PseudoTarget: | 266 case CSSSelector::PseudoTarget: |
263 return &ensurePseudoInvalidationSet(selector.pseudoType()); | 267 return &ensurePseudoInvalidationSet(selector.pseudoType()); |
264 default: | 268 default: |
265 break; | 269 break; |
266 } | 270 } |
267 } | 271 } |
268 return nullptr; | 272 return nullptr; |
269 } | 273 } |
270 | 274 |
271 // Given a selector, update the descendant invalidation sets for the features fo
und | 275 // Given a rule, update the descendant invalidation sets for the features found |
272 // in the selector. The first step is to extract the features from the rightmost | 276 // in its selector. The first step is to extract the features from the rightmost |
273 // compound selector (extractInvalidationSetFeatures). Secondly, add those featu
res | 277 // compound selector (extractInvalidationSetFeatures). Secondly, add those featu
res |
274 // to the invalidation sets for the features found in the other compound selecto
rs | 278 // to the invalidation sets for the features found in the other compound selecto
rs |
275 // (addFeaturesToInvalidationSets). If we find a feature in the right-most compo
und | 279 // (addFeaturesToInvalidationSets). If we find a feature in the right-most compo
und |
276 // selector that requires a subtree recalc, we addFeaturesToInvalidationSets for
the | 280 // selector that requires a subtree recalc, we addFeaturesToInvalidationSets for
the |
277 // rightmost compound selector as well. | 281 // rightmost compound selector as well. |
278 | 282 |
279 void RuleFeatureSet::updateInvalidationSets(const CSSSelector& selector) | 283 void RuleFeatureSet::updateInvalidationSets(const RuleData& ruleData) |
280 { | 284 { |
281 InvalidationSetFeatures features; | 285 InvalidationSetFeatures features; |
282 auto result = extractInvalidationSetFeatures(selector, features, false); | 286 auto result = extractInvalidationSetFeatures(ruleData.selector(), features,
false); |
283 if (result.first) { | 287 if (result.first) { |
284 features.forceSubtree = result.second == ForceSubtree; | 288 features.forceSubtree = result.second == ForceSubtree; |
285 addFeaturesToInvalidationSets(*result.first, features); | 289 addFeaturesToInvalidationSets(*result.first, features); |
286 } | 290 } |
| 291 |
| 292 // If any ::before and ::after rules specify 'content: attr(...)', we |
| 293 // need to create invalidation sets for those attributes. |
| 294 if (features.hasBeforeOrAfter) |
| 295 updateInvalidationSetsForContentAttribute(ruleData); |
| 296 } |
| 297 |
| 298 void RuleFeatureSet::updateInvalidationSetsForContentAttribute(const RuleData& r
uleData) |
| 299 { |
| 300 const StylePropertySet& propertySet = ruleData.rule()->properties(); |
| 301 |
| 302 int propertyIndex = propertySet.findPropertyIndex(CSSPropertyContent); |
| 303 |
| 304 if (propertyIndex == -1) |
| 305 return; |
| 306 |
| 307 StylePropertySet::PropertyReference contentProperty = propertySet.propertyAt
(propertyIndex); |
| 308 CSSValue* contentValue = contentProperty.value(); |
| 309 |
| 310 if (!contentValue->isValueList()) |
| 311 return; |
| 312 |
| 313 for (CSSValueListIterator i = contentValue; i.hasMore(); i.advance()) { |
| 314 CSSValue* item = i.value(); |
| 315 if (!item->isPrimitiveValue()) |
| 316 continue; |
| 317 CSSPrimitiveValue* primitiveItem = toCSSPrimitiveValue(item); |
| 318 if (!primitiveItem->isAttr()) |
| 319 continue; |
| 320 ensureAttributeInvalidationSet(AtomicString(primitiveItem->getStringValu
e())); |
| 321 } |
287 } | 322 } |
288 | 323 |
289 std::pair<const CSSSelector*, RuleFeatureSet::UseFeaturesType> | 324 std::pair<const CSSSelector*, RuleFeatureSet::UseFeaturesType> |
290 RuleFeatureSet::extractInvalidationSetFeatures(const CSSSelector& selector, Inva
lidationSetFeatures& features, bool negated) | 325 RuleFeatureSet::extractInvalidationSetFeatures(const CSSSelector& selector, Inva
lidationSetFeatures& features, bool negated) |
291 { | 326 { |
292 bool foundFeatures = false; | 327 bool foundFeatures = false; |
293 for (const CSSSelector* current = &selector; current; current = current->tag
History()) { | 328 for (const CSSSelector* current = &selector; current; current = current->tag
History()) { |
294 if (!negated) | 329 if (!negated) |
295 foundFeatures |= extractInvalidationSetFeature(*current, features); | 330 foundFeatures |= extractInvalidationSetFeature(*current, features); |
296 // Initialize the entry in the invalidation set map, if supported. | 331 // Initialize the entry in the invalidation set map, if supported. |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
385 if (current->relation() == CSSSelector::SubSelector) | 420 if (current->relation() == CSSSelector::SubSelector) |
386 continue; | 421 continue; |
387 | 422 |
388 if (current->isShadowSelector()) | 423 if (current->isShadowSelector()) |
389 features.treeBoundaryCrossing = true; | 424 features.treeBoundaryCrossing = true; |
390 | 425 |
391 features.adjacent = current->isAdjacentSelector(); | 426 features.adjacent = current->isAdjacentSelector(); |
392 } | 427 } |
393 } | 428 } |
394 | 429 |
395 void RuleFeatureSet::addContentAttr(const AtomicString& attributeName) | |
396 { | |
397 ensureAttributeInvalidationSet(attributeName); | |
398 } | |
399 | |
400 void RuleFeatureSet::collectFeaturesFromRuleData(const RuleData& ruleData) | 430 void RuleFeatureSet::collectFeaturesFromRuleData(const RuleData& ruleData) |
401 { | 431 { |
402 updateInvalidationSets(ruleData.selector()); | 432 updateInvalidationSets(ruleData); |
403 | 433 |
404 FeatureMetadata metadata; | 434 FeatureMetadata metadata; |
405 collectFeaturesFromSelector(ruleData.selector(), metadata); | 435 collectFeaturesFromSelector(ruleData.selector(), metadata); |
406 m_metadata.add(metadata); | 436 m_metadata.add(metadata); |
407 | 437 |
408 if (metadata.foundSiblingSelector) | 438 if (metadata.foundSiblingSelector) |
409 siblingRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex(
), ruleData.hasDocumentSecurityOrigin())); | 439 siblingRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex(
), ruleData.hasDocumentSecurityOrigin())); |
410 if (ruleData.containsUncommonAttributeSelector()) | 440 if (ruleData.containsUncommonAttributeSelector()) |
411 uncommonAttributeRules.append(RuleFeature(ruleData.rule(), ruleData.sele
ctorIndex(), ruleData.hasDocumentSecurityOrigin())); | 441 uncommonAttributeRules.append(RuleFeature(ruleData.rule(), ruleData.sele
ctorIndex(), ruleData.hasDocumentSecurityOrigin())); |
412 } | 442 } |
(...skipping 197 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
610 visitor->trace(uncommonAttributeRules); | 640 visitor->trace(uncommonAttributeRules); |
611 visitor->trace(m_classInvalidationSets); | 641 visitor->trace(m_classInvalidationSets); |
612 visitor->trace(m_attributeInvalidationSets); | 642 visitor->trace(m_attributeInvalidationSets); |
613 visitor->trace(m_idInvalidationSets); | 643 visitor->trace(m_idInvalidationSets); |
614 visitor->trace(m_pseudoInvalidationSets); | 644 visitor->trace(m_pseudoInvalidationSets); |
615 visitor->trace(m_styleInvalidator); | 645 visitor->trace(m_styleInvalidator); |
616 #endif | 646 #endif |
617 } | 647 } |
618 | 648 |
619 } // namespace blink | 649 } // namespace blink |
OLD | NEW |