How to select multiple elements using CSS - css

I have the following markup:
<div class="c1">
<div class="c2">
<div class="c3">
<input>
<textarea></textarea>
</div>
<input>
<textarea></textarea>
</div>
</div>
I want to match the input and textarea elements from the div.c3 with only one CSS rule. I'm using
div.c1 .c2 .c3 input,textarea { border: 1px solid #f00; }
but this matches all textareas, not only the one cotnained in the c3 div.
Is this possible, or must I write separate CSS selectors for each element?
Look at http://jsfiddle.net/Bp3qn/1/ for the live example.
I updated http://jsfiddle.net/Bp3qn/3/
I only need the input and textarea contained in the c1->c2->c3 containers to be highlighted, not other combinations.

You don't need the other elements in the selector, unless you only want to match .c3 if it is within div.c1 .c2:
.c3 input,
.c3 textarea {
/* that's it! */
}
If you do (per your edit), use this:
div.c1 .c2 .c3 input,
div.c1 .c2 .c3 textarea{
border: 1px solid #f00;
}
Demo: http://jsfiddle.net/wesley_murch/Bp3qn/6/
after edit: thats what i'm trying to avoid (my real stylesheet is a lot more complex and css rules are longer, and its getting hard to read)
In that case, to make things easier just add another class to that .c3 like this:
<div class="c3 special">
.c3.special input,
.c3.special textarea{
border: 1px solid #f00;
}
Demo: http://jsfiddle.net/wesley_murch/Bp3qn/7/
If you MUST have the selector as small as possible and there are no other children of .c3.special, just use the star selector (almost never recommended):
.c3.special * {border: 1px solid #f00;}

div.c1 .c2 .c3 input,.c3 textarea { border: 1px solid #f00; }

I know it's an old topic but I wanted to add some points on this because I just ended up here while trying to apply the same king of logic.
And thanks to this question, I know now that we should reconsider that logic a bit.
First, the upvoted answer does solve the question but I don't understand why the use of .c1 .c2 classes in the CSS.
As #Wesley Murch first wrote, that should be enough:
.c3 input,.c3 textarea {
/* that's it! */ }
It's also ok to specify a bit more with:
div.c3 input,
div.c3 textarea {
border: 1px solid #f00;
}
which is already the shorthand for:
div.c3 > input,
div.c3 > textarea {
border: 1px solid #f00;
}
But, IMO, unless you really have no control of what's inside your div, you should simplify everything by just adding one more class in your HTML and then you'll also end up with only one rule which will be even a bit easier to read:
HTML update with one more class special-border-color for exemple:
<div class="c1">
<div class="c2">
<div class="c3">
<input class="special-border-color">
<textarea class="special-border-color"></textarea>
</div>
<input>
<textarea></textarea>
</div>
</div>
CSS simple rule:
.special-border-color {
border: 1px solid #f00;
}

Related

What does '--' dash dash mean in CSS property value

I bought a website template which used -- in their CSS property value. This gives the errors property value expected and at-rule or selector expected. I know of -- being used in for CSS property but never for property value. What does the -- used here mean?
.my-sm-nn1 {
margin-top: --0.25rem !important;
}
The use is absolutely useless. If you try run your code you will see the browser ignores it, it looks like:
Sorry to say, but unfortunately you bought a template which is not perfectly clean. This can happen. Maybe it was just a typo by the developer, maybe he didn't care. Hopefully the rest of your template works as expected.
You can run the code and try yourself. The line margin-top: --0.25rem !important; will just be ignored by any browser.
.outer {
background-color: orange;
border: solid 1px black;
}
.inner {
background-color: yellow;
border: solid 1px fuchsia;
margin-top: --0.25rem !important;
}
<div class="outer">
<div class="inner">
</div>
</div>
Note: if you wonder why is there now more CSS then in your question: I like to add background-colors and borders to elements to be 100% sure that some rules do or do not effect any styling of the elements.

Decoration elements and Accessibility

I'm not sure how to deal with anything(except images) that is used for design/decoration only in terms of accessibility. For example, if in case like this I'll use an image, I'd simply use alt="" or use CSS background image, so the AT for example will ignore it. But what if I'm using some <div> or anything else? It can be a div with some CSS styling that is presented in a code-way, instead of image, or it can be some text with CSS styling so it will be just for decoration(instead of images), or really, anything else. How should I mark it so it will be ignored in a proper way by AT?
Simple example(for request):
<div><span>For Decoration</span></div>
div{
width:0; height:0;
border-bottom:116px solid #009;
border-left:500px solid #900;
margin:0 auto;
}
div span{
display:block;
position:absolute;
margin:0 auto;
left:0;
right:0;
width:150px;
color:#fff;
}
There are two solutions to this:
1) if you are using an empty tag such as a div with no text in it, the screen reader will ignore it automatically. You don't need to do anything in particular.
2) if you are using a tag with text inside you should: a) give it an aria-hidden="true" if you don't want the screen-reader to read the text or b) give it a role="presentation" if you do want the screen-reader to read the text but not announce it as a particular type of element.
-------------------
Based on the comments on this post I have added code below showing an example. It shows when you wouldn't need to do anything (the first and last div) and when you would want to use aria-hidden and role="presentation".
The top line is purely for decoration. Part of it is empty divs and part of it is text. The different words for "Hello" in the p tag should be seen but don't need to be read since they're purely ornamental which is why I am using role and aria-hidden on it.
.end {
display: inline-block;
width: 5%;
height: 20px;
border: 5px solid transparent;
}
.end-left {
border-left-color: #999;
border-top-color: #999;
}
.end-right {
border-right-color: #999;
border-top-color: #999;
}
.languages {
display: inline-block;
width: 80%;
text-align: center;
font-family: 'copperplate', 'century gothic';
color: #999;
}
.languages span {
display: inline-block;
width: 15%;
}
<div class="end end-left"></div>
<p class="languages" aria-hidden="true" role="presentation">
<span class="english">Hello</span>
<span class="french">Bonjour</span>
<span class="italian">Ciao</span>
<span class="spanish">Hola</span>
<span class="hinid">Namaste</span>
<span class="persian">Salaam</span>
</p>
<div class="end end-right"></div>
<h1>Languages</h1>
<p>Welcome to your first language lesson. You will learn how to speak fluently.</p>

