автордың кітабын онлайн тегін оқу CSS для профи
Научный редактор С. Черников
Переводчик С. Черников
Технические редакторы Н. Гринчик, Н. Рощина
Литературный редактор Н. Рощина
Художник Н. Гринчик
Корректоры Е. Павлович, Е. Рафалюк-Бузовская
Верстка Г. Блинов
Кит Грант
CSS для профи. — СПб.: Питер, 2021.
ISBN 978-5-4461-0909-8
© ООО Издательство "Питер", 2021
Все права защищены. Никакая часть данной книги не может быть воспроизведена в какой бы то ни было форме без письменного разрешения владельцев авторских прав.
Предисловие
«Минута, чтобы научиться… Целая жизнь, чтобы овладеть». Эта фраза в наши дни может показаться немного банальной, но она отображает суть CSS. Фраза обрела популярность, став слоганом настольной игры «Реверси», в которой игроки по очереди перемещают белые и черные фигуры по клеткам на доске. Если, например, белая фигура захватывает ряд черных между двумя белыми, все черные фигуры переворачиваются и ряд становится полностью белым.
Правила CSS изучить так же несложно, как правила «Реверси». Вы создаете селектор, чтобы сопоставить элементы; затем вы пишете пары «ключ/значение», которые форматируют эти элементы. Даже начинающим разработчикам не составит большого труда понять основной синтаксис. Секрет того, как стать гуру в CSS, как и в «Реверси»: нужно точно знать, что делать и когда.
CSS (каскадные таблицы стилей) — это один из языков для веб-разработки, но работа с ним не совсем то же самое, что программирование. В CSS мало логики и циклов. Математика ограничивается одной функцией. Лишь недавно стало возможно использовать в нем переменные. Вы почти не будете думать о безопасности. Каскадные таблицы стилей ближе к живописи, чем к языку программирования Python. С помощью CSS вы вольны делать все, что нравится. Каскадные таблицы стилей не будут озадачивать вас какими-то ошибками или сбоями в компиляции.
На пути к тому, чтобы стать гуру в CSS, вы должны изучить все, на что способны каскадные таблицы стилей. Чем больше вы знаете, тем более легким покажется старт. Чем больше тренируетесь, тем легче получите идеальные компоновку и расстояния между блоками. Чем больше читаете, тем увереннее будете чувствовать себя при создании любого дизайна.
Действительно хорошие разработчики CSS не ограничиваются единым дизайном. Каждая работа может стать зубодробительной головоломкой, которую нужно решить. Опытные разработчики CSS имеют полный и широкий спектр знаний о том, на что способны каскадные таблицы стилей. Эта книга станет этапом на пути к тому, чтобы вы могли стать хорошим разработчиком CSS. Прочитав ее, вы узнаете, как создавать макеты любой сложности.
Разрешите еще одну метафору: несмотря на то что каскадные таблицы стилей разрабатываются уже пару десятилетий, можно провести некую аналогию с Диким Западом. Вы можете делать все, что захотите, до тех пор, пока CSS делает то, что вы хотите. Нет никаких жестких правил. Но, поскольку вы предоставлены сами себе и не ограничены строгими рамками, вы должны быть предельно аккуратны. Мельчайшие изменения могут иметь огромные последствия. Каскадные таблицы стилей способны расти и становиться громоздкими. Вы можете испугаться собственных стилей!
Кит описывает в этой книге почти все особенности CSS, и каждый, даже маленький ее фрагмент поможет вам стать отличным разработчиком CSS и приручить этот Дикий Запад. Вы глубоко погрузитесь в сам язык, поймете, на что способны каскадные таблицы стилей. Вы будете лучше писать код — работоспособный и понятный.
Книга будет полезна даже опытным разработчикам. Обнаружив, что читаете о чем-то уже известном, вы укрепите свои навыки, подтвердите знания и дополните их недостающими фрагментами, которые удивят вас и расширят вашу теоретическую базу.
Крис Койер (Chris Coyier), сооснователь компании CodePen
Введение
Впервые о каскадных таблицах стилей заговорили в 1994 году, и уже в 1996-м они были реализованы (частично) в браузере Internet Explorer 3. Примерно в то время я нажал прекрасную кнопку просмотра исходного кода и увидел, что все секреты веб-страницы расшифрованы в виде простого текста. Я сам изучил HTML и CSS, развлекаясь в текстовом редакторе и наблюдая за тем, что получалось. Это был приятный повод провести как можно больше времени в Интернете.
Тем временем мне нужно было найти настоящую работу. Я получил степень в области компьютерных наук. Но не знал, что в 2000-х годах это словосочетание потеряет смысл, так как появится профессия «веб-разработчик».
Я начал пользоваться каскадными таблицами стилей еще с момента их появления. Я работал и на стороне сервера, и с клиентскими интерфейсами, но в любой команде всегда оказывался экспертом в области CSS. Надо признать, что это часть Всемирной паутины, которой пренебрегают. Но как только вы поработаете над проектом с чистым кодом CSS, вы уже не захотите впредь обходиться без него. Увидев его в действии, даже опытные веб-разработчики спрашивают: «Как выучить CSS?»
На этот вопрос нет краткого и однозначного ответа. Недостаточно освоить один или два быстрых приема. Скорее, вам нужно разобраться в отдельных составляющих языка и понять, как они могут сочетаться. Одни книги дают общее представление о CSS, но многие разработчики уже что-то в нем понимают. В других книгах рассмотрено много полезных приемов, но предполагается, что читатель уже владеет языком.
В то же время темпы изменения CSS постоянно растут. Адаптивный дизайн сейчас стал стандартом де-факто. Веб-шрифты считаются банальщиной. В 2016 году мы наблюдали расцвет гибких контейнеров, а в 2017-м развитие получила CSS-сетка. Режимы смешивания, тени блоков, преобразования, переходы и анимация — все это нововведения в создании веб-страниц. Поскольку все больше и больше браузеров становятся «вечнозелеными», автоматически обновляясь до последней версии, новые возможности будут продолжать добавляться. Их достаточно, чтобы идти в ногу со временем.
Независимо от того, новичок вы в веб-дизайне или занимаетесь им уже некоторое время, вам нужно развивать или обновлять свои навыки работы с каскадными таблицами стилей. И я написал эту книгу, чтобы дать вам «волшебный пинок». Весь материал в нее отбирался по одному из трех оснований.
1. Он важен. Существует множество фундаментальных понятий языка, в которых, к сожалению, многие разработчики не до конца разбираются. К ним относятся каскадность, поведение элементов с обтеканием и позиционирование. Мы внимательно изучим их, и я объясню, как они работают.
2. Он актуален. За последние несколько лет появилось много новых функций. Я расскажу о последних улучшениях CSS и нескольких неочевидных возможностях. Это перспективная книга. Я укажу на проблемы обратной совместимости, когда это уместно, но я оптимистично отношусь к настоящему и будущему развития кросс-браузерности.
3. Он не раскрыт в большинстве книг, посвященных CSS. Мир каскадных таблиц стилей огромен. В современном мире разработки веб-приложений существуют важные передовые методы и общие подходы. Строго говоря, они являются частью не самого языка CSS, а скорее его культуры. И жизненно важны для современной веб-разработки.
Итак, как изучить CSS? Эта книга позиционируется как попытка ответить на данный вопрос.
Благодарности
Написание книги требует невероятных усилий. Я считаю, что это отличная книга, и надеюсь, вы согласитесь, но ее не было бы без помощи других людей.
Прежде всего я хотел бы поблагодарить свою супругу Кортни. Ты поддерживала и поощряла меня на протяжении всего процесса. Ты взяла на себя бремя написания этой книги вместе со мной. И даже помогла с редактурой в некоторых ключевых местах. Я не смог бы сделать это без тебя.
Я хотел бы поблагодарить своего начальника Марка Игла (Mark Eagle) и остальных членов моей команды в сети Intercontinental Exchange. Благодарю вас за то, что помогли мне на этом пути и позволили иногда отвлекаться от основной работы, чтобы писать книгу во время бесчисленных обеденных перерывов.
Благодарю редактора Грега Уайлда (Greg Wild), который нашел мои первые жалкие черновики в Интернете и убедил меня продолжать. Также благодарю главу издательства Manning Марьяна Баце (Marjan Bace), который почувствовал потенциал в этой идее. Всегда есть риск, связанный с изданием книги, особенно с новым автором. Спасибо, что дали шанс.
Хорошая книга не получится без редактора. Благодарю Кристен Уоттерсон (Kristen Watterson) за ее педантизм. Эта книга стала намного лучше благодаря вашим усилиям. И спасибо техническому редактору Робину Деусону (Robin Dewson), который играл роль защитника команды, за терпение и понимание на протяжении всего длительного процесса.
Благодарю Бирну Себарте (Birnou Sebarte') и Луиса Лазариса (Louis Lazaris) за то, что они тщательно откорректировали книгу от корки до корки. Спасибо Крису Койеру (Chris Coyier) за предисловие к ней.
Я также хотел бы поблагодарить технических рецензентов и друзей, которые нашли время, чтобы изучить мои проекты на разных этапах и отправить отзывы: Адама Раккиса (Adam Rackis), Ала Пезевски (Al Pezewski), Амита Ламба (Amit Lamba), Анто Аравинта (Anto Aravinth), Брайна Гайнеса (Brian Gaines), Дико Гольдони (Dico Goldoni), Джанкарло Массари (Giancarlo Massari), Гетца Хеллера (Goetz Heller), Арса Раваля (Harsh Raval), Джеймса Анайпакоса (James Anaipakos), Джеффри Лима (Jeffrey Lim), Джима Артура (Jim Arthur), Мэтью Хальверсона (Matthew Halverson), Митчелл Роблес-мл. (Mitchell Robles, Jr.), Нитина Варму (Nitin Varma), Патрика Гетца (Patrick Goetz), Фили Австрия (Phily Austria), Пьерфранческо Д’Орсогну (Pierfrancesco D’Orsogna), Рафаэля Кассемиро Фрейре (Rafael Cassemiro Freire), Рафаэля Фрейре (Rafael Freire), Сачина Синхи (Sachin Singhi), Таню Вильке (Tanya Wilke), Трента Уайтли (Trent Whiteley) и Уильяма Э. Уилера (William E. Wheeler). Ваши отзывы оказались очень полезны, так как книга попадет в руки разработчиков всех уровней квалификации.
Наконец, я хотел бы выразить огромную благодарность толковым людям из рабочей группы каскадных таблиц стилей W3C за работу над спецификациями CSS. Вы трудитесь над решением очень сложных задач, благодаря чему разработчикам не приходится с ними разбираться самостоятельно. Спасибо за ваши усилия по улучшению каскадных таблиц стилей и Всемирной паутины.
Об этой книге
Мир каскадных таблиц стилей непрерывно совершенствуется. Все больше и больше веб-разработчиков осознают, что, хотя они, как им кажется, знают CSS, до полного понимания им далеко. В последние годы язык сильно развился, поэтому даже те разработчики, которые когда-то были искусны в CSS, сегодня могут получить абсолютно новые навыки, чтобы наверстать упущенное. Данная книга призвана удовлетворить эти потребности: обеспечить глубокое владение языком и привести к успеху в новых разработках и применении новейших возможностей CSS.
Эта книга называется «CSS для профи», но это также всеобъемлющая книга. В тех случаях, когда какие-то понятия или принципы трудны либо, как правило, трактуются неправильно, я подробно объясняю, что они обозначают или как работают и почему именно так. Другие главы, возможно, не настолько исчерпывающи, но я дам достаточно сведений, чтобы вы могли эффективно работать и двигаться в правильном направлении, если захотите расширить свои знания. В целом эта книга заполнит пробелы в ваших теоретических познаниях.
Некоторые темы: анимация, типографика, гибкие контейнеры и даже CSS-стек — достойны отдельных книг. Мои цели — конкретизировать ваши знания, помочь ликвидировать пробелы в них и привить вам любовь к языку CSS.
Для кого предназначена книга
Прежде всего эта книга предназначена для разработчиков, которые устали сражаться с каскадными таблицами стилей и хотят действительно разобраться, как они работают. И неважно, они новички или имеют за плечами многолетний опыт.
Я рассчитываю, что у вас есть поверхностное знание языка HTML, CSS и отчасти JavaScript. Если вы знакомы с основами синтаксиса CSS, то, скорее всего, сможете понять эту книгу. Но в первую очередь она написана для разработчиков, которые некоторое время работали с CSS, столкнулись с проблемами и разочаровались. Код JavaScript я максимально упрощал, поэтому, изучая короткие листинги, вы все поймете.
Если вы дизайнер, который решил приоткрыть для себя мир веб-дизайна, то, подозреваю, тоже многое почерпнете из этой книги, хотя я не писал ее непосредственно для вас. По крайней мере вы научитесь лучше понимать разработчиков, с которыми будете сотрудничать.
Структура издания
Книга состоит из 16 глав, разделенных на четыре части. В части I мы поговорим об основах, сосредоточив внимание на некоторых деталях.
• Глава 1 охватывает каскадность и наследование. Эти понятия определяют, как стили применяются к элементам на странице.
• В главе 2 рассматриваются относительные единицы em и rem. Относительные единицы в CSS универсальны и важны, и эта глава научит вас работать с ними.
• В главе 3 рассматривается блочная модель, суть которой — управление размерами элементов на странице и объемом пространства между ними.
В части II я познакомлю вас с ключевыми инструментами для компоновки элементов на странице.
• Глава 4 погружает в принципы обтекания элементов макета. Мы создадим многоколоночную страницу и рассмотрим решения некоторых необычных проблем обтекания.
• В главе 5 говорится о Flexbox — способе гибкой верстки. Начнем мы с фундаментальных понятий, затем перейдем к практическим примерам.
• Глава 6 рассказывает о технологии верстки с помощью CSS-сетки. Она позволяет создавать макеты, которые ранее средствами каскадных таблиц стилей получить было невозможно.
• Глава 7 рассматривает позиционирование с использованием свойства position: абсолютное позиционирование, фиксированное позиционирование и многое другое. Это область, в которой многие разработчики сталкиваются с трудностями, поэтому им необходимо хорошо в ней разобраться.
• В главе 8 описывается адаптивный дизайн. Мы рассмотрим три ключевых принципа построения сайтов, работающих на экранах различных размеров и на широком спектре устройств.
В части III представлены некоторые передовые методы. Разместить элементы на странице желаемым образом — это одно, а организовать код так, чтобы его можно было понимать и поддерживать в будущем по мере развития веб-приложения, — совершенно другое. Из следующих двух глав вы узнаете о некоторых важных методах управления кодом.
• В главе 9 описано, как организовать каскадные таблицы стилей в модули, чтобы код стал многоразовым и удобным в сопровождении.
• В главе 10 рассказывается о создании библиотеки паттернов. Это важная часть использования и поддержки каскадных таблиц стилей в команде.
В части IV я познакомлю вас с миром дизайна. Мы рассмотрим важные соображения, касающиеся работы с дизайнером, и поговорим о том, как работать над дизайном самостоятельно, потому что иногда приходится и это делать.
• В главе 11 рассматриваются тени, градиенты и режимы смешивания. В совокупности эти эффекты позволяют создать элегантный пользовательский интерфейс.
• В главе 12 показано, как работать с контрастностью, цветом и пространством (воздухом). Эти детали — важный шаг на долгом пути от хорошего дизайна к отличному.
• Глава 13 посвящена типографике в Интернете — использованию веб-шрифтов для придания индивидуальности сайту или приложению.
• Глава 14 рассказывает, как наделить страницу переходами и анимацией, изменять форму, цвета и размеры элементов на странице.
• В главе 15 рассматриваются трансформации — важные инструменты, действующие совместно с переходами и анимацией. В этой главе обсуждаются также вопросы производительности анимации на странице.
• В главе 16 говорится об анимации ключевых кадров. Вы узнаете, как использовать сложную анимацию для взаимодействия с пользователем.
В конце книги приведены два приложения.
• Приложение А содержит перечень селекторов CSS всех типов.
• Приложение Б представляет собой введение в препроцессоры. Если вы еще не знакомы с ними, можете начать с этого приложения.
Я затаратил много усилий для того, чтобы подробно раскрыть все темы книги. Начну с самых основ, которые вам нужно знать. Далее темы опираются друг на друга. Во многих местах я ссылаюсь на ранние концепции и стараюсь связать их вместе, если это необходимо. Хотя я и добавил полезные справочные приложения, рекомендую читать главы по порядку.
Условные обозначения и файлы примеров
Эта книга содержит много примеров исходного кода как в пронумерованных листингах, так и в обычном тексте. В обоих случаях исходный код обозначается моноширинным шрифтом, чтобы отделить его от основного текста. Иногда он выделен полужирным моноширинным шрифтом, чтобы показать код, который изменился с предыдущих шагов, приведенных в той же главе, например, если к строке кода добавляется новая функция или в нее вносятся какие-то изменения.
Во многих случаях исходный код был переформатирован: я добавил переносы и переделал отступы, чтобы сэкономить пространство страницы. Кроме того, во многих случаях из исходного кода были удалены комментарии, если он описан в тексте. Большинство листингов сопровождаются примечаниями, которые выделяют важные понятия.
Каскадные таблицы стилей работают в тандеме с HTML. Я всегда предоставляю листинги с кодом, один для HTML, а другой — для CSS. В большинстве разделов для нескольких листингов CSS используется один и тот же HTML-код. Я научу вас изменять каскадные таблицы стилей на многих этапах и рассчитываю, что вы будете менять свою таблицу стилей по мере перехода от одного листинга к другому.
Исходный код файлов примеров из этой книги размещен в репозитории git на странице github.com/CSSInDepth/css-in-depth и сайте издательства по адресу www.manning.com/books/css-in-depth. На первых порах может показаться, что некоторых листингов не хватает, так как примеры требуют указания как HTML-, так и CSS-кода. Учитывайте, что в большинстве примеров я поместил каскадные таблицы стилей в HTML-файлы, добавляя элементы style. Это означает, что оба листинга, HTML и CSS, в репозитории объединяются в один файл.
Например, в главе 1 листинг 1.1 — это HTML-код, а листинг 1.2 — CSS-код стилей, которые предназначены для применения к этому HTML-коду. В репозитории оба листинга объединены в один файл с именем listing-1.2.html. В листинге 1.3 в этот CSS-код вносятся изменения, он включен в файл listing-1.3.html вместе с соответствующим HTML-кодом из листинга 1.1.
Версии браузеров
Кросс-браузерное тестирование — важная часть веб-разработки. Бо'льшая часть кода в этой книге поддерживается браузерами Internet Explorer 10 и 11, Microsoft Edge, Chrome, Firefox, Safari, Opera и почти всеми мобильными браузерами. Новые функции будут работать не во всех этих браузерах, что я буду особо отмечать.
То, что функция не поддерживается в определенном браузере, не означает, что ее нельзя использовать. Часто можно включить альтернативное поведение для старых браузеров, которые не поддерживают какой-либо новый функционал. Я расскажу о таких случаях.
Если вы хотите придерживаться примеров кода, которые описаны в книге, на своем компьютере, рекомендую работать в последней версии браузера Firefox или Chrome.
Об авторе
Кит Дж. Грант (Keith J. Grant) в настоящее время трудится старшим веб-разработчиком в корпорации Intercontinental Exchange, Inc. (ICE), где пишет и поддерживает CSS-код для корпоративных клиентов, в том числе Нью-Йоркской фондовой биржи. У него за плечами 11-летний опыт создания и поддержки профессиональных веб-приложений и сайтов, сочетающих технологии HTML, CSS и JavaScript. Кит — классический самоучка в плане работы с HTML- и CSS-кодом: до того как его приняли в штат компании, он потратил несколько лет, самостоятельно приобретая опыт веб-разработчика.
Менеджер пригласил его в команду веб-разработчиков именно из-за опыта работы с CSS, когда компании ICE понадобился редизайн корпоративных сайтов. Каскадные таблицы стилей позволяют создавать уникальные креативные сайты, а также сложные веб-приложения с громоздкими макетами.
Хотя Кит в первую очередь занимался разработкой на языке JavaScript, для всех компаний, где он трудился, он становился крайне важным человеком, поскольку отлично разбирался в каскадных таблицах стилей.
Иллюстрация на обложке
Иллюстрация на обложке книги «CSS для профи» — это работа французского художника Октава Пингвилли Л’Харидона, которая называется La Flamande («Фламандка»). Картина входит в коллекцию произведений художников XIX века, собранную Луисом Курмером и впервые представленную в Париже в 1842 году. Название коллекции — Les Fran
С тех пор такие кардинальные различия в одеяниях размылись и разнообразие, характеризующее регионы, столь богатое в прежние времена, исчезло. Сейчас трудно отличить друг от друга даже жителей разных континентов, не говоря уже о разных регионах страны и городах. Возможно, мы сменили культурные различия на более разнообразную личную и, безусловно, более многообразную и быстро развивающуюся технологическую жизнь.
В настоящее время, когда трудно отличить одну компьютерную книгу от другой, издательство Manning объединяет компьютерную литературу с выпущенными более двух столетий назад книгами, украшая обложки иллюстрациями, основанными на богатом разнообразии жизненного уклада людей тех времен.
Часть I. Обзор основных принципов
В части I подробно рассматриваются наиболее важные составляющие CSS — каскадность, относительные единицы и блочная модель. Из первых трех глав вы узнаете, как стили применяются к элементам на странице и как определяются размеры элементов. Всестороннее усвоение данных понятий — это база для всех последующих тем книги.
1. Каскадность, специфичность и наследование
В этой главе
• Четыре компонента каскадности.
• Разница между каскадностью и наследованием.
• Управление стилями, применяемыми к элементам.
• Распространенные недоразумения с сокращенными объявлениями.
CSS отличается от многих средств разработки программного обеспечения. Строго говоря, это не язык программирования, хотя он требует абстрактного мышления. Это не исключительно инструмент дизайна, хотя понадобится толика креатива. Каскадные таблицы стилей обеспечивают обманчиво простой декларативный синтаксис, но если вы использовали его при работе над крупными проектами, то знаете, что он способен перерасти в серьезную проблему.
Если требуется научиться делать что-то в обычном программировании, вы чаще всего знаете, что искать (например, «как найти элементы типа x в массиве»). С CSS не всегда легко решить проблему с помощью только одного запроса в Интернете. Даже когда вы можете это сделать, ответ часто от чего-то зависит. Чтобы добиться чего-либо, нередко нужно уметь обрабатывать разнообразные ситуации.
Первая часть книги начинается с рассмотрения фундаментальных принципов языка: каскадности, блочной модели и широкого набора доступных единиц измерения. Большинство веб-разработчиков знают о каскадности и блочной модели. Они знают о пикселах как о единицах, в которых можно измерять размер элементов, и, вероятно, слышали, что должны использовать единицы em. Но суть в том, что подобных тем очень много и поверхностного их рассмотрения недостаточно. Если вы решили изучить CSS, то должны сначала разобраться в фундаментальных понятиях, причем досконально.
Я знаю, что вам не терпится начать изучать современные и красивые правила CSS. Это очень интересный материал. Но сначала обратимся к основам. Я кратко расскажу о базовых вещах, с которыми вы, вероятно, уже знакомы, а затем мы подробно разберем каждую тему. Моя цель — укрепить фундамент, на котором строится ваше понимание CSS.
В этой главе начнем с каскадности. Я сформулирую, как она действует, а затем покажу, как работать с каскадностью на практике. После этого мы рассмотрим смежную тему — наследование. Я буду придерживаться этого плана, говоря о свойствах и некоторых распространенных недоразумениях, возникающих по поводу них.
Все эти темы касаются применения желаемых стилей к нужным элементам. Здесь можно допустить много нелепых ошибок. Глубокое понимание этих тем позволит лучше контролировать работу вашего CSS-кода, чтобы он делал то, что вы хотите. Если повезет, вам даже понравится работать с CSS.
1.1. Каскадность
По сути, CSS — это объявленные правила: мы хотим, чтобы в различных условиях происходили определенные вещи. Если этот класс добавлен к тому элементу — применить такие-то стили. Если элемент X является потомком элемента Y — вот эти. Затем браузер принимает эти правила, определяет, какие из них действуют, в каком порядке и в каком месте, и использует их при визуализации страницы.
Когда рассматриваются небольшие примеры, этот процесс обычно не вызывает сложностей. Но по мере увеличения размера таблицы стилей или количества веб-страниц, к которым вы ее применяете, код может неожиданно быстро усложниться. В CSS существует несколько способов делать одно и то же. При изменении структуры HTML или использовании стилей на разных страницах результаты могут оказаться совершенно разными. Это зависит от того, какое решение задействовано. Ключевая часть разработки CSS сводится к написанию правил таким образом, чтобы они были предсказуемыми.
Первый шаг — разобраться в том, как именно браузер понимает ваши правила. Каждое из них может быть простым, но что происходит, когда два правила противоречат друг другу в том, как форматировать элемент? Вы можете обнаружить, что одно из ваших правил не делает того, что вы ожидаете, поскольку с ним конфликтует другое правило.
Предсказывать, как поведут себя правила, реально, если понимать принципы каскадности. Продемонстрирую это. Создайте простенькую шапку типа той, которая находится в верхней части веб-страницы (рис. 1.1). В шапке указано название сайта, под ним — навигационные ссылки. Последняя ссылка окрашена в оранжевый цвет — так выделяются важные элементы. (Внимание: в печатной версии книги изображения черно-белые.)
Рис. 1.1. Название страницы и навигационные ссылки
Для начала создайте HTML-документ и таблицу стилей с именем styles.css. Добавьте код, показанный в листинге 1.1, в HTML-файл.
Примечание
Репозиторий, содержащий все примеры для этой книги, доступен для загрузки по адресу github.com/CSSInDepth/css-in-depth. В нем вы найдете HTML-файлы со встроенными правилами CSS.
Листинг 1.1. Разметка для шапки страницы
Если к одному и тому же элементу страницы применяется два правила или больше, это может привести к конфликту объявлений. Листинг 1.2 показывает, как это происходит. В нем три набора правил задают шрифт для названия страницы. Название не может отображаться тремя разными шрифтами одновременно. Какой конкретно будет использован? Добавьте этот листинг в свой CSS-файл, чтобы узнать ответ.
Инструкции с конфликтующими объявлениями могут следовать одна за другой или оказаться разбросанными по всей таблице стилей. В любом случае, учитывая HTML-код, все они нацелены на один и тот же элемент.
Листинг 1.2. Конфликтующие объявления
Все три набора правил пытаются установить для названия собственное семейство шрифтов. Кто победит? Чтобы получить ответ, браузер следует конкретному набору правил, поэтому результат оказывается предсказуем. В этом случае правила указывают, что выигрывает второе объявление, с селектором идентификатора. Название будет оформлено рубленым шрифтом (sans-serif), применяемым по умолчанию (рис. 1.2).
Рис. 1.2. Селектор идентификатора выигрывает у других наборов правил, отображая название страницы рубленым шрифтом
Каскадность — так называется этот набор правил. Каскадность определяет способы разрешения конфликтов, и это фундаментальная часть работы CSS. Большинство опытных разработчиков имеют общее представление о каскадности, однако не всегда правильно интерпретируют ее.
Разберемся с каскадностью. Когда объявления конфликтуют, для устранения проблемы нужно учесть три показателя.
1. Источник стилей — место их расположения. Ваши стили накладываются на стили браузера, применяемые по умолчанию.
2. Специфичность селекторов — то, какие селекторы имеют приоритет над другими.
3. Исходный порядок — порядок, в котором стили объявляются в таблице стилей.
Правила каскадирования рассматривают их именно в этом порядке. Рисунок 1.3 обобщенно показывает, как они работают.
Рис. 1.3. Обобщенная блок-схема каскадности с указанием приоритета объявления
Эти правила определяют поведение браузера при появлении какой-либо неясности с CSS. Давайте разберемся с ними.
| Быстрое ознакомление с терминологией Возможно, вы уже знакомы с основной терминологией, относящейся к синтаксису CSS. Я не буду углубляться в эту тему, но, поскольку стану использовать термины в книге, напомню, что они означают. Далее приведена строка CSS-кода. Она называется объявлением. Объявление состоит из свойства (color) и значения (black): color: black; Свойства не следует путать с атрибутами, которые относятся к синтаксису HTML. Например, в элементе <a href="/"> часть href — это атрибут элемента a. Группа объявлений внутри фигурных скобок называется блоком объявлений. Блоку объявлений предшествует селектор (в данном случае body): body { color: black; font-family: Helvetica; } В совокупности селектор и блок объявлений называются набором правил. Набор правил также называют правилом, хотя, по моему мнению, это слово редко используется в таком смысле. Обычно оно стоит во множественном числе и обозначает набор стилей. Наконец, @правила — это языковые конструкции, начинающиеся с символа @, такие как запросы @import или @media. |
1.1.1. Источник стилей
Таблицы стилей, добавляемые вами на вашу веб-страницу, не единственные, к которым обращается браузер. Существуют разные типы, или источники, таблиц стилей. Созданные вами таблицы называются авторскими, существуют также браузерные стили — стили браузера по умолчанию. Браузерные стили имеют более низкий приоритет, поэтому ваши стили заменяют их.
Примечание
Некоторые браузеры позволяют пользователям определять свои стили. Это третий источник стилей, по приоритету они занимают промежуточное положение между браузерными и авторскими стилями. Пользовательские стили применяются редко и не поддаются контролю, поэтому для упрощения я их пропускаю.
Браузерные стили различаются в разных браузерах, но обычно выполняют одни и те же задачи: форматируют заголовки (от h1 до h6) и абзацы (p), задают верхнее и нижнее значения полей, форматируют списки (ol и ul), устанавливают отступ слева, определяют цвет ссылок и размеры шрифта по умолчанию.
Браузерные стили
Снова взглянем на страницу из примера (рис. 1.4). Название выполнено рубленым шрифтом, что определено теми стилями, которые вы добавили. Браузерные стили определяют ряд других параметров: для списка задан левый отступ, для отображения маркеров — свойство list-style-type со значением disc. Ссылки окрашены в синий цвет и подчеркнуты. У заголовка и списка есть верхние и нижние поля.
Рис. 1.4. Браузерные стили устанавливают форматирование по умолчанию для элементов на веб-странице
После применения браузерных стилей браузер задействует ваши авторские стили. Благодаря этому указанные вами объявления замещают браузерные. Если вы в своем HTML-файле ссылаетесь на несколько таблиц стилей, все они имеют один источник — авторский.
Обычно браузерные стили устанавливают подходящие параметры, поэтому ничего неожиданного не происходит. Если вам не нравится, как они влияют на то или иное свойство, задайте собственное значение в таблице стилей. Сделаем это сейчас. Можете переопределить некоторые браузерные стили, добавляющие не то форматирование, какое вы хотите, чтобы ваша страница выглядела, например, как на рис. 1.5.
Рис. 1.5. Авторские стили переопределяют браузерные, поскольку имеют более высокий приоритет
В листинге 1.3 я удалил конфликтующие объявления font-family из предыдущего примера, добавил новые для установки цветов и переопределил браузерные настройки полей, отступа списка и маркеров.
Листинг 1.3. Переопределение браузерных стилей
Отредактируйте таблицу стилей, чтобы она соответствовала этим изменениям.
Если вы уже давно работаете с CSS, то, вероятно, уже переопределяли браузерные стили. В этот момент вы пользовались таким принципом каскадности, как определение источника стиля. Ваш стиль всегда будет переопределять браузерный, потому что у них разные источники.
Примечание
Возможно, вы заметили, что в данном коде я использовал селекторы идентификатора. Но в работе лучше не делать этого, о чем я вкратце еще расскажу.
Ключевое слово important
Объявления, отмеченные как важные, стоят особняком при определении источника стилей. Объявление может быть помечено как важное с помощью слова !important, указанного в конце, перед точкой с запятой:
color: red !important;
Объявление со словом !important рассматривается как источник с более высоким приоритетом. Далее стили перечислены в порядке убывания приоритета.
1. Важные авторские стили.
2. Авторские стили.
3. Браузерные стили.
Каскадность самостоятельно разрешает конфликты для всех свойств любого элемента на странице. Например, вы установили полужирный шрифт для абзацев текста. Тогда значения верхнего и нижнего полей будут применены согласно браузерным стилям, если вы явно не переопределите их. Приоритеты начинают играть важную роль, когда речь заходит об анимациях и переходах, так как те вводят дополнительные источники стилей. Аннотация !important — интересная причуда CSS, к которой мы еще вернемся.
1.1.2. Специфичность селекторов
Если конфликт объявлений не может быть разрешен на основании их источника, браузер попытается решить проблему, рассматривая их специфичность. Понять принципы специфичности очень важно. Вы можете долго работать, не вникая в источники стилей, потому что 99 % стилей на вашем сайте происходят из одного источника. Но если вы не знакомы с понятием специфичности, то дальше вам будет трудно. К сожалению, это часто упускают из виду.
Браузер оценивает специфичность в два этапа: сначала проверяет стили, встроенные в HTML-код (их еще называют строчными), затем стили, применяемые с помощью селекторов.
Встроенные стили
Если для задания стилей конкретного элемента в HTML-коде используется атрибут style, то объявления применяются только к данному элементу. Это, по сути, объявления с ограниченной областью действия, которые переопределяют любые объявления, задаваемые в вашей таблице стилей или теге <style>. Во встроенных стилях нет селектора, потому что они действуют непосредственно на элемент, на который нацелены.
Вы хотите, чтобы ссылка Акции! в меню навигации была оранжевой (рис. 1.6)? Рассмотрим несколько способов решения задачи, начиная с применения встроенных стилей (листинг 1.4).
Рис. 1.6. Встроенные стили переопределяют стили, применяемые с помощью селекторов
Листинг 1.4. Встроенные стили, переопределяющие объявления из других источников
Чтобы увидеть результат в своем браузере, отредактируйте код в соответствии с приведенным листингом. (Вы отмените это изменение за секунду.)
Чтобы переопределить встроенные объявления стилей, необходимо добавить к нужному объявлению ключевое слово !important, изменив его приоритет на более высокий. Если же встроенные стили отмечены как важные, их не получится так переопределить. Рекомендуется сделать это из таблицы стилей. Отмените изменение, и мы рассмотрим более удачные способы.
Специфичность селекторов
Вторая составляющая специфичности касается селекторов. Например, селектор с двумя классами более специфичен, чем с одним. Если одно объявление задает оранжевый фон, а другое, более специфичное, меняет его, скажем, на бирюзовый, то в браузере вы увидите бирюзовый цвет.
Посмотрим, что произойдет, если мы попытаемся окрасить ссылку в оранжевый цвет с помощью простого селектора классов. Обновите заключительную часть таблицы стилей, чтобы она соответствовала коду, приведенному в листинге 1.5.
Листинг 1.5. Селекторы разной специфичности
Не сработало! Все ссылки остаются бирюзовыми. Почему? Первый селектор здесь специфичнее, чем второй. Он состоит из идентификатора и тега, в то время как второй — из класса. Однако можно сделать еще кое-что вместо того, чтобы учитывать, какой селектор длиннее.
Различные типы селекторов также имеют особенности. К примеру, селектор идентификатора специфичнее селектора класса. На самом деле один идентификатор специфичнее селектора с любым количеством классов. Аналогично селектор класса специфичнее селектора тега, называемого также селектором типа.
Итак, существуют следующие правила специфичности.
1. Наиболее специфичным будет селектор с идентификаторами. Чем больше идентификаторов, тем специфичнее будет селектор.
2. Далее идет селектор с наибольшим количеством классов.
3. Следующий по специфичности будет селектор с наибольшим количеством тегов.
Рассмотрим селекторы, показанные в листинге 1.6 (но не добавляйте их в свой код). Они написаны в порядке возрастания специфичности.
Листинг 1.6. Селекторы с возрастающей специфичностью
Наиболее специфичный селектор —
Примечание
Селекторы псевдоклассов (например, :hover) и селекторы атрибутов (например, [type = "input"]) специфичны в той же степени, что и селектор класса. Универсальный селектор (*) и комбинаторы (>, +, ~) не влияют на специфичность.
Если вы добавили в CSS объявление, но оно не вызвало никакого эффекта, то, скорее всего, более специфичное правило переопределяет его. Зачастую разработчики пишут селекторы идентификаторов, не понимая, что создают более высокий уровень специфичности, который позже будет трудно переопределить. Если нужно переопределить стиль, примененный с помощью селектора идентификатора, придется использовать другой идентификатор.
Это концепция проста, но если вы не разбираетесь в специфичности, то можете сойти с ума, пытаясь выяснить, почему одно работает, а другое — нет.
Замечание по поводу специфичности
Обычно специфичность выражается в числовой форме, чаще через запятую. Например, значение «1,2,2» указывает на специфичность одного идентификатора, двух классов и двух тегов. Сначала перечисляются идентификаторы с наивысшим приоритетом, за которыми следуют классы и далее теги.
Селектор #page-header #page-title содержит два идентификатора без классов и тегов. Мы можем представить эту специфичность в виде «2,0,0». Селектор ul li с двумя тегами, но без идентификаторов и классов имеет специфичность «0,0,2». В табл. 1.1 показаны селекторы из листинга 1.6.
Таблица 1.1. Различные селекторы и их особенности
| Селектор |
Идентификаторы |
Классы |
Теги |
Нотация |
| html body header h1 |
0 |
0 |
4 |
0,0,4 |
| body header.page-header h1 |
0 |
1 |
3 |
0,1,3 |
| .page-header .title |
0 |
2 |
0 |
0,2,0 |
| #page-title |
1 |
0 |
0 |
1,0,0 |
Теперь возникает вопрос: как сравнить числа, чтобы определить, какой селектор специфичнее? Специфичность «1,0,0» имеет приоритет над специфичностью «0,2,2» и даже «0,10,0», потому что первое число (идентификатор) имеет более высокий приоритет.
Иногда для записи используют четыре числа, добавляя цифру 0 или 1 в начале значения и указывая таким образом наличие встроенных стилей. В этом случае строчный стиль имеет специфичность «1,0,0,0». Он будет переопределять стили со специфичностью «0,1,2,0» и т.п.
Специфичность на практике
Попытка установить оранжевый фон с помощью селектора .featured успехом не увенчалась. Селектор #main-nav содержит идентификатор, который переопределяет селектор классов (специфичность «1,0,1» и «0,1,0»). Исправить это можно разными способами. Рассмотрим несколько вероятных изменений.
Самый быстрый способ решения проблемы заключается в том, чтобы добавить ключевое слово !important к объявлению, которое вы хотите применить. Измените код объявления следующим образом (листинг 1.7).
Листинг 1.7. Первое возможное решение проблемы
Прием работает, потому что аннотация !important придает объявлению более высокий приоритет. Способ простой, но наивный. Так поступить можно, но в будущем вероятны проблемы. Если вы добавите ключевое слово !important к нескольким объявлениям, что произойдет, если понадобится задать более высокий приоритет стилям, уже имеющим аннотацию !important? Если вы добавите несколько объявлений !important, то будут применяться обычные правила определения источника и специфичности. В конечном счете вы вернетесь в исходную позицию, только с аннотацией!important в множестве объявлений.
Определим способ получше. Вместо того чтобы пытаться обойти правила специфичности селектора, направим их работу в нужное русло. Как вы смотрите на то, чтобы повысить специфичность селектора? Обновите код правил в своей каскадной таблице стилей следующим образом (листинг 1.8).
Листинг 1.8. Второе возможное решение проблемы
Этот способ тоже работает. Теперь у вашего селектора есть один идентификатор и один класс, формирующие специфичность «1,1,0», что выше, чем #main-nav (специфичность «1,0,1»), поэтому оранжевый цвет фона применяется к элементу.
Тем не менее есть способ сделать еще лучше. Посмотрим, реально ли вместо повышения специфичности второго селектора понизить специфичность первого. У элемента также есть класс <ul id="main-nav" class="nav">, поэтому можно изменить CSS-код, чтобы нацелиться на элемент с помощью его имени класса, а не идентификатора. Измените строку #main-nav на .nav в своих селекторах, как показано в листинге 1.9.
Специфичность селекторов понижена. Специфичность оранжевого фона достаточно высока для того, чтобы переопределить бирюзовый цвет.
Как видно из этих примеров, специфичность нередко становится своего рода «гонкой вооружений». Это особенно актуально для крупных проектов. Обычно лучше всего сохранять более низкую специфичность, если возможно, и тогда, если нужно будет переопределить что-то, вы сможете решить проблему несколькими способами.
Листинг 1.9. Третье возможное решение проблемы
1.1.3. Исходный порядок
Третий и последний показатель при определении каскадности — исходный порядок. Если источник и уровень специфичности одинаковы, то объявление, которое указано позже в таблице стилей или находится в таблице стилей, на которую ссылаются на странице позже, имеет больший приоритет.
Это означает, что вы можете менять исходный порядок, чтобы форматировать ссылку Акции!. Если добавите два конфликтующих селектора одинаковой специфичности, победит последний. Рассмотрим четвертый вариант решения проблемы (листинг 1.10).
Листинг 1.10. Четвертый способ решения проблемы
В этом коде специфичности идентичны. Порядок определяет, какое объявление применяется к ссылке Акции!, в результате отображается оранжевый цвет.
Это решение проблемы может породить новую сложность: хотя код кнопки Акции! внутри объявления nav выглядит корректным, что произойдет, если вы захотите применить класс featured к другой ссылке в другой позиции страницы, вне nav? Получите странное сочетание стилей: белый текст на оранжевом фоне, увеличенные отступы и закругленные углы в оформлении ссылок на панели навигации (рис. 1.7).
Рис. 1.7. Класс featured вне объявления nav дает неправильный результат
В листинге 1.11 показана разметка, создающая такое форматирование. Теперь на элемент нацелен только второй селектор, но не первый, что приводит к нежелательному результату. Нужно решить, хотите ли вы, чтобы этот оранжевый стиль использовался за пределами nav, и если да — убедиться, что к нему применяются все нужные стили.
Листинг 1.11. Ссылка featured за пределами nav
На сайте, схожем с показанным в примере, я бы придерживался третьего варианта решения проблемы (см. листинг 1.9). Разрабатывая сайт, нужно продумывать и другие (в иных позициях сайта) элементы и их форматирование. Вероятно, вам следует поместить аналогичную ссылку в иных разделах сайта. В этом случае, думаю, как нельзя лучше подойдет четвертый вариант (см. листинг 1.10) с добавлением стилей для поддержки класса featured в других местах страницы.
Очень часто в CSS, как я уже говорил, все «зависит от обстоятельств». Существует много путей, ведущих к одному и тому же конечному результату. Рекомендуется рассмотреть несколько вариантов и продумать последствия каждого из них. При возникновении проблемы форматирования я часто решаю ее в два этапа: во-первых, выясняю, какие объявления будут применяться корректно, во-вторых, думаю о возможных способах структурирования селекторов и выбираю тот, который наилучшим образом решает мои задачи.
Форматирование ссылок и исходный порядок
Когда вы начали изучать каскадные таблицы стилей, то узнали, что селекторы для форматирования ссылок следует указывать в определенном порядке. Ведь порядок влияет на каскадность. В листинге 1.12 показаны стили ссылок на странице в правильном порядке.
Листинг 1.12. Стили ссылок
a:link {
color: blue;
text-decoration: none;
}
a:visited {
color: purple;
}
a:hover {
text-decoration: underline;
}
a:active {
color: red;
}
Каскадность — причина того, что этот порядок имеет значение: стили, указанные позже, переопределяют ранние стили с той же специфичностью. Если два подобных стиля или более одновременно относятся к одному и тому же элементу, последний переопределяет предыдущие. Если пользователь наводит указатель мыши на посещенную ссылку, стиль наведения получает приоритет над стилем посещенной ссылки. Если пользователь активизирует ссылку, то есть щелкает на ней кнопкой мыши, стиль активной ссылки становится приоритетным над стилем наведения.
Запомните порядок применения стилей ссылок: непосещенная, посещенная, наведение, активная. Обратите внимание: если вы измените один из селекторов для коррекции специфичности, это приведет к сбою и вы получите неожиданные результаты.
Каскадные значения
Браузер проверяет три параметра: источник, специфичность и порядок — для каждого свойства, применяемого к любому элементу на странице. Объявление, которое «побеждает» каскадность, называется каскадным значением. На каждое свойство любого элемента приходится не более одного каскадного значения. Определенный абзац (p) на странице может иметь верхнее и нижнее поля, но не два разных верхних или нижних поля. Если CSS задает различные значения для одного свойства, то при визуализации элемента каскадность выберет только одно. Это каскадное значение.
|
|
Каскадное значение — значение определенного свойства, применяемого к элементу в результате каскадности. |
Если свойство для элемента не указано, то он не имеет каскадного значения для этого свойства. Например, тот же абзац не имеет границ или отступов.
1.1.4. Два правила
Существует два распространенных правила работы с каскадностью.
1. Не используйте идентификаторы в селекторе. Даже один идентификатор усиливает специфичность. Когда требуется переопределить селектор, может не оказаться другого идентификатора, который реально задействовать, поэтому вам придется скопировать исходный селектор и добавить другой класс, чтобы отличить его от того, который вы пытаетесь переопределить.
2. Не используйте аннотацию !important. Ее еще труднее переопределить, чем идентификатор, и, как только вы ее примените, нужно будет добавлять ее каждый раз, когда захотите переопределить исходное объявление, и тогда все равно придется иметь дело со специфичностью.
Эти два правила хороши, но годятся не на все случаи жизни. Никогда (за некоторыми исключениями) не используйте их, если нужно разобраться с проблемами специфичности.
| Главное о главном Я настоятельно рекомендую: создавая модуль JavaScript для последующего распространения (например, пакет NPM), не задействуйте стили, встроенные в JavaScript, когда этого можно избежать. Если вы это сделаете, разработчики, применяющие ваш пакет, будут вынуждены либо принять ваши стили без изменений, либо использовать аннотацию !important для каждого свойства, которое они захотят изменить. Вместо этого добавьте в пакет таблицу стилей. Если ваш компонент должен динамически менять стили, почти всегда предпочтительнее задействовать JavaScript для добавления и удаления классов элементов. Кроме того, пользователи смогут отредактировать таблицу стилей как им нравится, не сталкиваясь с конфликтами специфичности. |
За последние несколько лет было разработано немало практических методик, призванных помочь в управлении специфичностью селекторов. Мы подробно рассмотрим их в главе 9. Там я больше расскажу о работе со специфичностью, в том числе о том, когда приемлемо применять ключевое слово !important.
Теперь, когда мы разобрались с каскадностью, перейдем к наследованию.
1.2. Наследование
Существует еще один принцип, по которому к элементу применяются стили, — наследование. Каскадность часто упоминается наряду с наследованием. Хотя эти две темы взаимосвязаны, вы должны разбираться в каждой из них по отдельности.
Если элемент не имеет каскадного значения для данного свойства, он может наследовать его от родительского элемента (предка). Рядовой пример — применение свойства font-family к элементу body. Все дочерние элементы (потомки) внутри будут наследовать этот шрифт, и вам не нужно явно применять его к каждому элементу на странице. На рис. 1.8 показано, как наследование распространяется по дереву DOM.
Однако не все свойства наследуются, а по умолчанию — только определенные. В общем, это свойства, которые вы хотите унаследовать. Прежде всего относящиеся к шрифтам: color, font, font-family, font-size, font-weight, font-variant, font-style, line-height, letter-spacing, text-align, text-indent, text-transform, white-space и word-spacing.
Наследуются и некоторые другие, такие как свойства списков: list-style, list-style-type, list-style-position и list-style-image. Свойства границ таблицы border-collapse и border-spacing также наследуются. Обратите внимание на то, что они управляют поведением границ таблиц и отличаются от часто применяемых свойств для форматирования границ нетабличных элементов. (Нам же не нужно, чтобы элемент div передавал свои стили границ каждому дочернему элементу.) Вот практически полный список.
Рис. 1.8. Наследуемые свойства передаются по дереву DOM от предка к потомкам
Вы можете воспользоваться наследованием на своей странице, применив шрифт к элементу body и позволяя его дочерним элементам наследовать это значение (рис. 1.9).
Рис. 1.9. Добавьте свойство font-family к body, и пусть все дочерние элементы наследуют одно и то же значение
Добавьте этот код в начало таблицы стилей, чтобы применить правило к своей странице (листинг 1.13).
Листинг 1.13. Применение свойства font-family к родительскому элементу
Стиль используется на всей странице, так как назначен всему ее телу. Но вы можете настроить определенный элемент на странице, и данный стиль будут наследовать только его потомки. Наследование станет применяться от элемента к элементу, пока не будет переопределено каскадным значением.
| Инструменты разработчика Уследить за наследуемыми значениями, переопределяющими друг друга, может быть очень сложно. Если вы еще не знакомы с инструментами разработчика своего браузера, научитесь их использовать. Инструменты разработчика наглядно демонстрируют, какие правила к каким элементам применяются и почему. Каскадность и наследование — абстрактные понятия, инструменты разработчика — лучший из известных мне способов разобраться в них. Откройте панель инструментов разработчика, щелкнув правой кнопкой мыши на элементе на странице, и выберите в контекстном меню команду с названием наподобие Исследовать элемент (Inspect element). Далее представлен пример панели инструментов разработчика.
Инспектор стилей показывает все ориентированные на выбранный элемент селекторы, упорядоченные согласно специфичности. Внизу перечислены все наследуемые свойства. Так наглядно показаны каскадность и наследование выбранного элемента. Есть много неявных признаков, которые помогут вам понять, что происходит со стилями элемента. Стили, расположенные ближе к верхней части панели, переопределяют следующие за ними. Переопределенные (замещенные) стили зачеркнуты. Имя файла таблицы стилей и номер строки в ней для каждого набора правил показаны справа, чтобы их легко было найти в исходном коде. Так вы узнаете, какой именно элемент какие стили унаследовал и где они расположены. Можете также ввести запрос в поле Фильтр стилей, чтобы скрыть все, кроме определенного набора объявлений. |
1.3. Специальные значения
Существует два специальных значения, которые можно применять к любому свойству, чтобы управлять каскадностью: inherit и initial. Рассмотрим их.
1.3.1. Ключевое слово inherit
Иногда необходимо унаследовать стиль, когда каскадное значение замещает его. В этом случае используйте ключевое слово inherit. Заместите одно значение другим, чтобы элемент унаследовал его от своего родителя.
Предположим, на страницу добавлен светло-серый подвал (footer, иногда еще называют колонтитулом). В нем могут быть размещены какие-то ссылки, но вы не хотите, чтобы они сильно выделялись, потому что подвал не слишком важная часть страницы. Таким образом, вы делаете ссылки в нем темно-серыми (рис. 1.10).
Рис. 1.10. Ссылка Условия эксплуатации с унаследованным серым цветом шрифта
Добавьте приведенную далее разметку в конец страницы. На обычной странице будет больше контента между шапкой и подвалом, но для нашего примера этого достаточно.
Листинг 1.14. Подвал со ссылкой
<footer class="footer">
© 2019 Профессиональная техника для обжарщиков —
<a href="/terms-of-use">Условия эксплуатации</a>
</footer>
По умолчанию шрифт ссылок будет того цвета, который установлен для всех ссылок на странице (если вы этого не сделаете, его определят браузерные стили), в том числе ссылки Условия эксплуатации. Чтобы окрасить ссылку в подвале в серый цвет, нужно переопределить этот ее стиль. Добавьте в таблицу стилей следующий код (листинг 1.15).
Третий набор правил переопределяет синий цвет ссылки, передавая ссылке, расположенной в подвале, каскадное значение inherit. Таким образом, она наследует цвет от родительского элемента footer.
Преимущество здесь в том, что ссылка будет менять цвет вместе с остальной частью подвала, если такие изменения будут внесены. (На это способно повлиять изменение второго набора правил или указание нового стиля в другой позиции.) Если, например, текст в подвале на других страницах будет более темным, то и ссылка окрасится в тот же цвет.
Листинг 1.15. Значение inherit
Вы можете использовать ключевое слово inherit и для принудительного наследования свойства, которое обычно не наследуется, например параметров границ или отступов. Этот прием применяется на практике в нескольких случаях, и вы увидите один из них в главе 3, когда мы займемся блочной моделью.
1.3.2. Ключевое слово initial
Иногда к элементу применяются стили, которые хотелось бы отменить. Это делается при добавлении ключевого слова initial. Каждое свойство CSS имеет начальное, или применяемое по умолчанию, значение. Если вы присваиваете свойству значение initial, оно сбрасывается до начального. Как будет выглядеть подвал, если вы присвоите значение initial, а не inherit, показано на рис. 1.11.
Рис. 1.11. Начальное значение свойства color — black
Внимание!
Ключевое слово initial поддерживается не во всех версиях браузеров Internet Explorer или Opera Mini. Во всех других браузерах, включая Edge, созданный корпорацией Microsoft как преемник Internet Explorer 11, оно работает.
CSS-код для подвала на рис. 1.11 показан в листинге 1.16. Поскольку черный цвет — начальное значение свойства color в большинстве браузеров, color: initial — это эквивалент правила color: black.
Листинг 1.16. Значение initial
.footer a {
color: initial;
text-decoration: underline;
}
Его преимущество в том, что вам не нужно задумываться об указании каких-то специальных значений в коде. Если вы хотите удалить заданную границу элемента, установите border: initial. Если нужно восстановить исходную ширину элемента, используйте код width: initial.
Возможно, у вас осталась привычка устанавливать значение auto для сброса. Фактически для достижения того же результата применяется правило width: auto. Это связано с тем, что ширина по умолчанию — auto.
Однако важно отметить, что auto — значение по умолчанию не для всех свойств. Например, строки border-width: auto и padding: auto недопустимы и, следовательно, не действуют. Вы могли бы потратить некоторое время, чтобы определить начальные значения этих свойств, но обычно проще задействовать ключевое слово initial.
Примечание
Объявление display: initial эквивалентно коду display: inline. Оно не будет определено как display: block независимо от того, к элементу какого типа вы его применяете. Это потому, что ключевое слово initial выполняет сброс до начального значения для свойства, а не элемента, а inline — значение по умолчанию для свойства display.
1.4. Сокращенная запись свойств
Сокращенная запись свойств — это присвоение значений нескольких свойств одновременно. Например, font — это сокращенное свойство, позволяющее задать несколько свойств шрифта. Свойства font-style, font-weight, font-size, lineheight и font-family определяет следующее объявление:
font: italic bold 18px/1.2 "Helvetica", "Arial", sans-serif;
Аналогично:
• background — сокращенная запись свойств фона background-color, background-image, background-size, background-repeat, background-position, background-origin, background-chip и background-attachment;
• border — сокращенная запись свойств border-width, border-style и border-color;
• border-width — сокращенная запись свойств top, right, bottom и left ширины границ.
Сокращенные записи свойств полезны, они делают код кратким и понятным, но некоторые подводные камни здесь все-таки есть.
1.4.1. Остерегайтесь сокращений, скрыто переопределяющих другие стили
Большинство сокращенных записей свойств позволяют опускать определенные значения и указывать только нужные. Однако важно знать, что пропущенные свойства все равно задаются — им присваиваются начальные значения. Это может скрыто отменять стили, которые вы указали в других правилах. Если, например, нужно использовать запись font для названия страницы без указания свойства font-weight, значение normal для ширины шрифта все равно будет применено (рис. 1.12).
Рис. 1.12. Сокращенные записи свойств сбрасывают пропущенные свойства до их начальных значений
Добавьте код из листинга 1.17 в таблицу стилей, чтобы посмотреть, как это происходит.
Листинг 1.17. Сокращенная запись свойства, определяющая все соответствующие значения
h1 {
color: #2f4f4f;
margin-bottom: 10px;
font-weight: bold;
}
.title {
font: 32px Helvetica, Arial, sans-serif;
}
На первый взгляд может показаться, что код <h1 class = "title"> сделает шрифт заголовка полужирным, но это не так. Примененные стили эквивалентны стилям из следующего кода (листинг 1.18).
Листинг 1.18. Полный эквивалент сокращенной записи свойства из листинга 1.17
Это означает, что в результате применения данных стилей к элементу h1 шрифт отображается в обычном, а не в полужирном начертании. Запись способна переопределять и другие стили шрифта, которые в противном случае были бы унаследованы от родительского элемента. Из всех сокращенных записей свойств font чаще всего вызывает проблемы, поскольку определяет очень широкий набор параметров. По этой причине я избегаю использовать указанное свойство во всех случаях, кроме установки общих стилей в теле страницы. Вы можете столкнуться с данной проблемой, применяя и другие сокращенные записи свойств, поэтому учитывайте эту особенность.
1.4.2. Порядок записи сокращенных значений
Сокращенные записи свойств могут быть гибкими, когда речь заходит о порядке указания вами значений. Вы можете использовать код border: 1px solid black или border: black 1px solid, в обоих случаях результат будет идентичен. Так происходит потому, что браузеру ясно, какое значение определяет ширину, какое — цвет, а какое — стиль границы.
Но есть много свойств, когда значения могут трактоваться неоднозначно. В этих случаях порядок указания значений важен. Следует соблюдать его при вводе сокращенных записей свойств.
Вверху, справа, внизу, слева
Сокращенные записи свойств вынуждают разработчиков запоминать порядок перечисления значений, когда дело касается свойств margin и padding или некоторых свойств границ, которые определяют значения для каждой из четырех сторон элемента. Для них значения записываются по часовой стрелке, начиная сверху — top.
Порядок необходимо запомнить, чтобы избежать потенциальных проблем. Навигационные ссылки, показанные на рис. 1.13, имеют следующие отступы: верхний — 10 пикселов, справа — 15 пикселов, снизу — 0, слева —5 пикселов. Выглядит некрасиво и неровно, но зато демонстрирует принцип работы сокращенной записи.
Рис. 1.13. Элементы с различными отступами со всех сторон
В листинге 1.19 показан CSS-код для этих ссылок.
Листинг 1.19. Указание отступов со всех сторон элемента
Свойства, значения которых указаны в этом порядке, также поддерживают сокращенную запись. Если объявление закончилось прежде, чем одной из четырех сторон было присвоено значение, сторона без значения использует указанное для противоположной стороны. Задайте три значения, и левая и правая стороны будут соответствовать второму значению. Укажите два значения, и верхняя и нижняя стороны будут соответствовать первому значению, а левая и правая — второму. Если вы укажете только одно значение, оно будет применяться ко всем четырем сторонам. Таким образом, следующие объявления идентичны:
padding: 1em 2em;
padding: 1em 2em 1em;
padding: 1em 2em 1em 2em;
Эти объявления также идентичны друг другу:
padding: 1em;
padding: 1em 1em;
padding: 1em 1em 1em;
padding: 1em 1em 1em 1em;
Многие разработчики испытывают наибольшие затруднения, когда нужно задать три значения. В этом случае указываются верхняя, правая и нижняя стороны. Поскольку для левой значение не указано, оно будет таким же, как и для правой, — второе значение будет применено к обеим сторонам. Таким образом, правило padding: 10px 15px 0 создает отступы по 15 пикселов как с левой, так и с правой стороны, тогда как верхний отступ равен 10 пикселам, а нижний — 0.
Однако чаще указывают два значения. Небольшие элементы лучше выглядят, когда слева и справа отступы больше, чем сверху и снизу. Этот подход идеален для форматирования кнопок или навигационных ссылок на странице (рис. 1.14).
Рис. 1.14. Многие элементы выглядят лучше с большим отступом по горизонтали
Измените код таблицы стилей, чтобы он соответствовал листингу 1.20. Здесь используются сокращенные записи свойств, чтобы сначала применить вертикальный отступ, а затем горизонтальный.
Листинг 1.20. Указание двух значений
Существует много общих свойств, которые придерживаются этого порядка, поэтому рекомендуется запомнить его.
Горизонтально, вертикально
Мы рассмотрели свойства, которые назначают отдельные значения каждой из четырех сторон. Но существуют и свойства, поддерживающие только два значения. К ним относятся background-position, box-shadow и text-shadow (строго говоря, это несокращенные записи). По сравнению с четырьмя значениями таких свойств, как padding, порядок указания значений у двузначных свойств противоположен. Если padding: 1em 2em сначала определяет вертикальные отступы (сверху/снизу), а затем горизонтальные (справа/слева), то свойство background-position: 25% 75% определяет сначала горизонтальные значения (справа/слева) и только потом вертикальные (сверху/снизу).
Рис. 1.15. Свойству box-shadow присвоено значение 10рх 2рх
Эта противоположность кажется нелогичной, но ее причина проста: два значения представляют собой прямоугольную систему координат. Значения в ней обычно задаются в порядке x, y (горизонтальное значение, а затем вертикальное). Если, например, вы хотите применить тень, подобную показанной на рис. 1.15, сначала укажите значение x (горизонтальное).
CSS-код показан в листинге 1.21.
Листинг 1.21. Свойство box-shadow определяет сначала значение x, а затем y
Первое (большее) значение определяет смещение по горизонтали, а второе (меньшее) — по вертикали.
Если вы работаете со свойством, которое принимает два значения, х и у, вспомните прямоугольную систему координат, если же со свойством, определяющим значения для всех сторон элемента, — часы.
Итоги главы
• Контролируйте специфичность селекторов.
• Не путайте каскадность с наследованием.
• Некоторые свойства наследуются в том числе для текста, списков и границ таблиц.
• Не путайте значения initial и auto.
• Остерегайтесь сокращений, скрыто переопределяющих другие стили.
• Представляйте прямоугольную систему координат, работая с двузначными свойствами, и часы, используя четырехзначные.
2. Работа с относительными единицами
В этой главе
• Гибкость относительных единиц.
• Как использовать единицы em и rem и не сойти с ума.
• Применение экранных единиц измерения.
• Введение в переменные CSS.
При указании значений CSS предоставляет широкий спектр возможностей для выбора единиц измерения. Одними из самых известных и, вероятно, самых простых для работы являются пикселы. Это абсолютные единицы — 5 пикселов всегда означают одно и то же. Другие единицы, такие как em и rem, не абсолютные, а относительные. Значение относительных единиц меняется под влиянием внешних факторов: размер 2 em меняется в зависимости от того, для какого элемента (а иногда даже свойства) вы его задаете. Естественно, это усложняет работу с относительными единицами.
Разработчикам CSS, даже опытным, не очень нравится работать с относительными единицами, включая пресловутую em. Значение em может меняться абсолютно по-разному, что делает ее непредсказуемой и менее четкой, чем пиксел. В данной главе я сниму завесу тайны вокруг относительных единиц. Сначала объясню, в чем их уникальная польза для CSS, затем помогу в них разобраться. Я расскажу, как они работают, и покажу, как укротить их сущность, на первый взгляд кажущуюся непредсказуемой. Вполне реально сделать так, чтобы относительные единицы работали на вас. Если правильно их применять, ваш код станет более простым и универсальным, а работа над ним упростится.
2.1. Мощь относительных значений
CSS позволяет динамически связывать стили с веб-страницей: контент и его стили не объединяются, пока их разработка не завершена. В процессе веб-дизайна это создает дополнительные проблемы, которых нет в других видах графического дизайна, но в то же время обеспечивает очень широкие возможности — одну таблицу стилей реально применить к сотням и даже тысячам страниц. Более того, пользователь может напрямую изменить итоговую отрисовку страницы. Например, задать другой размер шрифта по умолчанию или размер окна браузера.
В ранних версиях компьютерных приложений разработчики знали точные ограничения своего носителя. Размер отдельного программного окна составлял 400 пикселов в ширину и 300 пикселов в высоту. Соответственно, когда разработчики приступали к разметке кнопок и текста приложения, они точно знали, насколько большими могут сделать эти элементы и сколько места останется у них для работы над другими объектами на странице. В Интернете дело обстоит иначе.
2.1.1. Борьба за pixel-perfect-дизайн
В интернет-среде окна браузера у пользователей могут быть любого размера, и CSS должен адаптироваться под них. Более того, пользователи способны изменить размер страницы после того, как ее откроют, и CSS должен подстроиться под новые ограничения. Это означает, что браузер должен рассчитывать стили в момент отображения страницы на экране.
Это повышает уровень абстрактности CSS. Мы не можем стилизовать элемент в соответствии с идеальным контекстом, нам нужны определенные правила, работающие в любом контексте, в котором способен оказаться этот элемент. В сегодняшнем Интернете страница должна отображаться на четырехдюймовом экране смартфона так же, как и на 30-дюймовом мониторе.
Дизайнеры долго смягчали эту сложность, концентрируясь на дизайне pixel-perfect. Они создавали строго ограниченный контейнер, зачастую это была выровненная по центру колонка около 800 пикселов шириной. Затем в рамках этих ограничений занимались дизайном приблизительно так же, как их предшественники — компоновкой ранних приложений.
2.1.2. Конец эпохи pixel-perfect
С развитием технологий и выпуском в производство мониторов более высокого разрешения подход pixel-perfect начал медленно терять актуальность. В начале 2000-х годов было много дискуссий о том, можем ли мы, разработчики, безопасно создавать дизайн для дисплеев шириной 1024 пикселов вместо 800. Затем тот же разговор велся о 1280 пикселах. Нам приходилось принимать спорные решения. Что было лучше: сделать сайт слишком широким под старые компьютеры или слишком узким под новые?
Когда появились смартфоны, разработчикам пришлось перестать делать вид, что можно добиться единого отображения их сайтов для каждого пользователя. Нравилось ли нам это, или мы это ненавидели, но пришлось отказаться от колонок фиксированной ширины и начать думать об адаптивном дизайне. Мы больше не могли избежать абстрактности, которая сопровождала CSS. Необходимо было ее принять.
|
|
Адаптивный — в CSS это определение относится к стилям, реакция которых зависит от размера окна браузера. Из-за этого необходимо принимать во внимание то, что экраны мобильных телефонов, планшетных или настольных компьютеров могут быть любого размера. Адаптивный дизайн подробно рассматривается в главе 8. |
Введенная абстрактность означает дополнительную сложность. Если я задаю элементу ширину 800 пикселов, как он будет выглядеть в окне меньшего размера? Как будет выглядеть горизонтальное меню, если не уместится в одну строчку? Когда вы пишете CSS-код, вам необходимо уметь мыслить одновременно как в деталях, так и в общем. Когда есть множество способов решить конкретную проблему, следует отдать предпочтение тому, который будет работать в большинстве случаев в разнообразных обстоятельствах.
Относительные единицы — одно из средств CSS, обеспечивающих работу на данном уровне абстрактности. Вместо того чтобы устанавливать размер шрифта 14 пикселов, вы можете задать его в масштабе, пропорциональном размеру окна. Или установить размер всего, что есть на странице, относительно основного размера шрифта и затем менять размер всей страницы одной строкой кода. Рассмотрим, что CSS предлагает для реализации такого подхода.
| Пикселы, пункты, пики Каскадные таблицы стилей поддерживают некоторые абсолютные единицы измерения. Наиболее распространенные из них и основные — это пикселы (px). Менее распространенные абсолютные единицы: миллиметры (mm), сантиметры (cm), дюймы (in), пункты (pt, типографский термин для обозначения значения 1/72 дюйма) и пики (pc, типографский термин для обозначения 12 пунктов). Любая из этих единиц может быть напрямую переведена в другую: 1 дюйм = 25,4 мм = 2,54 см = 6 пик = 72 пункта = 96 пикселов. Отсюда 16 пикселов — то же самое, что 12 пунктов (16 / 96 · 72). Дизайнеры обычно используют пункты, тогда как разработчикам более привычны пикселы, поэтому вам, вероятно, придется делать перевод между этими значениями при общении с дизайнером. Пиксел — понятие, немного вводящее в заблуждение: пиксел в CSS не совсем равен пикселу монитора. Это особенно характерно для дисплеев с высоким разрешением (retina). Несмотря на то что измерения в CSS могут быть в некоторой степени масштабированы в зависимости от браузера, операционной системы и аппаратного обеспечения, 96 пикселов обычно составляют приблизительно 1 физический дюйм экрана, хотя это значение может варьироваться на определенных устройствах или в зависимости от пользовательских настроек разрешения. |
2.2. Единицы em и rem
Самая распространенная относительная единица измерения em — это мера, использовавшаяся изначально в полиграфии и ссылающаяся на определенный размер шрифта. В CSS 1 em означает размер шрифта текущего элемента, его точное значение варьируется в зависимости от того, к какому элементу вы его применяете. Рисунок 2.1 показывает элемент div с отступами 1 em.
Рис. 2.1. Элемент, чье свойство padding имеет значение 1 em (пунктирные линии добавлены для иллюстрации отступа)
Код для создания этого оформления показан в листинге 2.1. Набор правил о
