Modified: trunk/Source/WebCore/css/SelectorChecker.cpp (131001 => 131002)
--- trunk/Source/WebCore/css/SelectorChecker.cpp 2012-10-11 03:06:24 UTC (rev 131001)
+++ trunk/Source/WebCore/css/SelectorChecker.cpp 2012-10-11 03:07:32 UTC (rev 131002)
@@ -439,11 +439,10 @@
// * SelectorFailsLocally - the selector fails for the element e
// * SelectorFailsAllSiblings - the selector fails for e and any sibling of e
// * SelectorFailsCompletely - the selector fails for e and any sibling or ancestor of e
-template<typename CheckingContext>
-SelectorChecker::SelectorMatch SelectorChecker::checkSelector(const CheckingContext& context, PseudoId& dynamicPseudo, bool& hasUnknownPseudoElements) const
+SelectorChecker::SelectorMatch SelectorChecker::checkSelector(const SelectorCheckingContext& context, PseudoId& dynamicPseudo, bool& hasUnknownPseudoElements) const
{
// first selector has to match
- if (!checkOneSelector(context))
+ if (!checkOneSelector(context, DOMSiblingTraversalStrategy()))
return SelectorFailsLocally;
if (context.selector->m_match == CSSSelector::PseudoElement) {
@@ -473,7 +472,7 @@
if (!historySelector)
return SelectorMatches;
- CheckingContext nextContext(context);
+ SelectorCheckingContext nextContext(context);
nextContext.selector = historySelector;
PseudoId ignoreDynamicPseudo = NOPSEUDO;
@@ -727,8 +726,8 @@
return false;
}
-template<typename CheckingContext>
-bool SelectorChecker::checkOneSelector(const CheckingContext& context) const
+template<typename SiblingTraversalStrategy>
+bool SelectorChecker::checkOneSelector(const SelectorCheckingContext& context, const SiblingTraversalStrategy& siblingTraversalStrategy) const
{
Element* const & element = context.element;
CSSSelector* const & selector = context.selector;
@@ -765,7 +764,7 @@
if (!selectorList)
return false;
- CheckingContext subContext(context);
+ SelectorCheckingContext subContext(context);
subContext.isSubSelector = true;
for (subContext.selector = selectorList->first(); subContext.selector; subContext.selector = subContext.selector->tagHistory()) {
// :not cannot nest. I don't really know why this is a
@@ -775,7 +774,7 @@
// We select between :visited and :link when applying. We don't know which one applied (or not) yet.
if (subContext.selector->pseudoType() == CSSSelector::PseudoVisited || (subContext.selector->pseudoType() == CSSSelector::PseudoLink && subContext.visitedMatchType == VisitedMatchEnabled))
return true;
- if (!checkOneSelector(subContext))
+ if (!checkOneSelector(subContext, DOMSiblingTraversalStrategy()))
return true;
}
} else if (context.hasScrollbarPseudo) {
@@ -819,7 +818,7 @@
case CSSSelector::PseudoFirstChild:
// first-child matches the first child that is an element
if (element->parentElement()) {
- bool result = DOMTraversalStrategy<CheckingContext>::isFirstChild(context, element);
+ bool result = siblingTraversalStrategy.isFirstChild(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element->renderStyle();
RenderStyle* parentStyle = context.elementStyle ? context.elementParentStyle : element->parentNode()->renderStyle();
@@ -834,7 +833,7 @@
case CSSSelector::PseudoFirstOfType:
// first-of-type matches the first element of its type
if (element->parentElement()) {
- bool result = DOMTraversalStrategy<CheckingContext>::isFirstOfType(context, element, element->tagQName());
+ bool result = siblingTraversalStrategy.isFirstOfType(element, element->tagQName());
if (m_mode == ResolvingStyle) {
RenderStyle* parentStyle = context.elementStyle ? context.elementParentStyle : element->parentNode()->renderStyle();
if (parentStyle)
@@ -846,7 +845,7 @@
case CSSSelector::PseudoLastChild:
// last-child matches the last child that is an element
if (Element* parentElement = element->parentElement()) {
- bool result = parentElement->isFinishedParsingChildren() && DOMTraversalStrategy<CheckingContext>::isLastChild(context, element);
+ bool result = parentElement->isFinishedParsingChildren() && siblingTraversalStrategy.isLastChild(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element->renderStyle();
RenderStyle* parentStyle = context.elementStyle ? context.elementParentStyle : parentElement->renderStyle();
@@ -868,13 +867,13 @@
}
if (!parentElement->isFinishedParsingChildren())
return false;
- return DOMTraversalStrategy<CheckingContext>::isLastOfType(context, element, element->tagQName());
+ return siblingTraversalStrategy.isLastOfType(element, element->tagQName());
}
break;
case CSSSelector::PseudoOnlyChild:
if (Element* parentElement = element->parentElement()) {
- bool firstChild = DOMTraversalStrategy<CheckingContext>::isFirstChild(context, element);
- bool _onlyChild_ = firstChild && parentElement->isFinishedParsingChildren() && DOMTraversalStrategy<CheckingContext>::isLastChild(context, element);
+ bool firstChild = siblingTraversalStrategy.isFirstChild(element);
+ bool _onlyChild_ = firstChild && parentElement->isFinishedParsingChildren() && siblingTraversalStrategy.isLastChild(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element->renderStyle();
RenderStyle* parentStyle = context.elementStyle ? context.elementParentStyle : parentElement->renderStyle();
@@ -902,14 +901,14 @@
}
if (!parentElement->isFinishedParsingChildren())
return false;
- return DOMTraversalStrategy<CheckingContext>::isFirstOfType(context, element, element->tagQName()) && DOMTraversalStrategy<CheckingContext>::isLastOfType(context, element, element->tagQName());
+ return siblingTraversalStrategy.isFirstOfType(element, element->tagQName()) && siblingTraversalStrategy.isLastOfType(element, element->tagQName());
}
break;
case CSSSelector::PseudoNthChild:
if (!selector->parseNth())
break;
if (Element* parentElement = element->parentElement()) {
- int count = 1 + DOMTraversalStrategy<CheckingContext>::countElementsBefore(context, element);
+ int count = 1 + siblingTraversalStrategy.countElementsBefore(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element->renderStyle();
RenderStyle* parentStyle = context.elementStyle ? context.elementParentStyle : parentElement->renderStyle();
@@ -927,7 +926,7 @@
if (!selector->parseNth())
break;
if (Element* parentElement = element->parentElement()) {
- int count = 1 + DOMTraversalStrategy<CheckingContext>::countElementsOfTypeBefore(context, element, element->tagQName());
+ int count = 1 + siblingTraversalStrategy.countElementsOfTypeBefore(element, element->tagQName());
if (m_mode == ResolvingStyle) {
RenderStyle* parentStyle = context.elementStyle ? context.elementParentStyle : parentElement->renderStyle();
if (parentStyle)
@@ -949,7 +948,7 @@
}
if (!parentElement->isFinishedParsingChildren())
return false;
- int count = 1 + DOMTraversalStrategy<CheckingContext>::countElementsAfter(context, element);
+ int count = 1 + siblingTraversalStrategy.countElementsAfter(element);
if (selector->matchNth(count))
return true;
}
@@ -966,7 +965,7 @@
if (!parentElement->isFinishedParsingChildren())
return false;
- int count = 1 + DOMTraversalStrategy<CheckingContext>::countElementsOfTypeAfter(context, element, element->tagQName());
+ int count = 1 + siblingTraversalStrategy.countElementsOfTypeAfter(element, element->tagQName());
if (selector->matchNth(count))
return true;
}
@@ -977,7 +976,7 @@
break;
case CSSSelector::PseudoAny:
{
- CheckingContext subContext(context);
+ SelectorCheckingContext subContext(context);
subContext.isSubSelector = true;
bool hasUnknownPseudoElements = false;
PseudoId ignoreDynamicPseudo = NOPSEUDO;
@@ -1359,20 +1358,17 @@
return true;
}
-template<>
-inline bool SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::isFirstChild(const SelectorChecker::SelectorCheckingContext&, Element* element)
+inline bool SelectorChecker::DOMSiblingTraversalStrategy::isFirstChild(Element* element) const
{
return !element->previousElementSibling();
}
-template<>
-inline bool SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::isLastChild(const SelectorChecker::SelectorCheckingContext&, Element* element)
+inline bool SelectorChecker::DOMSiblingTraversalStrategy::isLastChild(Element* element) const
{
return !element->nextElementSibling();
}
-template<>
-inline bool SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::isFirstOfType(const SelectorChecker::SelectorCheckingContext&, Element* element, const QualifiedName& type)
+inline bool SelectorChecker::DOMSiblingTraversalStrategy::isFirstOfType(Element* element, const QualifiedName& type) const
{
for (const Element* sibling = element->previousElementSibling(); sibling; sibling = sibling->previousElementSibling()) {
if (sibling->hasTagName(type))
@@ -1381,8 +1377,7 @@
return true;
}
-template<>
-inline bool SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::isLastOfType(const SelectorChecker::SelectorCheckingContext&, Element* element, const QualifiedName& type)
+inline bool SelectorChecker::DOMSiblingTraversalStrategy::isLastOfType(Element* element, const QualifiedName& type) const
{
for (const Element* sibling = element->nextElementSibling(); sibling; sibling = sibling->nextElementSibling()) {
if (sibling->hasTagName(type))
@@ -1391,8 +1386,7 @@
return true;
}
-template<>
-inline int SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::countElementsBefore(const SelectorChecker::SelectorCheckingContext&, Element* element)
+inline int SelectorChecker::DOMSiblingTraversalStrategy::countElementsBefore(Element* element) const
{
int count = 0;
for (const Element* sibling = element->previousElementSibling(); sibling; sibling = sibling->previousElementSibling()) {
@@ -1408,8 +1402,7 @@
return count;
}
-template<>
-inline int SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::countElementsOfTypeBefore(const SelectorChecker::SelectorCheckingContext&, Element* element, const QualifiedName& type)
+inline int SelectorChecker::DOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element* element, const QualifiedName& type) const
{
int count = 0;
for (const Element* sibling = element->previousElementSibling(); sibling; sibling = sibling->previousElementSibling()) {
@@ -1420,8 +1413,7 @@
return count;
}
-template<>
-inline int SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::countElementsAfter(const SelectorChecker::SelectorCheckingContext&, Element* element)
+inline int SelectorChecker::DOMSiblingTraversalStrategy::countElementsAfter(Element* element) const
{
int count = 0;
for (const Element* sibling = element->nextElementSibling(); sibling; sibling = sibling->nextElementSibling())
@@ -1430,8 +1422,7 @@
return count;
}
-template<>
-inline int SelectorChecker::DOMTraversalStrategy<SelectorChecker::SelectorCheckingContext>::countElementsOfTypeAfter(const SelectorChecker::SelectorCheckingContext&, Element* element, const QualifiedName& type)
+inline int SelectorChecker::DOMSiblingTraversalStrategy::countElementsOfTypeAfter(Element* element, const QualifiedName& type) const
{
int count = 0;
for (const Element* sibling = element->nextElementSibling(); sibling; sibling = sibling->nextElementSibling()) {
@@ -1442,7 +1433,4 @@
return count;
}
-template
-SelectorChecker::SelectorMatch SelectorChecker::checkSelector<SelectorChecker::SelectorCheckingContext>(const SelectorCheckingContext&, PseudoId&, bool&) const;
-
}
Modified: trunk/Source/WebCore/css/SelectorChecker.h (131001 => 131002)
--- trunk/Source/WebCore/css/SelectorChecker.h 2012-10-11 03:06:24 UTC (rev 131001)
+++ trunk/Source/WebCore/css/SelectorChecker.h 2012-10-11 03:07:32 UTC (rev 131002)
@@ -81,24 +81,23 @@
bool hasSelectionPseudo;
};
- template<typename Context>
- struct DOMTraversalStrategy {
- static bool isFirstChild(const Context&, Element*);
- static bool isLastChild(const Context&, Element*);
- static bool isFirstOfType(const Context&, Element*, const QualifiedName&);
- static bool isLastOfType(const Context&, Element*, const QualifiedName&);
+ class DOMSiblingTraversalStrategy {
+ public:
+ bool isFirstChild(Element*) const;
+ bool isLastChild(Element*) const;
+ bool isFirstOfType(Element*, const QualifiedName&) const;
+ bool isLastOfType(Element*, const QualifiedName&) const;
- static int countElementsBefore(const Context&, Element*);
- static int countElementsAfter(const Context&, Element*);
- static int countElementsOfTypeBefore(const Context&, Element*, const QualifiedName&);
- static int countElementsOfTypeAfter(const Context&, Element*, const QualifiedName&);
+ int countElementsBefore(Element*) const;
+ int countElementsAfter(Element*) const;
+ int countElementsOfTypeBefore(Element*, const QualifiedName&) const;
+ int countElementsOfTypeAfter(Element*, const QualifiedName&) const;
};
bool checkSelector(CSSSelector*, Element*, bool isFastCheckableSelector = false) const;
- template<typename CheckingContext>
- SelectorMatch checkSelector(const CheckingContext&, PseudoId&, bool& hasUnknownPseudoElements) const;
- template<typename CheckingContext>
- bool checkOneSelector(const CheckingContext&) const;
+ SelectorMatch checkSelector(const SelectorCheckingContext&, PseudoId&, bool& hasUnknownPseudoElements) const;
+ template<typename SiblingTraversalStrategy>
+ bool checkOneSelector(const SelectorCheckingContext&, const SiblingTraversalStrategy&) const;
static bool isFastCheckableSelector(const CSSSelector*);
bool fastCheckSelector(const CSSSelector*, const Element*) const;