Рецепты CSS

Рецепты CSS

В этой категории вы найдете уроки по CSS, которые показывают нестандартное применение CSS для простых и не очень задач

Проблема

Можно назвать много ситуаций, когда возникает необходимость определять для элементов разные стили в зависимости от того, сколько у них всего смежных элементов. Главный сценарий использования здесь — улучшение восприятия пользователем и экономия экранного пространства в раскрывающемся списке за счет скрывания элементов управления или уменьшения их в размере по мере увеличения списка. Вот несколько примеров: ‰ список сообщений электронной почты или схожих текстовых элементов. Если их всего лишь несколько штук, то для предварительного просмотра элементов мы можем отображать большие текстовые отрывки.

По мере того как список растет, мы сокращаем количество строк в области предварительного просмотра. Когда длина списка становится больше высоты окна просмотра, мы можем даже полностью скрыть текстовые отрывки и уменьшить размер кнопок, для того чтобы минимизировать необходимость прокрутки; ‰ приложение с напоминаниями о предстоящих делах, в котором каждый элемент отображается крупным шрифтом, пока элементов не много. Чем больше элементов создает пользователь, тем меньше мы делаем размер шрифта (для всех элементов);
‰ приложение с цветовой палитрой, в котором элементы управления отображаются на каждом образце цвета. Эти элементы управления можно делать более компактными по мере того, как количество цветов растет, а место, занимаемое каждым образом, соответственно уменьшается;
‰ приложение с несколькими элементами  <textarea> , в котором все их приходится уменьшать с добавлением каждого нового элемента.


Однако с помощью селекторов CSS решить задачу по выбору элементов в зависимости от общего количества «братьев» не так-то просто. Предположим, мы хотели бы применить определенные стили к элементам списка в случае, когда общее количество элементов равно 4. Мы могли бы использовать  li:nth-child(4) для выбора четвертого элемента в списке, но это не то, что нам нужно;нам необходимо выбрать все элементы, но только в том случае, когда их общее число равно четырем.

Следующей идеей могло бы быть использование обобщенного комбинатора «братьев» ( ~ ) совместно с  :nth-child() , как в  li:nth-child(4) ,  li:nthchild(4) ~ li. Однако при этом в выборку попадают только четвертый потомок и элементы после него, независимо от общего количества. Так как не существует комбинатора, который мог бы «оглянуться назад» и выбрать предыдущих «братьев», следует ли вовсе отказаться от попыток добиться нужного результата с помощью CSS?  Нет, давайте не терять надежды.

Проблема

Хотя мы уже очень давно прекратили использовать таблицы для создания макетов, они все же занимают достойное место на современных веб-сайтах: они используются для отображения таких табличных данных, как статистика, сообщения электронной почты, перечисления элементов с большим объемом метаданных и многого другого. Кроме того, мы можем заставлять другие элементы демонстрировать свойства, характерные для таблицы, используя ключевые слова свойства  display , связанные с таблицами. Однако каким бы удобным инструментом они ни были в определенных обстоятельствах, макет таблиц ведет себя очень непредсказуемо, когда дело доходит до динамического содержимого. Причина этого в том, что размеры столбцов корректируются в зависимости от объема содержимого, и даже явные объявления  width считаются не более чем подсказками, как видно на риcунке ниже.


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

Проблема

Как мы все знаем, если мы не устанавливаем конкретное значение  height для элемента, то его высота автоматически корректируется в зависимости от размера содержимого (подробнее о размерах элементов читайте здесь) . А что, если нам бы хотелось наблюдать схожее поведение атрибута  width ? Например, предположим, что мы оформляем иллюстрации с помощью HTML5, используя примерно такую разметку:
HTML
<p>Some text […]</p>
<figure>
<img src="/adamcatlace.jpg" />
<figcaption>
The great Sir Adam Catlace was named after
Countess Ada Lovelace, the first programmer.
</figcaption>
</figure>
<p>More text […].</p>
Также предположим, что мы применяем какую-то простейшую стилизацию, скажем, создаем рамку вокруг иллюстраций. По умолчанию результат выглядит как на рисунке. Но мы хотим, чтобы ширина иллюстраций была равна ширине содержащихся в них изображений (которые могут быть абсолютно разными), а также чтобы они выравнивались по центру по горизонтали. Текущий вариант визуализации далек от желаемого результата: строки текста намного длиннее изображения.

