CSS BEM children of a modifier - css

I'm new into BEM methodology, and I have a question targeting a child of a modifier.
Lets say I have this HTML:
<div class="block-container">
<div class="block-container__element"></div>
</div>
At block-container I add a modifier block-container--modifier.
And the CSS would be:
.block-container {
...
}
.block-container__element {
...
}
.block-container--modifier {
...
}
And my question here is: how I can change some CSS attributes of the __element when the modifier is applied?
As far as I read, we have to avoid using nested children, but I think that sometimes that rule must be broken to achieve this kind of things, I'm right?
I'm using pure CSS, no LESS, no SASS.

In general cascades should be avoided, but not in this case.
If you are sure that the block block-container is never recursively included in another block-container, then you can do:
.block-container--modifier .block-container__element {
}
Otherwise you have to put another modifier on the element: block-container__element--modifier.
There is a third solution but it is unorthodox. In some case, I suggest to use the child selector if you are sure that, at the DOM level, the element is a direct child of the block (for example if the block always is a <ul> and the elements are the <li> children). Then you can do:
.block-container--modifier > .block-container__element {
}

Related

Should you style elements when using BEM or should we add extra classes

What is the more appropriate approach when using BEM ?
Are we allowed to not add extra classes to elements and style the elements themselves
<section class="news-section">
<a>link</a>
</section>
.news-section {
a {
color: blue;
}
}
Or do we have to add extra classes to all elements and style those classes?
<section class="news-section">
<a class="news-section_link">link</a>
</section>
.news-section {
&_link {
color: blue;
}
}
Are we allowed to not add extra classes to elements and style the elements themselves
No.
With BEM, you have to always use CSS classes:
In HTML, BEM entities are represented by the class attribute. (bem.info)
In return for this rigidity, BEM will bring you :
Scalability, because blocks can be nested without limit;
Flexibility, because CSS selectors are loosely coupled with HTML tags.
You should definitely add extra classes to style elements like links. It's the same situation as when you add styles to buttons header__btn or images use-profile__img
It is never bad to add additional classes and they make code expandable in the future. Imagine a situation where you would like to add more elements inside this <a> tag. You wouldn't code it like this news-section__a__link-header right?
Important: you shouldn't target elements 2 levels down with BEM as it's block__element-modifier, not block__element__element--modifier :)
BEM is pretty well explained here
To add to the existing answers, yes avoid using specificity to style items unless absolutly needed (CMS wysiwyg content for example), so your second code block it correct BEM
However in your specific example, all you are setting is a color, and you probably have other items you want the same color right?
So i probably makes more sense to use a utility class for that:
<section class="news-section">
<a class="u-txt-blue">link</a>
<p class="news-section__title">...</p>
</section>
.news-section {
...
&__title{
...
}
}
//utilities.scss
.u-txt-blue{
color: blue;
}
Add classes to all the elements so as not to tie your styling of your components to your HTML structure.
In your example your first example, the new-section__link will have to be an anchor element, in the second it can be any type of element which is a lot more powerful and flexible.

What is the point of BEM's explicit descendant class naming in the presence of SCSS?

