🔍 Начните печатать, чтобы искать по книге или перейти к нужной странице по номеру

Удобно листать не только прокруткой, но и клавишами‑стрелками:

 
между важными местами
Shift
между
разворотами
Васи­лий Полов­нёв, Игорь Пет­ров

ХТМЛ.
Вёрстка сайтов

Изда­тель­ство Бюро Гор­бу­нова
2021
Василий Половнёв, Игорь Петров

ХТМЛ.
Вёрстка сайтов

Издательство Бюро Горбунова
2021
удк 004.42
ббк З973.42
П52
Васи­лий Полов­нёв, Игорь Пет­ров
П52
ХТМЛ. Вёрстка сай­тов для дизай­не­ров, редак­то­ров и руко­во­ди­те­лей.—
М.: Изд‑во Бюро Гор­бу­нова, 2021

Эта книга — поша­го­вая инструк­ция по вёрстке сай­тов на язы­ках ХТМЛ и ЦСС. Вы узна­ете не только как свер­стать сайт, но и как опуб­ли­ко­вать его в интер­нете, настро­ить кра­си­вый шаринг в соц­сети и под­клю­чить системы аналитики.

Отдель­ный раз­дел книги посвя­щён работе с вер­сталь­щи­ком: как ста­вить задачи, полу­чать пред­ска­зу­е­мый резуль­тат и пра­вильно при­ни­мать и внед­рять вёрстку.

Оглавление

удк 004.42
ббк З973.42
П52
П52
Василий Половнёв, Игорь Петров
ХТМЛ. Вёрстка сайтов для дизайнеров, редакторов и руководителей.—
М.: Изд‑во Бюро Горбунова, 2021

Эта книга — пошаговая инструкция по вёрстке сайтов на языках ХТМЛ и ЦСС. Вы узнаете не только как сверстать сайт, но и как опубликовать его в интернете, настроить красивый шаринг в соцсети и подключить системы аналитики.

Отдельный раздел книги посвящён работе с верстальщиком: как ставить задачи, получать предсказуемый результат и правильно принимать и внедрять вёрстку.

Оглавление

Скрыто 112 разворотов

flex-basis часто исполь­зуют для вёрстки по сетке. Напри­мер, так может выгля­деть про­стей­шая сетка на 4 колонки.

Нач­нём с раз­метки. Без сти­лей колонки заняли всё доступ­ное пространство.

<div class="row">
  <div class="col-4">
    <!-- Колонка на всю ширину страницы -->
  </div>
</div>

<div class="row">
  <div class="col-3">
    <!-- Колонка на три четверти страницы -->
  </div>
  <div class="col-1">
    <!-- Колонка на четверть страницы -->
  </div>
</div>

<div class="row">
  <div class="col-1">
    <!-- Колонка на четверть страницы -->
  </div>
  <div class="col-1"></div>
  <div class="col-1"></div>
  <div class="col-1"></div>
</div>

Сти­ли­зуем .row — флекс‑кон­тей­нер, этаж сетки. Теперь колонки при­жа­лись друг к другу у левого края.

.row {
  display: flex;
  flex-direction: row; /* Раскладываем флекс-элементы по колонкам */
  justify-content: flex-start; /* Прижимаем флекс-элементы к левому краю */
  flex-wrap: nowrap; /* Если места для элементов не хватает, запрещаем их перенос на следующую строку */
  margin-left: -10px; /* Компенсируем межколонник */
  margin-right: -10px;
}

Сти­ли­зуем колонки и зада­дим их раз­меры. Появился меж­ко­лон­ник, а колонки стали зани­мать фик­си­ро­ван­ную ширину.

.col-1,
.col-2,
.col-3,
.col-4 {
  flex-grow: 0; /* Не даём элементу растягиваться больше указанного размера */
  flex-shrink: 0; /* Не даём элементу уменьшаться меньше указанного размера */
  padding-left: 10px; /* Задаём межколонник падингами */
  padding-right: 10px;
}