Styling an inline element with linebreak (after) within a content editable element - caret position

I'm styling an inline element within a contenteditable element to visually represent a linebreak.
First text(Linebreak)
[C]Second Line
I want to be able to place the cursor at [C] position which I'm unable to.
I believe there's a reasonable explanation for the current behavior. Anyone care to explain and maybe provide me a different approach?
EDIT: Apparently it works for IE and Firefox but not Chrome.
.lb{
display:inline;
}
.lb:after{
content: "\21B2\A";
white-space: pre;
word-wrap: break-word;
}
.edit-box{
border: 1px solid black;
padding: 10px;
}
<div id="test" contenteditable="true" class="edit-box">
How to style the span element<span class="lb"></span>so it's possible to place the cursor at the beginning of this line, before "S".
</div>
Try the follow css changes in your lb classes with addition of .lb:before:
.lb{
display:inline;
white-space: nowrap;
}
.lb:before{
content:'';
display:block;
}
.lb:after{
content: "\21B2\A";
}
This will achieve what you want. What we are doing is that we are telling the main lb to not wrap the text in and around it. Next we create lb before as block to get it into new line and then a lb after to add the cursor and the rest of the text flows along with it. Hope this helps.
You could wrap each new line in a <p>.
.edit-box {
border: 1px solid black;
padding: 10px;
}
.edit-box p {
margin: 0
}
p:not(:last-child):after {
content: "\21B2";
}
<div id="test" contenteditable="true" class="edit-box">
<p>How to style the span element</p>
<p>so it's possible to place the cursor at the beginning of this line, before "S".</p>
</div>
Or wrap that 2nd line in a span that displays as a block:
.edit-box {
border: 1px solid black;
padding: 10px;
}
.edit-box span {
display: block;
}
<div id="test" contenteditable="true" class="edit-box">
How to style the span element
<span>so it's possible to place the cursor at the beginning of this line, before "S".</span>
</div>
I've come up with a different approach by wrapping the BR element with a span as such:
.edit-box{
border: 1px solid black;
padding: 10px;
}
.icon{
width:15px;
}
.icon::before{
content: "\21B2";
}
<div id="test" contenteditable="true" class="edit-box">
How to style the span element so it's possible to place the cursor<span class="icon"><br></span> at the beginning of this line, before "at".
</div>
Basically, the linebreak sort of receives a visual dimension and keeps its regular behavior.
For the specific contenteditable element, I capture all keypress events for the return key and paste <span class="icon"><br></span>, preventing the default behavior.
It seems to work when you wrap your "second line" in div: https://jsfiddle.net/n944cfgo/2/