Как же сделать так, чтобы ширина иллюстрации определялась шириной содержащегося в ней изображения, а не шириной родительского элемента?  За время своей карьеры вы наверняка успели составить собственный список CSS-стилей, которые приводят к такому поведению свойства  width, чаще всего в качестве побочного эффекта: ‰ если мы сделаем элемент  <figure> плавающим, то это даст нам нужную ширину, но кардинальным образом изменит макет иллюстрации, что нам, скорее всего, совершенно не нужно;‰ установка свойства  display: inline-block для иллюстрации позволяет определять ее размер в зависимости от ее содержимого, но не так, как нам бы этого хотелось. Помимо этого, даже если бы способ вычисления ширины соответствовал нашим ожиданиям, было бы чрезвычайно сложно в таких условиях выравнивать иллюстрацию по центру.

Нам понадобилось бы применить  textalign: center к ее родительскому элементу и  text-align: left к любым другим возможным потомкам этого родительского элемента ( p,  ul,  ol,  dl, ...);‰ в качестве последнего средства разработчики часто прибегают к установке фиксированного значения width или  max-width для иллюстраций и применению  max-width: 100% к  figure > img . Однако это приводит к неэффективному расходованию доступного пространства, может давать уродливые результаты для слишком маленьких иллюстраций, а также не адаптивно. Существует ли достойное решение этой проблемы на чистом CSS или же нам следует сдаться и приступить к кодированию сценария, динамически устанавливающего ширину иллюстраций?

Проблема

Иногда перед вами встает задача показать визуальные различия между двумя изображениями, обычно в качестве иллюстрации «было — стало». Например, для того чтобы продемонстрировать в портфолио результаты обработки фотографии, показать эффект определенных процедур на веб-сайте салона красоты или проиллюстрировать видимые последствия катастрофического события в какой-то географической области. Самое распространенное решение — просто поместить два изображения рядом друг с другом. Однако при этом человеческий глаз замечает только очевидные различия и упускает мелочи. Это не страшно, если детали не так важны или же различия действительно очень значительные, но во всех остальных случаях нам требуется более удобный способ сравнения. С точки зрения удобства использования у данной проблемы есть несколько решений. Одно из наиболее распространенных — показывать оба изображения в одном и том же месте, быстро сменяя одно другим, используя для этого анимированное изображение в формате GIF или анимацию CSS. Это намного лучше, чем выводить изображения подле друг друга, но пользователю приходится потратить время на то, чтобы заметить все различия, так как ему нужно просмотреть несколько итераций, каждый раз фиксируя взгляд на новой области изображения. В некоторых вариациях пользователь всего лишь двигает указатель мыши, вместо того чтобы перетаскивать полосу. Преимущество такого подхода в том, что его проще заметить и использовать, но создаваемое мельтешение может раздражать.

Пример интерактивного виджета для сравнения изображений.
Намного более удобное для пользователя решение — так называемый слайдер сравнения изображений. Этот элемент управления содержит оба изображения, одно поверх другого, и позволяет пользователю перетаскивать разделитель, открывая одно или второе. Разумеется, такого элемента управления в HTML в действительности не существует. Его приходится имитировать средствами имеющихся элементов, и в Сети можно найти массу вариантов реализации, чаще всего требующих каркасов JavaScript и большого количества JS-кода. Существует ли более простой способ добавления на страницу подобного элемента управления? Да, причем целых два!

Проблема