.col-1 {
  flex-basis: 25%;
}

.col-2 {
  flex-basis: 50%;
}

.col-3 {
  flex-basis: 75%;
}

.col-4 {
  flex-basis: 100%;
}

Обра­тите вни­ма­ние: отступы между колон­ками мы задали не с помо­щью gap, а с помо­щью падин­гов у коло­нок и отри­ца­тель­ных мар­жи­нов у эта­жей. Всё потому, что flex-basis не учи­ты­вает gap: колонки полу­чают точно 25%, 50% и 75% ширины, а допол­ни­тель­ный меж­ко­лон­ник вытал­ки­вает их за пре­делы этажа:

.row {
  display: flex;
  flex-direction: row;
  justify-content: flex-start;
  flex-wrap: nowrap;
  margin-left: -10px;
  margin-right: -10px;
  gap: 20px;
}

.col-1,
.col-2,
.col-3,
.col-4 {
  flex-grow: 0;
  flex-shrink: 0;
  padding-left: 10px;
  padding-right: 10px;
}

Чтобы колон­ками было проще управ­лять, пара­мет­ри­зуем ширину меж­ко­лон­ника. Для этого нам пона­до­бится ЦСС‑пере­мен­ная и функ­ция calc для расчётов:

.row {
  --gutter: 20px; /* Вводим переменную для межколонника */
  --halfGutter: calc(var(--gutter) / 2); /* Считаем половинку межколонника для маржинов и падингов */
  
  display: flex;
  flex-direction: row;
  justify-content: flex-start;
  flex-wrap: nowrap;
  margin-left: calc(-1 * var(--halfGutter)); /* В ЦСС нельзя просто написать -var(--halfGutter), приходится изощряться с умножением на -1 */
  margin-right: calc(-1 * var(--halfGutter));
}

.col-1,
.col-2,
.col-3,
.col-4 {
  flex-grow: 0;
  flex-shrink: 0;
  padding-left: var(--halfGutter);
  padding-right: var(--halfGutter);
}

flex-basis часто используют для вёрстки по сетке. Например, так может выглядеть простейшая сетка на 4 колонки.

Начнём с разметки. Без стилей колонки заняли всё доступное пространство.

<div class="row">
  <div class="col-4">
    <!-- Колонка на всю ширину страницы -->
  </div>
</div>

<div class="row">
  <div class="col-3">
    <!-- Колонка на три четверти страницы -->
  </div>
  <div class="col-1">
    <!-- Колонка на четверть страницы -->
  </div>
</div>

<div class="row">
  <div class="col-1">
    <!-- Колонка на четверть страницы -->
  </div>
  <div class="col-1"></div>
  <div class="col-1"></div>
  <div class="col-1"></div>
</div>

Стилизуем .row — флекс‑контейнер, этаж сетки. Теперь колонки прижались друг к другу у левого края.

.row {
  display: flex;
  flex-direction: row; /* Раскладываем флекс-элементы по колонкам */
  justify-content: flex-start; /* Прижимаем флекс-элементы к левому краю */
  flex-wrap: nowrap; /* Если места для элементов не хватает, запрещаем их перенос на следующую строку */
  margin-left: -10px; /* Компенсируем межколонник */
  margin-right: -10px;
}

Стилизуем колонки и зададим их размеры. Появился межколонник, а колонки стали занимать фиксированную ширину.

.col-1,
.col-2,
.col-3,
.col-4 {
  flex-grow: 0; /* Не даём элементу растягиваться больше указанного размера */
  flex-shrink: 0; /* Не даём элементу уменьшаться меньше указанного размера */
  padding-left: 10px; /* Задаём межколонник падингами */
  padding-right: 10px;
}

.col-1 {
  flex-basis: 25%;
}

.col-2 {
  flex-basis: 50%;
}

.col-3 {
  flex-basis: 75%;
}

