Introduction
There are several modular architectures, methodologies for writing CSS styles. Each has its own specific style that we have to stick to. In Part One, we will cover the most popular ones, OOCSS and BEM.
What is OOCSS?
Object Oriented CSS. The object programming way for writing styles. The main purpose of this methodology is to reuse and facilitate maintenance of CSS. Using this approach first of all we should create a class that will define the global structure of the element. Then, we should define a class that has a more specific purpose. The styles for button element will be a good example.
/* */ .btn { color: #000; border-radius: 5px; border: 1px solid #000; padding: 5px 10px; } .btn-danger { background-color: red; } .btn-warning { background-color: yellow; } /* */
<!-- --> <button class="btn btn-danger">Delete</button> <button class="btn btn-warning">Warning</button> <!-- -->
As you can see, the global btn class is part of the styles we can add to both buttons, because our button will look almost the same, with one little difference. The difference is a helpful class like btn-danger or btn-warning, where we change only the color of the button.
OOCSS – separation for containers
The second rule of OOCSS is to think a little bit different about our HTML containers and their children. Let’s take a look at this code below.
<!-- --> <section class="introduction"> <h2>Introduction</h2> </section> <section class="content"> <h2>Content</h2> </section> <!-- -->
We have two sections but we want to style headings a little bit differently. Let’s say, the first heading should be bigger than the second one. Normally we would use similar syntax as below.
/* */ .introduction h2 { font-size: 1.5em; } .content h2 { font-size: 1em; } /* */
But the OOCSS methodology forces us to think different in this situation. The example above shows us that our headings are depending on where they are located. In OOCSS the element should look the same, no matter in what container it is. So here, we should focus more on adding class to one of our headings than selecting them by parents.
/* */ h2 { font-size: 1.5em; } h2.content-heading { font-size: 1em; } /* */
<!-- --> <section class="introduction"> <h2>Introduction</h2> </section> <section class="content"> <h2 class="content-heading">Content</h2> </section> <!-- -->
What is BEM?
BEM – Block Element Modifier. An easy methodology or as other says an architecture. This stands for:
block – container like div, section, form, etc.
element – element of that container
modifier – the modifier of the element/block
In BEM we have naming convention:
.block – the first word in class, it refers to the block
__element – the second word in a class, it refers to the element
–modifier – the last word in a class, it refers to the modifier
BEM in action
<!-- --> <form class="registration"> <input class="registration__input" type="text" placeholder="Username" /> <input class="registration__input registration__input--password" type="password" /> <input class="registration__input registration__input--checkbox" type="checkbox" /> <button class="registration__button" type="submit">Save</button> <button class="registration__button registration__button--cancel" type="button">Cancel</button> </form> <!-- -->
The registration class stands for our block. That’s why all classes inside registration form begin with this word. Inside this form we have variant elements and their modifiers.
/* Selectors in BEM */ /* BEM block */ .registration { } /* .block__element - direct element of this block */ .registration__input, .registration__button { } /* .block__element--modifier - direct element of this block and also element modifier */ .registration__input--password, .registration__input--checkbox, .registration__button--cancel { } /* */
BEM – Deep nesting
What about deep nesting, when we have much more nested elements than one or two in HTML? How to use classes in this case in BEM methodology?
<!-- --> <section class="posts"> <h1 class="posts__heading">Posts</h1> <article class="post"> <h2 class="post__heading">First post</h2> </article> </section> <!-- -->
It should look like this. We should concentrate on creating classes starting from the closest HTML block. We should avoid this kind of situations as in example below because at the end, with more nested elements we would end up with very long class names.
<!-- --> <section class="posts"> <h1 class="posts__heading">Posts</h1> <article class="posts_post"> <h2 class="posts_post__heading">First post</h2> </article> </section> <!-- -->