Style Guide <write less, do more>

Часть информации из книги которая касается стиля кодирования я вынес на данную страницу,
это позволит легко и быстро добавить данную страницу в избранное :)

HTML

Данное раздел написан на основе руководства от Google HTML/CSS Style Guide

Общие правила

  1. Стандарт - HTML5: <!DOCTYPE html>
  2. Указываем язык страницы в HTML: <html lang="en">
  3. Кодировка текста и файлов - UTF8: <meta charset="utf-8">
  4. Валидный HTML - используем сервис W3C HTML Validator
    для проверки ваших творений (хотя лучше настройте свою IDE или даже CI, чтобы не делать вручную монотонную работу)
  5. Семантичный HTML - используйте элементы согласно назначения
  6. Отделяйте данные от представления и поведения
    не стоит выравнивать текст пробелами, кесарю кесарево
  7. Использование inline стилей и обработчиков событий НЕДОПУСТИМО, от слова совсем
  8. Избегайте использования блоков <style> и <script>, подключайте внешние скрипты и стили, даже если там «одна маленькая функция»
  9. Не указывайте стандартный type для подключаемых скриптов и стилей (т.е. указываем только в том случае, если они отличаются от text/css и text/javascript)
  10. Указывайте альтернативное содержание для мультимедиа alt для картинок, caption для видео и т.д.
  11. Для тегов <img> указывайте размеры (в пикселях или процентах)
  12. Не используйте entity: &mdash;, &quot; и т.д.

Правила форматирования

  1. Отступы - два пробела (никогда не используйте табуляцию)
  2. Каждый блочный элемент должен начинаться с новой строки
  3. Дочерние элементы должны иметь отступы относительно родительского элемента
  4. Теги и атрибуты должны быть строчными (lowercase)
  5. Значение атрибутов должны заключаться в двойные кавычки:
    <img src="/img.jpg" alt="image alt"/>
  6. Порядок атрибутов должен быть единообразным, атрибуты data-* пусть будут последними
  7. Следите за тем, чтобы у вас не было пробелов в конце строк

Шаблон

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title></title>
</head>
<body>
  <!-- content -->
</body>
</html>

CSS

Данное раздел написан на основе следующих руководств:

  1. Google HTML/CSS Style Guide
  2. Airbnb CSS/Sass Styleguide
  3. Hacks for dealing with specificity
  4. Руководство по написанию кода

Общие правила

  1. Кодировка файлов - UTF8
  2. Названия селекторов - только на английском языке
  3. Комментарии только на английском языке, любой другой - только в сопроводительной документации
  4. Валидный CSS - используем сервис W3C CSS validator (правильная IDE + CI конечно же лучше)
  5. Старайтесь не использовать @import без необходимости, он медленный, куда как предпочтительней использование CSS препроцессоров, или даже несколько <link> - это всё же будет лучше чем @import сам по себе
  6. Никогда не используйте #ID в CSS, у них нет никаких преимуществ перед классами, но при этом - высокая специфичность и отсутствие возможности повторного использования
  7. Используйте минимально необходимую вложенность селектора, если работает .nav-head, то не нужно прописывать .nav .nav-head, результат тот же
  8. Не квалифицируйте селектор без необходимости, не стоит писать ul.nav, если можно обойтись лишь .nav
  9. Всегда используйте селекторы классов - низкая (одинаковая) специфичность, высокая портативность и возможность повторного использования
  10. Имя класса (или ID) должен быть как можно меньше, но при этом оно должно быть всё так же информативным
  11. При выборе имени класса (или ID) следует помнить, что имя должно однозначно указывать на назначение либо содержание элементов, но никак не визуальные атрибуты
/* nice */
.warning-text {
  color: #f00;
}
/* too sad */
.red {
  color: #f00;
}
Исходя из данных правил, может сложиться впечатление, что нельзя использовать ID в проекте, но это не так, правило касается только CSS, т.е. если вы хотите применить стиль к элементу с ID, то вам следует присвоить ему класс и применять стили уже непосредственно к нему

