CSS - target the first element with class - html

HTML:
<p class=menu_top>Title</p>
<p class=menu_top>Order</p>
<p class=menu_top>Position</p>
<p class=menu_top>Number</p>
How can I target just the first element?

Use the :first-child pseudo-class.
.menu_top:first-child {
your: rules;
}
http://jsfiddle.net/uKJcK/1/

Just as a point of note, the way you're structuring is going to cause you more work in the future, as well. It would be far better to have something like this:
<div class="menu_top">
<p>Title</p>
<p>Order</p>
<p>Position</p>
<p>Number</p>
</div>
(and more semantically-correct would be to make it an unordered list)
The repetition is not necessary, when you can simply spec in CSS like so:
.menu_top p {
//all my basic styles for each menu item
}
.menu_top p:first-child {
// specific styles for just the first menu item
}
Over-classing causes a load of rework in the future, and muddies the code. Use the cascade to your advantage; it cuts down on repetitive code, and makes it easier to override only the outliers.

Related

Preventing CSS from affecting child views

In the context of .NET MVC (but that could also apply to other similar technologies), let :
A tree of views, e.g the page view FileUploadPage and its child partial view FileDropZone that would have a class identifying their view "type" on their root node :
FileUploadPage.cshtml :
<div class="view-fileuploadpage">
<h2>File upload page view</h2>
#Html.Partial("FileDropZone")
</div>
FileDropZone.cshtml :
<div class="view-filedropzone">
File drop zone partial view
</div>
Some CSS rules which I would like to apply only to the view's own elements instead of globally :
Like this :
.view-fileuploadpage h2 {
/* Spécific to the view FileUploadPage */
}
But NOT like this :
h2 {
/* Global, not what I want */
}
I like this way of doing things, because it prevents interferences from other pages in the CSS due to needlessly global selectors.
However there is a problem with that : the view-specific CSS rules apply to the view's own elements, but also to any other view that is being included as a child view. In the example above, the view FileDropZone inherits the rules that are supposed to be specific to the view FileUploadPage, which is an undesired consequence.
So my question is : how can I make the CSS rules that are supposed to be specific to my views own elements NOT apply to the child views as well ?
I could use the "direct child" opeartor in my selectors to specify the full "path" to the elements I want to style, like so :
.view-fileuploadpage > h2 {
/* Applies to the h2 of the view FileUploadPage */
/* DOes NOT apply to any h2 that would exist in a child view of FileUploadPage */
}
But this would make the code hard to maintain, because the selectors would have to be updated everytime a piece of markup gets moved or modified within a view.
I'm having the exact same problem with JavaScript and query selectors, but I guess finding a solution for CSS would also solve the JavaScript problem.
Thank you.
You can use the :not() pseudo-class to deselect grandchildren within a particular child.
.view-fileuploadpage h2:not(.file-drop-zone *):not(.more-children *){
color: #f00;
}
This assigns the color to all h2 elements excluding those in the stated classes within the :not() selector.
The CSS file will need to be updated with the classes of new children if any.
The best solution will be to wrap all the contents of the view-fileuploadpage or parent div that should not get the styling and use the class of this wrapper as a single selector. This way, the file will not need constant updating all future children and grandchildren are added within the wrapper.
Hence, instead of having:
<div class='view-fileuploadpage-one'>
<h2>Container</h2>
<p>...</p>
<div class='file-drop-zone'>
<h2>file drop zone</h2>
...
</div>
<div class='more-children'>
<h2>More children</h2>
...
</div>
</div>
You can opt for:
<div class='view-fileuploadpage-two'>
<h2>Container</h2>
<p>...</p>
<div class='content-wrapper'>
<!-- this wrapper will contain everything else -->
<div class='file-drop-zone'>
...
</div>
<div class='more-children'>
...
</div>
</div>
</div>
</div>
Which will be more or less:
<div class='view-fileuploadpage-two'>
...
<div class='content-wrapper'>
...
</div>
</div>
Kindly see my idea on this pen.

CSS Syntax for children that are not direct descendents?

