1/* 2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org) 3 * Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved. 4 * 5 * This library is free software; you can redistribute it and/or 6 * modify it under the terms of the GNU Library General Public 7 * License as published by the Free Software Foundation; either 8 * version 2 of the License, or (at your option) any later version. 9 * 10 * This library is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 * Library General Public License for more details. 14 * 15 * You should have received a copy of the GNU Library General Public License 16 * along with this library; see the file COPYING.LIB. If not, write to 17 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 18 * Boston, MA 02110-1301, USA. 19 * 20 */ 21 22#ifndef StyleResolver_h 23#define StyleResolver_h 24 25#include "CSSToStyleMap.h" 26#include "CSSValueList.h" 27#include "DocumentRuleSets.h" 28#include "InspectorCSSOMWrappers.h" 29#include "LinkHash.h" 30#include "MediaQueryExp.h" 31#include "RenderStyle.h" 32#include "RuleFeature.h" 33#include "RuleSet.h" 34#include "RuntimeEnabledFeatures.h" 35#include "ScrollTypes.h" 36#include "SelectorChecker.h" 37#include "SelectorFilter.h" 38#include "StyleInheritedData.h" 39#include "StyleScopeResolver.h" 40#include "ViewportStyleResolver.h" 41#if ENABLE(CSS_FILTERS) && ENABLE(SVG) 42#include "WebKitCSSSVGDocumentValue.h" 43#endif 44#if ENABLE(CSS_SHADERS) 45#include "CustomFilterConstants.h" 46#endif 47#include <wtf/HashMap.h> 48#include <wtf/HashSet.h> 49#include <wtf/RefPtr.h> 50#include <wtf/Vector.h> 51#include <wtf/text/AtomicStringHash.h> 52#include <wtf/text/StringHash.h> 53 54namespace WebCore { 55 56enum ESmartMinimumForFontSize { DoNotUseSmartMinimumForFontSize, UseSmartMinimumForFontFize }; 57 58class CSSCursorImageValue; 59class CSSFontSelector; 60class CSSFontFace; 61class CSSFontFaceRule; 62class CSSImageGeneratorValue; 63class CSSImageSetValue; 64class CSSImageValue; 65class CSSPageRule; 66class CSSPrimitiveValue; 67class CSSProperty; 68class CSSSelector; 69class CSSStyleSheet; 70class CSSValue; 71class ContainerNode; 72class CustomFilterOperation; 73class CustomFilterParameter; 74class CustomFilterParameterList; 75class CustomFilterProgram; 76struct CustomFilterProgramMixSettings; 77class Document; 78class DeprecatedStyleBuilder; 79class Element; 80class Frame; 81class FrameView; 82class KURL; 83class KeyframeList; 84class KeyframeValue; 85class MediaQueryEvaluator; 86class Node; 87class RenderRegion; 88class RenderScrollbar; 89class RuleData; 90class RuleSet; 91class Settings; 92class StyleCustomFilterProgramCache; 93class StyleScopeResolver; 94class StyleImage; 95class StyleKeyframe; 96class StylePendingImage; 97class StylePropertySet; 98class StyleRule; 99#if ENABLE(SHADOW_DOM) 100class StyleRuleHost; 101#endif 102class StyleRuleKeyframes; 103class StyleRulePage; 104class StyleRuleRegion; 105class StyleShader; 106class StyleSheet; 107class StyleSheetList; 108class StyledElement; 109class ViewportStyleResolver; 110class WebKitCSSFilterValue; 111class WebKitCSSShaderValue; 112class WebKitCSSSVGDocumentValue; 113 114class MediaQueryResult { 115 WTF_MAKE_NONCOPYABLE(MediaQueryResult); WTF_MAKE_FAST_ALLOCATED; 116public: 117 MediaQueryResult(const MediaQueryExp& expr, bool result) 118 : m_expression(expr) 119 , m_result(result) 120 { 121 } 122 123 MediaQueryExp m_expression; 124 bool m_result; 125}; 126 127enum StyleSharingBehavior { 128 AllowStyleSharing, 129 DisallowStyleSharing, 130}; 131 132// MatchOnlyUserAgentRules is used in media queries, where relative units 133// are interpreted according to the document root element style, and styled only 134// from the User Agent Stylesheet rules. 135 136enum RuleMatchingBehavior { 137 MatchAllRules, 138 MatchAllRulesExcludingSMIL, 139 MatchOnlyUserAgentRules, 140}; 141 142class PseudoStyleRequest { 143public: 144 PseudoStyleRequest(PseudoId pseudoId, RenderScrollbar* scrollbar = 0, ScrollbarPart scrollbarPart = NoPart) 145 : pseudoId(pseudoId) 146 , scrollbarPart(scrollbarPart) 147 , scrollbar(scrollbar) 148 { 149 } 150 151 PseudoId pseudoId; 152 ScrollbarPart scrollbarPart; 153 RenderScrollbar* scrollbar; 154}; 155 156class MatchRequest { 157public: 158 MatchRequest(RuleSet* ruleSet, bool includeEmptyRules = false, const ContainerNode* scope = 0) 159 : ruleSet(ruleSet) 160 , includeEmptyRules(includeEmptyRules) 161 , scope(scope) { } 162 const RuleSet* ruleSet; 163 const bool includeEmptyRules; 164 const ContainerNode* scope; 165}; 166 167// This class selects a RenderStyle for a given element based on a collection of stylesheets. 168class StyleResolver { 169 WTF_MAKE_NONCOPYABLE(StyleResolver); WTF_MAKE_FAST_ALLOCATED; 170public: 171 StyleResolver(Document*, bool matchAuthorAndUserStyles); 172 ~StyleResolver(); 173 174 // Using these during tree walk will allow style selector to optimize child and descendant selector lookups. 175 void pushParentElement(Element*); 176 void popParentElement(Element*); 177 void pushParentShadowRoot(const ShadowRoot*); 178 void popParentShadowRoot(const ShadowRoot*); 179#if ENABLE(SHADOW_DOM) 180 void addHostRule(StyleRuleHost* rule, bool hasDocumentSecurityOrigin, const ContainerNode* scope) { ensureScopeResolver()->addHostRule(rule, hasDocumentSecurityOrigin, scope); } 181#endif 182 183 PassRefPtr<RenderStyle> styleForElement(Element*, RenderStyle* parentStyle = 0, StyleSharingBehavior = AllowStyleSharing, 184 RuleMatchingBehavior = MatchAllRules, RenderRegion* regionForStyling = 0); 185 186 void keyframeStylesForAnimation(Element*, const RenderStyle*, KeyframeList&); 187 188 PassRefPtr<RenderStyle> pseudoStyleForElement(Element*, const PseudoStyleRequest&, RenderStyle* parentStyle); 189 190 PassRefPtr<RenderStyle> styleForPage(int pageIndex); 191 PassRefPtr<RenderStyle> defaultStyleForElement(); 192 PassRefPtr<RenderStyle> styleForText(Text*); 193 194 static PassRefPtr<RenderStyle> styleForDocument(Document*, CSSFontSelector* = 0); 195 196 RenderStyle* style() const { return m_state.style(); } 197 RenderStyle* parentStyle() const { return m_state.parentStyle(); } 198 RenderStyle* rootElementStyle() const { return m_state.rootElementStyle(); } 199 Element* element() { return m_state.element(); } 200 Document* document() { return m_document; } 201 StyleScopeResolver* scopeResolver() const { return m_scopeResolver.get(); } 202 bool hasParentNode() const { return m_state.parentNode(); } 203 204 // FIXME: It could be better to call m_ruleSets.appendAuthorStyleSheets() directly after we factor StyleRsolver further. 205 // https://bugs.webkit.org/show_bug.cgi?id=108890 206 void appendAuthorStyleSheets(unsigned firstNew, const Vector<RefPtr<CSSStyleSheet> >&); 207 208 DocumentRuleSets& ruleSets() { return m_ruleSets; } 209 const DocumentRuleSets& ruleSets() const { return m_ruleSets; } 210 SelectorFilter& selectorFilter() { return m_selectorFilter; } 211 212#if ENABLE(STYLE_SCOPED) || ENABLE(SHADOW_DOM) 213 StyleScopeResolver* ensureScopeResolver() 214 { 215#if ENABLE(STYLE_SCOPED) 216#if ENABLE(SHADOW_DOM) 217 ASSERT(RuntimeEnabledFeatures::shadowDOMEnabled() || RuntimeEnabledFeatures::styleScopedEnabled()); 218#else 219 ASSERT(RuntimeEnabledFeatures::styleScopedEnabled()); 220#endif 221#else 222 ASSERT(RuntimeEnabledFeatures::shadowDOMEnabled()); 223#endif 224 if (!m_scopeResolver) 225 m_scopeResolver = adoptPtr(new StyleScopeResolver()); 226 return m_scopeResolver.get(); 227 } 228#endif 229 230private: 231 void initElement(Element*); 232 RenderStyle* locateSharedStyle(); 233 bool styleSharingCandidateMatchesRuleSet(RuleSet*); 234 bool styleSharingCandidateMatchesHostRules(); 235 Node* locateCousinList(Element* parent, unsigned& visitedNodeCount) const; 236 StyledElement* findSiblingForStyleSharing(Node*, unsigned& count) const; 237 bool canShareStyleWithElement(StyledElement*) const; 238 239 PassRefPtr<RenderStyle> styleForKeyframe(const RenderStyle*, const StyleKeyframe*, KeyframeValue&); 240 241public: 242 // These methods will give back the set of rules that matched for a given element (or a pseudo-element). 243 enum CSSRuleFilter { 244 UAAndUserCSSRules = 1 << 1, 245 AuthorCSSRules = 1 << 2, 246 EmptyCSSRules = 1 << 3, 247 CrossOriginCSSRules = 1 << 4, 248 AllButEmptyCSSRules = UAAndUserCSSRules | AuthorCSSRules | CrossOriginCSSRules, 249 AllCSSRules = AllButEmptyCSSRules | EmptyCSSRules, 250 }; 251 Vector<RefPtr<StyleRuleBase> > styleRulesForElement(Element*, unsigned rulesToInclude = AllButEmptyCSSRules); 252 Vector<RefPtr<StyleRuleBase> > pseudoStyleRulesForElement(Element*, PseudoId, unsigned rulesToInclude = AllButEmptyCSSRules); 253 254 // Given a CSS keyword in the range (xx-small to -webkit-xxx-large), this function will return 255 // the correct font size scaled relative to the user's default (medium). 256 static float fontSizeForKeyword(Document*, int keyword, bool shouldUseFixedDefaultSize); 257 258 // Given a font size in pixel, this function will return legacy font size between 1 and 7. 259 static int legacyFontSize(Document*, int pixelFontSize, bool shouldUseFixedDefaultSize); 260 261public: 262 void applyPropertyToStyle(CSSPropertyID, CSSValue*, RenderStyle*); 263 264 void applyPropertyToCurrentStyle(CSSPropertyID, CSSValue*); 265 266 void updateFont(); 267 void initializeFontStyle(Settings*); 268 269 static float getComputedSizeFromSpecifiedSize(Document*, float zoomFactor, bool isAbsoluteSize, float specifiedSize, ESmartMinimumForFontSize = UseSmartMinimumForFontFize); 270 271 void setFontSize(FontDescription&, float size); 272 273private: 274 static float getComputedSizeFromSpecifiedSize(Document*, RenderStyle*, bool isAbsoluteSize, float specifiedSize, bool useSVGZoomRules); 275 276public: 277 bool useSVGZoomRules(); 278 279 static bool colorFromPrimitiveValueIsDerivedFromElement(CSSPrimitiveValue*); 280 Color colorFromPrimitiveValue(CSSPrimitiveValue*, bool forVisitedLink = false) const; 281 282 bool hasSelectorForId(const AtomicString&) const; 283 bool hasSelectorForClass(const AtomicString&) const; 284 bool hasSelectorForAttribute(const AtomicString&) const; 285 286 CSSFontSelector* fontSelector() const { return m_fontSelector.get(); } 287#if ENABLE(CSS_DEVICE_ADAPTATION) 288 ViewportStyleResolver* viewportStyleResolver() { return m_viewportStyleResolver.get(); } 289#endif 290 291 void addViewportDependentMediaQueryResult(const MediaQueryExp*, bool result); 292 bool hasViewportDependentMediaQueries() const { return !m_viewportDependentMediaQueryResults.isEmpty(); } 293 bool affectedByViewportChange() const; 294 295 void addKeyframeStyle(PassRefPtr<StyleRuleKeyframes>); 296 297 bool checkRegionStyle(Element* regionElement); 298 299 bool usesSiblingRules() const { return !m_ruleSets.features().siblingRules.isEmpty(); } 300 bool usesFirstLineRules() const { return m_ruleSets.features().usesFirstLineRules; } 301 bool usesBeforeAfterRules() const { return m_ruleSets.features().usesBeforeAfterRules; } 302 303 void invalidateMatchedPropertiesCache(); 304 305#if ENABLE(CSS_FILTERS) 306 bool createFilterOperations(CSSValue* inValue, RenderStyle* inStyle, RenderStyle* rootStyle, FilterOperations& outOperations); 307#if ENABLE(CSS_SHADERS) 308 StyleShader* styleShader(CSSValue*); 309 StyleShader* cachedOrPendingStyleShaderFromValue(WebKitCSSShaderValue*); 310 bool parseCustomFilterParameterList(CSSValue*, CustomFilterParameterList&); 311 PassRefPtr<CustomFilterParameter> parseCustomFilterParameter(const String& name, CSSValue*); 312 PassRefPtr<CustomFilterParameter> parseCustomFilterColorParameter(const String& name, CSSValueList*); 313 PassRefPtr<CustomFilterParameter> parseCustomFilterArrayParameter(const String& name, CSSValueList*, bool); 314 PassRefPtr<CustomFilterParameter> parseCustomFilterNumberParameter(const String& name, CSSValueList*); 315 PassRefPtr<CustomFilterParameter> parseCustomFilterTransformParameter(const String& name, CSSValueList*); 316 PassRefPtr<CustomFilterOperation> createCustomFilterOperationWithAtRuleReferenceSyntax(WebKitCSSFilterValue*); 317 PassRefPtr<CustomFilterOperation> createCustomFilterOperationWithInlineSyntax(WebKitCSSFilterValue*); 318 PassRefPtr<CustomFilterOperation> createCustomFilterOperation(WebKitCSSFilterValue*); 319 void loadPendingShaders(); 320 PassRefPtr<CustomFilterProgram> lookupCustomFilterProgram(WebKitCSSShaderValue* vertexShader, WebKitCSSShaderValue* fragmentShader, 321 CustomFilterProgramType, const CustomFilterProgramMixSettings&, CustomFilterMeshType); 322#endif 323#if ENABLE(SVG) 324 void loadPendingSVGDocuments(); 325#endif 326#endif // ENABLE(CSS_FILTERS) 327 328 void loadPendingResources(); 329 330 struct RuleRange { 331 RuleRange(int& firstRuleIndex, int& lastRuleIndex): firstRuleIndex(firstRuleIndex), lastRuleIndex(lastRuleIndex) { } 332 int& firstRuleIndex; 333 int& lastRuleIndex; 334 }; 335 336 struct MatchRanges { 337 MatchRanges() : firstUARule(-1), lastUARule(-1), firstAuthorRule(-1), lastAuthorRule(-1), firstUserRule(-1), lastUserRule(-1) { } 338 int firstUARule; 339 int lastUARule; 340 int firstAuthorRule; 341 int lastAuthorRule; 342 int firstUserRule; 343 int lastUserRule; 344 RuleRange UARuleRange() { return RuleRange(firstUARule, lastUARule); } 345 RuleRange authorRuleRange() { return RuleRange(firstAuthorRule, lastAuthorRule); } 346 RuleRange userRuleRange() { return RuleRange(firstUserRule, lastUserRule); } 347 }; 348 349 struct MatchedProperties { 350 MatchedProperties(); 351 ~MatchedProperties(); 352 353 RefPtr<StylePropertySet> properties; 354 union { 355 struct { 356 unsigned linkMatchType : 2; 357 unsigned whitelistType : 2; 358 }; 359 // Used to make sure all memory is zero-initialized since we compute the hash over the bytes of this object. 360 void* possiblyPaddedMember; 361 }; 362 }; 363 364 struct MatchResult { 365 MatchResult() : isCacheable(true) { } 366 Vector<MatchedProperties, 64> matchedProperties; 367 Vector<StyleRule*, 64> matchedRules; 368 MatchRanges ranges; 369 bool isCacheable; 370 371 void addMatchedProperties(const StylePropertySet* properties, StyleRule* = 0, unsigned linkMatchType = SelectorChecker::MatchAll, PropertyWhitelistType = PropertyWhitelistNone); 372 }; 373 374private: 375 // This function fixes up the default font size if it detects that the current generic font family has changed. -dwh 376 void checkForGenericFamilyChange(RenderStyle*, RenderStyle* parentStyle); 377 void checkForZoomChange(RenderStyle*, RenderStyle* parentStyle); 378 379 void adjustRenderStyle(RenderStyle* styleToAdjust, RenderStyle* parentStyle, Element*); 380 381 bool fastRejectSelector(const RuleData&) const; 382 383 void applyMatchedProperties(const MatchResult&, const Element*); 384 385 enum StyleApplicationPass { 386#if ENABLE(CSS_VARIABLES) 387 VariableDefinitions, 388#endif 389 HighPriorityProperties, 390 LowPriorityProperties 391 }; 392 template <StyleApplicationPass pass> 393 void applyMatchedProperties(const MatchResult&, bool important, int startIndex, int endIndex, bool inheritedOnly); 394 template <StyleApplicationPass pass> 395 void applyProperties(const StylePropertySet* properties, StyleRule*, bool isImportant, bool inheritedOnly, PropertyWhitelistType = PropertyWhitelistNone); 396#if ENABLE(CSS_VARIABLES) 397 void resolveVariables(CSSPropertyID, CSSValue*, Vector<std::pair<CSSPropertyID, String> >& knownExpressions); 398#endif 399 static bool isValidRegionStyleProperty(CSSPropertyID); 400#if ENABLE(VIDEO_TRACK) 401 static bool isValidCueStyleProperty(CSSPropertyID); 402#endif 403 void matchPageRules(MatchResult&, RuleSet*, bool isLeftPage, bool isFirstPage, const String& pageName); 404 void matchPageRulesForList(Vector<StyleRulePage*>& matchedRules, const Vector<StyleRulePage*>&, bool isLeftPage, bool isFirstPage, const String& pageName); 405 Settings* documentSettings() { return m_document->settings(); } 406 407 bool isLeftPage(int pageIndex) const; 408 bool isRightPage(int pageIndex) const { return !isLeftPage(pageIndex); } 409 bool isFirstPage(int pageIndex) const; 410 String pageName(int pageIndex) const; 411 412 DocumentRuleSets m_ruleSets; 413 414 typedef HashMap<AtomicStringImpl*, RefPtr<StyleRuleKeyframes> > KeyframesRuleMap; 415 KeyframesRuleMap m_keyframesRuleMap; 416 417public: 418 typedef HashMap<CSSPropertyID, RefPtr<CSSValue> > PendingImagePropertyMap; 419#if ENABLE(CSS_FILTERS) && ENABLE(SVG) 420 typedef HashMap<FilterOperation*, RefPtr<WebKitCSSSVGDocumentValue> > PendingSVGDocumentMap; 421#endif 422 423 class State { 424 WTF_MAKE_NONCOPYABLE(State); 425 public: 426 State() 427 : m_element(0) 428 , m_styledElement(0) 429 , m_parentNode(0) 430 , m_parentStyle(0) 431 , m_rootElementStyle(0) 432 , m_regionForStyling(0) 433 , m_elementLinkState(NotInsideLink) 434 , m_distributedToInsertionPoint(false) 435 , m_elementAffectedByClassRules(false) 436 , m_applyPropertyToRegularStyle(true) 437 , m_applyPropertyToVisitedLinkStyle(false) 438#if ENABLE(CSS_SHADERS) 439 , m_hasPendingShaders(false) 440#endif 441 , m_lineHeightValue(0) 442 , m_fontDirty(false) 443 , m_hasUAAppearance(false) 444 , m_backgroundData(BackgroundFillLayer) { } 445 446 public: 447 void initElement(Element*); 448 void initForStyleResolve(Document*, Element*, RenderStyle* parentStyle = 0, RenderRegion* regionForStyling = 0); 449 void clear(); 450 451 Document* document() const { return m_element->document(); } 452 Element* element() const { return m_element; } 453 StyledElement* styledElement() const { return m_styledElement; } 454 void setStyle(PassRefPtr<RenderStyle> style) { m_style = style; } 455 RenderStyle* style() const { return m_style.get(); } 456 PassRefPtr<RenderStyle> takeStyle() { return m_style.release(); } 457 458 const ContainerNode* parentNode() const { return m_parentNode; } 459 void setParentStyle(PassRefPtr<RenderStyle> parentStyle) { m_parentStyle = parentStyle; } 460 RenderStyle* parentStyle() const { return m_parentStyle.get(); } 461 RenderStyle* rootElementStyle() const { return m_rootElementStyle; } 462 463 const RenderRegion* regionForStyling() const { return m_regionForStyling; } 464 EInsideLink elementLinkState() const { return m_elementLinkState; } 465 bool distributedToInsertionPoint() const { return m_distributedToInsertionPoint; } 466 void setElementAffectedByClassRules(bool isAffected) { m_elementAffectedByClassRules = isAffected; } 467 bool elementAffectedByClassRules() const { return m_elementAffectedByClassRules; } 468 469 void setApplyPropertyToRegularStyle(bool isApply) { m_applyPropertyToRegularStyle = isApply; } 470 void setApplyPropertyToVisitedLinkStyle(bool isApply) { m_applyPropertyToVisitedLinkStyle = isApply; } 471 bool applyPropertyToRegularStyle() const { return m_applyPropertyToRegularStyle; } 472 bool applyPropertyToVisitedLinkStyle() const { return m_applyPropertyToVisitedLinkStyle; } 473 PendingImagePropertyMap& pendingImageProperties() { return m_pendingImageProperties; } 474#if ENABLE(CSS_FILTERS) && ENABLE(SVG) 475 PendingSVGDocumentMap& pendingSVGDocuments() { return m_pendingSVGDocuments; } 476#endif 477#if ENABLE(CSS_SHADERS) 478 void setHasPendingShaders(bool hasPendingShaders) { m_hasPendingShaders = hasPendingShaders; } 479 bool hasPendingShaders() const { return m_hasPendingShaders; } 480#endif 481 482 void setLineHeightValue(CSSValue* value) { m_lineHeightValue = value; } 483 CSSValue* lineHeightValue() { return m_lineHeightValue; } 484 void setFontDirty(bool isDirty) { m_fontDirty = isDirty; } 485 bool fontDirty() const { return m_fontDirty; } 486 487 void cacheBorderAndBackground(); 488 bool hasUAAppearance() const { return m_hasUAAppearance; } 489 BorderData borderData() const { return m_borderData; } 490 FillLayer backgroundData() const { return m_backgroundData; } 491 Color backgroundColor() const { return m_backgroundColor; } 492 493 const FontDescription& fontDescription() { return m_style->fontDescription(); } 494 const FontDescription& parentFontDescription() { return m_parentStyle->fontDescription(); } 495 void setFontDescription(const FontDescription& fontDescription) { m_fontDirty |= m_style->setFontDescription(fontDescription); } 496 void setZoom(float f) { m_fontDirty |= m_style->setZoom(f); } 497 void setEffectiveZoom(float f) { m_fontDirty |= m_style->setEffectiveZoom(f); } 498 void setWritingMode(WritingMode writingMode) { m_fontDirty |= m_style->setWritingMode(writingMode); } 499 void setTextOrientation(TextOrientation textOrientation) { m_fontDirty |= m_style->setTextOrientation(textOrientation); } 500 501 bool useSVGZoomRules() const { return m_element && m_element->isSVGElement(); } 502 503 private: 504 // FIXME(bug 108563): to make it easier to review, these member 505 // variables are public. However we should add methods to access 506 // these variables. 507 Element* m_element; 508 RefPtr<RenderStyle> m_style; 509 StyledElement* m_styledElement; 510 ContainerNode* m_parentNode; 511 RefPtr<RenderStyle> m_parentStyle; 512 RenderStyle* m_rootElementStyle; 513 514 // Required to ASSERT in applyProperties. 515 RenderRegion* m_regionForStyling; 516 517 EInsideLink m_elementLinkState; 518 519 bool m_distributedToInsertionPoint; 520 521 bool m_elementAffectedByClassRules; 522 523 bool m_applyPropertyToRegularStyle; 524 bool m_applyPropertyToVisitedLinkStyle; 525 526 PendingImagePropertyMap m_pendingImageProperties; 527#if ENABLE(CSS_SHADERS) 528 bool m_hasPendingShaders; 529#endif 530#if ENABLE(CSS_FILTERS) && ENABLE(SVG) 531 PendingSVGDocumentMap m_pendingSVGDocuments; 532#endif 533 CSSValue* m_lineHeightValue; 534 bool m_fontDirty; 535 536 bool m_hasUAAppearance; 537 BorderData m_borderData; 538 FillLayer m_backgroundData; 539 Color m_backgroundColor; 540 }; 541 542 static RenderStyle* styleNotYetAvailable() { return s_styleNotYetAvailable; } 543 544 PassRefPtr<StyleImage> styleImage(CSSPropertyID, CSSValue*); 545 PassRefPtr<StyleImage> cachedOrPendingFromValue(CSSPropertyID, CSSImageValue*); 546 PassRefPtr<StyleImage> generatedOrPendingFromValue(CSSPropertyID, CSSImageGeneratorValue*); 547#if ENABLE(CSS_IMAGE_SET) 548 PassRefPtr<StyleImage> setOrPendingFromValue(CSSPropertyID, CSSImageSetValue*); 549#endif 550 PassRefPtr<StyleImage> cursorOrPendingFromValue(CSSPropertyID, CSSCursorImageValue*); 551 552 bool applyPropertyToRegularStyle() const { return m_state.applyPropertyToRegularStyle(); } 553 bool applyPropertyToVisitedLinkStyle() const { return m_state.applyPropertyToVisitedLinkStyle(); } 554 555 static Length convertToIntLength(const CSSPrimitiveValue*, const RenderStyle*, const RenderStyle* rootStyle, double multiplier = 1); 556 static Length convertToFloatLength(const CSSPrimitiveValue*, const RenderStyle*, const RenderStyle* rootStyle, double multiplier = 1); 557 558 CSSToStyleMap* styleMap() { return &m_styleMap; } 559 InspectorCSSOMWrappers& inspectorCSSOMWrappers() { return m_inspectorCSSOMWrappers; } 560 const FontDescription& fontDescription() { return m_state.fontDescription(); } 561 const FontDescription& parentFontDescription() { return m_state.parentFontDescription(); } 562 void setFontDescription(const FontDescription& fontDescription) { m_state.setFontDescription(fontDescription); } 563 void setZoom(float f) { m_state.setZoom(f); } 564 void setEffectiveZoom(float f) { m_state.setEffectiveZoom(f); } 565 void setWritingMode(WritingMode writingMode) { m_state.setWritingMode(writingMode); } 566 void setTextOrientation(TextOrientation textOrientation) { m_state.setTextOrientation(textOrientation); } 567 568private: 569 static RenderStyle* s_styleNotYetAvailable; 570 571 void cacheBorderAndBackground(); 572 573private: 574 bool canShareStyleWithControl(StyledElement*) const; 575 576 void applyProperty(CSSPropertyID, CSSValue*); 577 578#if ENABLE(SVG) 579 void applySVGProperty(CSSPropertyID, CSSValue*); 580#endif 581 582 PassRefPtr<StyleImage> loadPendingImage(StylePendingImage*); 583 void loadPendingImages(); 584 585 static unsigned computeMatchedPropertiesHash(const MatchedProperties*, unsigned size); 586 struct MatchedPropertiesCacheItem { 587 Vector<MatchedProperties> matchedProperties; 588 MatchRanges ranges; 589 RefPtr<RenderStyle> renderStyle; 590 RefPtr<RenderStyle> parentRenderStyle; 591 }; 592 const MatchedPropertiesCacheItem* findFromMatchedPropertiesCache(unsigned hash, const MatchResult&); 593 void addToMatchedPropertiesCache(const RenderStyle*, const RenderStyle* parentStyle, unsigned hash, const MatchResult&); 594 595 // Every N additions to the matched declaration cache trigger a sweep where entries holding 596 // the last reference to a style declaration are garbage collected. 597 void sweepMatchedPropertiesCache(Timer<StyleResolver>*); 598 599 bool classNamesAffectedByRules(const SpaceSplitString&) const; 600 bool sharingCandidateHasIdenticalStyleAffectingAttributes(StyledElement*) const; 601 602 unsigned m_matchedPropertiesCacheAdditionsSinceLastSweep; 603 604 typedef HashMap<unsigned, MatchedPropertiesCacheItem> MatchedPropertiesCache; 605 MatchedPropertiesCache m_matchedPropertiesCache; 606 607 Timer<StyleResolver> m_matchedPropertiesCacheSweepTimer; 608 609 OwnPtr<MediaQueryEvaluator> m_medium; 610 RefPtr<RenderStyle> m_rootDefaultStyle; 611 612 Document* m_document; 613 SelectorFilter m_selectorFilter; 614 615 bool m_matchAuthorAndUserStyles; 616 617 RefPtr<CSSFontSelector> m_fontSelector; 618 Vector<OwnPtr<MediaQueryResult> > m_viewportDependentMediaQueryResults; 619 620#if ENABLE(CSS_DEVICE_ADAPTATION) 621 RefPtr<ViewportStyleResolver> m_viewportStyleResolver; 622#endif 623 624 const DeprecatedStyleBuilder& m_deprecatedStyleBuilder; 625 626 OwnPtr<StyleScopeResolver> m_scopeResolver; 627 CSSToStyleMap m_styleMap; 628 InspectorCSSOMWrappers m_inspectorCSSOMWrappers; 629 630 State m_state; 631 632#if ENABLE(CSS_SHADERS) 633 OwnPtr<StyleCustomFilterProgramCache> m_customFilterProgramCache; 634#endif 635 636 friend class DeprecatedStyleBuilder; 637 friend bool operator==(const MatchedProperties&, const MatchedProperties&); 638 friend bool operator!=(const MatchedProperties&, const MatchedProperties&); 639 friend bool operator==(const MatchRanges&, const MatchRanges&); 640 friend bool operator!=(const MatchRanges&, const MatchRanges&); 641}; 642 643inline bool StyleResolver::hasSelectorForAttribute(const AtomicString &attributeName) const 644{ 645 ASSERT(!attributeName.isEmpty()); 646 return m_ruleSets.features().attrsInRules.contains(attributeName.impl()); 647} 648 649inline bool StyleResolver::hasSelectorForClass(const AtomicString& classValue) const 650{ 651 ASSERT(!classValue.isEmpty()); 652 return m_ruleSets.features().classesInRules.contains(classValue.impl()); 653} 654 655inline bool StyleResolver::hasSelectorForId(const AtomicString& idValue) const 656{ 657 ASSERT(!idValue.isEmpty()); 658 return m_ruleSets.features().idsInRules.contains(idValue.impl()); 659} 660 661inline bool checkRegionSelector(const CSSSelector* regionSelector, Element* regionElement) 662{ 663 if (!regionSelector || !regionElement) 664 return false; 665 666 SelectorChecker selectorChecker(regionElement->document(), SelectorChecker::QueryingRules); 667 for (const CSSSelector* s = regionSelector; s; s = CSSSelectorList::next(s)) { 668 SelectorChecker::SelectorCheckingContext selectorCheckingContext(s, regionElement, SelectorChecker::VisitedMatchDisabled); 669 PseudoId ignoreDynamicPseudo = NOPSEUDO; 670 if (selectorChecker.match(selectorCheckingContext, ignoreDynamicPseudo) == SelectorChecker::SelectorMatches) 671 return true; 672 } 673 return false; 674} 675 676} // namespace WebCore 677 678#endif // StyleResolver_h 679