За пределы вьюпорта мобильного браузера

30.11.2025 • css, html

Вступление

На телефонах сайты не занимают всю поверхность экрана — обычно есть как верхняя панель, так и нижняя. Это могут быть как часы с зарядом батареи, так и браузерные панели с урлом страницы и так далее. В попытках сделать сайты похожими на приложения, часто перед разработчиками стоит задача как-то повлиять на это место — ну что за приложение, которое так выбивается по цветам?

Важно: в этой статье мы не будем говорить про PWA и про Fullscreen API. Только обычные сайты, обычные браузеры и возможности для них. И только мобильные устройства — на десктопы заглядывать почти не будем.

theme-color

В 2014м появился новый функционал в хроме 39 для Android: мета-тег с цветом сайта.

<meta name="theme-color" content="blue">

Можно использовать эту конструкцию и в 2025м:

Google Chrome with theme-color and light theme

Однако, если попробовать использовать это в тёмной теме… Что ж…

Google Chrome with theme-color and dark theme

Ныне theme-color на андроиде работает только в светлой теме или если сайт установлен в виде приложения.

В Яндекс Браузере, на удивление, работает и в тёмной теме тоже.

Кстати, о темах. В 93м хроме появилась возможность задать цвет для каждой темы отдельно (да и не только для темы):

<meta name="theme-color" content="red" media="(prefers-color-scheme: light)" />
<meta name="theme-color" content="blue" media="(prefers-color-scheme: dark)" />

Однако в тёмной теме это не помогает — как было системное оформление, так и осталось. В Яндекс Браузере работает.

А что там по Safari? С ним сложно. С 15й версии поддержка появилась, а с 26й — её уже не стало (за исключением десктопов в режиме PWA). Но если вдруг вы целитесь в старые версии браузеров с этим свойством — имейте ввиду, что Сафари принудительно ограничивает определённые цвета и не использует их. Все значения стоит проверить.

css background

Если theme-color не работает в Сафари, хотя поддержка была, то что пришло на замену? Нынче Сафари использует цвет фона страницы, например, с <body>:

body {
    background: green;
}

Верхняя панель красится и в десктопном Сафари, который тоже перешёл на подобный подход. Но на тачах красится ещё и нижнюю панель.

В андроиде подобного поведения не замечено, хотя кто знает? Если это не так, дайте мне знать, пожалуйста)

color-scheme

CSS-свойство color-scheme, хоть и влияет на цвета скроллбаров и на ряд других элементов, напрямую на панели за пределами вьюпорта не влияет. И всё же я рекомендую его задавать для десктопов, а лучше на всех платформах.

Safe-Area

С выходом iPhone X у производителей телефонов появился новый тренд, так называемая “чёлка”, “бровь” и тому подобное. Сейчас этот элемент дизайна повсеместно используется и в андроид-смартфонах. В iOS с первым появлением вышла статья в блоге вебкита, которая представила новое апи по работе с safe-area в виде viewport-fit для мета-тега viewport:

<meta name='viewport' content='initial-scale=1, viewport-fit=cover'>

В ландшафтном режиме это позволяло “растянуть” вьюпорт больше обычного, затащив его под “чёлку” и другие панели. В портретном режиме ничего не менялось. Для того, чтобы контент не пострадал, появилось ещё одно новшество: css-функция env() с четырьмя значениями. Ныне вариантов использования env() стало больше, а в статье это выглядело так:

padding-right: env(safe-area-inset-right);
padding-bottom: env(safe-area-inset-bottom);
padding-left: env(safe-area-inset-left);
Safe area in iPhone

И по сей день это именно так и работает: в портретном режиме ничего от viewport-fit=cover не меняется, а в ландшафтном есть только right, bottom и left (env(safe-area-inset-left) равен нулю).

А на андроиде?

env() caniuse

В хроме поддержка появилась с 69й версии, т..е в этой версии конструкция вида env(safe-area-inset-right) начала успешно парситься. Успешно ли она работала? Есть некоторые сомнения, я проверил только 134й и 142ю версии, и там всё было одинаково.

Дальше начинается интересное. viewport-fit=cover работает в портретном режиме, в отличии от iOS!

Chrome bottom bar

В ландшафтном режиме механика тоже работает, однако у меня не получилось заставить его работать с “верхней” панелью (на скриншоте снизу она справа). Итого получается не очень симметричная картина:

Android in landscape

Может быть не очень заметно, но сайт не выровнен по центру экрана, справа есть неубираемая панель, а скругление (которое не попало в скриншот) ещё больше подчёркивает проблему.

Цвет панелей на основе элементов

Если нижнюю панель на андроиде можно покрасить через элементы сайта, можно ли задать ей отдельный от шапки цвет на iOS? Способ тоже есть, и на этот раз это будет… Эвристики Сафари. Сафари ищет элементы, которые прибиты к нижнему краю страницы. Может угадать, а может и не угадать, в зависимости от вёрстки.

Исходя из экспериментов, работает элемент с position: fixed, прибитый к низу страницы.

iOS bottom bar

Если элемент просто находится снизу, то это не работает.

Собираем всё вместе для портретного режима

На андроиде верхнюю панель можно покрасить в светлой теме браузера через theme-color. В тёмной теме это работает лишь в части браузеров.

Нижнюю панель можно покрасить через контент самой страницы, используя viewport-fit=cover.

В iOS верхнюю панель можно покрасить, используя background на body.

Нижняя панель красится либо тем же фоном, либо элементом, прибитым к низу страницы.

Обсудить в Telegram