The question I want to ask is, "Is it possible/good practice to refer to a child of an element that is not a direct child?"
For instance, if you have HTML like this:
<form class="formation">
<p>
<span>
<input class="phone input">
</span>
</p>
<p>
<span>
<input class="text input">
</span>
</p>
</form>
And you want to refer in CSS to the inputs only in that particular form, so you call the class of the form followed by the class of the inputs without referring to the elements in between, like this:
.formation .input {
width: 10px;
}
will this work properly?
I tend to think I've done this already on projects and it has worked properly but usually I refer to all the children in between (because I don't go that deep). But I'm currently working on a media query for a wordpress site that doesn't seem to be respecting this rule. Is this bad practice? Or is this downright incorrect? Thanks for all your help!
Yes, it is not only possible but also advisable to do so. Choose your selectors for your css rules as lean as needed to reduce dependency on your markup structure. This is not only wise for performance reasons, it also saves you quite some work in case your markup should ever change, e.g. later on you notice the span is not needed any longer and you remove it to keep your markup as clean as possible. In case you used the full DOM path to your .input you will then also have to adjust your css selectors. Same if for any reason in the future your <p> should become a <div>.
Just make sure you give the rules as much DOM context as necessary to not apply your rules to the same classed element in other contexts (if you have any at all, and if you want to apply a different set of style rules for it).
Yes, it'll work fine. What youv'e got with .form .input allows for any number of intermediate nodes between the two classes.
If you'd had .form > .input, then your CSS wouldn't match at all. > is the "immediate descendant" selector, so
.form .input { color: green }
.form > .input { color: red }
<div class="form">
<div class="input">This is red</div>
<div class="whatever">
<div class="input">This is green</div>
</div>
</div>

Logical AND for CSS3

