CSS Methodologies - OOCSS, SMACSS, BEM
Published: 2021-11-12 14:59:28

#OOCSS
: making different kinds of modules and combining them like lego blocks.

The "Object" in OOCSS refers to an HTML element or anything associated with it like CSS classes or Javascript methods. 
As with any object-based programming method, the purpose of OOCSS is to encourage code reuse and, ultimately, faster and more efficient stylesheets that are easier to add and maintain.

##Separation of structure from skin(visual features)
such as width, height, padding, margin belongs to structure and things that doesn't affect layout but affect elements visually like font-related properties, color, background, border will be included in skin.
Some styles like color, font, etc get repeated. When these different features are abstracted into class-based modules, they <strong><em>become reusable</em></strong> and can be applied to any element. 

```css
#button {
  width: 200px;
  height: 50px;
  padding: 10px;
  border: solid 1px #ffffff;
  background: linear-gradient(#7ad9ff, #84ffe8);
  box-shadow: rgba(0, 0, 0, .5) 2px 2px 5px;
}

#box {
  width: 400px;
  overflow: hidden;
  border: solid 1px #000000;
  background: linear-gradient(#7ad9ff, #84ffe8);
  box-shadow: rgba(0, 0, 0, .5) 2px 2px 5px;
}
``` 
These elements above have styles that are unique to each but they have a number of styles in common. Instead of applying them to the non-reusable id to define styles, you can abstract the common styles.
```css
.button {
  width: 200px;
  height: 50px;
}

.box {
  width: 400px;
  overflow: hidden;
}

.skin {
  border: solid 1px #000000;
  background: linear-gradient(#7ad9ff, #84ffe8);
  box-shadow: rgba(0, 0, 0, .5) 2px 2px 5px
}
```
All the elements are using classes now, the common styles are combined into "skin" which is reusable and there isn't repeated code now. You just have to apply the "skin" class to all elements if you want to have the same style like the first code.

##Separation of container from content.
The second principle is the separation of containers from their content.
Two different buttons have have the same structure but different styles.
```html
<main id="main">
  <button type="button" class="btn general">기본 버튼</button>
  <button type="button" class="btn warning">취소 버튼</button>
</main>
```

```css
#main .btn {
  width: 300px;
  padding: 20px 10px;
  margin: 10px;
  font-size: 18px;
  line-height: 1.5;
}

#main .general {
  background-color: aquamarine;
  color: black;
}

#main .warning {
  background-color: azure;
  color: blue;
}
```


#SMASS(Scalable and Modular Architecture for CSS)
ref: http://smacss.com/
The core of SMACSS is categorisation. You can categorise by it's 
These are five types of categories:
- <strong>Base</strong>: A Base rule is applied to an element using an element selector, a descendent selector, or a child selector, along with any pseudo-classes. It doesn’t include any class or ID selectors. It is defining the default styling for how that element should look in all occurrences on the page. 
```css
body, form {
    margin: 0;
    padding: 0;
}

a {
    color: #039;
}

a:hover {
    color: #03F;    
}
```
- <strong>Layout</strong>: Layout styles can also be divided into major and minor styles based on reuse. Major layout styles such as header and footer are traditionally styled using ID selectors but take the time to think about the elements that are common across all components of the page and use class selectors where appropriate. (Usually layout modules are not many so id selector can be used)
```css
#header, #article, #footer {
    width: 960px;
    margin: auto;
}

#article {
    border: solid #CCC;
    border-width: 1px 0 0;
}
```
- <strong>Moudule</strong>: Each Module should be designed to exist as a standalone component. In doing so, the page will be more flexible. If done right, Modules can easily be moved to different parts of the layout without breaking. When defining the rule set for a module, ><u>avoid using IDs and element selectors</u>, <storng><em>sticking only to class names</em></strong>. A module will likely contain a number of elements and there is likely to be a desire to use descendent or child selectors to target those elements.
Subclassing Modules.
When we have the same module in different sections, the first instinct is to use a parent element to style that module differently.
```html
<ul class="tabnav">
    <li class="" tabnav__item"><a href="" class="tabnav__link">탭1</a></li>
    <li><a href="">탭2</a></li>
    <li><a href="">탭3</a></li>
    <li><a href="">탭4</a></li>
</ul>
```
```css
.tabnav {
  display: flex;
}

.tabnav li {
  border-top: 1px solid black;
  border-right: 1px solid black;
  border-bottom: 1px solid black;
}

.tabnav li:first-child {
  border-left: 1px solid black;
}

.tabnav li a {
  display: block;
  padding: 10px 30px;
  text-decoration: none;
}
```
- <strong>State</strong>: States are generally applied to the same element as a layout rule or applied to the same element as a base module class. A state is something that augments and overrides all other styles.
```css
/* .is-hidden / .is-active  => can add different class depending on the state */
.is-active {
  background-color: blanchedalmond;
}
/* pointer-events: 클릭할 수 없는 스타일 */
.is-active a {
  pointer-events: none;
  color: red;
}
```
Difference from subclass.
1.State styles can apply to layout and/or module styles; and
2.State styles indicate a JavaScript dependency.(It can be added or taken out) / 
- <strong>Theme</strong>: It is probably self-evident but a theme defines colours and images that give your application or site its look and feel. Separating the theme out into its own set of styles allows for those styles to be easily redefined for alternate themes.
```css
// in module-name.css
.mod {
    border: 1px solid;
}

// in theme.css
.mod {
    border-color: blue;
}
```

#BEM(Block, Element, Modifier)
ref: http://getbem.com/
It doesn't recommend using id and element selector.(Only use class)
- <strong>Block</strong>: Standalone entity that is meaningful on its own. (header, container, menu, checkbox, input...)
*You should name classes very clear.
*If want to use lowercase and more than one word for class name, you should use hyphen case(kebab case) e.g: cont-nav
- <strong>Element</strong>: A part of a block that has no standalone meaning and is <strong>semantically tied to its block</strong>.(menu item, list item, checkbox caption, header title...). Elements inherit class name from block.
*Use class name selector only
*No tag name or ids
*No dependency on other blocks/elements on a page
```html
<!-- Naming -->
<div class="block">
	  ...
	  <span class="block__elem"></span>
	</div>
```
```css
/* Good */
.block__elem { color: #042; }

/* Bad */
.block .block__elem { color: #042; }
	div.block__elem { color: #042; }
```
- <strong>Modifier</strong>: Flags on blocks or elements. Use them to change appearance, behavior or state.(disabled, highlighted, checked, fixed, size big, color yellow...)
```html
<!-- Good -->
<div class="block block--mod">...</div>
	<div class="block block--size-big
		block--shadow-yes">...</div>

<!-- Bad -->
<div class="block--mod">...</div>
```
```css
/* Use modifier class name as selector: */
.block--hidden { }

/* To alter elements based on a block-level modifier: */
.block--mod .block__elem { }

/* Element modifier: */
.block__elem--mod { }
```
<strong>Example</strong>
```html
<form class="form form--theme-xmas form--simple">
  <input class="form__input" type="text" />
  <input
    class="form__submit form__submit--disabled"
    type="submit" />
</form>
```
```css
.form { }
.form--theme-xmas { }
.form--simple { }
.form__input { }
.form__submit { }
.form__submit--disabled { }
```