I'm trying to pickup and understand the reasoning behind CSS naming conventions such as BEM or SUITCss. I'm having a hard time understanding the value of descendent class names in the presence of SCSS.
For example:
<ul class="menu">
<li class="menu__item"></li>
<li class="menu__item"></li>
<li class="menu__item">
link
</li>
</ul>
.menu {
.menu__item {
//styles
.menu__item__link { //styles }
}
//or alternatively this syntax..
&__item { //styles }
}
With the ability to nest rules in SCSS, I don't see the compelling reasons for me to include the ancestor class names in my code. Above I have defined styles that should only be used for an "item" that is inside of a "menu", using descendant class names. However, the nested structure already communicates this! The rules for menu__item would only apply to an item under a menu anyway, so why do I need include that in the class name?
Why not:
<ul class="menu">
<li class="item"></li>
</ul>
.menu {
.item {//styles}
}
I understand that the descendant naming convention is more explicit and perhaps more future friendly. I argue, however, that it is only more explicit in the html. If I wanted to consult how to build this "menu" module, I could just consult the CSS and see just as clearly how a menu has items nested inside.
I guess one possible advantage is that I could write my css un-nested, like so:
.menu { //styles }
.menu__item { //styles }
.menu__item__link { //styles }
And then use a "menu__item" anywhere and it would still be explicit in the class name that this was the styling of an item under a menu..but then why define it as a descendant of a menu at all then? (Another advantage, I suppose, is shorter CSS identifier strings if things aren't nested)
It seems to me that if a class name is to be used as a descendant under another, then nesting in SCSS achieves this and presents that logic clearly. Why would this BEM syntax be necessary then?
I'd like to hear someone explain the reasoning of this type of convention. I want to adhere to so called best practices, but it's hard for me to do so blindly without fulling understanding a convention.
Several remarks.
1/ First,
.menu {
.menu__item { /* ... */ }
//or alternatively this syntax..
&__item { /* ... */ }
}
The two SCSS syntaxes are not equivalent. The first one uses a cascade (".menu .menu__item"), not the second one (".menu__item"). Only the second one is BEM compliant.
2/ Why not a cascade:
.menu {
.item { /* styles */ }
}
BEM allows scalability. When we write CSS, we focus only on one small context: the block. And each block can be reused many times.
But cascades are not context-free. In your example, there is a block "menu" that contains an element "item". The context of the element "item" is the block "menu". But the cascade breaks the context separation for the sub-blocks. A prefixed BEM syntax allows nesting blocks, the cascade doesn't. For example:
<ul class="menu">
<li class="menu__item"></li>
<li class="menu__item">
<div class="other-block">
<span class="other-block__item"></span>
</div>
</li>
</ul>
Notice the element "item" in the sub-block. With a cascade instead of a prefix, it would be styled by a rule that would target the elements "item" of the parent block.
3/ This class name is not BEM compliant:
.menu__item__link { /* styles */ }
Elements don't provide any context. Only blocks provide contexts. The context of a an element is the context of its block. So, "link" is not a descendant of "item" in the BEM tree. The two are brothers, independently of their situations in the DOM tree. You should use:
.menu { /* styles */ }
.menu__item { /* styles */ }
.menu__link { /* styles */ }
Lets start with idea of BEM or SMACSS.
The main task any methodology resolves is structuring and modularize your code.
For example BEM use following abstractions:
Block - independent part of UI (like feedback form),
Element - part of block cant exist without block (like feedback form button),
Modificator - helper that let you modify block or element ( like make button bigger or smaller).
SMACSS use different abstractions : Module, Layout, Base, State, Theme.
To clearly got the idea, imagine your html page contains from logic layers,
1) BASE - you add css resets, define H1, H2 ... font sizes, define colors. So in base you put things than should be changed.
2) LAYOUT - adds grids, or separate page in regions. 3) Module - independent content item
3) STATE - very close to BEM modificator but connected with some action with module, like is_hided, is_collapsed
4) Theme - may be used for BASE override.
So to separate this abstractions you have to follow some naming convention , so you could from first look understand what does this class do. If you follow naming convention its also much easier to maintain you project6 its easily to explain new team members how code organized and how to write new code that looks like written by one person.
Its extremely important in large scale projects with large teams.
Plus, naming convention helps you to decrease number of descendant selectors, that improve performance.

Overriding CSS attributes

I'm trying to make a very basic HTML/CSS/JS widget, but I'm having some problems with the CSS layer. It seems that I can't write selectors that work, and it's becoming very aggravating. In particular, I'm trying to override the font-size setting inherited from the body css selector for the widget. My HTML (actually, it's Hamlet) is:
<div class="container">
<div id="flashcard-container">
<div class="span6 offset3 well flashcard">
<div class="front">
<p class="flashcard">This is the front of the card.
and my CSS file says:
.flashcard p {
font-size: 24px;
}
div .back {
display: none;
}
Actually, I have a problem with both selectors. In particular, the first one just does not work to match the xml structure. The second one seems sub-optimal. Why should I need to specify that I'm talking about a div at all? I just want to quantify over backs, whatever tag they are.
I realize this is extremely basic, but I think that between this and some Chrome bugs with 3d transitions, I got myself extremely confused. It has been many years since I've dealt with the front-end. :(
If you wish to target a node with a class attached, the syntax is
elementname.classname {...}
(although OOCSS fanatics will suggest just using .classname and making your CSS structurally agnostic).
I am not sure what you mean by 'quantifying over backs', but if you simply want to target an element with a 'back' class, you can target it as so:
.back {...}
Though it might be best to contain the styles as 'back' is a rather generic class name:
.flashcard .back {...}
Try this:
p.flashcard { ... }
div.back { ... }
Actually I can't see a div with back class in your code.
You may as well use just .flashcard and .back. Specifying div or p just narrow the choice. If you specify .flashcard it will be applied both to, say, or .
But if you write
.flashcard p { ... }
It means that you chose all descendants of .flashcard, like:
<div class="flashcard">
<p>...</p>
</div>

recommended css notation

I have a div with an ID:
<div id="main">
What's the correct (or difference) between
div#main {
and
#main {
Regards,
There is a great doco on using efficient CSS selectors, focus on rules with overly qualified selectors:
ID selectors are unique by definition. Including tag or class
qualifiers just adds redundant information that needs to be evaluated
needlessly.
Instead of just applying the style to an element with id main, your selector will re-qualify the element by checking whether or not it's also a div (in that order). To clarify: css selectors are evaluated right to left, unlike same selector syntax when used in jQuery etc.
Re pixelistik's suggestion that div#main is more specific than #main - yes, that is technically correct, however if you have to resort to this to raise a rule's specificity, chances are the structure of CSS you're working on is not as thought through as it should be.
#main matches everything with ID 'main', whereas div#main matches only <div> elements with ID main.
Ideally, you should never have two elements with the same ID, so realistically the two don't make a difference, but there's probably performance related issues regarding whether specifying div makes it find the result faster.
So difference is that:
When you write div#main style will be only for <div> element.
When you write #main it can be used as style for <div>, <span>, <p>, etc.
And what recommend is hard to say, every developer it has it different. So i using for example
span.<nameClass> when is nested in <li> for example.
#nav li span.href a {
...
}
I think it's used when you want that someone class with specific name can have only one element.
So when your write span#href it will works only for <span id="href">Simply dummy text</span> not for others. When you write #href it will works for <span id="href">Simply dummy text</span> or Link but both are correct when you also asking about this. Differences i wrote above.
Both are correct.
div#main is more specific than #main, which means that styles defined with the first selector will override the ones of the second.
Here's a good introduction to CSS specifity:
http://htmldog.com/guides/cssadvanced/specificity/

CSS Rules affecting other Objects

is it possible for a css rule (such as #testobject1:hover {}) to have an effect on another object #testobject2?
Nope.
The only way this could work is if #testobject2 was a descendant of #testobject1:
<div id="testobject1">
<div id="testobject2">
Hello.
</div>
</div>
The CSS would then be:
#testobject1:hover #testobject2 {
...
}
Yes, if you write something like:
#testobject1:hover, #testobject2:hover {}
or if #testobject2 is a children of the #testobject1 element and it inherits the properties declared in that CSS piece.
Otherwise, no.
It is possible if the 2nd element is a descendant of the first:
#testobject1:hover #testobject2 {}
This will cause the css of this rule to be applied to #testobject2 only when #testobject1 is hovered.
EDIT: An Interesting use of this involves absolutely positioned elements. You can have an element which is a descendant of another but visually does not appear within the other element at all. The hover will still work.
http://jsfiddle.net/F2psw/
With CSS, the only way to apply the same style to two different objects like you said is construct your style with more than one selectors. Like this:
#testobject1:hover, #testobject2 {
[...]
}

Resources