Полоса прокрутки — главный способ указать, что элемент включает больше содержимого, чем видно на экране. Однако очень часто они бывают неуклюжими и отвлекают внимание пользователя, поэтому разработчики современных операционных систем стремятся их упрощать, зачастую даже полностью скрывают полосы прокрутки с экрана до тех пор, пока пользователь не начинает активно взаимодействовать с элементом, поддерживающим прокрутку. Хотя сегодня полосы прокрутки используются все реже (пользователи обычно прокручивают содержимое с помощью жестов), указание на то, что внутри элемента больше содержимого, чем видно в данный момент на экране, — чрезвычайно полезная информация, и ее рекомендуется ненавязчиво добавлять даже к тем элементам, с которыми пользователь в настоящее время не взаимодействует. Дизайнеры-проектировщики пользовательского взаимодействия, разрабатывавшие Google Reader, клиент для чтения RSS-лент от Google (сейчас этот проект уже закрыт), нашли очень элегантный способ указания на наличие дополнительного


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


Однако для того чтобы добиться этого эффекта в Google Reader, разработчикам пришлось добавить немало сценариев. Было ли это действительно необходимо или тот же эффект можно реализовать на чистом CSS?

Проблема

В статье  «Как сделать эффект лайтбокса » мы познакомились со способом отвлечения внимания от фрагментов веб-приложения посредством их затемнения с помощью полупрозрачной черной подложки. Но если страница содержит большое количество деталей, то затемнять ее приходится очень сильно, для того чтобы обеспечить достаточный контраст с отображающимся поверх текстом или привлечь внимание к световому коробу или другому элементу. Более элегантный способ, заключается в том, что мы размываем все остальное, за исключением подсвеченного элемента, в дополнение к затемнению или вместо него. Кроме того, это создает более реалистичный эффект глубины, имитируя то, как наше зрение воспринимает объекты, находящиеся физически ближе к нам, когда мы на них фокусируемся. Однако реализовать этот эффект куда сложнее. До появления спецификации Filter Effects это было вообще невозможно, и даже с использованием фильтра  blur() задача остается непростой. К чему привязывать размывающий фильтр? Или мы должны применить его ко всему, за исключением определенного элемента? Если мы применим его к элементу <body> , то будет размыто все содержимое страницы, включая элемент, к которому мы хотим привлечь внимание. Ситуация очень похожа на ту, которую мы рассматривали в статье «Эффект матированного стекла», однако прибегнуть к тому же решению здесь мы не можем, так как позади нашего диалоговогоокна может находиться все что угодно, а не только фоновое изображение. Что же делать?

Проблема

Нередко возникает необходимость затемнить все содержимое позади элемента с помощью полупрозрачной темной подложки, для того чтобы подчеркнуть данный элемент пользовательского интерфейса и привлечь к нему внимание пользователя. Например, этот эффект часто используется для создания «световых коробов» или лайтбоксов  и «экскурсий» по интерфейсу. В самой распространенной технике реализации роль затемняющего занавеса играет новый элемент HTML, к которому применено немного стилизации CSS, как в следующем
фрагменте кода:
.overlay { /* Для затемнения */
position: fixed;
top: 0;
right: 0;
bottom: 0;
left: 0;
background: rgba(0,0,0,.8);
}
.lightbox { /* Элемент, к которому мы хотим привлечь внимание */
position: absolute;
z-index: 1;
/* [остальные стили] */
}


Подложка затеняет все содержимое позади того элемента, к которому мы хотим привлечь внимание.  .lightbox получает более высокое значение  z-index , для того чтобы этот элемент выводился поверх подложки. Это, конечно, прекрасно, но все же данное решение требует дополнительного элемента HTML, то есть реализовать его с помощью чистого CSS невозможно. Не самая большая проблема, но по возможности нам все же хотелось бы избежать этого неудобства. К счастью, в большинстве случаев это возможно.

Проблема