I have a quite interesting problem here.
I want to target elements that match two conditions at the same time, but I can not find the way
<div class='redLink'>
<!-- ... ... ... -->
<a href='#'>Link</a>
<!-- ... ... ... -->
</div>
<div>
<!-- ... ... ... -->
<a href='#' class='redLink'>Link</a>
<!-- ... ... ... -->
</div>
My ideal CSS would be
[*:not(.redLink) a] AND [* a:not(.redLink)] {
color:green;
/* i.e., color NOT red */
}
However, the operand , is just an OR (and, when it doesn't match one condition, it matches the other...!).
And the only AND I can find is the logical concatenation div#myDivId.someClass, though what I would like is something like [div#myDiv a].[div.someClass a]
My goal is to target ONLY those anchors <a/> that don't have the class .redLink and have no parents with the .redLink class eiher.
And, very important, the only thing I want to target is the final anchor, not the whole div or the whole element.redLink...
Thank you!
Unfortunately, you can't achieve this using a CSS selector with a single rule. Currently you can only target a elements without the class using a:not(.redLink).
It is not possible to target a elements that do not have any .redLink ancestors, because the :not() pseudo-class doesn't accept combinators (otherwise you would do a:not(.redLink a)). A selector like :not(.redLink) a wouldn't work either, because that targets a elements with at least one ancestor without the class, which is not the same as a elements that have no ancestors with the class.
For example if your structure looked like this:
<div class='redLink'>
<p>
<a href='#'>Link</a>
</p>
</div>
That p doesn't have the class, so :not(.redLink) a would match.
If you happen to have the option of using jQuery, though, $('a:not(.redLink, .redLink a)') will work, because :not() is much more permissive in jQuery than in CSS.
If you need to do this using CSS only, the easiest solution is to make all a elements green, then override it:
a {
color: green;
}
a.redLink, .redLink a {
color: red;
}
Maybe you can reverse the logic like this. Make every link green (if that is possible in your site) and make the specific links red again.
a {
color: green;
}
a.redlink,
.redlink a {
color: red;
}
Of course it depends on the structure and complexity of your site and the existance of other styling that might collide with this, but I would prefer a CSS-only solution like this over JQuery if it is reasonably possible.

Simplest way to convert all the classes to inline in CSS

I have some classes that are used for Styling and all of them display using block mode.. I would like to convert them all to inline.. Is there a simple way to convert them all to inline, instead of manually going to each class to convert them individually to inline...
Section of your code:
<div class="contentbody">
<p>
Register here!
</p>
<a href="{% url 'parent_register_step1' %}"
class="bbutton textshadowclass boxshadow">
<div class="boxshadowinset green">
Register
</div>
</a>
<p>
Forgot your password?
</p>
<a href="{% url 'parent_forgot_password' %}"
class="bbutton textshadowclass boxshadow">
<div class="boxshadowinset green">
Reset Password
</div>
</a>
</div>
I would like to change the classes bbutton, textshadowclass, box shadow, boxshadowinset green into inline.. What is the simplest way?
Note: This classes are used in other sections of the page. I would like to change the certain section to be inline only. It shouldn't affect the whole page...
Let me explain more in detail what i am doing:
I would like to convert this into inline such that the register and reset password appear on the same line...
To only select the classes that are instead the contentbody class, you need a CSS element>element Selector:
div.contentbody>.bbutton, div.contentbody>.textshadowclass, ... {
display: inline;
}
(add more classes to the list if you want others included as well)
Additional note: If you permanently need these classes to be inline, then I would suggest to just (once) going to each class and add an inline class to each element, this keeps your code clearer in the long run.
Edit:
use the union selector (sorry I cannot find a more official link) to select elements that have multiple classes set:
div.contentbody>.boxshadowinset.green {
display: inline;
}
Note the . (and no space) between boxshadowinset and green
I do believe this is supported by modern browsers, but IE6 does seem to have some problems with it.
One way is just to apply an id to your wrapping element.
<div class="contentbody" id="contentbody">
Then in your css, add the styling
div#contentbody a, div#contentbody div{ display: inline; }
Due to CSS Element Hierarchy, they will all take the inline style rather than their own style.
Basic example here. http://jsfiddle.net/H97c5/2/

CSS: Highlight current menu item

I have a menu with links in the following form, in which I am trying to highlight the current menu item. I can't seem to get it working. Please advice as to what I am doing wrong
HTML
<body id="home">
<div id="topMenu">
<div class="nav-home" id="topMenuBlock"><p>Home</p></div>
<div id="nav-about"><p>About</p></div>
<div id="nav-rates"><p>Rates</p></div>
<div id="nav-faq"><p>FAQ</p></div>
<div id="nav-contact"><p>Contact</p></div>
<div id="nav-careers"><p>Careers</p></div>
</div>
<div id="rightTopMenu"></div>
</div>...other stuff</body>
Then for the CSS I have the following:
#home a.nav-home{ border-bottom:2px solid white; }
Do the links HAVE to be in a List, or can I leave them in div's, and if so, how can I make this work?
Thanks.
You've a little bit of a mess here.
Do the links HAVE to be in a List, or can I leave them in div's?
They don't have to be, but they probably should be. There's not good reason to use the strange markup you have chosen, you should definitely consider switching to a list and <li> tags.
Problem with duplicate ids
You have <body id="home"> and <a href="" id="home">
You also have several instances of id="topMenuBlock" (I see you fixed this in your edit.)
You cannot have more than one element with the same id. id attributes must be unique, always. Use class names instead, if anything.
You are using this selector: #home a.nav-home {} but it doesn't match anything. There is no <a class="nav-home">. You can use something like:
#home {} because that's the id of the <a> element you want
.nav-home a {} - Selects the <a> inside an element with class="nav-home"
Perhaps you have the concept of ids and classes mixed up. Ids are supposed to uniquely identify HTML elements, whereas classes can be used as many times as you like. Right now you have 6 elements with the id #topMenuBlock. You should make a .topMenuBlock class instead. I would also make a #nav-home id instead of a class since there should only be one such element on each page.
Secondly, there is no need for the <p> tags you have within your <a> tags. In fact, it's against HTML standards to do so since anchors are inline elements and paragraphs are block-level elements.
Lastly, your CSS selector that sets the border is incorrect because the .nav-home div is not contained within an <a> element. Use this CSS instead (assuming you change nav-home to be an id rather than a class):
#nav-home{ border-bottom:2px solid white; }
Fix these issues and then see what happens. If you're new to HTML and CSS, I would recommend going through some tutorials, such as the ones found at http://www.w3schools.com/.
Your class identifier should be in the <a /> tag
You have
<div class="nav-home" id="topMenuBlock"><p>Home</p></div>
but you want
<div class="something" id="topMenuBlock"><a class = "nav-home" href="" id="home"><p>Home</p></a></div>
Modify your CSS class accordingly.