Правила форматирования

Для проверки форматирования используйте stylelint со стандартным конфигом

Подробная инструкция по подключению данной утилиты к продуктам компании JetBrains можно найти в официальном руководстве

Но чтобы долго не томить, вот вам краткое содержание последних двадцати серий:

  1. Отступы - два пробела
  2. Теги, классы, свойства - всё в нижнем регистре (lowercase)
  3. В качестве разделителя в имени классов следует использовать - (kebab-case)
  4. При перечислении селекторов каждый из них должен быть записан с новой строки
  5. Между селектором и открывающей фигурной скобочкой должен быть пробел
  6. При описании свойств добавляйте пробел только после двоеточия
  7. Каждое новое свойство следует записывать с новой строки
  8. В конце строчки со свойствами следует писать точку с запятой
  9. При указании цвета, не используйте именованные цвета: пишите color: #ff0; вместо color:red;
  10. Для отключения границ, следует использовать border: 0; вместо border: none;
  11. Избегайте сокращенных объявлений, используйте margin-bottom: 10px; вместо margin: 0 0 10px;
  12. Закрывающаяся фигурная скобочка должна быть на новой строке
  13. Удаляем пробелы в конце строк
  14. Между блоками правил должна быть пустая строка
  15. Соблюдаем единый порядок следования свойств внутри правил:
    1. позиционирование
    2. блочная модель и размеры
    3. свойства текста
    4. отображение
    5. остальные свойства
    6. анимация
Если у вас проект будет посложнее чем сайт-визитка вашего питомца, то рекомендуется придерживаться БЭМ методологии, но помните - это отнюдь не панацея, и тянет за собой избыточность в HTML, ломает мантичность классов и обрастает тулзами, которые не всем одинаково полезны. Если вы засомневались, и не можете решиться, то переложите вопрос «БЭМ или неБЭМ» на вашего техлида, пусть у него голова болит.

Примеры

Пример форматирования CSS

/* looks good */
.avatar {
  border-radius: 50%;
  border-collapse: separate;
  border: 2px solid white;
}

.one,
.selector,
.per-line {
  border: 0;
}
/* so sad */
.avatar{
border-radius:50%;border-collapse:separate;
border:2px solid white; }
.no, .nope, .not_good {
  border:none
}
#lol-no {
/* ... */
}


Комплексный пример порядка свойств

.selector {
  position: absolute;
  top: 0;
  right: 0;
  bottom: 0;
  left: 0;
  z-index: 100;

  display: block;
  float: right;
  width: 100px;
  height: 100px;

  font: 13px/1.5 "Helvetica Neue", sans-serif;
  color: #333;
  text-align: center;

  background-color: #f5f5f5;
  border: 1px solid #e5e5e5;
  border-radius: 3px;
  opacity: 1;

  transition: all 0.3s;
}

JavaScript

Данный раздел - это лишь небольшое дополнение к правилам Airbnb JavaScript Style Guide

Общие правила

  1. Кодировка файлов - UTF8
  2. Названия переменных и функций - только на английском языке
  3. Комментирование кода только на английском языке, любой другой - только в сопроводительной документации

Правила форматирования

Для проверки форматирования используйте ESLint с Airbnb конфигом.

Подробная инструкция по подключению данной утилиты к продуктам компании JetBrains можно найти в официальном руководстве.

jQuery

Модульность

Весь код должен быть инкапсулирован внутри модуля (все функции и переменные).

Один модуль === один файл, откройте для примера файл style.guide.js

/**
 * @param jQuery $  - be sure `$` is `jQuery`
 * @param window w  - be sure `w` is `window`
 */
(function($, w){
  // your code here
  let foo = "bar";
  // ... 
})(jQuery, window);

Именование переменных

