rem в CSS. Загальні відомості і способи застосування

13

Від автора: сьогодні ми розглянемо ще один тип одиниці виміру rem в css. Даний тип відмінно підтримується браузерами і полифиллами у випадку зі старими браузерами.

Опис

Одиниці виміру rem в CSS що це? Якщо ви любитель музики, то має бути стикалися з групою «REM». Але на відміну від своїх колег «Rapid Eye Movement» наш rem розшифровується, як «root em». Даний тип одиниці виміру створений для гармонії і балансу з дизайном. Визначення однієї одиниці rem на W3C:

Рівна обчисленому значенню властивості font-size для основного тексту. Якщо властивість font-size встановлено для основного тексту, то rem одиниці зв’язуються з цією властивістю.

Це означає, що 1rem дорівнює розміру тексту для тега html (в більшості браузерів за замовчуванням це 16px).

Rem проти Em

Основна заковика з em в тому, що вони визначаються за розміром тексту конкретного елемента. Крім того, вони успадковуються, що призводить до непередбачуваних наслідків. Розглянемо наступний приклад. Списки будуть мати шрифт 12px, а основний текст 16px:

html {
font-size: 100%;
}
ul {
font-size: 0.75 em;
}

Якщо наш список вкладений в інший список, розмір шрифту внутрішнього буде становити 75% від батька, тобто 9px. Виправити це так:

ul ul {
font-size: 1em;
}

Це вирішує проблему, однак не варто забувати про більш глибокому спадкування. З rem все набагато простіше:

html {
font-size: 100%;
}
ul {
font-size: 0.75 rem;
}

Так як всі розміри шрифтів визначаються за кореневого тексту, нам не потрібно стежити за усілякими випадками вкладеності.

Розмір тексту Rem

Jonathan Snook у своїй статті Розмір тексту Rem у травні 2011 р. був одним з першопрохідців у застосуванні даних одиниць вимірювання до шрифтів. Як і безліч інших CSS розробників, він зіткнувся з проблемою з em одиницями в складних макетів.

У той час IE ще займав велику частку ринку, і розробники не могли масштабувати текст, так як він був в пікселях. І як ми вже бачили вище, дуже легко не встежити за всілякими наследованиями і отримати несподівані результати.

Основна проблема rem для шрифтів у тому, що дані одиниці досить важко застосувати. Нижче я склав короткий список основних розмірів шрифтів в rem одиницях, за умови, що за замовчуванням стоїть 16px:

10px = 0.625 rem

12px = 0.75 rem

14px = 0.875 rem

16px = 1rem (base)

18px = 1.125 rem

20px = 1.25 rem

24px = 1.5 rem

30px = 1.875 rem

32px = 2rem

Як видно, дані значення незручні при обчисленнях. З цієї причини Snook використовували трюк під назвою «62,5%». Це старий трюк, його вже застосовували з em одиницями:

body { font-size:62.5%; } /* =10px */
h1 { font-size: 2.4 em; } /* =24px */
p { font-size: 1.4 em; } /* =14px */
li { font-size: 1.4 em; } /* =14px? */

Так як rem пов’язані з кореневим текстом, то варіант від Snook виглядає так:

html { font-size: 62.5%; } /* =10px */
body { font-size: 1.4 rem; } /* =14px */
h1 { font-size: 2.4 rem; } /* =24px */

Але варто врахувати і ті браузери, які не підтримують дані одиниці вимірювання. Для них ми змінимо наш код на такий:

html {
font-size: 62.5%;
}
body {
font-size: 14px;
font-size: 1.4 rem;
}
h1 {
font-size: 24px;
font-size: 2.4 rem;
}

З вигляду дане рішення може здатися ідеальним, однак є розробники, які остерігають від бездумного використання даного підходу. Harry Roberts написав свою статтю з приводу застосування rem одиниць. На його думку, хоч правило 62,5% і полегшує обчислення, у результаті воно змушує розробників переписувати абсолютно всі розміри шрифтів на їх сайті.

Третій спосіб підказав Chris Coyier на сайті CSS-Tricks. Він використовує всі три типи одиниць виміру. Кореневий текст, він залишає px, модулі в rem, а елементи модулів em. Даний підхід полегшує маніпулювання розмірами основного тексту. На основі базового тексту обчислюється розмір модулів, а за розміром модулів обчислюється розмір шрифту для тексту в модулях. Louis Lazaris обговорювала цей останній спосіб у статті Міць em одиниць вимірювання CSS. У цьому прикладі можна побачити, як працює останній спосіб:

Як видно, панацеї не існує. Комбінація різних способів обмежується тільки уявою розробників.

Rem і медіа запити

Використання em або rem в медіа запитах зводиться до поняття «оптимальна довжина рядка», і як вона впливає на користувачів. У 2014 році веб-сайт Smashing Magazine опублікував статтю з комплексним дослідженням типографіки під назвою Розмір має значення: оптимальна довжина рядка і розмір шрифту в адаптивному веб-дизайні. У статті багато цікавого, в тому числі була обчислена оптимальна довжина рядка: від 45 до 75-85 символів (включаючи пробіли та розділові знаки). Ідеальне значення рядка – 65 символів.

При грубому округленні 1rem = 1 символ, можна маніпулювати текстом в одній колонці для мобільних пристроїв:

.container {
width: 100%;
}
@media (min-width: 85rem) {
.container {
width: 65rem;
}
}

Є одна цікава деталь при використанні rem і em в медіа запитах: всі вони мають одне значення 1rem = 1em = розмір браузера за замовчуванням. Пояснення можна знайти у специфікації media query:

«Відносні одиниці вимірювання в медіа запитах засновані на значенні браузера за замовчуванням. Наприклад, в HTML em обчислюється за розміром шрифту font-size, який заданий юзер агентом або налаштуваннями браузера, а не стилями сторінки.»

Подивіться демо на CodePen

Спершу створимо span, в ньому будемо писати ширину екрану: Document width: px.

Створимо два медіа запиту: один для rem, інший для em (Для простоти використаємо Sass):

html {
font-size: 62.5%; /* 62.5% of 16px = 10px */
@media (min-width: 20rem) {
/* 20*16px = 320px */
background-color: lemonchiffon;
font-size: 200%;
/* 200% of 16px = 32px */
}
@media (min-width: 30em) {
/* 30*16px = 480px */
background-color: lightblue;
font-size: 300%; /* 300% of 16px = 30px */
}
}

Додамо трохи JQuery для відображення розміру екрану, оновлюємо значення при зміні розміру вікна:

$(‘span’).text($(window).width());
$(window).on(‘resize’, function(e) {
$(‘span’).text($(window).width());
});

Спочатку ми показали, що правило 62,5% не працює для шрифтів у медіа запитах. При зміні ширини вікна браузера, ми бачимо, як перший медіа запит перестає працювати на 320px (20x16px), а другий починає на 480px (30x16px). Розмір шрифту не змінюється, оголошені нами в стилях при зміні розміру вікна. Єдиний спосіб це змінити в настройках браузера.

З цієї причини не має значення, використовуємо ми em або rem в медіа запитах. В таких проектах, як Foundation v5 і Bootstrap v4 alpha в медіа запитах використовуються em одиниці.

Використання rem для масштабування документів

Третій спосіб застосування rem одиниць це створення масштабованих документів. Використовуючи rem одиниці в значеннях ширини, зовнішніх і внутрішніх відступів, можна створити інтерфейс, який буде збільшуватися і зменшуватися в залежності від розміру шрифту. Розглянемо цей спосіб на парі прикладів:

Демо №1

У першому прикладі ми змінюємо розмір шрифту за допомогою медіа запитів. Як в попередньому розділі статті. Основна мета домогтися зручного розміру на різних пристроях користувача. Якщо padding та margin елемента виражені в rem, то весь елемент масштабується під розмір екрану пристрою.

Ще один приклад:

У другому прикладі ми робимо те ж саме але з допомогою JS. У цьому прикладі користувачу надана можливість налаштування розміру інтерфейсу. Напишіть метод для збору даних про розміри екранів користувачів (можна зберігати в БД, куки або на знімному носії), і ви будете знати про переваги ваших користувачів.

Висновок

Закінчуємо наш урок з rem в CSS. Немає потреби пояснювати всі переваги даних одиниць вимірювання: адаптивність, масштабованість, зручність при читанні і велика гнучкість. Однак rem не панацея. При правильному застосуванні вони можуть вирішити безліч проблем, які дратували розробників багато років. Кожен з нас може створити свій підхід. Відкривайте текстові редактори, експериментуйте та діліться результатами в коментарях.