.col-4 {
  flex-basis: 100%;
}

Обратите внимание: отступы между колонками мы задали не с помощью gap, а с помощью падингов у колонок и отрицательных маржинов у этажей. Всё потому, что flex-basis не учитывает gap: колонки получают точно 25%, 50% и 75% ширины, а дополнительный межколонник выталкивает их за пределы этажа:

.row {
  display: flex;
  flex-direction: row;
  justify-content: flex-start;
  flex-wrap: nowrap;
  margin-left: -10px;
  margin-right: -10px;
  gap: 20px;
}

.col-1,
.col-2,
.col-3,
.col-4 {
  flex-grow: 0;
  flex-shrink: 0;
  padding-left: 10px;
  padding-right: 10px;
}

Чтобы колонками было проще управлять, параметризуем ширину межколонника. Для этого нам понадобится ЦСС‑переменная и функция calc для расчётов:

.row {
  --gutter: 20px; /* Вводим переменную для межколонника */
  --halfGutter: calc(var(--gutter) / 2); /* Считаем половинку межколонника для маржинов и падингов */
  
  display: flex;
  flex-direction: row;
  justify-content: flex-start;
  flex-wrap: nowrap;
  margin-left: calc(-1 * var(--halfGutter)); /* В ЦСС нельзя просто написать -var(--halfGutter), приходится изощряться с умножением на -1 */
  margin-right: calc(-1 * var(--halfGutter));
}

.col-1,
.col-2,
.col-3,
.col-4 {
  flex-grow: 0;
  flex-shrink: 0;
  padding-left: var(--halfGutter);
  padding-right: var(--halfGutter);
}
flex‑basis: 150px
flex‑basis: 150px

Два элемента с flex‑basis: 150px занимают ровно по 150 пк

flex‑basis: 150px
flex‑basis: 150px; flex‑grow: 1

Первый элемент занимает 150 пк, а второй увеличивается так, чтобы занять всё свободное пространство

flex‑basis: 150px; flex‑grow: 2
flex‑basis: 150px; flex‑grow: 1

Два элемента делят свободное пространство в соотношении 2:1

flex‑basis: 0; flex‑grow: 2
flex‑basis: 0; flex‑grow: 1
flex‑basis: 0; flex‑grow: 2

Три элемента делят контейнер в соотношении 2:1:2

flex‑grow

Свой­ство flex-grow задаёт коэф­фи­ци­ент, опре­де­ля­ю­щий, какую долю сво­бод­ного места полу­чит эле­мент. Пред­по­ло­жим, что в кон­тей­нере с двумя эле­мен­тами у пер­вого эле­мента задан flex-grow: 2, а у вто­рого — flex-grow: 1. Тогда эти эле­менты поде­лят сво­бод­ное про­стран­ство в про­пор­ции 2:1.

flex-grow зада­ётся без­раз­мер­ными поло­жи­тель­ными чис­лами. Эти числа могут быть и дроб­ными: напри­мер, 1,618, золо­тое сече­ние. Зна­че­ние по умол­ча­нию равно 0 — эле­мент полу­чит мини­маль­ный раз­мер по сво­ему содержимому.

flex‑grow

Свойство flex-grow задаёт коэффициент, определяющий, какую долю свободного места получит элемент. Предположим, что в контейнере с двумя элементами у первого элемента задан flex-grow: 2, а у второго — flex-grow: 1. Тогда эти элементы поделят свободное пространство в пропорции 2:1.

flex-grow задаётся безразмерными положительными числами. Эти числа могут быть и дробными: например, 1,618, золотое сечение. Значение по умолчанию равно 0 — элемент получит минимальный размер по своему содержимому.

flex‑basis: 150px
flex‑basis: 150px

Два элемента с flex‑basis: 150px занимают ровно по 150 пк

flex‑basis: 150px
flex‑basis: 150px; flex‑grow: 1

