1.Introduction
This section is not normative.
Aselectoris a boolean predicate that takes an element in a tree structure and tests whether the element matches the selector or not.
These expressions may be used for many things:
- directly on an element to test whether it matches some criteria,
such as in the
element.matches()
function defined in[DOM] - applied to an entire tree of elements
to filter it into a set of elements that match the criteria,
such as in the
document.querySelectorAll()
function defined in[DOM]or the selector of a CSS style rule. - used "in reverse" to generate markup that would match a given selector, such as inHAMLorEmmet.
Selectors Levels 1, 2, and 3 are defined as the subsets of selector functionality defined in theCSS1,CSS2.1,andSelectors Level 3specifications, respectively. This module defines Selectors Level 4.
1.1.Module Interactions
This module replaces the definitions of and extends the set of selectors defined for CSS in[SELECT]and[CSS21].
Pseudo-element selectors, which define abstract elements in a rendering tree, are not part of this specification: their generic syntax is described here, but, due to their close integration with the rendering model and irrelevance to other uses such as DOM queries, they will be defined in other modules.
2.Selectors Overview
This section is non-normative, as it merely summarizes the following sections.
A selector represents a structure. This structure can be used as a condition (e.g. in a CSS rule) that determines which elements a selector matches in the document tree, or as a flat description of the HTML or XML fragment corresponding to that structure.
Selectors may range from simple element names to rich contextual representations.
The following table summarizes the Selector syntax:
Pattern | Represents | Section | Level |
---|---|---|---|
*
| any element | § 5.2 Universal selector | 2 |
E
| an element of type E | § 5.1 Type (tag name) selector | 1 |
E:not(s1,s2,…)
| an E element that does not match eithercompound selectors1orcompound selectors2 | § 4.3 The Negation (Matches-None) Pseudo-class::not() | 3/4 |
E:is(s1,s2,…)
| an E element that matchescompound selectors1and/orcompound selectors2 | § 4.2 The Matches-Any Pseudo-class::is() | 4 |
E:where(s1,s2,…)
| an E element that matchescompound selectors1and/orcompound selectors2but contributes no specificity. | § 4.4 The Specificity-adjustment Pseudo-class::where() | 4 |
E:has(rs1,rs2,…)
| an E element, if there exists an element that matches either of therelative selectorsrs1orrs2, when evaluated with E as theanchor elements | § 4.5 The Relational Pseudo-class::has() | 4 |
E.warning
| an E element belonging to the classwarning (the document language specifies how class is determined).
| § 6.6 Class selectors | 1 |
E#myid
| an E element with ID equal tomyid .
| § 6.7 ID selectors | 1 |
E[foo]
| an E element with afoo attribute
| § 6.1 Attribute presence and value selectors | 2 |
E[foo= "bar" ]
| an E element whosefoo attribute value is
exactly equal tobar
| § 6.1 Attribute presence and value selectors | 2 |
E[foo= "bar" i]
| an E element whosefoo attribute value is
exactly equal to any (ASCII-range) case-permutation ofbar
| § 6.3 Case-sensitivity | 4 |
E[foo= "bar" s]
| an E element whosefoo attribute value isidentical tobar
| § 6.3 Case-sensitivity | 4 |
E[foo~= "bar" ]
| an E element whosefoo attribute value is
a list of whitespace-separated values, one of which is
exactly equal tobar
| § 6.1 Attribute presence and value selectors | 2 |
E[foo^= "bar" ]
| an E element whosefoo attribute value
begins exactly with the stringbar
| § 6.2 Substring matching attribute selectors | 3 |
E[foo$= "bar" ]
| an E element whosefoo attribute value
ends exactly with the stringbar
| § 6.2 Substring matching attribute selectors | 3 |
E[foo*= "bar" ]
| an E element whosefoo attribute value
contains the substringbar
| § 6.2 Substring matching attribute selectors | 3 |
E[foo|= "en" ]
| an E element whosefoo attribute value is
a hyphen-separated list of values beginning withen
| § 6.1 Attribute presence and value selectors | 2 |
E:dir(ltr)
| an element of type E with left-to-right directionality (the document language specifies how directionality is determined) | § 7.1 The Directionality Pseudo-class::dir() | 4 |
E:lang(zh, "*-hant" )
| an element of type E tagged as being either in Chinese (any dialect or writing system) or otherwise written with traditional Chinese characters | § 7.2 The Language Pseudo-class::lang() | 2/4 |
E:any-link
| an E element being the source anchor of a hyperlink | § 8.1 The Hyperlink Pseudo-class::any-link | 4 |
E:link
| an E element being the source anchor of a hyperlink of which the target is not yet visited | § 8.2 The Link History Pseudo-classes::link and:visited | 1 |
E:visited
| an E element being the source anchor of a hyperlink of which the target is already visited | § 8.2 The Link History Pseudo-classes::link and:visited | 1 |
E:local-link
| an E element being the source anchor of a hyperlink targeting the current URL | § 8.3 The Local Link Pseudo-class::local-link | 4 |
E:target
| an E element being the target of the current URL | § 8.4 The Target Pseudo-class::target | 3 |
E:target-within
| an E element that is the target of the current URL or contains an element that does. | § 8.5 The Target Container Pseudo-class::target-within | 4 |
E:scope
| an E element being ascoping root | § 8.6 The Reference Element Pseudo-class::scope | 4 |
E:current
| an E element that is currently presented in a time-dimensional canvas | § 10.1 The Current-element Pseudo-class::current | 4 |
E:current(s)
| an E element that is the deepest:currentelement that matches selectors | § 10.1 The Current-element Pseudo-class::current | 4 |
E:past
| an E element that is in the past in a time-dimensional canvas | § 10.2 The Past-element Pseudo-class::past | 4 |
E:future
| an E element that is in the future in a time-dimensional canvas | § 10.3 The Future-element Pseudo-class::future | 4 |
E:active
| an E element that is in an activated state | § 9.2 The Activation Pseudo-class::active | 1 |
E:hover
| an E element that is under the cursor, or that has a descendant under the cursor | § 9.1 The Pointer Hover Pseudo-class::hover | 2 |
E:focus
| an E element that has user input focus | § 9.3 The Input Focus Pseudo-class::focus | 2 |
E:focus-within
| an E element that has user input focus or contains an element that has input focus. | § 9.5 The Focus Container Pseudo-class::focus-within | 4 |
E:focus-visible
| an E element that has user input focus, and the UA has determined that a focus ring or other indicator should be drawn for that element | § 9.4 The Focus-Indicated Pseudo-class::focus-visible | 4 |
E:enabled
| a user interface element E that is enabled or disabled, respectively | § 13.1.1 The:enabled and:disabled Pseudo-classes | 3 |
E:read-write E:read-only
| a user interface element E that is user alterable, or not | § 13.1.2 The Mutability Pseudo-classes::read-only and:read-write | 3-UI/4 |
E:placeholder-shown
| an input control currently showing placeholder text | § 13.1.3 The Placeholder-shown Pseudo-class::placeholder-shown | 3-UI/4 |
E:default
| a user interface element E that is the default item in a group of related choices | § 13.1.5 The Default-option Pseudo-class::default | 3-UI/4 |
E:checked
| a user interface element E that is checked/selected (for instance a radio-button or checkbox) | § 13.2.1 The Selected-option Pseudo-class::checked | 3 |
E:indeterminate
| a user interface element E that is in an indeterminate state (neither checked nor unchecked) | § 13.2.2 The Indeterminate-value Pseudo-class::indeterminate | 4 |
E:valid E:invalid
| a user-input element E that meets, or doesn’t, its data validity semantics | § 13.3.2 The Validity Pseudo-classes::valid and:invalid | 3-UI/4 |
E:in-range E:out-of-range
| a user-input element E whose value is in-range/out-of-range | § 13.3.3 The Range Pseudo-classes::in-range and:out-of-range | 3-UI/4 |
E:required E:optional
| a user-input element E that requires/does not require input | § 13.3.4 The Optionality Pseudo-classes::required and:optional | 3-UI/4 |
E:blank
| a user-input element E whose value is blank (empty/missing) | § 13.3.1 The Empty-Value Pseudo-class::blank | 4 |
E:user-invalid
| a user-altered user-input element E with incorrect input (invalid, out-of-range, omitted-but-required) | § 13.3.5 The User-interaction Pseudo-classes::user-valid and:user-invalid | 4 |
E:root
| an E element, root of the document | § 14.1:root pseudo-class | 3 |
E:empty
| an E element that has no children (neither elements nor text) except perhaps white space | § 14.2:empty pseudo-class | 3 |
E:nth-child(n[ofS]?)
| an E element, then-th child of its parent matchingS | § 14.3.1:nth-child() pseudo-class | 3/4 |
E:nth-last-child(n[ofS]?)
| an E element, then-th child of its parent matchingS, counting from the last one | § 14.3.2:nth-last-child() pseudo-class | 3/4 |
E:first-child
| an E element, first child of its parent | § 14.3.3:first-child pseudo-class | 2 |
E:last-child
| an E element, last child of its parent | § 14.3.4:last-child pseudo-class | 3 |
E:only-child
| an E element, only child of its parent | § 14.3.5:only-child pseudo-class | 3 |
E:nth-of-type(n)
| an E element, then-th sibling of its type | § 14.4.1:nth-of-type() pseudo-class | 3 |
E:nth-last-of-type(n)
| an E element, then-th sibling of its type, counting from the last one | § 14.4.2:nth-last-of-type() pseudo-class | 3 |
E:first-of-type
| an E element, first sibling of its type | § 14.4.3:first-of-type pseudo-class | 3 |
E:last-of-type
| an E element, last sibling of its type | § 14.4.4:last-of-type pseudo-class | 3 |
E:only-of-type
| an E element, only sibling of its type | § 14.4.5:only-of-type pseudo-class | 3 |
E F
| an F element descendant of an E element | § 15.1 Descendant combinator ( ) | 1 |
E > F
| an F element child of an E element | § 15.2 Child combinator (>) | 2 |
E + F
| an F element immediately preceded by an E element | § 15.3 Next-sibling combinator (+) | 2 |
E ~ F
| an F element preceded by an E element | § 15.4 Subsequent-sibling combinator (~) | 3 |
F || E
| an E element that represents a cell in a grid/table belonging to a column represented by an element F | § 16.1 Column combinator (||) | 4 |
E:nth-col(n)
| an E element that represents a cell belonging to thenth column in a grid/table | § 16.2:nth-col() pseudo-class | 4 |
E:nth-last-col(n)
| an E element that represents a cell belonging to thenth column in a grid/table, counting from the last one | § 16.3:nth-last-col() pseudo-class | 4 |
Note:Some Level 4 selectors (noted above as "3-UI" ) were introduced in[CSS3UI].
3.Selector Syntax and Structure
3.1.Structure and Terminology
Aselectorrepresents a particular pattern of element(s) in a tree structure. The termselectorcan refer to asimple selector,compound selector,complex selector,orselector list. Thesubject of a selectoris any element that selector is defined to be about; that is, any elementmatchingthatselector.
Asimple selectoris a single condition on an element. Atype selector,universal selector,attribute selector,class selector,ID selector, orpseudo-classis asimple selector. (It is represented by<simple-selector>in the selectorsgrammar.) A given element is said tomatchasimple selectorwhen thatsimple selector, as defined in this specification and in accordance with thedocument language, accurately describes the element.
Acompound selectoris a sequence ofsimple selectorsthat are not separated by acombinator, and represents a set of simultaneous conditions on a single element. If it contains atype selectororuniversal selector, that selector must come first in the sequence. Only one type selector or universal selector is allowed in the sequence. (Acompound selectoris represented by<compound-selector>in the selectorsgrammar.) A given element is said tomatchacompound selectorwhen it matches allsimple selectorsin thecompound selector.
Note:As whitespace represents thedescendant combinator, no whitespace is allowed between thesimple selectorsin acompound selector.
Apseudo-compound selectoris apseudo-elementselector, optionally followed by additionalpseudo-classselectors, and optionally preceded by acompound selectoror anotherpseudo-compound selector, without anycombinators. (Apseudo-compound selectoris represented by<pseudo-compound-selector>in the selectorsgrammar.) Apseudo-elementmatchesapseudo-compound selectorwhen it has the specified pseudo-element name, matches the additional conditions represented by anypseudo-classes, and has anoriginating elementrepresented by the adjacent preceding selector. If there is no adjacent preceding selector, theuniversal selectoris assumed. (For example,.foo::beforeis equivalent to.foo *::before, and distinct from.foo::before.)
Note:Apseudo-compound selectoris notacompound selector, and can’t be used in places that expect acompound selectoronly.Pseudo-compound selectorsact as if they carry acombinatorwith themselves, expressing their relationship with theiroriginating element, just as the>combinator expresses a relationship with a parent element.
Acombinatoris a condition of relationship between two elements
represented by thecompound selectorson either side.
Combinators in Selectors Level 4 include:
thedescendant combinator(white space),
thechild combinator(U+003E,>
),
thenext-sibling combinator(U+002B,+
),
and thesubsequent-sibling combinator(U+007E,~
).
Two given elements are said tomatchacombinatorwhen the condition of relationship between these elements is true.
Acomplex selectoris a sequence of one or morecompound selectorsand/orpseudo-compound selectors, withcompound selectorsseparated bycombinators. It represents a set of simultaneous conditions on a set of elements in the particular relationships described by itscombinators. (Complex selectors are represented by<complex-selector>in the selectorsgrammar.) A given element or pseudo-element is said tomatchacomplex selectorwhen it matches the finalcompound/pseudo-compound selectorin the sequence, and every preceding unit of the sequence alsomatchesan element orpseudo-element, with the correct relationship between consecutive units as expressed by the combinators separating them (or, forpseudo-compound selectors, the correctoriginating elementrelationship).
.ancestor >.foo.barmatches a subset of those elements: only those whose parent element (as indicated by the>combinator) has the "ancestor" class.
.foo.bar::beforematches a::beforepseudo-element, whoseoriginating elementmatches.foo.bar.
Alist of simple/compound/complex selectorsis a comma-separated list ofsimple,compound, orcomplex selectors. This is also called just aselector listwhen the type is either unimportant or specified in the surrounding prose; if the type is important and unspecified, it defaults to meaning alist of complex selectors. (See§ 4.1 Selector Listsfor additional information onselector listsand the various <*-selector-list> productions in thegrammarfor their formal syntax.) A given element is said tomatchaselector listwhen it matches any (at least one) of theselectorsin thatselector list.
3.2.Data Model
Selectors are evaluated against an element tree such as the DOM.[DOM]Within this specification, this may be referred to as the "document tree" or "source document".
Each element may have any of the following five aspects, which can be selected against, all of which are matched as strings:
- The element’s type (also known as its tag name).
- The element’s namespace.
- An ID.
- Classes (named groups) to which it belongs.
- Attributes, which are name-value pairs.
Many of the selectors depend on the semantics of thedocument language(i.e. the language and semantics of the document tree) and/or the semantics of thehost language(i.e. the language that is using selectors syntax). For example, the:lang()selector depends on thedocument language(e.g. HTML) to define how an element is associated with a language. As a slightly different example, the::first-linepseudo-element depends on thehost language(e.g. CSS) to define what a::first-linepseudo-element represents and what it can do.
3.2.1.Featureless Elements
While individual elements may lack any of the above features, some elements arefeatureless. Afeaturelesselement does not matchany selector at all, except:
-
simple selectorsit is explicitly defined to match
-
compound selectors, if all containedsimple selectorsare allowed to match it
-
complex selectors, if thecompound selectortargeting thesubjectis allowed to match it
-
selector lists, if at least one selector in the list is allowed to match it
-
logical combination pseudo-classes, if their argument selector is allowed to match it
-
the:has()pseudo-class, if and only if thecompound selectorit’s part of contains at least oneothersimple selectorthat’s allowed to match it.
If a selector would otherwise match afeaturelesselement, except for the existence of the default namespace[CSS-NAMESPACES-3](becausefeaturelesselements do not have a namespace unless otherwise defined), the default namespace does not prevent the match.
Logical combinations like:not(.foo:host)will never match the host element (even if it doesn’t have a "foo" class), because not all of the simple selectors in.foo:hostare allowed to match theshadow host.
Similarly,:not(:host >.foo)will never match theshadow host, even tho theshadow hostis indeed *not* a descendant of itself and doesn’t have the "foo" class, because the subject of the complex selector argument (.foo) isn’t allowed to match theshadow host.
The rule for:has(),above, works similarly. Even if ashadow hostcontains a.foodescendant,:has(.foo)will not match it, becausethe restof the compound selector (empty) doesn’t contain a simple selector that can match the host. You have to write:host:has(.foo)in order to match the host element.
3.3.Scoped Selectors
Some host applications may choose toscopeselectors to a particular subtree or fragment of the document, The root of the scoping subtree is called thescoping root.
When a selector isscoped, it matches an element only if the element is a descendant of thescoping root. (The rest of the selector can match unrestricted; it’s only the final matched elements that must be within the scope.)
querySelector()
method defined in[DOM]allows the author to evaluate ascopedselector
relative to the element it’s called on.
A call likewidget
will thus only finda
elements inside of thewidget
element,
ignoring any othera
s that might be scattered throughout the document.
3.4.Relative Selectors
Certain contexts may acceptrelative selectors, which are a shorthand for selectors that represent elements relative to one or morerelative selector anchor elements. Relative selectors begin with acombinator, with a selector representing theanchor elementimplied at the start of the selector. (If no combinator is present, thedescendant combinatoris implied.)
Relative selectors are represented by<relative-selector>in the selectorsgrammar, and lists of them by<relative-selector-list>.
3.5.Pseudo-classes
Pseudo-classesaresimple selectorsthat permit selection based on information that lies outside of the document tree or that can be awkward or impossible to express using the other simple selectors. They can also be dynamic, in the sense that an element can acquire or lose a pseudo-class while a user interacts with the document, without the document itself changing.Pseudo-classesdo not appear in or modify the document source or document tree.
The syntax of apseudo-classconsists of a ":" (U+003A COLON) followed by the name of thepseudo-classas a CSSidentifier, and, in the case of afunctional pseudo-class, a pair of parentheses containing its arguments.
For example,:validis a regular pseudo-class, and:lang()is afunctional pseudo-class.
Like all CSS keywords,pseudo-classnames areASCII case-insensitive. Nowhite spaceis allowed between the colon and the name of thepseudo-class, nor, as usual for CSS syntax, between afunctional pseudo-class’s name and its opening parenthesis (which thus form a CSSfunction token). Also as usual,white spaceis allowed around the arguments inside the parentheses of a functional pseudo-class unless otherwise specified.
Like othersimple selectors,pseudo-classesare allowed in allcompound selectorscontained in a selector, and must follow thetype selectororuniversal selector,if present.
Note:Somepseudo-classesare mutually exclusive (such that acompound selectorcontaining them, while valid, will never match anything), while others can apply simultaneously to the same element.
3.6.Pseudo-elements
Similar to how certainpseudo-classesrepresent additional state information not directly present in the document tree, apseudo-elementrepresents anelementnot directly present in the document tree. They are used to create abstractions about the document tree beyond those provided by the document tree. For example, pseudo-elements can be used to select portions of the document that do not correspond to a document-language element (including such ranges as don’t align to element boundaries or fit within its tree structure); that represent content not in the document tree or in an alternate projection of the document tree; or that rely on information provided by styling, layout, user interaction, and other processes that are not reflected in the document tree.
Pseudo-elementscan also represent content that doesn’t exist in the source document at all, such as the::beforeand::afterpseudo-elements which allow additional content to be inserted before or after the contents of any element.
Likepseudo-classespseudo-elementsdo not appear in or modify the document source or document tree. Accordingly, they also do not affect the interpretation ofstructural pseudo-classesor other selectors pertaining to theiroriginating elementor its tree.
The host language defines which pseudo-elements exist, their type, and their abilities. Pseudo-elements that exist in CSS are defined in[CSS21](Level 2),[SELECT](Level 3), and[CSS-PSEUDO-4](Level 4).
3.6.1.Syntax
The syntax of apseudo-elementis "::" (two U+003A COLON characters) followed by the name of thepseudo-elementas anidentifier, and, in the case of afunctional pseudo-element, a pair of parentheses containing its arguments.Pseudo-elementnames areASCII case-insensitive. Nowhite spaceis allowed between the two colons, or between the colons and the name.
BecauseCSS Level 1andCSS Level 2conflated pseudo-elements and pseudo-classes by sharing a single-colon syntax for both, user agents must also accept the previous one-colon notation for the Level 1 & 2 pseudo-elements (::before,::after,::first-line,and::first-letter). This compatibility notation is not allowed for any otherpseudo-elements. However, as this syntax is deprecated, authors should use the Level 3+ double-colon syntax for thesepseudo-elements.
Pseudo-elementsarefeatureless, and so can’t be matched by any other selector.
3.6.2.Binding to the Document Tree
Pseudo-elementsdo not exist independently in the tree: they are always bound to another element on the page, called theiroriginating element. Syntactically, apseudo-elementimmediately follows thecompound selectorrepresenting itsoriginating element. If thiscompound selectoris omitted, it is assumed to be theuniversal selector*.
The selector::first-lineis equivalent to*::first-line, which selects the::first-linepseudo-element oneveryelement in the document.
When apseudo-elementis encountered in a selector, the part of the selector before thepseudo-elementselects theoriginating elementfor thepseudo-element; the part of the selector after it, if any, applies to thepseudo-elementitself. (See below.)
3.6.3.Pseudo-classing Pseudo-elements
Certainpseudo-elementsmay be immediately followed by any combination of certainpseudo-classes, in which case thepseudo-elementis represented only when it is in the corresponding state. This specification allows anypseudo-elementto be followed by any combination of thelogical combination pseudo-classesand theuser action pseudo-classes. Other specifications may allow additionalpseudo-classesto be attached to particularpseudo-elements. Combinations that are not explicitly allowed areinvalid selectors.
Note:Thelogical combination pseudo-classespass any restrictions on validity of selectors at their position to their arguments.
Notice that::first-line:hoveris very different from:hover::first-line, which matches the first line of any originating element that is hovered! For example,:hover::first-linealso matches the first line of a paragraph when the second line of the paragraph is hovered, whereas::first-line:hoveronly matches if the first line itself is hovered.
3.6.4.Sub-pseudo-elements
Somepseudo-elementsare able to be theoriginating elementof otherpseudo-elements, which are defined as thesub-pseudo-elementsof thisoriginating pseudo-element. For example, when::beforeis given alist-itemdisplay type, it becomes theoriginating pseudo-elementof its::before::markersub-pseudo-element.
Where disambiguation is needed, the termultimate originating elementrefers to the real (non-pseudo) element from which apseudo-elementoriginates.
Unless the correspondingsub-pseudo-elementis explicitly defined to exist in another specification, pseudo-element selectors are not valid when compounded to another pseudo-element selector. So, for example,::before::beforeis an invalid selector, but::before::markeris valid (in implementations that support the::before::markersub-pseudo-element).
3.6.5.Internal Structure
Somepseudo-elementsare defined to have internal structure. Thesepseudo-elementsmay be followed by child/descendant combinators to express those relationships. Selectors containingcombinatorsafter the pseudo-element are otherwise invalid.
Note:A future specification may expand the capabilities of existing pseudo-elements, so some of these currently-invalid selectors (e.g.::first-line:any-link) may become valid in the future.
The children of suchpseudo-elementscan simultaneously be children of other elements, too. However, at least in CSS, their rendering must be defined so as to maintain the tree-ness of thebox tree.
3.7.Characters and case sensitivity
All Selectors syntax isASCII case-insensitive(i.e. [a-z] and [A-Z] are equivalent), except for the parts that are not under the control of Selectors: specifically, the case-sensitivity of document language element names, attribute names, and attribute values depends on the document language.
Case sensitivity of namespace prefixes is defined in[CSS3NAMESPACE]. Case sensitivity oflanguage rangesis defined in the:lang()section.
White spacein Selectors consists of the code points SPACE (U+0020), TAB (U+0009), LINE FEED (U+000A), CARRIAGE RETURN (U+000D), and FORM FEED (U+000C). Other space-like code points, such as EM SPACE (U+2003) and IDEOGRAPHIC SPACE (U+3000), are never considered syntactic white space.
Code points in Selectors can be escaped with a backslash
according to the sameescaping rulesas CSS.[CSS21]Note that escaping a code point “cancels out”
any special meaning it may have in Selectors.
For example, the selector#foo>acontains a combinator,
but#foo\>ainstead selects an element with the idfoo>a
.
3.8.Declaring Namespace Prefixes
Certain selectors support namespace prefixes. The mechanism by which namespace prefixes aredeclaredshould be specified by the language that uses Selectors. If the language does not specify a namespace prefix declaration mechanism, then no prefixes are declared. In CSS, namespace prefixes are declared with the@namespacerule.[CSS3NAMESPACE]
3.9.Invalid Selectors and Error Handling
User agents must observe the rules for handlinginvalid selectors:
- a parsing error in a selector, e.g. an unrecognized token or a token which is not allowed at the current parsing point (see overall§ 18 Grammarand per-selector syntax definitions), causes that selector to be invalid.
- a simple selector containing anundeclared namespace prefixis invalid
- a selector containing an invalid simple selector, an invalid combinator or an invalid token is invalid.
- a selector list containing an invalid selector is invalid.
- an empty selector, i.e. one that contains nocompound selector,is invalid.
Note:Consistent with CSS’s forwards-compatible parsing principle, UAsmusttreat asinvalidany pseudo-classes, pseudo-elements, combinators, or other syntactic constructs for which they have no usable level of support. SeePartial implementations.
Aninvalid selectorrepresents, and therefore matches, nothing.
3.10.Legacy Aliases
Some selectors have alegacy selector alias. This is a name which, at parse time, is converted to the standard name (and thus does not appear anywhere in any object model representing the selector).
4.Logical Combinations
Selector logic can be manipulated bycompounding(logical AND),selector lists(logical OR), and thelogical combination pseudo-classes:is(),:where(),and:not(). Thelogical combination pseudo-classesare allowed anywhere that any otherpseudo-classesare allowed, but pass any restrictions to their arguments. (For example, if onlycompound selectorsare allowed, then onlycompound selectorsare valid within an:is().)
Note:Since inside:is()and:where()invalid arguments are dropped without invaliding thepseudo-classitself, selector arguments that are invalidated by contextual restrictions likewise do not invalidate the:is()pseudo-class itself.
4.1.Selector Lists
A comma-separated list of selectors represents the union of all elements selected by each of the individual selectors in theselector list. (A comma is U+002C.) For example, in CSS when several selectors share the same declarations, they may be grouped into a comma-separated list. White space may appear before and/or after the comma.
h1 { font-family: sans-serif } h2 { font-family: sans-serif } h3 { font-family: sans-serif }
is equivalent to:
h1, h2, h3 { font-family: sans-serif }
Warning:the equivalence is true in this example because all the selectors are valid selectors. If just one of these selectors were invalid, the entireselector listwould be invalid. This would invalidate the rule for all three heading elements, whereas in the former case only one of the three individual heading rules would be invalidated.
h1 { font-family: sans-serif } h2..foo { font-family: sans-serif } h3 { font-family: sans-serif }
is not equivalent to:
h1, h2..foo, h3 { font-family: sans-serif }
because the above selector (h1, h2..foo, h3) is entirely invalid and the entire style rule is dropped. (When the selectors are not grouped, only the rule forh2..foois dropped.)
4.2.The Matches-Any Pseudo-class::is()
The matches-any pseudo-class,:is(), is a functional pseudo-class taking a<forgiving-selector-list>as its sole argument.
If the argument, after parsing, is an empty list, the pseudo-class is valid but matches nothing. Otherwise, the pseudo-class matches any element that matches any of the selectors in the list.
Note:The specificity of the:is()pseudo-class
is replaced by the specificity of its most specific argument.
Thus, a selector written with:is()does not necessarily have equivalent specificity
to the equivalent selector written without:is()For example, if we have:is(ul, ol,.list) > [hidden]andul > [hidden], ol > [hidden],.list > [hidden]a[hidden]child of anol
matches the first selector
with a specificity of (0,2,0)
whereas it matches the second selector
with a specificity of (0,1,1).
See§ 17 Calculating a selector’s specificity.
Pseudo-elements cannot be represented by the matches-any pseudo-class; they are not valid within:is().
Default namespace declarations do not affect thecompound selectorrepresenting thesubjectof any selector within a:is()pseudo-class, unless that compound selector contains an explicituniversal selectorortype selector.
*|*:is(:hover,:focus)
The following selector, however, represents only hovered or focused elements that are in the default namespace, because it uses an explicit universal selector within the:is()notation:
*|*:is(*:hover, *:focus)
As previous drafts of this specification used the name:matches()for this pseudo-class, UAs may additionally implement this obsolete name as alegacy selector aliasfor:is()if needed for backwards-compatibility.
4.3.The Negation (Matches-None) Pseudo-class::not()
The negation pseudo-class,:not(), is a functional pseudo-class taking a<complex-real-selector-list>as an argument. It represents an element that is not represented by its argument.
Note:In Selectors Level 3, only a singlesimple selectorwas allowed as the argument to:not().
Note:The specificity of the:not()pseudo-class is replaced by the specificity of the most specific selector in its argument; thus it has the exact behavior of:not(:is(argument)). See§ 17 Calculating a selector’s specificity.
Pseudo-elements cannot be represented by the negation pseudo-class; they are not valid within:not().
button:not([DISABLED])
The following selector represents all but FOO elements.
*:not(FOO)
The following compound selector represents all HTML elements except links.
html|*:not(:link):not(:visited)
As with:is(), default namespace declarations do not affect thecompound selectorrepresenting thesubjectof any selector within a:not()pseudo-class, unless that compound selector contains an explicituniversal selectorortype selector. (See:is()for examples.)
Note:The:not()pseudo-class allows useless selectors to be written. For instance:not(*|*),which represents no element at all, ordiv:not(span),which is equivalent todivbut with a higher specificity.
4.4.The Specificity-adjustment Pseudo-class::where()
The Specificity-adjustment pseudo-class,:where(), is a functional pseudo-class with the same syntax and functionality as:is(). Unlike:is(),neither the:where()pseudo-class, nor any of its arguments, contribute to thespecificityof the selector—itsspecificityis always zero.
This is useful for introducing filters in a selector while keeping the associated style declarations easy to override.
a:not(:hover) { text-decoration: none; } nav a { /* Has no effect */ text-decoration: underline; }
However, by using:where()the author can explicitly declare their intent:
a:where(:not(:hover)) { text-decoration: none; } nav a { /* Works now! */ text-decoration: underline; }
Note:Future levels of Selectors may introduce an additional argument to explicitly set the specificity of that instance of the pseudo-class.
4.5.The Relational Pseudo-class::has()
The relational pseudo-class,:has(), is a functional pseudo-class taking a<relative-selector-list>as an argument. It represents an element if any of therelative selectorswould match at least one element whenanchored againstthis element.
The:has()pseudo-class cannot be nested;:has()is not valid within:has(). Also, unless explicitly defined as a:has-allowed pseudo-element,pseudo-elementsare not valid selectors within:has(). (This specification does not define any:has-allowed pseudo-elements, but other specifications may do so.)
Note:Pseudo-elements are generally excluded from:has()because many of them exist conditionally, based on the styling of their ancestors, so allowing these to be queried by:has()would introduce cycles.
Note:Since:has()takes a<relative-selector-list>, its arguments areinherentlycomplex selectors(because they start, perhaps implicitly, with a combinator). This means:has()cannot be used in contexts that don’t allow complex selectors; its arguments will be guaranteed to be invalid.
<a>
elements that contain an<img>
child:
a:has(> img)
The following selector matches a<dt>
element
immediately followed by another<dt>
element:
dt:has(+ dt)
The following selector matches<section>
elements
that don’t contain any heading elements:
section:not(:has(h1, h2, h3, h4, h5, h6))
Note that ordering matters in the above selector. Swapping the nesting of the two pseudo-classes, like:
section:has(:not(h1, h2, h3, h4, h5, h6))
...would result in matching any<section>
element
which contains anything that’s not a heading element.
5.Elemental selectors
5.1.Type (tag name) selector
Atype selectoris the name of a document language element type, and represents an instance of that element type in the document tree.
Atype selectoris written as aCSS qualified name: anidentifierwith an optional namespace prefix.[CSS3NAMESPACE](See§ 5.3 Namespaces in Elemental Selectors.)
5.2.Universal selector
Theuniversal selectoris a specialtype selector, that represents an element of any element type.
It is written as aCSS qualified namewith an asterisk (*
U+002A) as the local name.
Like atype selector,
theuniversal selectorcan be qualified by a namespace,
restricting it to only elements belonging to that namespace,
and is affected by a default namespace as defined in§ 5.3 Namespaces in Elemental Selectors.
Unless an element isfeatureless, the presence of auniversal selectorhas no effect on whether the element matches the selector. (Featurelesselements do not match any selector, including theuniversal selector.)
- *[hreflang|=en]and[hreflang|=en]are equivalent,
- *.warningand.warningare equivalent,
- *#myidand#myidare equivalent.
Theuniversal selectorfollows the same syntax rules as othertype selectors: only one can appear percompound selector, and it must be the firstsimple selectorin thecompound selector.
Note:In some cases, adding auniversal selectorcan make a selector easier to read, even though it has no effect on the matching behavior. For example,div:first-childanddiv:first-childare somewhat difficult to tell apart at a quick glance, but writing the former asdiv *:first-childmakes the difference obvious.
5.3.Namespaces in Elemental Selectors
Type selectorsanduniversal selectorsallow an optional namespace component:
a namespace prefix that has been previouslydeclaredmay be prepended to the element name separated by the namespace separator “vertical bar” (|
U+007C).
(See, e.g.,[XML-NAMES]for the use of namespaces in XML.)
It has the following meaning in each form:
ns|E
- elements with name E in namespace ns
*|E
- elements with name E in any namespace, including those without a namespace
|E
- elements with name E without a namespace
E
- if no default namespace has beendeclaredfor selectors, this is equivalent to *|E. Otherwise it is equivalent to ns|E where ns is the default namespace.
@namespace foo url(http://www.example.com); foo|h1 { color: blue } /* first rule */ foo|* { color: yellow } /* second rule */ |h1 { color: red } /*...*/ *|h1 { color: green } h1 { color: green }
The first rule (not counting the@namespaceat-rule) will match onlyh1elements in the "http://www.example.com" namespace.
The second rule will match all elements in the "http://www.example.com" namespace.
The third rule will match onlyh1elements with no namespace.
The fourth rule will matchh1elements in any namespace (including those without any namespace).
The last rule is equivalent to the fourth rule because no default namespace has been defined.
If adefault namespaceis declared,compound selectorswithouttype selectorsin them still only match elements in that default namespace.
@namespace url( "http://example.com/foo" ); .special {... }
The.specialselector only matches elements in the "http://example.com/foo" namespace, even though no reference to the type name (which is paired with the namespace in the DOM) appeared.
Atype selectororuniversal selectorcontaining a namespace prefix that has not been previouslydeclaredis aninvalid selector.
5.4.The Defined Pseudo-class::defined
In some host languages, elements can have a distinction between being “defined” / “constructed” or not. The:definedpseudo-classmatches elements that are fully defined, as dictated by the host language.
If the host language does not have this sort of distinction, all elements in it match:defined.
p : defined{ ...}
Custom elements,on the other hand, start outundefined, and only become defined whenproperly registered. This means the:definedpseudo-class can be used to hide a custom element until it has been registered:
custom-element { visibility: hidden }
custom-element:defined { visibility: visible }
6.Attribute selectors
Selectors allow the representation of an element’s attributes. When a selector is used as an expression to match against an element, anattribute selectormust be considered to match an element if that element has an attribute that matches the attribute represented by the attribute selector.
Add comma-separated syntax formultiple-value matching? e.g. [rel ~= next, prev, up, first, last]
6.1.Attribute presence and value selectors
CSS2 introduced four attribute selectors:
- [att]
- Represents an element with the
att
attribute, whatever the value of the attribute. - [att=val]
- Represents an element with the
att
attribute whose value is exactly "val". - [att~=val]
- Represents an element with the
att
attribute whose value is awhitespace-separated list of words, one of which is exactly "val". If "val" contains whitespace, it will never represent anything (since the words areseparatedby spaces). Also if "val" is the empty string, it will never represent anything. - [att|=val]
- Represents an element with the
att
attribute, its value either being exactly "val" or beginning with "val" immediately followed by "-" (U+002D). This is primarily intended to allow language subcode matches (e.g., thehreflang
attribute on theaelement in HTML) as described in BCP 47 ([BCP47]) or its successor. Forlang
(orxml:lang
) language subcode matching, please see the:lang()pseudo-class.
Attribute values must be<ident-token>s or<string-token>s.[CSS3SYN]
The following attribute selector represents anh1element
that carries thetitle
attribute,
whatever its value:
h1[title]
In the following example, the selector represents aspanelement whoseclass
attribute has
exactly the value "example":
span[class= "example" ]
Multiple attribute selectors can be used to represent several
attributes of an element, or several conditions on the same
attribute. Here, the selector represents aspanelement
whosehello
attribute has exactly the value "Cleveland"
and whosegoodbye
attribute has exactly the value
"Columbus":
span[hello= "Cleveland" ][goodbye= "Columbus" ]
The following CSS rules illustrate the differences between
"=" and "~=". The first selector would match, for example, anaelement with the value "copyright copyleft
copyeditor" on arel
attribute. The second selector
would only match anaelement with anhref
attribute having the exact value "http://www.w3.org/".
a[rel~= "copyright" ] {... } a[href= "http://www.w3.org/" ] {... }
The following selector represents anaelement
whosehreflang
attribute is exactly "fr".
a[hreflang=fr]
The following selector represents anaelement for
which the value of thehreflang
attribute begins with
"en", including "en", "en-US", and "en-scouse":
a[hreflang|= "en" ]
The following selectors represent aDIALOGUEelement
whenever it has one of two different values for an attributecharacter
:
DIALOGUE[character=romeo] DIALOGUE[character=juliet]
6.2.Substring matching attribute selectors
Three additional attribute selectors are provided for matching substrings in the value of an attribute:
- [att^=val]
- Represents an element with the
att
attribute whose value begins with the prefix "val". If "val" is the empty string then the selector does not represent anything. - [att$=val]
- Represents an element with the
att
attribute whose value ends with the suffix "val". If "val" is the empty string then the selector does not represent anything. - [att*=val]
- Represents an element with the
att
attribute whose value contains at least one instance of the substring "val". If "val" is the empty string then the selector does not represent anything.
Attribute values must be<ident-token>s or<string-token>s.
object[type^= "image/" ]
The following selector represents an HTMLaelement
with anhref
attribute whose value ends with ".html".
a[href$= ".html" ]
The following selector represents an HTML paragraph
with atitle
attribute whose value contains the substring "hello"
p[title*= "hello" ]
6.3.Case-sensitivity
By default case-sensitivity of attribute names and values in selectors depends on the document language.
To match attribute valuesASCII case-insensitivelyregardless of document language rules,
the attribute selector may include the identifieri
before the closing bracket (]
).
When this flag is present,
UAs must match the attribute’s valueASCII case-insensitively(i.e. [a-z] and [A-Z] are considered equivalent).
Alternately, the attribute selector may include the identifiers
before the closing bracket (]
);
in this case the UA must match the value case-sensitively,
with “identical to”semantics[INFRA],
regardless of document language rules.
Like the rest of Selectors syntax,
thei
ands
identifiers themselves
areASCII case-insensitive.
frame
attribute when it
has a value ofhsides
,whether that value is represented
ashsides
,HSIDES
,hSides
,etc.
even in an XML environment where attribute values are case-sensitive.
[frame=hsides i] { border-style: solid none; }
type= "a"
attributes differently thantype= "A"
even though HTML defines thetype
attribute
to be case-insensitive.
[type= "a" s] { list-style: lower-alpha; } [type= "A" s] { list-style: upper-alpha; }
Note:Some document models normalize case-insensitive attribute values at parse time
such that checking if a string is case-sensitive matching is impossible.
Case-sensitive matching vias
flags is only possible
in systems that preserve the original case.
6.4.Attribute selectors and namespaces
The attribute name in an attribute selector is given as aCSS qualified name:a namespace prefix that has been previouslydeclaredmay be prepended to the attribute name separated by the namespace
separator "vertical bar" (|
). In keeping with
the Namespaces in the XML recommendation, default namespaces do not
apply to attributes, therefore attribute selectors without a namespace
component apply only to attributes that have no namespace (equivalent
to|attr). An asterisk may be used for
the namespace prefix indicating that the selector is to match all
attribute names without regard to the attribute’s namespace.
An attribute selector with an attribute name containing a namespace prefix that has not been previouslydeclaredis an invalid selector.
@namespace foo "http://www.example.com"; [foo|att=val] { color: blue } [*|att] { color: yellow } [|att] { color: green } [att] { color: green }
The first rule will match only elements with the attributeatt
in the "http://www.example.com" namespace with the
value "val".
The second rule will match only elements with the attributeatt
regardless of the namespace of the attribute
(including no namespace).
The last two rules are equivalent and will match only elements
with the attributeatt
where the attribute is not
in a namespace.
6.5.Default attribute values in DTDs
Attribute selectors represent attribute values in the document tree. How that document tree is constructed is outside the scope of Selectors. In some document formats default attribute values can be defined in a DTD or elsewhere, but these can only be selected by attribute selectors if they appear in the document tree. Selectors should be designed so that they work whether or not the default values are included in the document tree.
For example, a XML UA may, but isnotrequired to, read an “external subset” of the DTD, butisrequired to look for default attribute values in the document’s “internal subset”. (See, e.g.,[XML10]for definitions of these subsets.) Depending on the UA, a default attribute value defined in the external subset of the DTD might or might not appear in the document tree.
A UA that recognizes an XML namespace may, but is not required to use its knowledge of that namespace to treat default attribute values as if they were present in the document. (For example, an XHTML UA is not required to use its built-in knowledge of the XHTML DTD. See, e.g.,[XML-NAMES]for details on namespaces in XML 1.0.)
Note:Typically, implementations choose to ignore external subsets. This corresponds to the behavior of non-validating processors as defined by the XML specification.
Consider an elementEXAMPLE
with an attributeradix
that has a default value of"decimal"
.The DTD fragment might be
<!ATTLIST EXAMPLE radix (decimal,octal) "decimal" >
If the style sheet contains the rules
EXAMPLE[radix=decimal] { /*... default property settings...*/ } EXAMPLE[radix=octal] { /*... other settings...*/ }
the first rule might not match elements whoseradix
attribute is
set by default, i.e. not set explicitly. To catch all cases, the
attribute selector for the default value must be dropped:
EXAMPLE { /*... default property settings...*/ } EXAMPLE[radix=octal] { /*... other settings...*/ }
Here, because the selectorEXAMPLE[radix=octal]is
more specific than the type selector alone, the style declarations in
the second rule will override those in the first for elements that
have aradix
attribute value of"octal"
.Care has to be taken that
all property declarations that are to apply only to the default case
are overridden in the non-default cases' style rules.
6.6.Class selectors
Theclass selectoris given as a full stop (. U+002E) immediately
followed by an identifier. It represents an element belonging to the
class identified by the identifier, as defined by the document language.
For example, in[HTML5],[SVG11],and[MATHML]membership in a
class is given by theclass
attribute: in these languages
it is equivalent to the~=
notation applied to the
localclass
attribute
(i.e.[class~=identifier]
).
We can assign style information to all elements withclass~= "pastoral"
as follows:
*.pastoral { color: green } /* all elements with class~=pastoral */
or just
.pastoral { color: green } /* all elements with class~=pastoral */
The following assigns style only to H1 elements withclass~= "pastoral"
:
H1.pastoral { color: green } /* H1 elements with class~=pastoral */
Given these rules, the firstH1
instance below would not have
green text, while the second would:
<H1>Not green</H1> <H1 class= "pastoral" >Very green</H1>
The following rule matches anyPelement whoseclass
attribute has been assigned a list ofwhitespace-separated values that includes bothpastoral
andmarine
:
p.pastoral.marine { color: green }
This rule matches whenclass= "pastoral blue aqua
marine"
but does not match forclass= "pastoral
blue"
.
Note:Because CSS gives considerable power to the "class" attribute, authors could conceivably design their own "document language" based on elements with almost no associated presentation (such asdivandspanin HTML) and assigning style information through the "class" attribute. Authors should avoid this practice since the structural elements of a document language often have recognized and accepted meanings and author-defined classes may not.
Note:If an element has multiple class attributes, their values must be concatenated with spaces between the values before searching for the class. As of this time the working group is not aware of any manner in which this situation can be reached, however, so this behavior is explicitly non-normative in this specification.
When matching against a document which is inquirks mode, class names must be matchedASCII case-insensitively; class selectors are otherwise case-sensitive, only matching class names they areidentical to.[INFRA]
6.7.ID selectors
Document languages may contain attributes that are declared to be of type ID.
What makes attributes of type ID special
is that no two such attributes can have the same value in a conformant document,
regardless of the type of the elements that carry them;
whatever the document language,
an ID typed attribute can be used to uniquely identify its element.
In HTML all ID attributes are namedid
;
XML applications may name ID attributes differently,
but the same restriction applies.
Which attribute on an element is considered the “ID attribute “is defined by the document language.
AnID selectorconsists of a “number sign” (U+0023,#
)
immediately followed by the ID value,
which must be a CSSidentifier.
An ID selector represents an element instance that has an identifier that matches the identifier in the ID selector.
(It is possible in non-conforming documents for multiple elements to match a single ID selector.)
h1#chapter1
The following ID selector represents any element whose ID-typed attribute has the value "chapter1":
#chapter1
The following selector represents any element whose ID-typed attribute has the value "z98y".
*#z98y
Note:In XML 1.0[XML10],the information about which attribute contains an element’s IDs is contained in a DTD or a schema. When parsing XML, UAs do not always read the DTD, and thus may not know what the ID of an element is (though a UA may have namespace-specific knowledge that allows it to determine which attribute is the ID attribute for that namespace). If a style sheet author knows or suspects that a UA may not know what the ID of an element is, they should use normal attribute selectors instead:[name=p371]instead of#p371.
If an element has multiple ID attributes, all of them must be treated as IDs for that element for the purposes of the ID selector. Such a situation could be reached using mixtures of xml:id, DOM3 Core, XML DTDs, and namespace-specific knowledge.
When matching against a document which is inquirks mode, IDs must be matchedASCII case-insensitively; ID selectors are otherwise case-sensitive, only matching IDs they areidentical to.[INFRA]
7.Linguistic Pseudo-classes
7.1.The Directionality Pseudo-class::dir()
The:dir()pseudo-class allows the author to write
selectors that represent an element based on its directionality
as determined by thedocument language.
For example,[HTML5]defineshow to determine the directionality of an element,
based on a combination of thedir
attribute, the surrounding text, and other factors.
As another example, theits:dir
anddirRule
element
of the Internationalization Tag Set[ITS20]are able to define the directionality of an element in[XML10].
The:dir()pseudo-class does not select based on stylistic states—for example, the CSSdirectionproperty does not affect whether it matches.
The pseudo-class:dir(ltr)represents an element that
has a directionality of left-to-right (ltr
). The
pseudo-class:dir(rtl)represents an element that has
a directionality of right-to-left (rtl
). The argument to:dir()must be a single identifier, otherwise the selector
is invalid. White space is optionally allowed between the identifier
and the parentheses. Values other thanltr
andrtl
are not invalid, but do not match anything. (If a
future markup spec defines other directionalities, then Selectors may
be extended to allow corresponding values.)
The difference between:dir(C)and[dir=C]is that[dir=C]only performs a comparison against a given
attribute on the element, while the:dir(C)pseudo-class
uses the UAs knowledge of the document’s semantics to perform the
comparison. For example, in HTML, the directionality of an element
inherits so that a child without adir
attribute will have
the same directionality as its closest ancestor with a validdir
attribute. As another example, in HTML,
an element that matches[dir=auto]will match either:dir(ltr)or:dir(rtl)depending on the resolved
directionality of the elements as determined by its contents.[HTML5]
7.2.The Language Pseudo-class::lang()
If the document language specifies how the (human)content languageof an element is determined, it is possible to write selectors that represent an element based on itscontent language. The:lang()pseudo-class, which accepts a comma-separated list of one or morelanguage ranges, represents an element whosecontent languageis one of the languages listed in its argument. Eachlanguage rangein:lang()must be a valid CSS<ident>or<string>. (Thus language ranges containing asterisks, for example, must be either correctly escaped or quoted as strings, e.g.:lang(\*-Latn)or:lang( "*-Latn" ).)
Note:Thecontent languageof an element is defined by the document language.
For example, in HTML[HTML5],thecontent languageis determined
by a combination of thelang
attribute,
information frommetaelements,
and possibly also the protocol (e.g. from HTTP headers).
XML languages can use thexml:lang
attribute
to indicate language information for an element.[XML10]
The element’scontent languagematches alanguage rangeif itscontent language,as represented in BCP 47 syntax, matches the givenlanguage rangein anextended filteringoperation per[RFC4647]Matching of Language Tags(section 3.3.2). Both thecontent languageand thelanguage rangemust becanonicalizedand converted toextlang formas per section 4.5 of[RFC5646]prior to theextended filteringoperation. The matching is performed case-insensitively within the ASCII range.
Thelanguage rangedoes not need to be a valid language code to perform this comparison.
Alanguage rangeconsisting of an empty string (:lang( "" )) matches (only) elements whose language is not tagged.
Note:It is recommended that documents and protocols
indicate language using codes from[BCP47]or its successor,
and in the case of XML-based formats, by means ofxml:lang
attributes.[XML10]See“FAQ: Two-letter or three-letter language codes.”
html:lang(fr-be) html:lang(de) :lang(fr-be) > q :lang(de) > q
Note:One difference between:lang(C)and the|=operator is that the|=operator only performs a comparison against a given attribute on the element, while the:lang(C)pseudo-class uses the UAs knowledge of the document’s semantics to perform the comparison.
<body lang=fr> <p>Je suis français.</p> </body>
For example,:lang(de-DE)will match all ofde-DE,de-DE-1996,de-Latn-DE,de-Latf-DE,de-Latn-DE-1996, whereas of those[lang|=de-DE]will only matchde-DEandde-DE-1996.
To perform wildcard matching on the first subtag (the primary language), an asterisk must be used:*-CHwill match all ofde-CH,it-CH,fr-CH,andrm-CH.
To select against an element’s lang attribute value using this type of language range match, use both the attribute selector and language pseudo-class together, e.g.[lang]:lang(de-DE).
Note:Wildcard language matching and comma-separated lists are new in Level 4.
8.Location Pseudo-classes
8.1.The Hyperlink Pseudo-class::any-link
The:any-linkpseudo-class represents an element
that acts as the source anchor of a hyperlink.
For example, in[HTML5],
anya
orarea
elements with anhref
attribute are hyperlinks,
and thus match:any-link
.
It matches an element if the element would match either:linkor:visited,
and is equivalent to:is(:link,:visited).
8.2.The Link History Pseudo-classes::linkand:visited
User agents commonly display unvisitedhyperlinksdifferently from previously visited ones. Selectors provides the pseudo-classes:linkand:visitedto distinguish them:
- The:linkpseudo-class applies to links that have not yet been visited.
- The:visitedpseudo-class applies once the link has been visited by the user.
After some amount of time, user agents may choose to return a visited link to the (unvisited):linkstate.
The two states are mutually exclusive.
footnote
and already visited:
.footnote:visited
Since it is possible for style sheet authors to abuse the:link and:visited pseudo-classes to determine which sites a user has visited without the user’s consent, UAs may treat all links as unvisited links or implement other measures to preserve the user’s privacy while rendering visited and unvisited links differently.
8.3.The Local Link Pseudo-class::local-link
The:local-linkpseudo-class allows authors to stylehyperlinksbased on the users current location within a site. It represents an element that is the source anchor of a hyperlink whose target’s absolute URL matches the element’s own document URL. If the hyperlink’s target includes a fragment URL, then the fragment URL of the current URL must also match; if it does not, then the fragment URL portion of the current URL is not taken into account in the comparison.
nav:local-link { text-decoration: none; }
Note:The current URL of a page can change as a result of user actions
such as activating a link targeting a different fragment within the same page;
or by use of thepushState
API;
as well as by the more obvious actions of navigating to a different page
or following a redirect (which could be initiated by protocols such as HTTP,
markup instructions such as<meta http-equiv= "..." >
,
or scripting instructions ).
UAs must ensure that:local-link,
as well as the:targetand:target-withinpseudo-classes below,
respond correctly to all such changes in state.
8.4.The Target Pseudo-class::target
In some document languages, the document’s URL can further point to specific elementswithinthe document via the URL’sfragment. The elements pointed to in this way are the target elements of the document.
https://example.com/index.html#section2
,
for example,
points to the element withid= "section2"
in the document athttps://example.com/index.html
.The:targetpseudo-class matches the document’s target elements. If the document’s URL has no fragment identifier, then the document has no target elements.
p.note:target
This selector represents ap
element of classnote
that is the target element of the referring
URL.
:target { color: red } :target::before { content: url(target.png) }
8.5.The Target Container Pseudo-class::target-within
The:target-withinpseudo-class applies to any element to which the:targetpseudo class applies as well as to any element whose descendant in theflat tree(including non-element nodes, such as text nodes) matches the conditions for matching:target.
8.6.The Reference Element Pseudo-class::scope
In some contexts, selectors are matched
with respect to one or morescoping roots,
such as when calling thequerySelector()
method in[DOM].
The:scopepseudo-class represents
thisscoping root,
and may be either a true element
or a virtual one (such as aDocumentFragment
).
If there is noscoping rootthen:scoperepresents the root of the document (equivalent to:root). Specifications intending for this pseudo-class to match specific elements rather than the document’s root element must define theirscoping root(s).
A virtualscoping rootis some object representing the root of a document fragment, and can be used in selector patterns to represent other elements’ relationships to thisscoping root, acting as the parent of any root elements in the document fragment it represents. A virtualscoping rootisfeaturelessand cannot be thesubject of the selector.
DocumentFragment
df
,
thendf. querySelectorAll( ":scope >.foo" )
matches all the.fooelements that are "top-level" in the document fragment
(those that have the document fragment as theirparentNode
).
However,df
will not match anything,
as the document fragment itself can’t be thesubject of the selector.
9.User Action Pseudo-classes
Interactive user interfaces sometimes change the rendering in response to user actions. Selectors provides severaluser action pseudo-classesfor the selection of an element the user is acting on. (In non-interactive user agents, these pseudo-classes are valid, but never match any element.)
These pseudo-classes are not mutually exclusive. An element can match several such pseudo-classes at the same time.
a:hover /* user hovers over the link */ a:focus /* user focuses the link */ a:focus:hover /* user hovers over the link while it’s focused */
Note:The specifics of hit-testing, necessary to know when several of the pseudo-classes defined in this section apply, are not yet defined, but will be in the future.
9.1.The Pointer Hover Pseudo-class::hover
The:hoverpseudo-class applies while the user designates an element (or pseudo-element) with a pointing device, but does not necessarily activate it. For example, a visual user agent could apply this pseudo-class when the cursor (mouse pointer) hovers over a box generated by the element. Interactive user agents that cannot detect hovering due to hardware limitations (e.g., a pen device that does not detect hovering) are still conforming; the selector will simply never match in such a UA.
An element also matches:hoverif one of its descendants in theflat tree(including non-element nodes, such as text nodes) matches the above conditions.
Document languages may define additional ways in which an element can match:hover.
For example,[HTML5]defines a labeled control element asmatching:hover
when itslabelis hovered.
Note:Since the:hoverstate can apply to an element because its child is designated by a pointing device, it is possible for:hoverto apply to an element that is not underneath the pointing device.
9.2.The Activation Pseudo-class::active
The:activepseudo-class applies while an element is being “activated” by the user, as defined by the host language; for example, while a hyperlink is being triggered.
In addition, the:activepseudo-class applies while any generated box ofanyelement (or pseudo-element) is being actively indicated by a pointing device (in the “down” state), e.g. between the time the user presses the primary mouse button and releases it, or while a finger is pressing on a touchscreen.
Note:[HTML5]definesspecific conditions for HTML elements to be activated.
An element also matches:activeif one of its descendants in theflat tree(including non-element nodes, such as text nodes) matches the above conditions.
9.3.The Input Focus Pseudo-class::focus
The:focuspseudo-class applies while an element (or pseudo-element) has the focus (accepts keyboard or other forms of input).
There may be document language or implementation specific limits on which elements can acquire:focus. For example,[HTML]defines a list offocusable areas.
Document languages may define additional ways in which an element can match:focus, except that the:focuspseudo class must not automatically propagate to the parent element—see:focus-withinif matching on the parent is desired. (:focusmay still apply to the parent element if made to propagate due to other mechanisms, but not merely due to being the parent.)
There’s a desire from authors to propagate:focusfrom a form control to its associatedlabel
element;
the main objection seems to be implementation difficulty.
SeeCSSWG issue (CSS)andWHATWG issue (HTML).
9.4.The Focus-Indicated Pseudo-class::focus-visible
While the:focuspseudo-classalways matches the currently-focused element, UAs only sometimes visiblyindicate focus(such as by drawing a “focus ring” ), instead using a variety of heuristics to visibly indicate the focus only when it would be most helpful to the user. The:focus-visiblepseudo-classmatches a focused element (or pseudo-element) in these situations only, allowing authors to change the appearance of the focus indicator without changingwhena focus indicator appears.
:root{ --focus-gold : #ffbf47; } :focus-visible{ outline : 3 px solidvar ( --focus-gold); } a:focus-visible{ background-color : var ( --focus-gold); }
-
If the user has expressed a preference (such as via a system preference or a browser setting) to always see a visible focus indicator,indicate focusregardless of any other factors. (Another option may be for the user agent to show its own focus indicator regardless of author styles.)
-
If the element which supports keyboard input (such as an
input
element, or any other element that would triggers a virtual keyboard to be shown on focus if a physical keyboard were not present),indicate focus. -
If the user interacts with the page via keyboard or some other non-pointing device,indicate focus. (This means keyboard usage may change whether this pseudo-class matches even if it doesn’t affect:focus).
-
If the user interacts with the page via a pointing device (mouse, touchscreen, etc.) and the focused element does not support keyboard input, don’tindicate focus.
-
If the previously-focused elementindicated focus, and a script causes focus to move elsewhere,indicate focuson the newly focused element.
Conversely, if the previously-focused element did notindicate focus, and a script causes focus to move elsewhere, don’tindicate focuson the newly focused element.
-
If a newly-displayed element automatically gains focus (such as an action button in a freshly opened dialog), that element shouldindicate focus.
User agents should also use:focus-visibleto specify the default focus style, so that authors using:focus-visiblewill not also need to disable the default:focusstyle.
9.5.The Focus Container Pseudo-class::focus-within
The:focus-withinpseudo-class applies to any element (or pseudo-element) for which the:focuspseudo class applies, as well as to an element (or pseudo-element) whose descendant in theflat tree(including non-element nodes, such as text nodes) matches the conditions for matching:focus.
10.Time-dimensional Pseudo-classes
These pseudo-classes classify elements with respect to the currently-displayed or active position in some timeline, such as during speech rendering of a document, or during the display of a video using WebVTT to render subtitles.
CSS does not define this timeline; the host language must do so. If there is no timeline defined for an element, these pseudo-classes must not match the element.
Note:Ancestors of a:currentelement are also:current, but ancestors of a:pastor:futureelement are not necessarily:pastor:futureas well. A given element matches at most one of:current,:past,or:future.
10.1.The Current-element Pseudo-class::current
The:currentpseudo-class represents the element, or an ancestor of the element, that is currently being displayed.
Its alternate form:current(),like:is(), takes a list ofcompound selectorsas its argument: it represents the:currentelement that matches the argument or, if that does not match, the innermost ancestor of the:currentelement that does. (If neither the:currentelement nor its ancestors match the argument, then the selector does not represent anything.)
:current(p, li, dt, dd) { background: yellow; }
10.2.The Past-element Pseudo-class::past
The:pastpseudo-class represents any element that is defined to occur entirely prior to a:currentelement. For example, the WebVTT spec defines the:pastpseudo-classrelative to the current playback position of a media element. If a time-based order of elements is not defined by the document language, then this represents any element that is a (possibly indirect) previous sibling of a:currentelement.
10.3.The Future-element Pseudo-class::future
The:futurepseudo-class represents any element that is defined to occur entirely after a:currentelement. For example, the WebVTT spec defines the:futurepseudo-classrelative to the current playback position of a media element. If a time-based order of elements is not defined by the document language, then this represents any element that is a (possibly indirect) next sibling of a:currentelement.
11.Resource State Pseudo-classes
The pseudo-classes in this section apply to elements that represent loaded resources, particularly images/videos, and allow authors to select them based on some quality of their state.
11.1.Media Playback State: the:playing,:paused,and:seekingpseudo-classes
The:playingpseudo-class represents an element that is capable of being “played” or “paused”, when that element is “playing”. (This includes both when the element is explicitly playing, and when it’s temporarily stopped for some reason not connected to user intent, but will automatically resume when that reason is resolved, such as a “buffering” or “stalled” state.)
The:pausedpseudo-class represents an element that is capable of being “played” or “paused”, when that element is “paused” (i.e.not”playing” ). (This includes both an explicit “paused” state, and other non-playing states like “loaded, hasn’t been activated yet”, etc.)
The:seekingpseudo-class represents an element
that is capable of” seeking”
when that element is” seeking”.
(For theaudio
andvideo
elements of HTML, seeHTML§ 4.8.11.9 Seeking.)
11.2.Media Loading State: the:bufferingand:stalledpseudo-classes
The:bufferingpseudo-class represents an element that is capable of being “played” or “paused”, when that element cannot continue playing because it is actively attempting to obtainmedia databut has not yet obtained enough data to resume playback. (Note that the element is still considered to be “playing” when it is “buffering”. Whenever:bufferingmatches an element,:playingalso matches the element.)
The:stalledpseudo-class represents an element
when that element cannot continue playing
because it is actively attempting to obtainmedia databut it has failed to receive any data for some amount of time.
For theaudio
andvideo
elements of HTML,
this amount of time is themedia element stall timeout.[HTML](Note that, like with the:bufferingpseudo-class,
the element is still considered to be “playing” when it is “stalled”.
Whenever:stalledmatches an element,:playingalso matches the element.)
11.3.Sound State: the:mutedand:volume-lockedpseudo-classes
The:mutedpseudo-class represents
an element that is capable of making sound,
but is currently “muted “(forced silent).
(For theaudio
andvideo
elements of HTML, seemuted.[HTML])
The:volume-lockedpseudo-class represents
an element that is capable of making sound,
and currently has its volume "locked"
by the UA or the user,
so the page author cannot change it.
(For theaudio
andvideo
elements of HTML,
see the algorithm for setting the element’seffective media volume.[HTML])
12.Element Display State Pseudo-classes
12.1.Collapse State: the:openand:closedpseudo-class
The:openpseudo-class represents an element that has both “open” and “closed” states, and which is currently in the “open” state.
The:closedpseudo-class represents an element that has both “open” and “closed” states, and which is currently in the closed state.
Exactly what “open” and “closed” mean is host-language specific,
but exemplified by elements such as
HTML’sdetails
,select
,anddialog
elements,
all of which can be toggled “open” to display more content
(or any content at all, in the case ofdialog
).
Note:Being “open” or “closed” is a semantic state. An element not currently being displayed (for example, one that hasvisibility: collapse, or belongs to adisplay: nonesubtree) can still be “open” and will match:open.
12.2.Modal (Exclusive Interaction) State: the:modalpseudo-class
The:modalpseudo-class represents an element which is in a state that excludes all interaction with elements outside it until it has been dismissed. Multiple elements can be:modalsimultaneously, with only one of them active (able to receive input).
dialog
element is:modalwhen opened with theshowModal()
API.
Similarly, a:fullscreenelement is also:modalwhen opened with therequestFullscreen()
API,
since this prevents interaction with the rest of the page.12.3.Fullscreen Presentation State: the:fullscreenpseudo-class
The:fullscreenpseudo-class represents an element which is displayed in a mode that takes up most (usually all) of the screen, such as that defined by the Fullscreen API.[FULLSCREEN]
12.4.Picture-in-Picture Presentation State: the:picture-in-picturepseudo-class
The:picture-in-picturepseudo-class represents an element which is displayed in a mode that takes up most (usually all) of the viewport, and whose viewport is confined to part of the screen while being displayed over other content, for example when using the Picture-in-Picture API.[picture-in-picture]
13.The Input Pseudo-classes
The pseudo-classes in this section mostly apply to elements that take user input, such as HTML’sinputelement.
13.1.Input Control States
13.1.1.The:enabledand:disabledPseudo-classes
The:enabledpseudo-class represents user interface elements that are in an enabled state; such elements must have a corresponding disabled state.
Conversely, the:disabledpseudo-class represents user interface elements that are in a disabled state; such elements must have a corresponding enabled state.
What constitutes an enabled state, a disabled state, and a user interface element is host-language-dependent. In a typical document most elements will be neither:enablednor:disabled. For example,[HTML5]definesnon-disabled interactive elementsto be:enabled, and any such elements that areexplicitly disabledto be:disabled.
Note:CSS properties that might affect a user’s ability to interact with a given user interface element do not affect whether it matches:enabledor:disabled;e.g., thedisplayandvisibilityproperties have no effect on the enabled/disabled state of an element.
13.1.2.The Mutability Pseudo-classes::read-onlyand:read-write
An element matches:read-writeif it is user-alterable, as defined by the document language. Otherwise, it is:read-only.
For example, in[HTML5]anon-disabled non-readonly<input>
elementis:read-write,
as is any element with thecontenteditable
attribute set to the true state.
13.1.3.The Placeholder-shown Pseudo-class::placeholder-shown
Input elements can sometimes show placeholder text
as a hint to the user on what to type in.
See, for example, theplaceholder
attribute in[HTML5].
The:placeholder-shownpseudo-class
matches an input element that is showing such placeholder text,
whether that text is given by an attribute or a real element,
or is otherwise implied by the UA.
placeholder
attribute on theinput
andtextarea
elements
provide placeholder text.
The:placeholder-shownclass thus applies
whenever such placeholder text is shown.13.1.4.The Automatic Input Pseudo-class::autofill
The:autofillpseudo-class represents input elements that have been automatically filled by the user agent, and have not been subsequently altered by the user.
13.1.5.The Default-option Pseudo-class::default
The:defaultpseudo-class applies to the one or more UI elements that are the default among a set of similar elements. Typically applies to context menu items, buttons and select lists/menus.
One example is the default submit button among a set of buttons.
Another example is the default option from a popup menu.
In a select-many group (such as for pizza toppings), multiple elements can match:default.
For example,[HTML5]defines that:defaultmatchesthe “default button” in a form,
the initially-selected<option>
(s) in a<select>
,
and a few other elements.
13.2.Input Value States
13.2.1.The Selected-option Pseudo-class::checked
Radio and checkbox elements can be toggled by the user.
Some menu items are “checked” when the user selects them.
When such elements are toggled “on”
the:checkedpseudo-class applies.
For example,[HTML5]defines thatchecked checkboxes, radio buttons, and selected<option>
elementsmatch:checked.
While the:checkedpseudo-class is dynamic in nature,
and can altered by user action,
since it can also be based on the presence of semantic attributes in the document
(such as theselected
andchecked
attributes in[HTML5]),
it applies to all media.
input[type=checkbox]:not(:checked)
13.2.2.The Indeterminate-value Pseudo-class::indeterminate
The:indeterminatepseudo-class applies to UI elements whose value is in an indeterminate state. For example, radio and checkbox elements can be toggled between checked and unchecked states, but are sometimes in an indeterminate state, neither checked nor unchecked. Similarly a progress meter can be in an indeterminate state when the percent completion is unknown. For example,[HTML5]defines howcheckboxescan be made to match:indeterminate.
Like the:checkedpseudo-class,:indeterminateapplies to all media. Components of a radio-group initialized with no pre-selected choice, for example, would be:indeterminateeven in a static display.
13.3.Input Value-checking
13.3.1.The Empty-Value Pseudo-class::blank
The:blankpseudo-class applies to user-input elements whose input value is empty (consists of the empty string or otherwise null input).
A rule of thumb for interpreting:blankon form controls is:
-
If the control always submits, and would do so with an empty string, it matches:blank. (Such as HTML’s
<input type=text>
when its value is empty.) -
If it sometimes submits, and is set to not submit, it matches:blank. (Such as HTML’s
<input type=checkbox>
when not checked.) -
If it’s an “action button” (rather than a “toggle button” that represents a state) such as
<button>
,<input type=submit>
,etc., it never matches:blank.
Host languages can specify more precise rules for when form controls match:blank.
Note:This selector is at-risk.
13.3.2.The Validity Pseudo-classes::validand:invalid
An element is:validor:invalidwhen its contents or value is, respectively, valid or invalid with respect to data validity semantics defined by the document language (e.g.[XFORMS11]or[HTML5]). An element which lacks data validity semantics is neither:validnor:invalid.
Note:There is a difference between an element which has no constraints,
and thus would always be:valid,
and one which has no data validity semantics at all,
and thus is neither:validnor:invalid.
In HTML, for example, an<input type= "text" >
element may have no constraints,
but apelement has no validity semantics at all,
and so it never matches either of these pseudo-classes.
13.3.3.The Range Pseudo-classes::in-rangeand:out-of-range
The:in-rangeand:out-of-rangepseudo-classes apply only to elements that have range limitations. An element is:in-rangeor:out-of-rangewhen the value that the element is bound to is in range or out of range with respect to its range limits as defined by the document language. An element that lacks data range limits or is not a form control is neither:in-rangenor:out-of-range. E.g. a slider element with a value of 11 presented as a slider control that only represents the values from 1-10 is:out-of-range. Another example is a menu element with a value of "E" that happens to be presented in a popup menu that only has choices "A", "B" and "C".
13.3.4.The Optionality Pseudo-classes::requiredand:optional
A form element is:requiredor:optionalif a value for it is, respectively, required or optional before the form it belongs to can be validly submitted. Elements that are not form elements are neither required nor optional.
13.3.5.The User-interaction Pseudo-classes::user-validand:user-invalid
The:user-invalidand the:user-validpseudo-classes represent an element with incorrect or correct input, respectively, but onlyafterthe user has significantly interacted with it. Their purpose is to help the user identify mistakes in their input.
These pseudo-classes must at least match their respective elements after the user has attempted to submit the form and before the user has interacted again with the input element or reset the form. They may also match at other times, as would be appropriate for highlighting an error to the user. For example,:user-invalidcould start matching an:invalidinput element once the user has changed its value and focus has moved to another element; or stop matching only after the user has successfully corrected the input.
Host languages may define more precise matching rules or defer to platform conventions; otherwise the exact behavior is UA-defined. Regardless, the:user-invalidpseudo-class must only match:invalidelements; and the:user-validpseudo-class must only match:validelements. See theHTML specificationfor the specific rules pertaining to HTML elements.[HTML]
input
element in the following document fragment
would match:invalidas soon as the page is loaded
(because theinput
's initial value violates its max constraint)
but it won’t match:user-invaliduntil the user significantly interacts with the input field
or attempts to submit the form it’s part of.
<form> <label> Volume: <input name='vol' type=number min=0 max=10 value=11> </label> ... </form>
14.Tree-Structural pseudo-classes
Selectors introduces the concept ofstructural pseudo-classesto permit selection based on extra information that lies in the document tree but cannot be represented by other simple selectors or combinators.
Standalone text and other non-element nodes are not counted when calculating the position of an element in the list of children of its parent. When calculating the position of an element in the list of children of its parent, the index numbering starts at 1.
Thestructural pseudo-classesonly apply to elements in the document tree; they must never matchpseudo-elements.
14.1.:rootpseudo-class
The:rootpseudo-class represents an element that is the root of the document.
For example, in a DOM document,
the:rootpseudo-class matches thedocument element.
In HTML, this will be thehtml
element
(unless scripting has been used to modify the document).
14.2.:emptypseudo-class
The:emptypseudo-class represents an element that has no children except, optionally,document white space characters. In terms of the document tree, only element nodes and content nodes (such as[DOM]text nodes, and entity references) whose data has a non-zero length must be considered as affecting emptiness; comments, processing instructions, and other nodes must not affect whether an element is considered empty or not.
p
elements
in the following HTML fragment:
<p></p> <p> <p> </p> <p></p>
div:emptyis not a valid representation of the<div>
elements
in the following fragment:
<div>text</div> <div><p></p></div> <div> </div> <div><p>bla</p></div> <div>this is not <p>:empty</p></div>
Note:In Level 2 and Level 3 of Selectors,:emptydid not match elements that contained only white space. This was changed so that that—given white space is largely collapsible in HTML and is therefore used for source code formatting, and especially because elements with omitted end tags are likely to absorb such white space into their DOM text contents—elements which authors perceive of as empty can be selected by this selector, as they expect.
14.3.Child-indexed Pseudo-classes
The pseudo-classes defined in this section select elements based on their index amongst theirinclusive siblings.
Note:Selectors 3 described these selectors as selecting elements based on their index in the child list of their parents. (This description survives in the name of this very section, and the names of several of the pseudo-classes.) As there was no reason to exclude them from matching elements without parents, or with non-element parents, they have been rephrased to refer to an element’s relative index amongst its siblings.
14.3.1.:nth-child()pseudo-class
The:nth-child(An+B[ofS]? )pseudo-class notation represents elements that are amongAn+Bth elements from the list composed of theirinclusive siblingsthat match theselector listS, which is a<complex-real-selector-list>. IfSis omitted, it defaults to*|*.
TheAn+Bnotation and its interpretation are defined inCSS Syntax 3§ 6 The An+B microsyntax; it represents any indexi=An+Bfor any non-negative integern.
Note:For these purposes, the list of elements is1-indexed;
that is, the first child of an element has index 1, and will be matched by:nth-child(2n+1),
because whenn=0
the expression evaluates to1.
For example, this selector could address every other row in a table, and could be used to alternate the color of paragraph text in a cycle of four.
:nth-child(even) /* represents the 2nd, 4th, 6th, etc elements :nth-child(10n-1) /* represents the 9th, 19th, 29th, etc elements */ :nth-child(10n+9) /* Same */ :nth-child(10n+-1) /* Syntactically invalid, and would be ignored */
Note:The specificity of the:nth-child()pseudo-class is the specificity of a single pseudo-class plus, ifSis specified, the specificity of the most specificcomplex selectorinS. See§ 17 Calculating a selector’s specificity. ThusS:nth-child(An+B)and:nth-child(An+BofS)have the exact same specificity, although they do differ in behavior (see example below).
:nth-child(-n+3 of li.important)
Note that this is different from moving the selector outside of the function, like:
li.important:nth-child(-n+3)
This selector instead just selects the first three children if they also happen to be "important" list items.
Normally, to zebra-stripe a table’s rows, an author would use CSS similar to the following:
tr { background: white; } tr:nth-child(even) { background: silver; }
However, if some of the rows are hidden and not displayed, this can break up the pattern, causing multiple adjacent rows to have the same background color. Assuming that rows are hidden with the[hidden]attribute in HTML, the following CSS would zebra-stripe the table rows robustly, maintaining a proper alternating background regardless of which rows are hidden:
tr { background: white; } tr:nth-child(even of:not([hidden])) { background: silver; }
14.3.2.:nth-last-child()pseudo-class
The:nth-last-child(An+B[ofS]? )pseudo-class notation represents elements that are amongAn+Bth elements from the list composed of theirinclusive siblingsthat match theselector listS, counting backwards from the end.Sis<complex-real-selector-list>. IfSis omitted, it defaults to*|*.
Note:The specificity of the:nth-last-child()pseudo-class, like the:nth-child()pseudo-class, combines the specificity of a regular pseudo-class with that of its selector argumentS. See§ 17 Calculating a selector’s specificity.
The CSS Syntax Module[CSS3SYN]defines theAn+Bnotation.
tr:nth-last-child(-n+2) /* represents the two last rows of an HTML table */ foo:nth-last-child(odd) /* represents all odd foo elements in their parent element, counting from the last one */
14.3.3.:first-childpseudo-class
The:first-childpseudo-class represents an element that if first among itsinclusive siblings. Same as:nth-child(1).
div > p:first-child
This selector can represent thep
inside thediv
of the following fragment:
<p> The last P before the note.</p> <div class= "note" > <p> The first P inside the note.</p> </div>
but cannot represent the secondp
in the following fragment:
<p> The last P before the note.</p> <div class= "note" > <h2> Note </h2> <p> The first P inside the note.</p> </div>
The following two selectors are usually equivalent:
* > a:first-child /* a is first child of any element */ a:first-child /* Same (assuming a is not the root element) */
14.3.4.:last-childpseudo-class
The:last-childpseudo-class represents an element that is last among itsinclusive siblings. Same as:nth-last-child(1).
li
that
is the last child of an ordered listol
.
ol > li:last-child
14.3.5.:only-childpseudo-class
The:only-childpseudo-class represents an element that has no siblings. Same as:first-child:last-childor:nth-child(1):nth-last-child(1), but with a lower specificity.
14.4.Typed Child-indexed Pseudo-classes
The pseudo-classes in this section are similar to theChild Index Pseudo-classes, but they resolve based on an element’s indexamong elements of the sametype (tag name)in their sibling list.
14.4.1.:nth-of-type()pseudo-class
The:nth-of-type(An+B)pseudo-class notation
represents the same elements that would be matched by:nth-child(|An+B| ofS),
whereSis atype selectorand namespace prefix matching the element in question.
For example,
when considering whether an HTMLimg
element matches thispseudo-class,
theSin question ishtml|img(assuming an appropriatehtml
namespace is declared).
img:nth-of-type(2n+1) { float: right; } img:nth-of-type(2n) { float: left; }
Note:If the type of the element is known ahead of time, this pseudo-class is equivalent to using:nth-child()with a type selector. That is,img:nth-of-type(2)is equivalent to*:nth-child(2 of img).
14.4.2.:nth-last-of-type()pseudo-class
The:nth-last-of-type(An+B)pseudo-class notation
represents the same elements that would be matched by:nth-last-child(|An+B| ofS),
whereSis atype selectorand namespace prefix matching the element in question.
For example,
when considering whether an HTMLimg
element matches thispseudo-class,
theSin question ishtml|img(assuming an appropriatehtml
namespace is declared).
h2
children of an XHTMLbody
except the first and last, one could use the
following selector:
body > h2:nth-of-type(n+2):nth-last-of-type(n+2)
In this case, one could also use:not(),although the selector ends up being just as long:
body > h2:not(:first-of-type):not(:last-of-type)
14.4.3.:first-of-typepseudo-class
The:first-of-typepseudo-class represents the same element as:nth-of-type(1).
dt
inside a definition listdl
,thisdt
being the first of its type in the list of children of
its parent element.
dl dt:first-of-type
It is a valid description for the first twodt
elements in the following example but not for the third one:
<dl> <dt>gigogne</dt> <dd> <dl> <dt>fusée</dt> <dd>multistage rocket</dd> <dt>table</dt> <dd>nest of tables</dd> </dl> </dd> </dl>
14.4.4.:last-of-typepseudo-class
The:last-of-typepseudo-class represents the same element as:nth-last-of-type(1).
td
of a table rowtr
.
tr > td:last-of-type
14.4.5.:only-of-typepseudo-class
The:only-of-typepseudo-class represents the same element as:first-of-type:last-of-type.
15.Combinators
15.1.Descendant combinator (
)
At times, authors may want selectors to describe an element that is the descendant of another element in the document tree (e.g., "anemelement that is contained within anH1element "). Thedescendant combinatorexpresses such a relationship.
A descendant combinator is whitespace that separates twocompound selectors.
A selector of the formA Brepresents an elementB
that is an
arbitrary descendant of some ancestor elementA
.
h1 em
It represents anemelement being the descendant of anh1element. It is a correct and valid, but partial, description of the following fragment:
<h1>This <span class= "myclass" >headline is <em>very</em> important</span></h1>
The following selector:
div * p
represents apelement that is a grandchild or later
descendant of adivelement. Note the whitespace on
either side of the "*" is not part of the universal selector; the
whitespace is a combinator indicating that thediv
must be the
ancestor of some element, and that that element must be an ancestor
of thep
.
The following selector, which combines descendant combinators andattribute selectors,represents an
element that (1) has thehref
attribute set and (2) is
inside ap
that is itself inside adiv
:
div p *[href]
15.2.Child combinator (>
)
Achild combinatordescribes a childhood relationship between two elements. A child combinator is made of the "greater-than sign" (U+003E,>) code point and separates twocompound selectors.
body
:
body > p
The following example combines descendant combinators and child combinators.
div ol>li p
It represents apelement that is a descendant of anlielement; thelielement must be the
child of anolelement; theolelement must
be a descendant of adiv
.Notice that the optional white
space around the ">" combinator has been left out.
For information on selecting the first child of an element, please see the section on the:first-childpseudo-class above.
15.3.Next-sibling combinator (+
)
Thenext-sibling combinatoris made of the “plus sign” (U+002B,+) code point that separates twocompound selectors. The elements represented by the twocompound selectorsshare the same parent in the document tree and the element represented by the firstcompound selectorimmediately precedes the element represented by the second one. Non-element nodes (e.g. text between elements) are ignored when considering the adjacency of elements.
math + p
The following selector is conceptually similar to the one in the
previous example, except that it adds an attribute selector — it
adds a constraint to theh1element, that it must haveclass= "opener"
:
h1.opener + h2
15.4.Subsequent-sibling combinator (~
)
Thesubsequent-sibling combinatoris made of the "tilde" (U+007E,~) code point that separates twocompound selectors. The elements represented by the twocompound selectorsshare the same parent in the document tree and the element represented by the first compound selector precedes (not necessarily immediately) the element represented by the second one.
h1 ~ pre
represents apreelement following anh1
.It
is a correct and valid, but partial, description of:
<h1>Definition of the function a</h1> <p>Function a(x) has to be applied to all figures in the table.</p> <pre>function a(x) = 12x/13.5</pre>
16.Grid-Structural Selectors
The double-association of a cell in a 2D grid (to its row and column) cannot be represented by parentage in a hierarchical markup language. Only one of those associations can be represented hierarchically: the other must be explicitly or implicitly defined in the document language semantics. In both HTML and DocBook, two of the most common hierarchical markup languages, the markup is row-primary (that is, the row associations are represented hierarchically); the columns must be implied. To be able to represent such implied column-based relationships, thecolumn combinatorand the:nth-col()and:nth-last-col()pseudo-classes are defined. In a column-primary format, these pseudo-classes match against row associations instead.
16.1.Column combinator (||
)
Thecolumn combinator,which consists of two pipes (||) represents the relationship of a column element to a cell element belonging to the column it represents. Column membership is determined based on the semantics of the document language only: whether and how the elements are presented is not considered. If a cell element belongs to more than one column, it is represented by a selector indicating membership in any of those columns.
col.selected || td { background: gray; color: white; font-weight: bold; }
<table> <col span= "2" > <col class= "selected" > <tr><td>A <td>B <td>C <tr><td colspan= "2" >D <td>E <tr><td>F <td colspan= "2" >G </table>
16.2.:nth-col()pseudo-class
The:nth-col(An+B)pseudo-class notation represents a cell element belonging to a column
that hasAn+B-1 columnsbeforeit, for any positive
integer or zero value ofn
.Column membership is determined
based on the semantics of the document language only: whether and how the
elements are presented is not considered. If a cell element belongs to
more than one column, it is represented by a selector indicating any of
those columns.
The CSS Syntax Module[CSS3SYN]defines theAn+Bnotation.
16.3.:nth-last-col()pseudo-class
The:nth-last-col(An+B)pseudo-class notation represents a cell element belonging to a column
that hasAn+B-1 columnsafterit, for any positive
integer or zero value ofn
.Column membership is determined
based on the semantics of the document language only: whether and how the
elements are presented is not considered. If a cell element belongs to
more than one column, it is represented by a selector indicating any of
those columns.
The CSS Syntax Module[CSS3SYN]defines theAn+Bnotation.
17.Calculating a selector’s specificity
A selector’sspecificityis calculated for a given element as follows:
- count the number of ID selectors in the selector (=A)
- count the number of class selectors, attributes selectors, and pseudo-classes in the selector (=B)
- count the number of type selectors and pseudo-elements in the selector (=C)
- ignore the universal selector
If the selector is aselector list, this number is calculated for each selector in the list. For a given matching process against the list, the specificity in effect is that of the most specific selector in the list that matches.
A few pseudo-classes provide “evaluation contexts” for other selectors, and so have their specificity defined specially:
- The specificity of an:is(),:not(),or:has()pseudo-class is replaced by the specificity of the most specificcomplex selectorin itsselector listargument.
- Analogously, the specificity of an:nth-child()or:nth-last-child()selector is the specificity of the pseudo class itself (counting as one pseudo-class selector) plus the specificity of the most specificcomplex selectorin itsselector listargument (if any).
- The specificity of a:where()pseudo-class is replaced by zero.
- :is(em, #foo)has
a specificity of (1,0,0)—like an ID selector (#foo)—when matched against any of
<em>
,<p id=foo>
,or<em id=foo>
. - .qux:where(em, #foo#bar#baz)has a specificity of (0,1,0): only the.quxoutside the:where()contributes to selector specificity.
- :nth-child(even of li,.item)has
a specificity of (0,2,0)—like a class selector (.item) plus a pseudo-class—when matched against any of
<li>
,<ul class=item>
,or<li class=item id=foo>
. - :not(em, strong#foo)has a specificity of (1,0,1)—like a tag selector (strong) combined with an ID selector (#foo)—when matched against any element.
Specificities are compared by comparing the three components in order: the specificity with a largerAvalue is more specific; if the twoAvalues are tied, then the specificity with a largerBvalue is more specific; if the twoBvalues are also tied, then the specificity with a largerCvalue is more specific; if all the values are tied, the two specificities are equal.
Due to storage limitations, implementations may have limitations on the size ofA,B,orC. If so, values higher than the limit must be clamped to that limit, and not overflow.
* /* a=0 b=0 c=0 */ LI /* a=0 b=0 c=1 */ UL LI /* a=0 b=0 c=2 */ UL OL+LI /* a=0 b=0 c=3 */ H1 + *[REL=up] /* a=0 b=1 c=1 */ UL OL LI.red /* a=0 b=1 c=3 */ LI.red.level /* a=0 b=2 c=1 */ #x34y /* a=1 b=0 c=0 */ #s12:not(FOO) /* a=1 b=0 c=1 */ .foo:is(.bar, #baz) /* a=1 b=1 c=0 */
Note:Repeated occurrences of the same simple selector are allowed and do increase specificity.
Note:The specificity of the styles
specified in an HTMLstyle
attributeis described in CSS Style Attributes.[CSSSTYLEATTR]
18.Grammar
Selectors areparsedaccording to the following grammar:
<selector-list>=<complex-selector-list> <complex-selector-list>=<complex-selector># <complex-real-selector-list>=<complex-real-selector># <compound-selector-list>=<compound-selector># <simple-selector-list>=<simple-selector># <relative-selector-list>=<relative-selector># <relative-real-selector-list>=<relative-real-selector># <complex-selector>=<complex-selector-unit>[<combinator>?<complex-selector-unit>]* <complex-selector-unit>= [<compound-selector>?<pseudo-compound-selector>*]! <complex-real-selector>=<compound-selector>[<combinator>?<compound-selector>]* <relative-selector>=<combinator>?<complex-selector> <relative-real-selector>=<combinator>?<complex-real-selector> <compound-selector>= [<type-selector>?<subclass-selector>*]! <pseudo-compound-selector>=<pseudo-element-selector><pseudo-class-selector>* <simple-selector>=<type-selector>|<subclass-selector> <combinator>= '>'|'+'|'~'|[ '|' '|' ] <wq-name>=<ns-prefix>?<ident-token> <ns-prefix>= [<ident-token>|'*' ]?'|' <type-selector>=<wq-name>|<ns-prefix>?'*' <subclass-selector>=<id-selector>|<class-selector>| <attribute-selector>|<pseudo-class-selector> <id-selector>=<hash-token> <class-selector>= '.'<ident-token> <attribute-selector>= '['<wq-name>']'| '['<wq-name><attr-matcher>[<string-token>|<ident-token>]<attr-modifier>?']' <attr-matcher>= [ '~'|'|'|'^'|'$'|'*' ]?'=' <attr-modifier>= i|s <pseudo-class-selector>= ':'<ident-token>| ':'<function-token><any-value>')' <pseudo-element-selector>= ':'<pseudo-class-selector>|<legacy-pseudo-element-selector> <legacy-pseudo-element-selector>= ':' [before|after|first-line|first-letter]
In interpreting the above grammar, the following rules apply:
-
White space is forbidden:
-
Between any of the top-level components of a<compound-selector>or<complex-selector-unit>(that is, forbidden between the<type-selector>and<subclass-selector>, or between the<pseudo-element-selector>and<pseudo-class-selector>, etc).
-
Betweenanyof the components of a<type-selector>or a<class-selector>.
-
Between the ':'s, or between the ':' and<ident-token>or<function-token>, of a<pseudo-element-selector>or a<pseudo-class-selector>.
-
Betweenanyof the components of a<wq-name>.
-
Between the components of an<attr-matcher>.
-
Between the<compound-selector>or<pseudo-compound-selector>s in a<complex-selector-unit>
-
Between the components of a<combinator>.
Whitespace isrequiredbetween two<complex-selector-unit>s if the<combinator>between them is omitted. (This indicates the descendant combinator is being used.)
-
- In<id-selector>,the<hash-token>’s value must be anidentifier.
- The<pseudo-class-selector>production excludes the<legacy-pseudo-element-selector>production. (That is,:before/etc must never be parsed as a pseudo-class, even if doing so would cause the selector to become valid due to, for example, other simple selectors following it.)
Note:A selector is also subject to a variety of more specific syntactic constraints, and adherence to the grammar above is necessarybut not sufficientfor the selector to be considered valid. See§ 3.9 Invalid Selectors and Error Handlingfor additional rules for parsing selectors.
Note:In general, a<pseudo-element-selector>is only valid if placed at the end of the last<compound-selector>in a<complex-selector>. In some circumstances, however, it can be followed by more<pseudo-element-selector>s or<pseudo-class-selector>s; but these are specified on a case-by-case basis. (For example, theuser action pseudo-classesare allowed after anypseudo-element, and thetree-abiding pseudo-elementsare allowed after the::slotted()pseudo-element.)
The fourLevel 2pseudo-elements(::before,::after,::first-line,and::first-letter) may, for legacy reasons, be written with only a single ":" character at their front, making them resemble a<pseudo-class-selector>.
18.1.<forgiving-selector-list>and<forgiving-relative-selector-list>
For legacy reasons, the general behavior of a selector list is that if any selector in the list fails to parse (because it uses new or UA-specific selector features, for instance), the entire selector list becomes invalid. This can make it hard to write CSS that uses new selectors and still works correctly in older user agents.
The<forgiving-selector-list>production instead parses each selector in the list individually, simply ignoring ones that fail to parse, so the remaining selectors can still be used.
Note:Style rules still use the normal, unforgiving selector list behavior.<forgiving-selector-list>is used in:is()and:where()only. Although it does have some minor implications on specificity, wrapping a style rule’s selector in:is()effectively "upgrades" it to become forgiving, so long as it doesn’t contain any pseudo-elements (which aren’t valid in:is()or:where()).
Syntactically,<forgiving-selector-list>is equivalent to<any-value>?
.
It is thenparsed as a forgiving selector listto obtain its actual value.
-
Parse a listof<complex-real-selector>s frominput, and letselector listbe the result.
-
Remove all failure items fromselector list, and all items that areinvalid selectors, then return a<selector-list>representing the remaining items inselector list. (This might be empty.)
Any items in a<forgiving-selector-list>that are invalid (whether explicitly, by using unknown selectors or syntax, or merely contextually, using known syntax but in an invalid context) must be treated as having zero specificity.
Note:<forgiving-selector-list>is intentionally used only in:is()and:where(), not in any other selector that takes a selector argument.
19.API Hooks
To aid in the writing of specs that use Selectors concepts, this section defines several API hooks that can be invoked by other specifications.
Are these still necessary now that we have more rigorous definitions formatchandinvalid selector?
Nouns are a lot easier to coordinate across specification than predicates,
and details like the exact order of elements returned fromquerySelector
seem to make more sense being defined in the DOM specification than in Selectors.
19.1.Parse A Selector
This section defines how toparse a selectorfrom a stringsource. It returns either a complex selector list, or failure.
- Letselectorbe the result ofparsingsourceas a<selector-list>. If this returns failure, it’s aninvalid selector; return failure.
- Ifselectoris aninvalid selectorfor any other reason (such as, for example, containing an undeclared namespace prefix), return failure.
- Otherwise, returnselector.
19.2.Parse A Relative Selector
This section defines how toparse a relative selectorfrom a stringsource. It returns either a complex selector list, or failure.
- Letselectorbe the result ofparsingsourceas a<relative-selector-list>. If this returns failure, it’s aninvalid selector; return failure.
- Ifselectoris aninvalid selectorfor any other reason (such as, for example, containing an undeclared namespace prefix), return failure.
- Otherwise, returnselector.
19.3.Match a Selector Against an Element
This section defines how tomatch a selector against an element.
APIs using this algorithm must provide aselectorand anelement.
Callers may optionally provide:
- one or morescoping roots, for resolving the:scopepseudo-class against.
This algorithm returns either success or failure.
For eachcomplex selectorin the givenselector(which is taken to be alist of complex selectors), match the complex selector againstelement, as described in the following paragraph. If the matching returns success for any complex selector, then the algorithm return success; otherwise it returns failure.
Tomatch a complex selector against an element, process itcompound selectorat a time, in right-to-left order. This process is defined recursively as follows:
- If any simple selectors in the rightmost compound selector does not match the element, return failure.
- Otherwise, if there is only one compound selector in the complex selector, return success.
- Otherwise, consider all possible elements that could be related to this element by the rightmostcombinator. If the operation of matching the selector consisting of this selector with the rightmost compound selector and rightmost combinator removed against any one of these elements returns success, then return success. Otherwise, return failure.
19.4.Match a Selector Against a Pseudo-element
This section defines how tomatch a selector against a pseudo-element.
APIs using this algorithm must provide aselectorand apseudo-element. They may optionally provide the same things they may optionally provide to the algorithm tomatch a selector against an element.
This algorithm returns success or failure.
For eachcomplex selectorin the givenselector,if both:
- the rightmostsimple selectorin the complex selector matchespseudo-element,and
- the result of runningmatch a complex selector against an elementon the remainder of thecomplex selector(with just the rightmost simple selector of its rightmost complex selector removed),pseudo-element’s corresponding element, and any optional parameters provided to this algorithm returns success,
Otherwise (that is, if this doesn’t happen for any of the complex selectors inselector), return failure.
19.5.Match a Selector Against a Tree
This section defines how tomatch a selector against a tree.
APIs using this algorithm must provide a selector, and one or moreroot elementsindicating thesubtreesthat will be searched by the selector. All of theroot elementsmust share the sameroot, or else calling this algorithm is invalid.
They may optionally provide:
- One or morescoping rootsindicating the selector isscoped.
-
A list ofpseudo-elementsthat are allowed to show up in the match list.
If not specified, this defaults to allowing all pseudo-elements.
Only thetree-abiding pseudo-elementsare really handled in any way remotely like this.
This algorithm returns a (possibly empty) list of elements.
- Start with a list ofcandidate elements, which are theroot elementsand all of their descendant elements, sorted inshadow-including tree order, unless otherwise specified.
- Ifscoping rootwere provided, then remove from thecandidate elementsany elements that are notdescendantsof at least onescoping root.
- Initialize theselector match listto empty.
-
For eachelementin the set ofcandidate elements:
- If the result ofmatch a selector against an elementforelementandselectoris success, addelementto theselector match list.
-
For each possible pseudo-element associated withelementthat is one of the pseudo-elements allowed to show up in the match list,
if the result ofmatch a selector against a pseudo-elementfor the pseudo-element andselectoris success,
add the pseudo-element to theselector match list.
The relative position of pseudo-elements inselector match listis undefined. There’s not yet a context that exposes this information, but we need to decide on something eventually, before somethingisexposed.
Appendix A: Guidance on Mapping Source Documents & Data to an Element Tree
This section is informative.
The element tree structure described by the DOM is powerful and useful, but generic enough to model pretty much any language that describes tree-based data (or even graph-based, with a suitable interpretation).
Some languages, like HTML, already have well-defined procedures for producing a DOM object from a resource. If a given language does not, such a procedure must be defined in order for Selectors to apply to documents in that language.
At minimum, the document language must define what maps to the DOM concept of an "element".
The primary one-to-many relationship between nodes—parent/child in tree-based structures, element/neighbors in graph-based structures—should be reflected as the child nodes of an element.
Other features of the element should be mapped to something that serves a similar purpose to the same feature in DOM:
- type
-
If the elements in the document language have some notion of "type"
as a basic distinguisher between different groups of elements,
it should be reflected as the "type" feature.
If this "type" can be separated into a "basic" name and a "namespace" that groups names into higher-level groups, the latter should be reflected as the "namespace" feature. Otherwise, the element shouldn’t have a "namespace" feature, and the entire name should be reflected as the "type" feature.
- id
-
If some aspect of the element functions as a unique identifier across the document,
it should be mapped to the "id" feature.
Note:While HTML only allows an element to have a single ID, this should not be taken as a general restriction. The important quality of an ID is that each ID should be associated with a single element; a single element can validly have multiple IDs.
- classes and attributes
- Aspects of the element that are useful for identifying the element, but are not generally unique to elements within a document, should be mapped to the "class" or "attribute" features depending on if they’re something equivalent to a "label" (a string by itself) or a "property" (a name/value pair)
- pseudo-classes and pseudo-elements
-
If any elements match any pseudo-classes or have any pseudo-elements,
that must be explicitly defined.
Some pseudo-classes are *syntactical*, like:has()and:is(), and thus should always work. Need to indicate that somewhere. Probably the structural pseudos always work whenever the child list is ordered.
- The "elements" of the JSON document are each array, object, boolean, string, number, or null. The array and object elements have their contents as children.
- Each element’s type is its JS type name: "array", "object", etc.
- Children of an object have their key as a class.
- Children of an array match the:first-child,:nth-child(),etc pseudo-classes.
- The root object matches:root.
- It additionally defines:val()and:contains()pseudo-classes, for matching boolean/number/string elements with a particular value or which contain a particular substring.
This structure is sufficient to allow powerful, compact querying of JSON documents with selectors.
Appendix B: Obsolete but Required-webkit-
Parsing Quirks for Web Compat
This appendix is normative.
Due to legacy Web-compat constraints, user agents expecting to parse Web documents must support the following features:
-
:-webkit-autofillmust be treated as alegacy selector aliasof:autofill.
-
All otherpseudo-elementswhose names begin with the string “-webkit-” (matchedASCII case-insensitively) and that are not functional notations must be treated as valid at parse time. (That is,::-webkit-asdfis valid at parse time, but::-webkit-jkl()is not.) If they’re not otherwise recognized and supported, they must be treated as matching nothing, and areunknown -webkit- pseudo-elements.
Unknown -webkit- pseudo-elementsmust be serialized in ASCII lowercase.
What’s this quirk about?
Selectors have long had a behavior where a single unknown/invalid selector invalidates the entire selector list (rather than just invalidating the one complex selector it finds itself in). This is generally considered a legacy mistake by the WG, but can’t be fixed at this point, as too many stylesheets depend on this behavior, intentionally or not.
One aspect of this is that use of vendor-specific selectors invalidates the entire selector in other user agents that don’t recognize them, and takes the entire style rule down with it. This has been used intentionally in the past—in the severely-not-recommended practice of hiding style rules from some browsers by making them invalid in every other browser—and unintentionally, with people styling an element and also applying those styles to a vendor-specific pseudo-element (such as the various
input
-related pseudos some browsers expose), not realizing that this hides the entire rule from other browsers.In addition to this more general reasoning, WebKit-derived user agents, such as Safari or Chrome, have an additional quirk related to their vendor-prefixed pseudo-elements, where any::-webkit--prefixed selectors are considered valid at parse time. (This is probably a leftover quirk of an early CSS feature, since dropped, that intentionally treated all possible pseudo-elements as valid at parse time, in anticipation of a feature letting authors define their own pseudo-elements.)
Similar to other legacy quirks, such as those documented in[QUIRKS], this particular vendor-specific oddity has become common enough that other user agents are seeing sites breaking due to them depending on it, accidentally or not. As such, since the quirk is in practical termsrequiredto render the modern web correctly, specifying it and requiring it for all user agents ensures that today’s web pages are more likely to be correctly rendered in user agents both current and future.
As usual with quirks, however, webpages intentionally relying on this will be met with shaming and derision from members of the CSSWG, and all right-thinking web developers.
20.Changes
20.1.Changes since the 7 May 2022 Working Draft
Significant changes since the7 May 2022 Working Draft:
-
Marked:blankas at-risk and removed the at-risk status from:read-writeand:has()
-
Added:openand:closedpseudo-classes. (Issue 7319)
-
Disallowedpseudo-elementsfrom:has()unless explicitly allowed by the pseudo-element’s definition. (Issue 7463)
-
Disallowed nesting of:has(). (Issue 7344)
-
Made:has()and the selector argument of:nth-child()/:nth-last-child()no longer forgiving. (Issue 7676)
-
Defined matching of::lang( "" )and of elements not tagged with a language. (Issue 6915)
-
Untangled the concepts of "scoped" and "relative" selectors completely. (Issue 6399)
-
Removed "absolutize a selector" as well, and just defined relative selector matching in terms of the anchoring element.
-
-
Reverted compound selector limitation on:nth-child(). (Issue 3760)
-
Defined:-webkit-autofilllegacy selector alias. (Issue 7474)
-
Moved the legacy single-colon pseudo-element syntax into the grammar itself. (Issue 8122)
20.2.Changes since the 21 November 2018 Working Draft
Significant changes since the21 November 2018 Working Draft:
- Removed the Selector profiles, marked:has()as optional and at-risk instead. (Issue 3925)
- Added§ 3.6.4 Sub-pseudo-elementsto definesub-pseudo-elementsand related terminology.
- Added:defined. (Issue 2258)
- Added:modal. (Issue 6965)
- Added:fullscreenand:picture-in-picture. (Issue 3796)
- Added:seeking,:buffering,and:stalledmedia playback state pseudo-classes. (Issue 3821)
- Added:mutedand:volume-lockedsound state pseudo-classes. (Issue 3821andIssue 3933)
- Added:autofill. (Issue 5775)
- Added:user-valid. (Discussion)
- Defined:is(),:where(),:has(),:nth-child(),and:nth-last-child()to not be themselves invalidated when containing an invalid selector. (Issue 3264)
- Limited selectors in:nth-child()and:nth-last-child()tocompound selectorsfor now. (Issue 3760)
- Clarified case-sensitive string matching by referencing string identity as defined in[INFRA].
- Clarified that UA-provided placeholder text still triggers:placeholder-shown.
- Rewrote:focus-visibledefinition for clarity.
- Switched reminder note in the grammar section to normative text describing the requirement of whitespace between<compound-selector>s when a<combinator>token is missing.
20.3.Changes since the 2 February 2018 Working Draft
Significant changes since the2 February 2018 Working Draft:
- Named the zero-specificity selector to:where(). (Issue 2143)
- Renamed:matches()to:is(). (Issue 3258)
- Redefined:emptyto ignore white-space–only nodes. (Issue 1967)
- Redefined:blankto represent empty user input, rather than empty elements. (Issue 1283)
- Changed the specificity of:is(),:has(),and:nth-child()to not depend on which selector argument matched. (Issue 1027)
- Dropped the:drop()pseudo-classes since HTML dropped the related feature. (Issue 2257)
- Added the case-sensitive flag
s
to the attribute selector. (Issue 2101) - Added further guidance on:focus-visible.
- AddedAppendix B: Obsolete but Required -webkit- Parsing Quirks for Web Compatdefining::-webkit-pseudo-element parsing quirk. (Issue 3051)
- Rewrote grammar rules about where white space is allowed for clarity. (See§ 18 Grammar.)
20.4.Changes since the 2 May 2013 Working Draft
Significant changes since the2 May 2013 Working Draftinclude:
- Added the:target-within,:focus-within,:focus-visible,:playing,and:pausedpseudo-classes.
- Added a zero-specificity:matches()-type pseudo-class, with name TBD.
- Replaced subject indicator (!) feature with:has().
- Replaced the:nth-match()and:nth-last-match()selectors with:nth-child(… ofselector)and:nth-last-child(… ofselector).
- Changed the:active-drop-target,:valid-drop-target,:invalid-drop-targetwith:drop().
- Sketched out an empty-or-whitespace-only selector for discussion (Seeopen issue.)
- Renamed:user-errorto:user-invalid. (SeeDiscussion)
- Renamed:nth-column()/:nth-last-column()to:nth-col()/:nth-last-col()to avoid naming confusion with a potential::columnpseudo-class.
- Changed the non-functional form of the:local-linkpseudo-class to account for fragment URLs.
- Removed the functional form of the
:local-link()
pseudo-class and reference combinator for lack of interest. - Rewrote selectors grammar using the CSS Value Definition Syntax.
- Split outrelative selectorsfromscoped selectors, as these are different concepts that can be independently invoked.
- Moved definition of<An+B>microsyntax to CSS Syntax.
-
Added new sections:
- § 3.2 Data Model
-
§ 19 API Hooks
- Note that earlier versions of this section defined a section onevaluating a selector, but that section is no longer present. Specifications referencing that section should instead reference the algorithm tomatch a selector against a tree.
- Removed restriction on combinators within:matches()and:not(); seediscussion.
- Definedspecificityof aselector list.(Why?)
- Required quotes around:lang()values involving an asterisk; only language codes which happen to be CSS identifiers can be used unquoted.
Note:The 1 February 2018 draft included an inadvertent commit of unfinished work; 2 February 2018 has reverted this commit (and fixed some links because why not).
20.5.Changes since the 23 August 2012 Working Draft
Significant changes since the23 August 2012 Working Draftinclude:
- Added:placeholder-shownpseudo-classes.
- Released some restrictions on:matches()and:not().
- Defined fast and complete Selectors profiles (now called “live” and “snapshot” ).
- Improved definition ofspecificityto better handle:matches().
- Updated grammar.
- Cleaned up definition of<An+B>notation.
- Added definition ofscope-relativeselectors, changedscope-constrainedto scope-filtered for less confusion with scope-contained.
- The:local-link()pseudo-class now ignores trailing slashes.
20.6.Changes since the 29 September 2011 Working Draft
Significant changes since the29 September 2011 Working Draftinclude:
- Added language variant handling per RFC 4647.
- Added scoped selectors.
- Added:user-error(now called:user-invalid).
- Added:valid-drop-target.
- Changedcolumn combinatorfrom double slash to double pipe.
20.7.Changes Since Level 3
Additions sinceLevel 3:
- Extended:not()to accept a selector list.
- Added:is()and:where()and:has().
- Added:scope.
- Added:any-linkand:local-link.
- Addedtime-dimensional pseudo-classes.
- Added:target-within,:focus-within,and:focus-visible.
- Added:dir().
- Expanded:lang()to accept wildcard matching and lists of language codes.
- Expanded:nth-child()to accept a selector list.
- Merged in input selectors fromCSS Basic User Interface Module Level 3and added back:indeterminate.
- Added:blankand:user-invalid.
- Addedgrid-structural (column) selectors.
- Added case-insensitive / case-sensitive attribute-value matching flags.
21.Acknowledgements
The CSS working group would like to thank everyone who contributed to theprevious Selectorsspecifications over the years, as those specifications formed the basis for this one. In particular, the working group would like to extend special thanks to the following for their specific contributions to Selectors Level 4: L. David Baron, Andrew Fedoniouk, Daniel Glazman, Ian Hickson, Grey Hodge, Lachlan Hunt, Anne van Kesteren, Jason Cranford Teague, Lea Verou
Privacy Considerations
- The:visitedpseudo-class can expose information about which sites a user has previously visited, if the UA is not careful to screen from scripting any information that would reveal which elements match it.
- The:autofillpseudo-class can expose whether a user has interacted with this form before; however the same information can be derived by observing how quickly the form is filled out.
Security Considerations
ThePrivacy Considerationscould also be considered to affect Security.