Optional bottom border on a div

I have two HTML samples... Basically there is always a name div in the info div but the total number of could be more.
1)
<div class="person">
<div class="info">
<div class="name">Isabelle of_Bavaria</div>
</div>
</div>
2)
<div class="person">
<div class="info">
<div class="name">King of France Charles_V the_Wise</div>
<div class="title"><label>Title:</label>King of France</div>
<div class="date"><label>Birth:</label>Jan 21st, 1337</div>
<div class="date"><label>Death:</label>Sep 16th, 1380</div>
</div>
</div>
I'm using this bit of CSS to add a line under the name as well as a box around the person div.
.person .name
{
position: relative;
text-align: center;
border-bottom: 1px dotted black;
}
.person
{
position: relative;
width: 250px;
height: auto;
border: 1px solid black;
margin-top: 5px;
padding: 5px;
}
Is there anything I can do with the css to prevent the name from having a border in sample 1 while leaving it in sample 2 without the need for additional classes or divs?
Try adding this piece of CSS at the top of your .person .name entry
.person .name:only-of-type
{
border-bottom: 0px transparent;
}
This piece of CSS means that if there is only one of the element type using the .name class in .person (in this example it's a div), it will not have a bottom border. You have to put it before the .person .name in order to overwrite it.
EDIT :
After thinking about it a bit more, i think the pseudo class :only-child would be better suited for your needs instead of :only-of-type since it will only apply if the .name is the only child of .person. So here's the updated CSS
.person .name:only-child
{
border-bottom: 0px transparent;
}
Something logically like this?
.person > .info[having more than one div child] > .name
{
border-bottom: ...
}
sadly, i don't think there's a [...] selector quite like that, however, there are "adjacent sibling selectors" ( http://www.w3.org/TR/CSS2/selector.html#adjacent-selectors )
Maybe as #PhilPerry has suggested, you could change the concept to being "put a top-border on the div immediately following the first-child (or name)", like so:
.name:first-child + div
{
border-top: ...
}

how to change CSS priority (don't use !important)

If the css is as below:
input[type="text"]
{
border: 1px solid green;
}
.text
{
border: 1px solid red ;
}
And if the html is as below:
<div>
<input type="text" class="text"/>
</div>​
The border-color of the textbox is green.
It seems that the "element" has the higher priority.
How to make the .class valid? Is it a must to use the !important?
Any other choices?
I tested below CSS code:
input[type="text"]
{
border: 1px solid green;
}
input[type="text"] .text
{
border: 1px solid red;
}
HTML code:
<div>
<input type="text" class="text"/>
</div>
Guess what?​
Still Green.
Remove the space in 'input[type="text"] .text'
it becomes input[type="text"].text .
That's ok. The border color is red.
The C in CSS stands for cascading. You just need to give it higher precedence then the other rule.
input.text
{
border: 1px solid red ;
}
/* Set default border for `text` elements */
.text
{
border: 1px solid red;
}
/* Override for input elements */
input.text
{
border: 1px solid green;
}
Styles are applied in sequence, but also must follow specificity rules. The .text is less specific than input[type="text"], so the green border "wins." If you make the red border rule more specific, you can get the results you seem to be expecting.
Try something like input.text and see what happens. If that doesn't do it, you'll have to get even more specific.
It's a matter of weight of your selectors.
With
`input[type="text"]
You are passing both input and [type=text] as selector, so you're passing a total of two.
With
.text
You are passing only one. This translates in less weight and less specificity, so the first selector wins over the second.
By adding input before (i.e. input.text) you're adding more weight to second style, which will prevail as you'd expect from Cascading Style Sheets.
Specificity is easily visualized through websites like Specificity Calculator.

Resources