Первый элемент занимает 150 пк, а второй увеличивается так, чтобы занять всё свободное пространство

flex‑basis: 150px; flex‑grow: 2
flex‑basis: 150px; flex‑grow: 1

Два элемента делят свободное пространство в соотношении 2:1

flex‑basis: 0; flex‑grow: 2
flex‑basis: 0; flex‑grow: 1
flex‑basis: 0; flex‑grow: 2

Три элемента делят контейнер в соотношении 2:1:2

Пер­вая колонка
Вто­рая колонка
Тре­тья колонка
Чет­вёр­тая колонка
Пер­вая колонка
Вто­рая колонка
Пер­вая колонка
Вто­рая колонка
Тре­тья колонка
Чет­вёр­тая колонка
Пятая колонка

flex-grow: 1 удобно исполь­зо­вать для созда­ния адап­тив­ных коло­нок, рав­но­мерно деля­щих доступ­ное пространство:

.cols {
  display: flex;
  flex-direction: row;
  flex-wrap: nowrap;
  gap: 18px;
}

.cols > * {
  flex-grow: 1;
  flex-basis: 0;
}
<div class="cols">
  <div>Первая колонка</div>
  …
  <div>Четвёртая колонка</div>
</div>

<div class="cols">
  <div>Первая колонка</div>
  <div>Вторая колонка</div>
</div>

<div class="cols">
  <div>Первая колонка</div>
  …
  <div>Пятая колонка</div>
</div>
Первая колонка
Вторая колонка
Третья колонка
Чет­вёр­тая колонка
Первая колонка
Вторая колонка
Первая колонка
Вторая колонка
Третья колонка
Чет­вёр­тая колонка
Пятая колонка

flex-grow: 1 удобно использовать для создания адаптивных колонок, равномерно делящих доступное пространство:

.cols {
  display: flex;
  flex-direction: row;
  flex-wrap: nowrap;
  gap: 18px;
}

.cols > * {
  flex-grow: 1;
  flex-basis: 0;
}
<div class="cols">
  <div>Первая колонка</div>
  …
  <div>Четвёртая колонка</div>
</div>

<div class="cols">
  <div>Первая колонка</div>
  <div>Вторая колонка</div>
</div>

<div class="cols">
  <div>Первая колонка</div>
  …
  <div>Пятая колонка</div>
</div>

Чтобы управ­лять поряд­ком отдель­ных эле­мен­тов во флекс‑кон­тей­нере, исполь­зуют свой­ство order. По умол­ча­нию его зна­че­ние равно 0. Соот­вет­ственно, эле­менты с order: 1 ста­нут в конце глав­ной оси, а эле­менты с order: -1 — в начале.

Возь­мём адап­тив­ные колонки из преды­ду­щего примера:

.cols {
  display: flex;
  flex-direction: row;
  flex-wrap: nowrap;
  gap: 18px;
}

.cols > * {
  flex-grow: 1;
  flex-basis: 0;
}

Пере­ста­вим вто­рую колонку в начало и дадим ей вдвое больше места:

.cols > *:nth-child(2) {
  order: -1;
  flex-grow: 2;
}

Чаще всего order исполь­зуют для адап­та­ции в мобиль­ной вер­сии. Ска­жем, если в двух колон­ках идёт текст, опи­сы­ва­ю­щий иллю­стра­цию, а в послед­ней колонке сама иллю­стра­ция, то в мобиль­ной вер­сии стоит пере­ста­вить изоб­ра­же­ние в начало с помо­щью order: -1

Пер­вая
колонка
Вто­рая
колонка
Тре­тья
колонка
Чет­вёр­тая
колонка
Пер­вая
колонка
Вто­рая
колонка
Тре­тья
колонка
Чет­вёр­тая
колонка
Первая
колонка
Вторая
колонка
Третья
колонка
Четвёртая
колонка
Первая
колонка
Вторая
колонка
Третья
колонка
Четвёртая
колонка

