Diff
Modified: trunk/LayoutTests/ChangeLog (226702 => 226703)
--- trunk/LayoutTests/ChangeLog 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/LayoutTests/ChangeLog 2018-01-10 09:01:53 UTC (rev 226703)
@@ -1,3 +1,13 @@
+2018-01-10 Antti Koivisto <[email protected]>
+
+ Invalidate current element style on class change accurately
+ https://bugs.webkit.org/show_bug.cgi?id=181210
+
+ Reviewed by Zalan Bujtas.
+
+ * fast/css/set-inline-style-recalc-expected.txt:
+ * fast/css/set-inline-style-recalc.html:
+
2018-01-09 Antoine Quint <[email protected]>
[Web Animations] Expose the id property on Animation
Modified: trunk/LayoutTests/fast/css/set-inline-style-recalc-expected.txt (226702 => 226703)
--- trunk/LayoutTests/fast/css/set-inline-style-recalc-expected.txt 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/LayoutTests/fast/css/set-inline-style-recalc-expected.txt 2018-01-10 09:01:53 UTC (rev 226703)
@@ -14,7 +14,7 @@
PASS numStyleRecalcs is 0
PASS numStyleRecalcs is 1
PASS numStyleRecalcs is 0
-PASS numStyleRecalcs is 1
+PASS numStyleRecalcs is 0
PASS successfullyParsed is true
TEST COMPLETE
Modified: trunk/LayoutTests/fast/css/set-inline-style-recalc.html (226702 => 226703)
--- trunk/LayoutTests/fast/css/set-inline-style-recalc.html 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/LayoutTests/fast/css/set-inline-style-recalc.html 2018-01-10 09:01:53 UTC (rev 226703)
@@ -69,7 +69,7 @@
numStyleRecalcs = setStyleAndForceLayout(function() { testContainer.classList.add('foo'); });
shouldBe("numStyleRecalcs", "0");
numStyleRecalcs = setStyleAndForceLayout(function() { testContainer.classList.add('bar'); });
-shouldBe("numStyleRecalcs", "1");
+shouldBe("numStyleRecalcs", "0");
document.body.removeChild(testContainer);
</script>
Modified: trunk/Source/WebCore/ChangeLog (226702 => 226703)
--- trunk/Source/WebCore/ChangeLog 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/ChangeLog 2018-01-10 09:01:53 UTC (rev 226703)
@@ -1,3 +1,47 @@
+2018-01-10 Antti Koivisto <[email protected]>
+
+ Invalidate current element style on class change accurately
+ https://bugs.webkit.org/show_bug.cgi?id=181210
+
+ Reviewed by Zalan Bujtas.
+
+ * css/DocumentRuleSets.cpp:
+ (WebCore::DocumentRuleSets::collectFeatures const):
+ (WebCore::DocumentRuleSets::subjectClassRules const):
+
+ New rule set containing class rules affecting the subject element.
+
+ (WebCore::DocumentRuleSets::ancestorClassRules const):
+ * css/DocumentRuleSets.h:
+ * css/RuleFeature.cpp:
+ (WebCore::RuleFeatureSet::recursivelyCollectFeaturesFromSelector):
+
+ Classify selector components into various buckets based on the elements they match relative to
+ the subject element. There are more categories than this patch strictly needs, for future use.
+
+ (WebCore::RuleFeatureSet::collectFeatures):
+ (WebCore::RuleFeatureSet::add):
+ (WebCore::RuleFeatureSet::clear):
+ (WebCore::RuleFeatureSet::shrinkToFit):
+ * css/RuleFeature.h:
+ * css/StyleResolver.h:
+ (WebCore::StyleResolver::hasSelectorForClass const): Deleted.
+ * style/ClassChangeInvalidation.cpp:
+ (WebCore::Style::elementNeedsInvalidation):
+ (WebCore::Style::ClassChangeInvalidation::computeInvalidation):
+
+ Don't invalidate current element unconditionally on class change. Instead find the subject rulesets
+ that might affect it use them to perform invalidation.
+
+ (WebCore::Style::ClassChangeInvalidation::invalidateStyleWithRuleSets):
+ (WebCore::Style::ClassChangeInvalidation::invalidateStyle): Deleted.
+ (WebCore::Style::ClassChangeInvalidation::invalidateDescendantStyle): Deleted.
+ * style/ClassChangeInvalidation.h:
+ (WebCore::Style::ClassChangeInvalidation::ClassChangeInvalidation):
+ (WebCore::Style::ClassChangeInvalidation::~ClassChangeInvalidation):
+ * style/StyleSharingResolver.cpp:
+ (WebCore::Style::SharingResolver::classNamesAffectedByRules const):
+
2018-01-09 Antoine Quint <[email protected]>
[Web Animations] Expose the id property on Animation
Modified: trunk/Source/WebCore/css/DocumentRuleSets.cpp (226702 => 226703)
--- trunk/Source/WebCore/css/DocumentRuleSets.cpp 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/css/DocumentRuleSets.cpp 2018-01-10 09:01:53 UTC (rev 226703)
@@ -167,6 +167,7 @@
m_siblingRuleSet = makeRuleSet(m_features.siblingRules);
m_uncommonAttributeRuleSet = makeRuleSet(m_features.uncommonAttributeRules);
+ m_subjectClassRuleSets.clear();
m_ancestorClassRuleSets.clear();
m_ancestorAttributeRuleSetsForHTML.clear();
@@ -173,14 +174,20 @@
m_features.shrinkToFit();
}
+RuleSet* DocumentRuleSets::subjectClassRules(const AtomicString& className) const
+{
+ return m_subjectClassRuleSets.ensure(className, [&] {
+ auto* rules = m_features.subjectClassRules.get(className);
+ return rules ? makeRuleSet(*rules) : nullptr;
+ }).iterator->value.get();
+}
+
RuleSet* DocumentRuleSets::ancestorClassRules(const AtomicString& className) const
{
- auto addResult = m_ancestorClassRuleSets.add(className, nullptr);
- if (addResult.isNewEntry) {
- if (auto* rules = m_features.ancestorClassRules.get(className))
- addResult.iterator->value = makeRuleSet(*rules);
- }
- return addResult.iterator->value.get();
+ return m_ancestorClassRuleSets.ensure(className, [&] {
+ auto* rules = m_features.ancestorClassRules.get(className);
+ return rules ? makeRuleSet(*rules) : nullptr;
+ }).iterator->value.get();
}
const DocumentRuleSets::AttributeRules* DocumentRuleSets::ancestorAttributeRulesForHTML(const AtomicString& attributeName) const
Modified: trunk/Source/WebCore/css/DocumentRuleSets.h (226702 => 226703)
--- trunk/Source/WebCore/css/DocumentRuleSets.h 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/css/DocumentRuleSets.h 2018-01-10 09:01:53 UTC (rev 226703)
@@ -50,6 +50,7 @@
const RuleFeatureSet& features() const;
RuleSet* sibling() const { return m_siblingRuleSet.get(); }
RuleSet* uncommonAttribute() const { return m_uncommonAttributeRuleSet.get(); }
+ RuleSet* subjectClassRules(const AtomicString& className) const;
RuleSet* ancestorClassRules(const AtomicString& className) const;
struct AttributeRules {
@@ -90,6 +91,7 @@
mutable unsigned m_userAgentMediaQueryRuleCountOnUpdate { 0 };
mutable std::unique_ptr<RuleSet> m_siblingRuleSet;
mutable std::unique_ptr<RuleSet> m_uncommonAttributeRuleSet;
+ mutable HashMap<AtomicString, std::unique_ptr<RuleSet>> m_subjectClassRuleSets;
mutable HashMap<AtomicString, std::unique_ptr<RuleSet>> m_ancestorClassRuleSets;
mutable HashMap<AtomicString, std::unique_ptr<AttributeRules>> m_ancestorAttributeRuleSetsForHTML;
};
Modified: trunk/Source/WebCore/css/RuleFeature.cpp (226702 => 226703)
--- trunk/Source/WebCore/css/RuleFeature.cpp 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/css/RuleFeature.cpp 2018-01-10 09:01:53 UTC (rev 226703)
@@ -35,24 +35,78 @@
namespace WebCore {
-void RuleFeatureSet::recursivelyCollectFeaturesFromSelector(SelectorFeatures& selectorFeatures, const CSSSelector& firstSelector, bool matchesAncestor)
+RuleFeatureSet::MatchElement RuleFeatureSet::computeNextMatchElement(MatchElement matchElement, CSSSelector::RelationType relation)
{
+ if (matchElement == MatchElement::Subject || matchElement == MatchElement::IndirectSibling || matchElement == MatchElement::DirectSibling) {
+ switch (relation) {
+ case CSSSelector::Subselector:
+ return matchElement;
+ case CSSSelector::DescendantSpace:
+ return MatchElement::Ancestor;
+ case CSSSelector::Child:
+ return MatchElement::Parent;
+ case CSSSelector::IndirectAdjacent:
+ return MatchElement::IndirectSibling;
+ case CSSSelector::DirectAdjacent:
+ return matchElement == MatchElement::Subject ? MatchElement::DirectSibling : MatchElement::IndirectSibling;
+ case CSSSelector::ShadowDescendant:
+ return MatchElement::Host;
+ };
+ }
+ switch (relation) {
+ case CSSSelector::Subselector:
+ return matchElement;
+ case CSSSelector::DescendantSpace:
+ case CSSSelector::Child:
+ return MatchElement::Ancestor;
+ case CSSSelector::IndirectAdjacent:
+ case CSSSelector::DirectAdjacent:
+ return matchElement == MatchElement::Parent ? MatchElement::ParentSibling : MatchElement::AncestorSibling;
+ case CSSSelector::ShadowDescendant:
+ return MatchElement::Host;
+ };
+};
+
+RuleFeatureSet::MatchElement RuleFeatureSet::computeSubSelectorMatchElement(MatchElement matchElement, const CSSSelector& selector)
+{
+ ASSERT(selector.selectorList());
+
+ if (selector.match() == CSSSelector::PseudoClass) {
+ auto type = selector.pseudoClassType();
+ // For :nth-child(n of .some-subselector) where an element change may affect other elements similar to sibling combinators.
+ // FIXME: This is not entirely accurate but good enough for current users.
+ if (type == CSSSelector::PseudoClassNthChild || type == CSSSelector::PseudoClassNthLastChild)
+ return MatchElement::IndirectSibling;
+
+ // Similarly for :host().
+ if (type == CSSSelector::PseudoClassHost)
+ return MatchElement::Host;
+ }
+ if (selector.match() == CSSSelector::PseudoElement) {
+ // Similarly for ::slotted().
+ if (selector.pseudoElementType() == CSSSelector::PseudoElementSlotted)
+ return MatchElement::Host;
+ }
+
+ return matchElement;
+};
+
+void RuleFeatureSet::recursivelyCollectFeaturesFromSelector(SelectorFeatures& selectorFeatures, const CSSSelector& firstSelector, MatchElement matchElement)
+{
const CSSSelector* selector = &firstSelector;
do {
if (selector->match() == CSSSelector::Id) {
idsInRules.add(selector->value());
- if (matchesAncestor)
+ if (matchElement == MatchElement::Parent || matchElement == MatchElement::Ancestor)
idsMatchingAncestorsInRules.add(selector->value());
- } else if (selector->match() == CSSSelector::Class) {
- classesInRules.add(selector->value());
- if (matchesAncestor)
- selectorFeatures.classesMatchingAncestors.append(selector->value());
- } else if (selector->isAttributeSelector()) {
+ } else if (selector->match() == CSSSelector::Class)
+ selectorFeatures.classes.append(std::make_pair(selector->value(), matchElement));
+ else if (selector->isAttributeSelector()) {
auto& canonicalLocalName = selector->attributeCanonicalLocalName();
auto& localName = selector->attribute().localName();
attributeCanonicalLocalNamesInRules.add(canonicalLocalName);
attributeLocalNamesInRules.add(localName);
- if (matchesAncestor)
+ if (matchElement == MatchElement::Parent || matchElement == MatchElement::Ancestor)
selectorFeatures.attributeSelectorsMatchingAncestors.append(selector);
} else if (selector->match() == CSSSelector::PseudoElement) {
switch (selector->pseudoElementType()) {
@@ -71,15 +125,17 @@
selectorFeatures.hasSiblingSelector = true;
if (const CSSSelectorList* selectorList = selector->selectorList()) {
+ auto subSelectorMatchElement = computeSubSelectorMatchElement(matchElement, *selector);
+
for (const CSSSelector* subSelector = selectorList->first(); subSelector; subSelector = CSSSelectorList::next(subSelector)) {
if (!selectorFeatures.hasSiblingSelector && selector->isSiblingSelector())
selectorFeatures.hasSiblingSelector = true;
- recursivelyCollectFeaturesFromSelector(selectorFeatures, *subSelector, matchesAncestor);
+ recursivelyCollectFeaturesFromSelector(selectorFeatures, *subSelector, subSelectorMatchElement);
}
}
- if (selector->hasDescendantOrChildRelation())
- matchesAncestor = true;
+ matchElement = computeNextMatchElement(matchElement, selector->relation());
+
selector = selector->tagHistory();
} while (selector);
}
@@ -99,11 +155,28 @@
siblingRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex()));
if (ruleData.containsUncommonAttributeSelector())
uncommonAttributeRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex()));
- for (auto& className : selectorFeatures.classesMatchingAncestors) {
- auto addResult = ancestorClassRules.ensure(className, [] {
- return std::make_unique<Vector<RuleFeature>>();
- });
- addResult.iterator->value->append(RuleFeature(ruleData.rule(), ruleData.selectorIndex()));
+ for (auto& classNameAndMatchElement : selectorFeatures.classes) {
+ auto& className = classNameAndMatchElement.first;
+ switch (classNameAndMatchElement.second) {
+ case MatchElement::Subject:
+ subjectClassRules.ensure(className, [] {
+ return std::make_unique<Vector<RuleFeature>>();
+ }).iterator->value->append(RuleFeature(ruleData.rule(), ruleData.selectorIndex()));
+ break;
+ case MatchElement::Parent:
+ case MatchElement::Ancestor:
+ ancestorClassRules.ensure(className, [] {
+ return std::make_unique<Vector<RuleFeature>>();
+ }).iterator->value->append(RuleFeature(ruleData.rule(), ruleData.selectorIndex()));
+ break;
+ case MatchElement::DirectSibling:
+ case MatchElement::IndirectSibling:
+ case MatchElement::ParentSibling:
+ case MatchElement::AncestorSibling:
+ case MatchElement::Host:
+ otherClassesInRules.add(className);
+ break;
+ };
}
for (auto* selector : selectorFeatures.attributeSelectorsMatchingAncestors) {
// Hashing by attributeCanonicalLocalName makes this HTML specific.
@@ -121,17 +194,22 @@
{
idsInRules.add(other.idsInRules.begin(), other.idsInRules.end());
idsMatchingAncestorsInRules.add(other.idsMatchingAncestorsInRules.begin(), other.idsMatchingAncestorsInRules.end());
- classesInRules.add(other.classesInRules.begin(), other.classesInRules.end());
+ otherClassesInRules.add(other.otherClassesInRules.begin(), other.otherClassesInRules.end());
attributeCanonicalLocalNamesInRules.add(other.attributeCanonicalLocalNamesInRules.begin(), other.attributeCanonicalLocalNamesInRules.end());
attributeLocalNamesInRules.add(other.attributeLocalNamesInRules.begin(), other.attributeLocalNamesInRules.end());
siblingRules.appendVector(other.siblingRules);
uncommonAttributeRules.appendVector(other.uncommonAttributeRules);
for (auto& keyValuePair : other.ancestorClassRules) {
- auto addResult = ancestorClassRules.ensure(keyValuePair.key, [] {
+ ancestorClassRules.ensure(keyValuePair.key, [] {
return std::make_unique<Vector<RuleFeature>>();
- });
- addResult.iterator->value->appendVector(*keyValuePair.value);
+ }).iterator->value->appendVector(*keyValuePair.value);
}
+ for (auto& keyValuePair : other.subjectClassRules) {
+ subjectClassRules.ensure(keyValuePair.key, [] {
+ return std::make_unique<Vector<RuleFeature>>();
+ }).iterator->value->appendVector(*keyValuePair.value);
+ }
+
for (auto& keyValuePair : other.ancestorAttributeRulesForHTML) {
auto addResult = ancestorAttributeRulesForHTML.ensure(keyValuePair.key, [] {
return std::make_unique<AttributeRules>();
@@ -149,12 +227,13 @@
{
idsInRules.clear();
idsMatchingAncestorsInRules.clear();
- classesInRules.clear();
+ otherClassesInRules.clear();
attributeCanonicalLocalNamesInRules.clear();
attributeLocalNamesInRules.clear();
siblingRules.clear();
uncommonAttributeRules.clear();
ancestorClassRules.clear();
+ subjectClassRules.clear();
ancestorAttributeRulesForHTML.clear();
usesFirstLineRules = false;
usesFirstLetterRules = false;
@@ -166,6 +245,8 @@
uncommonAttributeRules.shrinkToFit();
for (auto& rules : ancestorClassRules.values())
rules->shrinkToFit();
+ for (auto& rules : subjectClassRules.values())
+ rules->shrinkToFit();
for (auto& rules : ancestorAttributeRulesForHTML.values())
rules->features.shrinkToFit();
}
Modified: trunk/Source/WebCore/css/RuleFeature.h (226702 => 226703)
--- trunk/Source/WebCore/css/RuleFeature.h 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/css/RuleFeature.h 2018-01-10 09:01:53 UTC (rev 226703)
@@ -51,12 +51,13 @@
HashSet<AtomicString> idsInRules;
HashSet<AtomicString> idsMatchingAncestorsInRules;
- HashSet<AtomicString> classesInRules;
HashSet<AtomicString> attributeCanonicalLocalNamesInRules;
HashSet<AtomicString> attributeLocalNamesInRules;
Vector<RuleFeature> siblingRules;
Vector<RuleFeature> uncommonAttributeRules;
HashMap<AtomicString, std::unique_ptr<Vector<RuleFeature>>> ancestorClassRules;
+ HashMap<AtomicString, std::unique_ptr<Vector<RuleFeature>>> subjectClassRules;
+ HashSet<AtomicString> otherClassesInRules;
struct AttributeRules {
WTF_MAKE_FAST_ALLOCATED;
@@ -70,12 +71,18 @@
bool usesFirstLetterRules { false };
private:
+ enum class MatchElement { Subject, Parent, Ancestor, DirectSibling, IndirectSibling, ParentSibling, AncestorSibling, Host };
+
+ static MatchElement computeNextMatchElement(MatchElement, CSSSelector::RelationType);
+ static MatchElement computeSubSelectorMatchElement(MatchElement, const CSSSelector&);
+
struct SelectorFeatures {
bool hasSiblingSelector { false };
- Vector<AtomicString, 32> classesMatchingAncestors;
+
+ Vector<std::pair<AtomicString, MatchElement>, 32> classes;
Vector<const CSSSelector*> attributeSelectorsMatchingAncestors;
};
- void recursivelyCollectFeaturesFromSelector(SelectorFeatures&, const CSSSelector&, bool matchesAncestor = false);
+ void recursivelyCollectFeaturesFromSelector(SelectorFeatures&, const CSSSelector&, MatchElement = MatchElement::Subject);
};
} // namespace WebCore
Modified: trunk/Source/WebCore/css/StyleResolver.h (226702 => 226703)
--- trunk/Source/WebCore/css/StyleResolver.h 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/css/StyleResolver.h 2018-01-10 09:01:53 UTC (rev 226703)
@@ -192,7 +192,6 @@
Color colorFromPrimitiveValue(const CSSPrimitiveValue&, bool forVisitedLink = false) const;
bool hasSelectorForId(const AtomicString&) const;
- bool hasSelectorForClass(const AtomicString&) const;
bool hasSelectorForAttribute(const Element&, const AtomicString&) const;
#if ENABLE(CSS_DEVICE_ADAPTATION)
@@ -521,12 +520,6 @@
return m_ruleSets.features().attributeLocalNamesInRules.contains(attributeName);
}
-inline bool StyleResolver::hasSelectorForClass(const AtomicString& classValue) const
-{
- ASSERT(!classValue.isEmpty());
- return m_ruleSets.features().classesInRules.contains(classValue);
-}
-
inline bool StyleResolver::hasSelectorForId(const AtomicString& idValue) const
{
ASSERT(!idValue.isEmpty());
Modified: trunk/Source/WebCore/style/ClassChangeInvalidation.cpp (226702 => 226703)
--- trunk/Source/WebCore/style/ClassChangeInvalidation.cpp 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/style/ClassChangeInvalidation.cpp 2018-01-10 09:01:53 UTC (rev 226703)
@@ -83,26 +83,35 @@
return changedClasses;
}
-void ClassChangeInvalidation::invalidateStyle(const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses)
+void ClassChangeInvalidation::computeInvalidation(const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses)
{
auto changedClasses = computeClassChange(oldClasses, newClasses);
- ClassChangeVector changedClassesAffectingStyle;
+ bool shouldInvalidateCurrent = false;
bool mayAffectStyleInShadowTree = false;
+ ClassChangeVector classesAffectingDescendant;
+ ClassChangeVector classesAffectingCurrent;
traverseRuleFeatures(m_element, [&] (const RuleFeatureSet& features, bool mayAffectShadowTree) {
for (auto* changedClass : changedClasses) {
- if (!features.classesInRules.contains(changedClass))
- continue;
- changedClassesAffectingStyle.append(changedClass);
- if (mayAffectShadowTree)
+ bool mayAffectStyle = false;
+ if (features.otherClassesInRules.contains(changedClass)) {
+ shouldInvalidateCurrent = true;
+ mayAffectStyle = true;
+ }
+ if (features.ancestorClassRules.contains(changedClass)) {
+ classesAffectingDescendant.append(changedClass);
+ mayAffectStyle = true;
+ }
+ if (features.subjectClassRules.contains(changedClass)) {
+ classesAffectingCurrent.append(changedClass);
+ mayAffectStyle = true;
+ }
+ if (mayAffectStyle && mayAffectShadowTree)
mayAffectStyleInShadowTree = true;
}
});
- if (changedClassesAffectingStyle.isEmpty())
- return;
-
if (mayAffectStyleInShadowTree) {
// FIXME: We should do fine-grained invalidation for shadow tree.
m_element.invalidateStyleForSubtree();
@@ -109,24 +118,30 @@
return;
}
- m_element.invalidateStyle();
+ auto& ruleSets = m_element.styleResolver().ruleSets();
- if (!childrenOfType<Element>(m_element).first())
+ if (childrenOfType<Element>(m_element).first()) {
+ for (auto* changedClass : classesAffectingDescendant) {
+ if (auto* rules = ruleSets.ancestorClassRules(changedClass))
+ m_invalidationRuleSets.append(rules);
+ }
+ }
+
+ if (shouldInvalidateCurrent) {
+ m_element.invalidateStyle();
return;
+ }
- auto& ruleSets = m_element.styleResolver().ruleSets();
- for (auto* changedClass : changedClassesAffectingStyle) {
- auto* ancestorClassRules = ruleSets.ancestorClassRules(changedClass);
- if (!ancestorClassRules)
- continue;
- m_descendantInvalidationRuleSets.append(ancestorClassRules);
+ for (auto* changedClass : classesAffectingCurrent) {
+ if (auto* rules = ruleSets.subjectClassRules(changedClass))
+ m_invalidationRuleSets.append(rules);
}
}
-void ClassChangeInvalidation::invalidateDescendantStyle()
+void ClassChangeInvalidation::invalidateStyleWithRuleSets()
{
- for (auto* ancestorClassRules : m_descendantInvalidationRuleSets) {
- Invalidator invalidator(*ancestorClassRules);
+ for (auto* rules : m_invalidationRuleSets) {
+ Invalidator invalidator(*rules);
invalidator.invalidateStyle(m_element);
}
}
Modified: trunk/Source/WebCore/style/ClassChangeInvalidation.h (226702 => 226703)
--- trunk/Source/WebCore/style/ClassChangeInvalidation.h 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/style/ClassChangeInvalidation.h 2018-01-10 09:01:53 UTC (rev 226703)
@@ -42,13 +42,13 @@
~ClassChangeInvalidation();
private:
- void invalidateStyle(const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses);
- void invalidateDescendantStyle();
+ void computeInvalidation(const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses);
+ void invalidateStyleWithRuleSets();
const bool m_isEnabled;
Element& m_element;
- Vector<const RuleSet*, 4> m_descendantInvalidationRuleSets;
+ Vector<const RuleSet*, 4> m_invalidationRuleSets;
};
inline ClassChangeInvalidation::ClassChangeInvalidation(Element& element, const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses)
@@ -58,8 +58,8 @@
{
if (!m_isEnabled)
return;
- invalidateStyle(oldClasses, newClasses);
- invalidateDescendantStyle();
+ computeInvalidation(oldClasses, newClasses);
+ invalidateStyleWithRuleSets();
}
inline ClassChangeInvalidation::~ClassChangeInvalidation()
@@ -66,7 +66,7 @@
{
if (!m_isEnabled)
return;
- invalidateDescendantStyle();
+ invalidateStyleWithRuleSets();
}
}
Modified: trunk/Source/WebCore/style/StyleSharingResolver.cpp (226702 => 226703)
--- trunk/Source/WebCore/style/StyleSharingResolver.cpp 2018-01-10 08:56:43 UTC (rev 226702)
+++ trunk/Source/WebCore/style/StyleSharingResolver.cpp 2018-01-10 09:01:53 UTC (rev 226703)
@@ -340,8 +340,13 @@
bool SharingResolver::classNamesAffectedByRules(const SpaceSplitString& classNames) const
{
for (unsigned i = 0; i < classNames.size(); ++i) {
- if (m_ruleSets.features().classesInRules.contains(classNames[i]))
+ if (m_ruleSets.features().otherClassesInRules.contains(classNames[i]))
return true;
+ if (m_ruleSets.features().ancestorClassRules.contains(classNames[i]))
+ return true;
+ if (m_ruleSets.features().subjectClassRules.contains(classNames[i]))
+ return true;
+
}
return false;
}