CSS selector for foo that contains bar?
No, what you are looking for would be called a parent selector. CSS has none; they have been proposed multiple times but I know of no existing or forthcoming standard including them. You are correct that you would need to use something like jQuery or use additional class annotations to achieve the effect you want.
Here are some similar questions with similar results:
- Is there a CSS parent selector?
- CSS Parent/Ancestor Selector
- Complex CSS selector for parent of active child
Why do 'foo bar' and 'foo bar' have the same specificity in CSS?
This has actually been brought up in the working group mailing list, way back when, in this thread.
It basically comes down to, yes, intuitively a selector with a combinator looks more specific, but an algorithm, extended form the current one, with this in mind becomes much more complicated than the "simple" triplets used now, which is pretty confusing for people as it is.
Finally,
While this could have been the case, this is one of the few things in CSS2
that have been interoperably implemented for years, and therefore won't
change in CSS2.1.
"If it ain't broke, don't fix it." seemed to be the final call.
The CSS selector for an element that its id is in the foo:bar form
According to the W3c spec linked to in this answer, using colons in element IDs is plain wrong if used unescaped.
In CSS, identifiers (including element names, classes, and IDs in selectors) can contain only the characters [a-z0-9] and ISO 10646 characters U+00A1 and higher, plus the hyphen (-) and the underscore (_); they cannot start with a digit, or a hyphen followed by a digit. Identifiers can also contain escaped characters and any ISO 10646 character as a numeric code (see next item). For instance, the identifier "B&W?" may be written as "B\&W\?" or "B\26 W\3F".
Is the JSF framework really outputting those IDs in the final rendered HTML?
Two classes in :not() selector
The :not
pseudo class takes a simple selector, so use i.e. the attribute selector
p:not([class="foo bar"]) { color: #ff0000;}
<p class="foo">This is a (.foo) paragraph.</p><p class="bar">This is a (.bar) paragraph.</p><p class="foo bar">This is a (.foo.bar) paragraph.</p><p>This is a normal paragraph.</p>
How do I do an and selector?
Concatenate the selector. So you would use .foo.bar {}
How to apply CSS to elements that have multiple classes?
Solutions
.foo.bar { ... }
[class="foo bar"] { ... } // explicit class name
[class~="foo"][class~="bar"] { ... } // inclusive class name
:has vs :matches - Selectors Level 4
In a nutshell:
E:has(rs1, rs2)
matches E when a different element F matches any of the selector arguments in relation to E. If you know jQuery's:has()
selector, this is exactly the same thing.E:matches(s1, s2)
matches E when E itself matches any of the selector arguments. Think of:matches()
as the direct opposite of:not()
, which matches E if E itself does not match any of the arguments.1 You can also think of:matches()
as a pseudo-class version of jQuery's.filter()
method.This notation is equivalent to concatenating every selector argument with E (provided you can actually concatenate them) such that you have a selector list
(E)(s1), (E)(s2)
. For example,div:matches(.foo, .bar)
is equivalent todiv.foo, div.bar
.
This fundamental difference is demonstrated most straightforwardly with the selectors div:matches(p)
and div:has(p)
:
div:has(p)
matches anydiv
element that has ap
descendant.
This is very similar todiv p
, except the former targets thediv
and the latter targets thep
.Since a
div
can never be ap
,div:matches(p)
will never match
anything. (Likewise,div:not(p)
will match alldiv
elements.)
Here's a more complex example with slightly less absurd selectors:
div:has(.foo, .bar)
div:matches(.foo, .bar)
With the following markup:
<div class="foo"></div> <!-- [1] -->
<div class="bar"></div> <!-- [1] -->
<div class="foo bar"> <!-- [2] -->
<p></p>
</div>
<div> <!-- [3] -->
<p class="foo"></p>
</div>
<div> <!-- [3] -->
<div> <!-- [3] -->
<p class="bar"></p>
</div>
</div>
<div> <!-- [4] -->
<div class="foo"> <!-- [5] -->
<p class="bar"></p>
</div>
</div>
Which elements are matched by which selectors?
Matched by
div:matches(.foo, .bar)
The firstdiv
element has the "foo" class, and the seconddiv
element has the "bar" class, so each of these satisfies its respective selector argument in the:matches()
pseudo-class.Matched by
div:matches(.foo, .bar)
The thirddiv
element has both classes, so it matches both selector arguments.A note on specificity: both of these arguments have equal specificity, making the total specificity
(0, 1, 1)
, but when an element matches multiple selector arguments with different specificity values, the spec says that the specificity is that of the most specific argument that is matched.Matched by
div:has(.foo, .bar)
Each of thesediv
elements has a descendant element (in this case, ap
) with a class that matches its respective selector argument in the:has()
pseudo-class.Matched by
div:has(.foo, .bar)
Thisdiv
element has adiv.foo
descendant and ap.bar
descendant, therefore it satisfies both relative selector arguments.A note on specificity: because
:has()
is not yet in the fast profile and is therefore tentatively excluded from CSS, the concept of specificity does not apply at all. There are plans to include a limited version of this in the fast profile for use in CSS, but there is nothing concrete as yet. Any new developments will be added at an appropriate time.Matched by
div:matches(.foo, .bar)
anddiv:has(.foo, .bar)
Thisdiv
element matches both pseudo-classes:- it is
.foo
(as it has the "foo" class), and - it has a descendant with the "bar" class.
This element would also match
div:matches(.foo, .bar):has(.foo, .bar)
, which would be a valid level 4 selector since a compound selector can have any combination of pseudo-classes.- it is
Another difference between :matches()
and :has()
is that :has()
accepts what's known as a relative selector. A relative selector has a scope; selector scoping is an entire topic in its own right, but for the purposes of :has()
, the scoping element is always the element you attach the :has()
pseudo-class to. But, more importantly, a relative selector can either have an implicit descendant combinator, or begin explicitly with a combinator such as >
, +
or ~
— this combinator is what links the rest of the relative selector to its scoping element.
For example, while :has()
defaults to an ancestor-descendant relationship, you can pass a relative selector that begins with +
and it then becomes an adjacent-sibling relationship: ul:has(+ p)
matches any ul
element that is directly followed by a p
(and not necessarily one that contains a p
descendant).
As for :matches()
, while the overview table says that it accepts a list of compound selectors, AFAIK it hasn't yet been set in stone whether it will take a list of compound selectors or complex selectors, and in which profile (fast or complete). But a compound selector is simply the new name for what Selectors 3 currently calls a sequence of simple selectors and a complex selector is an entire series of compound selectors and combinators. A relative selector is more like a complex selector in that respect. See this answer for a non-exhaustive list of the various terms used in selectors.
1 Yes, that's "arguments" in plural — in Selectors 4, :not()
can now accept a list of selectors as opposed to a single simple selector. A much-needed enhancement, but it's also to make it consistent with the other new functional pseudo-classes.
Related Topics
How to Make Ng-Select Remove-And-Read-Only
How to Scale an Image Proportionally Within a Table Cell of a Fixed Size
Bootstrap 4 - Change Position of Carousel Controls
Bootstrap 4 Table With One Column Larger Than Others
Is There a CSS Selector for Elements Containing Certain Text
How to Change Angular Material Table Row Height
How to Wrap or Truncate Long Strings in a Material-Ui Expansionpanelsummary
Add Footer Text in Each Page of Pdf Using CSS
How to Set the Size of a Column in a Bootstrap Responsive Table
Why It Is Not Taking 100% Height in Material Design
Bootstrap 4 Carousel Responsive (Image and Text)
Align an Image and Some Text on the Same Line Without Using Div Width
Overriding the Encapsulated CSS of External Component
How to Get the Footer to Stay At the Bottom of a Web Page
Column Order Manipulation Using Col-Lg-Push and Col-Lg-Pull in Twitter Bootstrap 3