Переменные содержащие jQuery объект должны начинаться со знака $

var $header = $("#header");
var $articles = $("article");

Используйте правильно единственное (singular) и множественное (plural) числа

var $sidebar = $("#sidebar");
var $articles = $(".article");

Правильно указывайте множественное число (plural) для слов исключений:

var $child = $("#child");
var $children = $(".child");
В данных примерах используется var, если вам нет нужды поддерживать старые браузеры, то смело используйте let и const в соответствии со стандартами от Airbnb и вашими задачами.
Так же следует быть осторожным, когда используете функции-стрелки, не забывайте про контекст.

Именование функций

Имена функций-оберток над селекторами должны начинаться со знака $

function $articles() {
return $("body").find(".content > article");
};

Имена функций должны быть короткими и содержательными, не нужно без нужды баламутить воду.

function changeColorToGreen() {}
function loadJSON() {}
function showErrorDialog() {}
function makeGreen() {} // color? background? WAT?
function loadData() {}  // data? rly?
function error() {}     // error in your DNA

Callback функции

Для упрощения чтения кода следует быть осторожным при использовании анонимных функций, т.к. это сводит на нет повторное их использование, и может затруднять чтение.

// on click handler
$("body")
  .on(
    "click.module",
    "p",
    changeColorToGreen
  );

// callback function
function changeColorToGreen() {
  $(this).css("color", "green");
}
// on click handler + callback function
$("body")
  .on(
    "click.module",
    "p",
    function() {
      $(this).css("color", "green");
    }
  );



Конечно данный пример ещё можно отнести к читабельным вариантам, но вот повторное использование функции уже стало невозможным.

Более комплексный пример:

// on click handler
$("header").on("click.module", loadJSON);

// callback with AJAX call
function loadJSON(event) {
  $.ajax("ajax/example.json", {context: event.currentTarget})
    .done(changeColorToGreen)
    .fail(changeColorToRed)
  ;
}

// callback for success
function changeColorToGreen() {
  $(this).css("color", "green");
}

// callback for error
function changeColorToRed() {
  $(this).css("color", "red");
}

Пространство имён

Все обработчики событий внутри модуля следует «вешать» внутри единого пространства имён, таким образом можно избежать конфликтов при одновременной работе сразу нескольких модулей

// file `module.js`
(function($, w){
  $("header").on("click.module", function() {
    // ...
  });
  $("header").trigger("click.module");
})(jQuery, window);

Кэширование

Если вы пропустили этот момент в моей книге, то повторю ещё разок ПОИСК ЭЛЕМЕНТОВ НЕ КЭШИРУЕТСЯ, следовательно, вам надо самостоятельно позаботиться о кэшировании ваших выборок:

let $sidebar = $("#sidebar");
// ...
$sidebar.css("color", "#ff0");
// ...
$sidebar.hide();
$("#sidebar");
// ...
$("#sidebar").css("color", "#ff0");
// ...
$("#sidebar").hide();

Как вариант можете использовать следующую функцию, возможно она вам пригодится:

const $function = function(selector) {
  let elements;
  return function() {
    if (!elements) {
      elements = $(selector);
    }
    return elements;
  }
};

С её помощью получается красивый КЭШИРУЕМЫЙ вариант для выборок элементов, которые не изменяются

let $headers = $function("h2");
let $articles = $function("article");
$articles().on("click.module", e => false)

Оптимизация

Стоит так же напомнить простое правило по оптимизации поиска элементов - указывайте контекст поиска

// fastest
$(DOMElement).find("p")
// fast
$("p", DOMElement)
// fast too
$("p", $article[0])
// slowest
$("article").find("p")
// slow too
$("p", "article")


Если данное правило вам не подходит, то посмотрите в сторону использования каскадных селекторов или селекторов вида parent > child

// not fast, not bad
$("article > p")
// slower, not bad
$("article p")
// slower
$article.find("p")