Идея для размера шрифтов: px для корневого элемента, rem для компонентов, em для текстовых элементов

Последний год или около того я не утверждал: «rem, - это так круто. Я могу задать все размеры с их помощью. Таким образом, я могу настроить размер шрифта в корневом элементе, и все остальные элементы будут масштабироваться соответственно!»

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

Изначально суть заключается в следующем:

/* Настройка уровня документа */
html {
  font-size: 17px;
}
@media (max-width: 900px) {
  html { font-size: 15px; }
}
@media (max-width: 400px) {
  html { font-size: 13px; }
}

        
        
Содержание
/* Шрифты масштабируются вместе с документом */ h1 { font-size: 3rem; } h2 { font-size: 2.5rem; } h3 { font-size: 2rem; }

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

Главная проблема: вы просто не можете быть уверенными, что шрифты, которые вы установили для одного размера экрана, будут выглядеть правильно на другом экране, если вы просто пропорционально масштабируете все размеры.

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

В любом из этих случаев вам придется выполнять корректировку для конкретных @media запросов, что не только может запутать вас, но это еще и очень неэффективно (зачем проводить корректировку, если потом нужно снова корректировать размер для устранения последствий корректировки).

Так что, вот моя идея: вы по-прежнему применяете px-корректировку размеров для уровней документа, чтобы можно было легко / эффективно производить радикальные изменения размеров. Но делаете это, когда каждый модуль на странице имеет размер шрифта, установленный через rem.

По сути, текстовые элементы (h1, h2, p, li и т.п.), если размер их задан через em. Таким образом, они становятся связанными с модулем.

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

Так что мы попробуем вот что:

Поиграв с настройками слайдера, вы можете попробовать разные варианты для реализации этой идеи:

HTML:

<div class="font-size-control">Управление размерами шрифтов документа: <input type="range" id="document-font-size-control" min="0.5" max="3.0" step="0.2" value="1.0">
</div>

<div class="page-wrap">

  <section class="main-content">

    <article class="module" data-font-size-in-rem="1.2">
      <h3>Заглавие модуля</h3>
      <time>5 августа 2014</time>
      <p>Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Vestibulum tortor quam, feugiat vitae, ultricies eget, tempor sit amet, ante. Donec eu libero sit amet quam egestas semper. Aenean ultricies mi vitae est. Mauris placerat eleifend leo.</p>
      <footer>
        Дополнительная информация.
      </footer>
    </article>

    <article class="module" data-font-size-in-rem="1.2">
      <h3>Заглавие модуля</h3>
      <time>Aug 10, 2014</time>
      <p>Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Vestibulum tortor quam, feugiat vitae, ultricies eget, tempor sit amet, ante. Donec eu libero sit amet quam egestas semper. Aenean ultricies mi vitae est. Mauris placerat eleifend leo.</p>
      <footer>
        Дополнительная информация.
      </footer>
    </article>

  </section>

  <aside>
    
    <div class="module" data-font-size-in-rem="0.9">
      <h3>Элементы сайд-бара</h3>
      <p>Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Vestibulum tortor quam</p>
      <ul>
        <li>Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</li>
        <li>Aliquam tincidunt mauris eu risus.</li>
        <li>Vestibulum auctor dapibus neque.</li>
      </ul>  
    </div>
    
    <div class="module" data-font-size-in-rem="0.9">
      <h3>Элементы сайд-бара</h3>
      <p>Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Vestibulum tortor quam</p>
      <ul>
        <li>Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</li>
        <li>Aliquam tincidunt mauris eu risus.</li>
        <li>Vestibulum auctor dapibus neque.</li>
      </ul>  
    </div>
    
  </aside>
  
  <footer class="module footer-module" data-font-size-in-rem="0.75">
    &copy;2014 Название сайта и прочее
  </footer>
  
</div>

SCSS:

body {
  padding: 10px;
}

.page-wrap {
  display: flex;
  flex-wrap: wrap;
}
.main-content {
  width: 66.66%;
  padding-right: 10px;
}
aside {
  width: calc(33.33% - 10px);
}
.footer-module {
  font-size: 0.75rem;
  flex: 0 0 90%;
}

.module {
  border: 1px solid #ccc;
  background: #eee;
  padding: 20px;
  margin: 0 0 20px 0;
  position: relative;
  .module-control {
    margin: -20px -20px 10px -20px;
  }
}

.font-size-control {
  background: #E77E23;
  padding: 10px;
  margin: 0 0 10px 0;
  font-size: 12px;
  > * {
    vertical-align: middle;
  }
}

article {
  font-size: 1.2rem;
  > h3 {
    font-size: 1.5em;
    margin: 0 0 0.5em;
  }
  > time {
    font-size: 0.9em;
    color: #999;
    display: block;
  }
  > footer {
    border-top: 1px solid #ccc;
    padding-top: 0.5em;
    font-size: 0.8em; 
  }
}

aside .module {
  font-size: 0.9rem;
  > h3 {
    font-size: 1.4em;
    margin: 0 0 0.4em 0;
  }
}

JS:

$(".module").prepend("<div class='module-control font-size-control'>Module: <input type='range'></div>");

$("input[type='range']").each(function() {
  var el = $(this);
  el.attr("min", 0.5);
  el.attr("max", 3.0);
  el.attr("step", 0.2);
  el.attr("value", el.parent().data("font-size-in-rem"));
})
.on("change", function() {
  $(this).closest(".module").css("font-size", $(this).val() + "rem");
});

$("#document-font-size-control")
.on("change", function() {
  $("html").css("font-size", $(this).val() + "rem");
});

На определенном среднем размере, все выглядит нормально. Увеличивая масштаб, вы можете добраться до точки, где основные статьи еще имеют удовлетворительно большие шрифты, но в сайдбаре текст уже выглядит чрезмерно увеличенным.

С помощью этой системы вы можете легко засечь эту точку и уменьшить некоторые шрифты. При уменьшении масштаба шрифты в модуле боковой панели слишком быстро становятся чрезмерно миниатюрными, поэтому чтобы засечь нужную точку, вам придется отмотать немного назад - в сторону увеличения.

Может случиться, что вы найдете точку, при которой разные элементы уравновешиваются.

Вот как это будет работать:

/* Настройка уровней документа */
html {
  font-size: 17px;
}
@media (max-width: 900px) {
  html { font-size: 15px; {
}
@media (max-width: 400px) {
  html { font-size: 13px; }
}

/* Модули масштабируются вместе с документом */
.header {
  font-size: 1.5rem;
}
.footer {
  font-size: 0.75rem;
}
.sidebar {
  font-size: 0.85rem;
}

/* Шрифты масштабируются вместе с модулем */
h1 {
  font-size: 3em;
}
h2 {
  font-size: 2.5em;
}
h3 {
  font-size: 2em;
}

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

РедакцияПеревод статьи «Font Size Idea: px at the Root, rem for Components, em for Text Elements»