Чтобы управлять порядком отдельных элементов во флекс‑контейнере, используют свойство order. По умолчанию его значение равно 0. Соответственно, элементы с order: 1 станут в конце главной оси, а элементы с order: -1 — в начале.

Возьмём адаптивные колонки из предыдущего примера:

.cols {
  display: flex;
  flex-direction: row;
  flex-wrap: nowrap;
  gap: 18px;
}

.cols > * {
  flex-grow: 1;
  flex-basis: 0;
}

Переставим вторую колонку в начало и дадим ей вдвое больше места:

.cols > *:nth-child(2) {
  order: -1;
  flex-grow: 2;
}

Чаще всего order используют для адаптации в мобильной версии. Скажем, если в двух колонках идёт текст, описывающий иллюстрацию, а в последней колонке сама иллюстрация, то в мобильной версии стоит переставить изображение в начало с помощью order: -1

flex‑basis: 400px
flex‑basis: 400px

Два элемента с flex‑basis: 400px вмещаются в контейнер шириной 900 пк

flex‑basis: 600px; flex‑shrink: 0
flex‑basis: 600px; flex‑shrink: 0

Два элемента с flex‑basis: 600px и flex‑shrink: 0 не вмещаются в контейнер

flex‑basis: 600px; flex‑shrink: 0
flex‑basis: 600px; flex‑shrink: 1

Первый элемент занимает 600 пк, а второй уменьшается, чтобы вместиться в контейнер

flex‑basis: 600px; flex‑shrink: 2
flex‑basis: 600px; flex‑shrink: 1

Первый элемент уменьшается в два раза быстрее второго

flex‑shrink

Свой­ство flex-shrink задаёт коэф­фи­ци­ент, опре­де­ля­ю­щий, какую долю недо­ста­ю­щего места отдаст эле­мент. flex-shrink исполь­зуют, чтобы обо­зна­чить, какие эле­менты умень­ша­ются, какие нет и с какой ско­ро­стью. Пред­по­ло­жим, что в кон­тей­нере с двумя эле­мен­тами у пер­вого эле­мента задан flex-shrink: 2, а у вто­рого — flex-shrink: 1. Тогда пер­вый эле­мент осво­бо­дит в два раза больше места для остав­шихся эле­мен­тов, чем второй.

flex-shrink зада­ётся без­раз­мер­ными поло­жи­тель­ными чис­лами. Зна­че­ние по умол­ча­нию равно 1 — если места не хва­тит, эле­менты умень­шатся равномерно.

flex‑shrink

Свойство flex-shrink задаёт коэффициент, определяющий, какую долю недостающего места отдаст элемент. flex-shrink используют, чтобы обозначить, какие элементы уменьшаются, какие нет и с какой скоростью. Предположим, что в контейнере с двумя элементами у первого элемента задан flex-shrink: 2, а у второго — flex-shrink: 1. Тогда первый элемент освободит в два раза больше места для оставшихся элементов, чем второй.

flex-shrink задаётся безразмерными положительными числами. Значение по умолчанию равно 1 — если места не хватит, элементы уменьшатся равномерно.

flex‑basis: 100px
flex‑basis: 100px

Два элемента с flex‑basis: 100px вмещаются в контейнер шириной 345 пк

flex‑basis: 200px; flex‑shrink: 0
flex‑basis: 200px; flex‑shrink: 0

Два элемента с flex‑basis: 200px и flex‑shrink: 0 не вмещаются в контейнер

flex‑basis: 200px; flex‑shrink: 0
flex‑basis: 200px; flex‑shrink: 1

Первый элемент занимает 200 пк, а второй уменьшается, чтобы вместиться в контейнер

flex‑basis: 200px; flex‑shrink: 2
flex‑basis: 200px; flex‑shrink: 1

Первый элемент уменьшается в два раза быстрее второго

Скрыто 103 разворота