
안녕하세요, 일루넥스 개발팀 퍼블리셔 정민지입니다.
최근 웹에서 CSS의 활용도가 높아짐에 따라 CSS를 보다 효율적으로 작성하는 다양한 방법이 생겨났는데요.
대표적인 방법론으로 BEM, SMACSS, OOCSS를 들 수 있습니다.
오늘은 이 3개의 방법론 중 BEM에 대해 소개해보고자 합니다.
BEM의 기본 구조
BEM은 Block, Element, Modifier를 뜻합니다. 이 3가지로 구성된 이름을 짓는 방법으로 “__”와 “—”로 구분합니다.
.header__nav--nav-content {
color: blue;
}
위의 CSS 코드에서 header
는 Block, nav
는 Element, nav-content
는 Modifier가 됩니다.
BEM은 기본적으로 class만을 사용하며, id는 사용하지 않습니다. 또한, ‘어떻게 보이는가’보다는 ‘어떤 목적인가’에 따라 이름을 짓습니다.
예를 들어, 에러 메세지를 띄우는 P태그에 .red
가 아닌 에러 메세지라는 목적이 담겨 있는 .error
라는 이름을 주어야 하는 것입니다.
이름을 연결할 때는 nav-content
와 같이 하이픈 하나를 사용해서 연결합니다.
Block / Element / Modifier
1. Block
block은 문단 전체에 적용된 element 또는 element를 담고 있는 컨테이너를 말합니다.
ex) logo / login form / menu / search from / content / footer
1.1 중첩 구조
block은 다른 block 내에 중첩될 수 있습니다. 예를 들어, 헤드 block은 로고, 검색폼, 메뉴 등 다른 block들을 포함할 수 있습니다.

1.2 자유로운 배치
block은 페이지 내의 어디든지 이동할 수 있습니다. 즉, block만 가져다가 다른 어딘가에 자유롭게 사용할 수 있습니다.


1.3 재사용
block은 헤더에 쓰일 수도 있고, 푸터에 쓰일 수도 있고, 여기저기에서 사용할 수 있습니다. 이렇게 재사용할 수 있는 요소를 block이라고 합니다.

2. Element
element는 block을 구성하는 단위입니다.
block은 독립적인 형태인 반면, element는 의존적인 형태입니다.
자신이 속한 block 내에서만 의미를 가지기 때문에 block 안에서 다른 데로 가져가서 사용할 수 없습니다.

2.1 block과 element의 차이
아래 HTML 코드에서 .search-form 은 block이고, .search-form__input 과 .search-form__button 은 element입니다.
.search-form 이라는 block은 여기저기 마음껏 사용해도 되지만 내부의 input과 button은 검색을 위한 것이기 때문에, search-form 안에서만 존재 의미가 있는 element입니다.
<form class="search-form">
<input class="search-form__input">
<button class="search-form__button">Search</button>
</div>
2.2 중첩가능
element 또한 중첩이 가능합니다. .block > .block__element > .block__element2
도 가능합니다.
BEM에서는 .bloxk_element2
를 .block_emenet1
의 하위 element로 보지 않고,
똑같이 .block
의 element로 취급하기 때문에, 클레스네임에 캐스케이딩을 여러번 표시할 필요가 없습니다.
<!--잘못된 사용 예시-->
<form class="search-form">
<div class="search-form__content">
<input class="search-form__content__input"/>
<button class="search-form__content__button">Search</button>
</div>
</form>
위 형태는 block-name__element-name이란 형식을 따르지 않은 것으로, BEM에서는 아래 형태를 사용합니다.
<!--올바른 사용 예시-->
<form class="search-form">
<div class="search-form__content">
<input class="search-form__input"/>
<button class="search-form__button">Search</button>
</div>
</form>
3. Modifier
modifier는 block이나 element의 속성을 담당합니다.
생긴 게 조금 다르거나 다르게 동작하는 block, element를 만들 때 사용합니다.
<ul class="tab">
<li class="tab__item tab__item--focused">탭 01</li>
<li class="tab__item">탭 02</li>
<li class="tab__item">탭 03</li>
</ul>
3.1 불리언 타입
위 HTML 코드에서 —focused 가 수식어에 해당합니다.
저렇게 작성된 것을 불리언(boolean) 타입이라고 하는데, 그 값이 true라고 가정하고 사용합니다.
<form class="search-form">
<input class="search-form__input">
<button class="search-form__button">Search</button>
</div>
3.2 키-밸류 타입
또 다른 타입으로, 키-밸류(key-value) 타입이 있습니다. 이것은 하이픈으로 성질-내용을 작성합니다.
<div class="column">
<strong class="title">일반 로그인</strong>
<form class="form-login form-login--theme-normal">
<input type="text" class="form-login__id"/>
<input type="password" class="form-login__password"/>
</form>
</div>
<div class="column">
<strong class="title title--color-gray">VIP 로그인 (준비중)</strong>
<form class="form-login form-login--theme-special form-login--disabled">
<input type="text" class="form-login__id"/>
<input type="password" class="form-login__password"/>
</form>
</div>
위 형태는 block-name__element-name이란 형식을 따르지 않은 것으로, BEM에서는 아래 형태를 사용합니다.
BEM의 장점
클래스네임만으로 마크업 구조를 알 수 있습니다.
block과 element로 구분되기 때문에 어디서부터 가져다 사용할 수 있는지, 어디부터 종속되는지 알 수 있습니다.
SASS의 부모참조자(&)와 함께 사용할 때 매우 편리합니다.
일루넥스에서는 SASS를 사용하고 있는데, BEM의 클래스네임 형태를 SASS에서 사용할 시 깔끔하게 코드를 정리할 수 있습니다.
작성된 SASS에서 요소를 쉽게 찾을 수 있습니다.
예를 들어, .header 아래에 &__logo , &__search 로 작성하기 때문에 로고와 검색창이 헤더에 있는 것임을 바로 알 수 있습니다.
SASS에서 중첩 사용을 줄일 수 있습니다.
중첩을 사용하다 보면 계속해서 {대괄호}가 늘어나는데, BEM에서는 모두 element로 지정해서 사용하기 때문에 정리된 형태를 유지할 수 있습니다.
//기존 방식
.header {
.nav {
position: absolute;
.list {
list-style: none;
}
.item {
outline: 0;
.link {
color: red;
}
}
}
}
//BEM
.header {
&__nav {
position: absolute;
}
&__list {
clor: red;
}
&__item {
outline: 0;
}
&__link {
color: red;
}
}
BEM의 단점
클래스네임이 지나치게 길어질 수 있습니다.
block과 element로 구분되기 때문에 어디서부터 가져다 사용할 수 있는지, 어디부터 종속되는지 알 수 있습니다.
마치며
지금까지 CSS 방법론 중 BEM에 대해 알아보았습니다.
읽어주셔서 감사합니다.