Дизайнеры всегда хотят иметь полный контроль над всеми элементами веб-страницы. Когда графического дизайнера, имеющего ограниченный опыт работы с CSS, просят создать макет веб-сайта, он практически всегда создает макет с уникальными стилизованными элементами управления форм, чем вгоняет в тоску разработчика, задача которого — перевести этот рисунок на язык CSS. Когда каскадные таблицы стилей CSS только появились, предлагаемая стилизация форм была очень ограниченной, и по сей день четкого определения этих элементов ни в одной из многочисленных спецификаций CSS не существует. Однако с годами браузеры получили больше свободы в том, какие свойства CSS допускается использовать с элементами управления форм, благодаря чему мы теперь в вопросах стилизации большинства из них можем чувствовать себя довольно вольготно. К сожалению, флажки и переключатели не относятся к вышеупомянутому большинству. По сей день большая часть браузеров допускает лишь минимальную их стилизацию или вообще не поддерживает стили для этих элементов форм. В результате разработчикам приходится либо мириться с их представлением по умолчанию, либо прибегать к ужасным трюкам, затрудняющим доступ к содержимому веб-страниц, таким как воссоздание этих элементов с помощью блоков  div и сценариев JavaScript.
Существует ли способ обойти подобные ограничения и настроить внешний вид флажков, не раздувая код и не жертвуя семантикой и доступностью содержимого?

Проблема

Если вы интересуетесь вопросами взаимодействия с пользователем, то наверняка слышали о законе Фиттса. Впервые предложенный американским психологом Полом Фиттсом (Paul Fitts) еще в 1954 году, закон Фиттса гласит, что время, необходимое для быстрого перемещения в целевую область, представляет собой логарифмическую функцию отношения между расстоянием до цели и шириной цели. Его наиболее часто используемая математическая формули ровка выражается как

, где T — затраченное время, D — расстояние до центра цели, W — ширина цели, а a и b — константы. Хотя графические интерфейсы пользователя в то время еще не существовали, закон Фиттса распространяется в том числе и на координатно-указательные устройства, а сегодня стал самым известным принципом человеко-машинного взаимодействия (Human-Computer Interaction, HCI). Возможно, поначалу это может казаться чем-то удивительным, но помните, что закон Фиттса в большей степени относится к человеческим моторным навыкам, чем к конкретному аппаратному обеспечению. Очевидное следствие данного закона состоит в том, что чем больше цель, тем проще в нее попасть. Следовательно, расширение области, реагирующей на щелчки мыши (области попадания), вокруг небольших элементов управления, с которыми в противном случае может быть сложно взаимодействовать (а увеличить их невозможно), зачастую повышает удобство использования.Это становится тем важнее, чем большую популярность завоевывают сенсорныеэкраны. Никому не нравится тыкать пальцем в экран десять раз подряд, чтобы попасть в эту мерзкую маленькую кнопочку, и все же подобные ситуации возникают каждый день. В других сценариях мы хотим, чтобы элемент выдвигался, когда пользователь подводит указатель мыши к краю окна, — как, например, в случае с автоматически скрываемым заголовком, который выскальзывает из-под верхней кромки при приближении указателя мыши. Это также включает необходимость увеличения области попадания (но только в одном направлении). Возможно ли это средствами чистого CSS?

Проблема

Назначение указателя мыши — не просто показывать, в какой точке экрана находится курсор, но также сообщать пользователю, какие действия ему доступны. Об этой распространенной практике проектирования пользовательских интерфейсов настольных приложений в веб-приложениях часто забывают. Но вина лежит не только на разработчиках. Во времена CSS 2.1 у нас попросту не было доступа ко многим встроенным курсорам. В основном мы использовали свойство  cursor для указания, что на чем-то можно щелкнуть, дополняя его курсором  pointer , или же иногда добавляли всплывающие подсказки с помощью курсора  help . Некоторые также применили курсоры  wait и  progress вместо или в дополнение к указателю загрузки. Но этим дело и ограничивалось. И хотя в CSS User Interface Level 3  мы получили целую пачку новых встроенных курсоров, большинство разработчиков продолжают в этом вопросе придерживаться старых привычек. Как это часто бывает при работе над взаимодействием с пользователем, вы в действительности не осознаете существования проблемы до тех пор, пока не сталкиваетесь с решением. Позвольте мне показать вам эти решения!

Страница 1 из 4

Поиск по сайту

Google+