What I want to do is something like:
#div_id > .some_class
{
}
I don't want to change the class everywhere. I only want to change the class if it in that particular div.
Is ther some other way to do that same thing?
You've already stumbled upon the answer yourself:
#div_id > .class {
/* CSS magic */
}
This selects .class if it is the direct descendant of #div_id. For all descendants regardless of depth, use the selector #div_id .class instead.
See also this JSFiddle.
Your question already contains the child combinator CSS selector and will target the elements with class .some_class that are children of the element with id div_id, so if you have only one <div> with an id of div_id then it will only target the child elements with the class some_class. So it should work as already expected, except in IE6 of course which does not support that selector natively.
If you want to select grandchildren, use the descendant combinator.
Child combinator body > p
Descendant combinator body p
You essentially have the answer there. If you want to modify all classes with in a div then the selector would be div#id .this_class. If it's just one instance of the class inside the div (say you have a div called 'test' with three divs with a class of 'test_class' then you could either use the :nth-child() selector or the :first-of-type selector.
Your code looks fine to me. Note that the > operator will only affect the children of the DIV not any lower decendants (i.e. grandchildren). Remove the > to affect everything inside the DIV with the class .some_class.
Related
This is driving me nuts:
HTML:
<div><h1>Hello World!</h1></div>
CSS:
*:not(div) h1 { color: #900; }
Doesn't this read, "Select all h1 elements that have an ancestor that is not a div element...?" Thus, "Hello World!" should not be coloured red, yet it still is.
For the above markup, adding the child combinator works:
*:not(div) > h1 { color: #900; }
But doesn't affect the h1 element if it is not a child of a div element. For example:
<div><article><h1>Hello World!</h1></article></div>
Which is why I'd like to indicate the h1 element as a descendant, not a child, of the div element. Anyone?
Doesn't this read, "Select all h1 elements that have an ancestor that is not a div element...?"
It does. But in a typical HTML document, every h1 has at least two ancestors that are not div elements — and those ancestors are none other than body and html.
This is the problem with trying to filter ancestors using :not(): it just doesn't work reliably, especially when the :not() is not being qualified by some other selector such as a type selector or a class selector, e.g. .foo:not(div). You'll have a much easier time simply applying styles to all h1 elements and overriding them with div h1.
In Selectors 4, :not() has been enhanced to accept full complex selectors containing combinators, including the descendant combinator. Whether this will be implemented in the fast profile (and thus CSS) remains to be tested and confirmed, but once it is implemented, then you will be able to use it to exclude elements with certain ancestors. Due to how selectors work, the negation has to be done on the element itself and not the ancestor in order to work reliably, and therefore the syntax will look a little different:
h1:not(div h1) { color: #900; }
Anyone who's familiar with jQuery will quickly point out that this selector works in jQuery today. This is one of a number of disparities between Selector 3's :not() and jQuery's :not(), which Selectors 4 seeks to rectify.
The <html> element is not a <div>. The <body> element is not a <div>.
So the condition "has an ancestor that is not a <div>" will be true for all elements.
Unless you can use the > (child) selector, I don't think you can do what you're trying to do - it doesn't really make sense. In your second example, <article> is not a div, so that matches *:not(div) too.
This is driving me nuts:
HTML:
<div><h1>Hello World!</h1></div>
CSS:
*:not(div) h1 { color: #900; }
Doesn't this read, "Select all h1 elements that have an ancestor that is not a div element...?" Thus, "Hello World!" should not be coloured red, yet it still is.
For the above markup, adding the child combinator works:
*:not(div) > h1 { color: #900; }
But doesn't affect the h1 element if it is not a child of a div element. For example:
<div><article><h1>Hello World!</h1></article></div>
Which is why I'd like to indicate the h1 element as a descendant, not a child, of the div element. Anyone?
Doesn't this read, "Select all h1 elements that have an ancestor that is not a div element...?"
It does. But in a typical HTML document, every h1 has at least two ancestors that are not div elements — and those ancestors are none other than body and html.
This is the problem with trying to filter ancestors using :not(): it just doesn't work reliably, especially when the :not() is not being qualified by some other selector such as a type selector or a class selector, e.g. .foo:not(div). You'll have a much easier time simply applying styles to all h1 elements and overriding them with div h1.
In Selectors 4, :not() has been enhanced to accept full complex selectors containing combinators, including the descendant combinator. Whether this will be implemented in the fast profile (and thus CSS) remains to be tested and confirmed, but once it is implemented, then you will be able to use it to exclude elements with certain ancestors. Due to how selectors work, the negation has to be done on the element itself and not the ancestor in order to work reliably, and therefore the syntax will look a little different:
h1:not(div h1) { color: #900; }
Anyone who's familiar with jQuery will quickly point out that this selector works in jQuery today. This is one of a number of disparities between Selector 3's :not() and jQuery's :not(), which Selectors 4 seeks to rectify.
The <html> element is not a <div>. The <body> element is not a <div>.
So the condition "has an ancestor that is not a <div>" will be true for all elements.
Unless you can use the > (child) selector, I don't think you can do what you're trying to do - it doesn't really make sense. In your second example, <article> is not a div, so that matches *:not(div) too.
Is it possible to write a CSS rule to select the first child of an element without a specific class?
example:
<div>
<span class="common-class ignore"></span>
<span class="common-class ignore"></span>
<span class="common-class"></span>
<span class="common-class"></span>
</div>
In this case I would like to select the first span without class ignore.
I tried this, but didn't seem to work:
.common-class:first-child:not(.ignore) {
...some rules...
}
UPDATE:
If I add a class to the parent div named parent-class, a modified version of the selector suggested by Jukka works except when the first span with class ignore comes after the first one without. The above-mentioned selector is the following:
.parent-class > .common-class.ignore + .common-class:not(.ignore) {
...some rules...
}
This question is similar to CSS selector for first element with class, except for the first element without a class. As mentioned, :first-child:not(.ignore) represents an element that is the first child of its parent and does not have the class "ignore", not the first child matching the rest of the selector.
You can use the overriding technique with a sibling combinator that I've described in my answer to the linked question, replacing the class selector with the :not() pseudo-class containing a class selector:
.common-class:not(.ignore) {
/* Every span without class .ignore, including the first */
}
.common-class:not(.ignore) ~ .common-class:not(.ignore) {
/* Revert above declarations for every such element after the first */
}
This selects all span with a .common-class and without an .ignore class.
span.common-class:not(.ignore) {
color: blue;
}
But, because we want to select only the first one, you can override the siblings that follow with the ~ selector.
span.common-class:not(.ignore) ~ span {
color: black; /* or color: inherit; */
}
jsBin demo
If you are already using jQuery, this can also be done with
$("span.common-class:not(.ignore):first").css('color', 'blue');
No, it is not possible. The selector :first-child:not(.ignore) selects an element that is the first child of its parent and does not belong to class ignore. There is no “first of class” selector and no “first not of class” selector either.
You could use the selector .ignore + :not(.ignore), but it matches any element that is not in class ignore and immediately follows an element in that class. But it matches too much, not just the first one of such elements. Depending on the markup structure, this selector might still be suitable in a particular situation, even though it is not an answer to the general question asked.
You don't have to select the div using a class. What about other css solutions like nth-child etc.? Of course, this requires the knowledge of a document structure.
Is it possible to define css class behaves dependent to an other css class?
For example; when
a:hover
Then I want to set
p {background:#fff;}
Is this possible with pure css?
Edit: Assume that no nested relation exist.
If you mean you want all p to have that style when a:hover regardless of where they are in the DOM, then no, you can't do that. You'll need to use a script to apply the style (or some class containing that style) to the p elements when a receives a hover.
if you have a structure like this:
<a><p>...</p></a>
then this:
a:hover p {background: #fff;}
will work. However, block elements should not be placed inside inline elements (in this case, no <p> inside <a>
if your markup is valid, and looks like this:
<p><a>...</a></p>
then you could have
p:hover {background: #fff;}
but a descendant can't affect the parent css (unless you use javascript) while the opposite is true (parent css affects descendants)
I do not see why you would be limited to these restrictions with a littl creativity. if you use fixed positioning the descendant can overlap its parent. and still respond like a descendant.
If the <p> tag immediately follows the <a> tag then you could use the adjacent sibling selector e.g.
a:hover+p{
background:#fff;
}
This is supported in IE8+
While debugging some css i noticed there is a difference between this order of declaration. The first caused headings inside anchors to display inline as desired, the second seems not to:
1/ a.aname { display:inline; margin:0px;}
2/ .aname a { display:inline; margin:0px;}
<a name="download" class="aname"><h2>Download</h2></a>
I have mostly been using the second form to apply class styles.
What is the difference in how these are applied, and are there any guide rules when to use each? (to avoid the css-puzzlement which arises when it's done wrong)
Basic solution from answers:
Use "direct selection" elementtype.class{} or elementtype#id{} to apply style to elements directly. For styling which is intended to affect once each time the rule is used eg. a margin change, a display change, a noninheriting font change. Direct selection does not inherit to child elements, it is applied to parent element only.
Use "descendant selection" .class elementtype{} or #id elementtype to apply style to type descendants/children of the named or classed element. For styling which is intended to change appearance of elementtypes under an element/within a section of page where it is applied eg. inheriting font changes to text sections, inheriting format changes to paragraphs or list elements. Descendant selection applies to all child elements but never the parent.
NBself: learn about other selectors too asap ;)
The difference is the space between them, which is the descendant combinator in CSS.
The selector a.aname will match an anchor element with the class aname while the .aname a will match an anchor element that is a descendant of an element with the class aname:
<a class="aname">This matches the first rule</a>
<span class="aname"><a>This matches the second rule</a></span>
CSS combinators:
space = descendant combinator
> = child combinator (direct descendant)
+ = adjacent sibling combinator
The Selectutorial gives a pretty good overview or selectors and combinators.
If you use selectors where you can put identifiers together without combinators between them, the order doesn't matter. Example:
#id.class { ... }
.class#id { ... }