Как правильно установить область действия элемента с помощью БЭМ?

Учитывая следующую древовидную структуру БЭМ, в которой существует пять вложенных уровней:

collection-main__features-top__story__byline__author

в соответствии с соглашением об именах БЭМ, где элемент является частью блока и не имеет значения за пределами блока, к которому он принадлежит, как правильно назвать класс author?

Поскольку author семантически связано с контекстом byline и story, но не имеет смысла в блоках features-top и collection-main, какое БЭМ-имя лучше?

collection-main__author
features-top__author
story__author (best?)
story__byline__author
byline__author

Что произойдет, если появится новый блок features?

collection-main__features-top__story__byline__author (target)
collection-main__features-bottom__story__byline__author

features-top__story__author
story--features-top__author (best?)

Наконец, что произойдет, если будет добавлен еще один блок collection, и мы захотим стилизовать второй элемент author в списке?

collection-main__features-top__story__byline__author
collection-main__features-bottom__story__byline__author (target)
collection-sub__features-top__story__byline__author
collection-sub__features-bottom__story__byline__author

Сделали бы мы что-то подобное?

story--collection-main--features-bottom__author

Должен быть лучший вариант.


person Eric Xu    schedule 12.01.2015    source источник
comment
Пожалуйста, покажите ваши данные для вывода. Это как {collection-main: [{"feature-item": { story: {author: ''} } }]} ?   -  person Alex Baumgertner    schedule 12.01.2015


Ответы (1)


БЭМ запрещает помещать элементы в элементы в CSS!
Вы делаете самую типичную ошибку в БЭМ-разметке - пишете block__element__element. Вы должны создавать новые блоки, а не копировать DOM-дерево.

Например:
Правильный HTML:

<div class='block'>
    <div class='block__elem1'>
        <div class='block__elem2'></div>
    </div>
    <div class='block__elem3'></div>
</div>

Правильный CSS:

.block {}
.block__elem1 {}
.block__elem2 {}
.block__elem3 {}

Если вам нужно сделать элемент из элемента, то вам нужно создать новый блок или создать свое bem-дерево с одним вложенным элементом!

НЕПРАВИЛЬНО:

<div class='block'>
    <div class='block__elem1'>
        <div class='block__elem1__elem2'></div>
    </div>
</div>

ПРАВИЛЬНО №1: Создайте новый блок

<div class='block1'>
    <div class='block2'>
        <div class='block2__elem'></div>
    </div>
</div>

ПРАВИЛЬНО №2: Создайте свое bem-дерево с одним вложенным элементом

<div class='block'>
    <div class='block__elem1'>
        <div class='block__elem2'></div>
    </div>
</div>

Обратите внимание - вы не можете помещать элементы в элементы в css, но вы можете и должны помещать элементы в элементы в html! DOM-дерево и БЭМ-дерево могут быть разными.

Не пишите странные названия, помещая имя элемента в название блока!

НЕПРАВИЛЬНО:

.block {}
.block-elem1 {}
.block-elem1__elem2 {}

Потому что у вас возникает проблема с нечетными именами при попытке переместить блок:

<div class='other-block'>
    <div class='block-elem1'></div>
</div>

Вложенные html-элементы — это DOM-дерево.
Названия классов, которые вы пишете, — это БЭМ-дерево.
Почувствуйте разницу!

DOM-дерево:

<ul>
  <li>
    <a>
      <span></span>
    </a>
  </li>
</ul>

.ul {}
.ul > li {}
.ul > li > a {}
.ul > li > a > span {}

БЭМ-дерево:

<ul class="menu">
  <li class="menu__item">
    <a class="menu__link">
      <span class="menu__text"></span>
    </a>
  </li>
</ul>

.menu {}
.menu__item {}
.menu__link {}
.menu__text {}

Использованная литература:

«Элемент — это составная часть блока, которую нельзя использовать вне его». https://en.bem.info/methodology/key-concepts/#element

Элемент является частью блока! Не часть элемента! Почитайте Виталия Харисова, автора БЭМ-методологии: https://twitter.com/harisov/status/403421669974618112< /а>

Название класса типа "block__elem__elem___elem" означает, что кодер ничего не понял в БЭМ.

Читайте также:

На эту тему есть отчет на веб-конференции WebCamp: Front-end Developers Day: https://www.youtube.com/watch?v=kBgHdSOj33A + слайды: http://ihorzenich.github.io/talks/2015/frontendweekend-bem/

person Ihor Zenich    schedule 12.01.2015