От автора: W3C определяет CSS как «простой механизм добавления стилей в веб-документ». Из определения следует, что HTML документ должен обрабатывать структуру и контент, то, что составляет семантику документа. Однако последние пару лет мы замечаем подъем популярных фреймворков, ускоряющих адаптивную разработку. Теперь увидеть в HTML документе теги <div class=»row»><div class=»col-md-12″>…</div></div> вполне нормально. В самом начале я сказал, что CSS является механизмом добавления стилей, а HTML должен обрабатывать структуру и контент. Можете ли вы сказать, что происходит с HTML структурой? Структура тесно связана с визуальным представлением контента, что непрактично в долгосрочной перспективе. Обслуживание кода станет сложным и дорогим.
Введение в БЭМ
Подумайте, сколько раз вы использовали эти CSS классы, чтобы сделать HTML документ более привлекательным, ну или просто приятным для чтения. Разве HTML не должен представлять значение структуры контента, который в нем хранится? Важен ли col-md-12 в вашем документе с точки зрения семантики? Ответ, скорее всего, нет. Вот тут нам и поможет БЭМ. Если вы не знаете, что такое БЭМ, то БЭМ методология – это способ именования классов в HTML и CSS. Технология разработана Yandex, и на сайте методологии они говорят:
«Методология БЭМ создана в Яндексе для разработки сайтов, которые надо делать быстро, а поддерживать долгие годы. Она позволяет создавать расширяемые и повторно используемые компоненты интерфейса.»
БЭМ полностью справляется со своей задачей. Существует еще несколько методологий типа SMACSS и OOCSS, но для меня БЭМ самая доступная и наименее громоздкая. Концепция легко усваивается, а обслуживание CSS и HTML очень простое, как в CSS препроцессорах.
Обычно при использовании какого-нибудь адаптивного фреймворка типа Bootstrap мы получаем примерно такой код:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
<body> <div class="row"> <div class="col-md-12 header"> <h1>Mi awesome website</h1> <p class="header-explanation">This is my….</p> </div> </div> <div class="row"> <div class="col-md-4 content-item picture"> ... </div> <div class="col-md-4 content-item audio>"> ... </div> <div class="col-md-4 content-item video"> ... </div> </div> </body> |
А что делать, если бы вы захотели узнать, для чего нужен каждый col-md-4? Что если на других страницах у вас больше тегов с классами audio и video, и вы их изменяли? Можете ли вы изменить что-то в большом коде, не боясь, что изменения затронут и другие страницы, ведь вы не знали, что эти классы используются где-то еще? Вот тут нам и поможет БЭМ, теперь HTML можно переписать в такой вид:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
<body> <div class="header"> <h1 class="header__title">...</h1> <p class="header__description">...</p> </div> <div class="content"> <div class="content__item content__item--picture"> ... </div> <div class="content__item content__item--audio"> ... </div> <div class="content__item content__item--video"> ... </div> </div> </body> |
В HTML появились классы типа content__item—video. Полученная структура и новый способ именования классов дают пояснение о тегах в документе, что в них хранится, а также как они работают с остальными частями документа. Так строится семантика того, что мы хотим представить при помощи HTML. Теперь можно с уверенностью изменять элементы с классом content__item—video. Стоять, это что, я потерял классы из Bootstrap типа col-md-4? Да, вы лишаетесь сетчатого макета и других стилей CSS фреймворка. НО БЕЗ ПАНИКИ, если вы пользуетесь препроцессором, что почти всегда правда в больших проектах. Продолжайте читать.
Подключаем SASS и LESS
При использовании БЭМ очень удобно работать с CSS препроцессорами. В наше время в нормальном фреймворке есть инструмент препроцессинга CSS. Часто используются языки SASS и LESS. Эти языки расширяют возможности методологии БЭМ для поддержания более организованного CSS, который потом можно разбить на отдельные модули. Кроме того, препроцессоры позволяют нам использовать переменные, функции и миксины. БЭМ предлагает файловую структуру, однако она необязательная, можно использовать свою, если она соблюдает БЭМ принципы.
Если использовать SCSS, то в файле main.scss было бы что-то типа того:
1 2 3 4 5 |
@import 'bootstrap'; @import 'lib/variables'; @import 'lib/mixins'; @import 'base/*'; @import 'components/*'; |
Учтите, что в зависимости от проекта и необходимостей файловая структура может быть более вложенной и специализированной. Более того, в Bootstrap есть миксины для сеток и другие компоненты. Также с помощью сторонних библиотек типа sass-globbing можно реализовать imports наподобие @import ‘base/*’. Так как мы работаем с БЭМ, порядок загрузки файлов одного уровня не имеет значения. В рамках нашего примера в файле components/homepage.scss может быть следующий код:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
.header { @include make-row; … &__title { ... } &__description { ... } } .content { @include make-row; &__item { @include make-md-column(4); &--yellow { background-color: yellow; } &--blue { background-color: blue; } &--red { background-color: red; } } } |
Теперь действительно заметно, что HTML используется для определения структуры и контента. CSS же используется только для выражения визуальных деталей документа. Более того, начиная с SASS 3.3, чтобы не писать длинные имена можно использовать &__element. Имена по началу могут быть довольно длинными и громоздкими. Если строго следовать методологии именования БЭМ, то в некоторых ситуациях можно получить очень длинные имена классов и селекторов. Человеку будет намного сложнее разобраться в коде. К нашему счастью, документы с большой вложенностью, где длинные имена могут вызвать проблемы, обычно можно разбить на более мелкие виды (в больших проектах обычно используются движки видов, с помощью которых можно разбивать виды). Точно так же нужно очень аккуратно определять независимые элементы, так как это сильно помогает при работе с длинными именами, и для этого не нужны движки видов. В конце концов, когда вы увидите, насколько легким и специфичным может быть БЭМ, а также как он выполняет вашу работу, вы сами захотите им пользоваться.
Наш опыт работы с БЭМ
Не так давно мы работали над редизайном сайта. Редизайн был полным, мы не работали со старым CSS и решили попробовать БЭМ. Проект был написан на Ruby On Rails и использовал гем Bootstrap. К сожалению, мы были привязаны к Bootstrap 2 (текущая версия 3, версия 4 все еще в альфа релизе), так как часть сайта редизайн не затрагивал, и она должна была работать под управлением Bootstrap 2. Нам нужно было сохранить версию гема, и тем самым мы ограничивали себя старой версией Bootstrap. В конечном счете мы мигрировали на Bootstrap 3, но поддержка частей сайта со старым и новым дизайном никуда не делась.
БЭМ помог нам сделать так, чтобы HTML файлы или наши виды отвечали только за структуру и контент, что придавало семантику всем видам. Виды не имели ничего общего с адаптивным фреймворком. А вот CSS файлы описывали визуальные стили при помощи расширения некоторых классов фреймворка и при помощи миксинов. В новом дизайне код CSS был полностью переписан, проект был правильно организован, и мы точно знали, какой файл на какую часть стилей приложения влияет. Общие стили были помещены в папку base, в которой хранились файлы, переписывающие стандартные HTML элементы. Вы можете сказать, что задача селекторов заключается в стилизации нескольких элементов, в отличие от специфичных селекторов в БЭМ. Достичь этой цели и высокого уровня повторного использования кода можно, комбинируя стили фреймворка и миксины, которые нужны в отдельных стилях.
Во время редизайна сайта мы пересмотрели некоторые требования к новому дизайну. В проектах всегда приходится менять некоторые требования, и это могут быть предпосылки к тому, чтобы рассмотреть гибкую методологию. Сначала мы решили использовать классы и стили Bootstrap 2. По сравнению с текущей версией функционал был ограничен. В итоге мы переросли Bootstrap 2 и столкнулись со сложностью создания плавных интерфейсов. Поэтому мы заменили классы сетки из bootstrap на flex блоковые компоненты (есть даже фреймворк, использующий flex блоки для создания сеток). Переход был плавным, изменения не затронули HTML. CSS файлы изменить не составило труда, так как повторно используемые компоненты были в миксинах, которые были переделаны в одно изменение, затрагивающее различные стили. Изменить стили или вид также не вызвало затруднений. К сожалению, проект должен был поддерживать IE 11, так как до сих пор множество пользователей сидят на этом браузере. В некоторых случаях, где мы использовали flexbox, не было полной поддержки в IE11 и браузерах на iPhone.
В конце концов, мы мигрировали на Bootstrap 3. И опять мы вообще не трогали HTML, так как изменения не затронули структуру, контент и семантику видов. Весь процесс прошел очень быстро.
Заключение
БЭМ был ключевым инструментом в поддержании обслуживаемости стилей в большом проекте. Однако БЭМ для расширения функционала может использовать и другие инструменты и языки. Языки SASS и LESS позволяют использовать более сложные функции и файловую структуру, чего по умолчанию в обычном CSS нет. Используя эти инструменты вместе, мы получаем простой в обслуживании CSS, а также мы можем с уверенностью вносить изменения в визуальную составляющую приложения. Все внесенные изменения затронут только те элементы, которые и должны измениться (больше никаких !important в CSS). HTML файлы с видами описывают структуру и контент. В итоге мы получили CSS код, который нам будет приятно поддерживать через пару лет в крупном проекте.
Источник: //www.stackbuilders.com/
Редакция: Команда webformyself.