Строчные элементы, базовая линия и неожиданные отступы
Где встречается inline, откуда берётся зазор под картинкой и почему Flex меняет расстояния между подписями.
На этой странице
Под картинкой осталось пустое место, хотя margin: 0? Иногда причина в том, что браузер располагает её в строке, рядом с текстом. Разберём два примера и способы управлять такими расстояниями.
Где встречается inline
inline означает «строчный». Такой элемент идёт вместе с текстом и сам по себе не начинает новую строку. Так по умолчанию ведут себя <span>, <a>, <strong> и <em>. Длинный текст внутри них может переноситься на следующие строки.
<p>Обычный текст, <span>выделенный фрагмент</span> и <a href="/">ссылка</a>.</p>Сам <p> – блочный элемент. Он создаёт отдельный абзац, а текст и строчные элементы внутри него располагаются в строках. <div> тоже по умолчанию блочный. Изменить это поведение можно свойством display.
У обычного текстового <span> с display: inline свойства width и height не задают размеры. Для небольшого блока внутри строки есть inline-block: он остаётся в строке, но получает собственные размеры. Изображение <img> – особый случай: оно по умолчанию строчное, однако его ширину и высоту задавать можно.
Откуда берётся зазор под картинкой
Буквы стоят на условной базовой линии (baseline). Части букв g, p и у опускаются ниже неё, поэтому строке нужно место и снизу.
Строчное изображение выравнивается по этой линии нижним краем. Под ним может остаться место строки – даже если текста рядом нет. Браузер учитывает размеры, заданные шрифтом, а не ищет конкретные буквы. line-height задаёт высоту строки: например, 20px × 1.5 = 30px для обычного текста. Картинка или более крупный текст могут сделать строку выше.
Переключите режимы и посмотрите на зазор. Код обновляется вместе с примером; подсвечены управляемые свойства. Серые строки сейчас не применяются – наведите на них указатель, чтобы увидеть причину. На узком экране код находится под примером.
Высота контейнера: …. Зазор под изображением: ….
Синяя линия – baseline строки. Цветная полоса под картинкой относится к строке, а не к отступам изображения.
<div class="photo-row"> <img src="mountains.jpg" alt="Горы" /></div>.photo-row { display: block; font-size: 32px; line-height: 1.5; font-family: Arial, sans-serif;}
.photo-row img { display: inline; vertical-align: baseline; width: 160px; height: 96px; margin: 0; padding: 0;}Как выбрать решение:
- Отдельная фотография в карточке: обычно достаточно
img { display: block; }. - Картинка должна остаться в строке:
vertical-align: bottomвыровняет её по низу строки. Для иконки рядом с текстом выбирайте выравнивание по задаче. - Родителю уже нужен Flex: изображение станет flex-элементом, и строчный зазор исчезнет.
У блочного изображения и flex-элемента vertical-align не действует. А font-size и line-height у родителя продолжают наследоваться, хотя в этом примере без текста они больше не создают зазор. Если его нет изначально, CSS-сброс мог заранее сделать картинки блочными.
Почему Flex меняет расстояния между подписями
В карточке ниже название – inline-block, а авторы находятся в следующем блоке. В обычном потоке название участвует в строке. При переключении на Flexbox оно становится отдельным flex-элементом, и место окружающей строки больше не добавляется.
Сравните оба режима. Затем включите несколько строк, увеличьте название или его хитбокс – область нажатия. Эти параметры можно сочетать. Серые flex-direction, align-items и gap не управляют обычным блочным контейнером; при включении Flex они начинают действовать.
Обложка → рамка названия: ….
Рамка названия → блок авторов: ….
Сравниваются границы элементов, а не контуры букв. В обоих режимах задано 16 px над подписями и 8 px перед авторами. При увеличении хитбокса добавляются padding: 4px 10px и margin: -4px -10px. Поэтому видимый зазор и размеры области нажатия нужно различать.
<div class="card"> <div class="cover">Обложка</div> <div class="caption"> <button class="title" type="button">Название композиции</button> <div class="artists">Анна Смирнова, Иван Петров</div> </div></div>.card { max-width: 260px; font: 24px/1.5 Arial, sans-serif; text-align: center;}.cover { height: 96px; }.caption { margin-top: 16px; display: block; flex-direction: column; align-items: center; gap: 8px;}.title { display: inline-block; font: 16px/1.3 Arial, sans-serif; white-space: pre-line; padding: 0px; margin: 0px; max-width: 100%; box-sizing: border-box; border: 1px dashed;}.artists { font: 14px/1.5 Arial, sans-serif; margin-top: 8px;}Здесь измеряются границы элементов, а не контуры букв. Поэтому gap: 8px не обещает ровно 8 px между видимыми буквами: внутри элементов тоже есть пространство. При увеличении хитбокса padding расширяет кнопку, а отрицательный margin компенсирует занятое место. Расстояние между рамками при этом меняется.
Для группы элементов интерфейса удобно задавать интервалы через gap у Flex- или Grid-контейнера. margin подходит для внешнего отступа отдельного элемента, padding – для внутреннего, а line-height – для строк текста. Переход на Flex меняет правила раскладки, поэтому одинаковые числа не всегда дают одинаковую картинку.
Что проверять на практике
Общие правила отступов разобраны в блочной модели.
- Выясните, откуда взялся зазор: из
margin,padding,gapили самой строки. Посмотритеdisplayэлемента и родителя в DevTools. - Для отдельной картинки попробуйте
display: block. Для последовательности элементов карточки рассмотрите Flex иgap. - Проверьте короткое и многострочное название. Не компенсируйте непонятный зазор случайным отрицательным отступом.