Выявление устройств с сенсорными экранами на чистом CSS

Kate

Administrator
Команда форума
У разработчиков, которым нужно выявлять устройства с сенсорными экранами, пользуясь исключительно CSS, появилась, благодаря новым возможностям CSS, надежда на светлое будущее. Речь идёт о черновике стандарта CSS Media Queries Level 4, в котором описаны два новых свойства — hover и pointer.


Свойство hover​


Вот что сказано о hover в стандарте:
Мультимедийная функция hover используется для выполнения запроса, направленного на выяснение возможности пользователя наводить указатель основного указывающего устройства на элементы. Если у устройства имеется несколько указывающих устройств, то hover-запрос должен отражать характеристики «основного» указывающего устройства, определённого пользовательским агентом.

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

Соответствующий стандарт W3C пока имеет статус черновика, но уже сейчас можно говорить о том, что свойство hover может принимать два значения — hover и none, которые можно использовать в медиазапросах.

Если при использовании основного механизма ввода можно без труда навести указатель на элемент — на него отреагирует медиазапрос, в котором применяется значение hover:

@media (hover: hover) {
/* ... */
}


Если основной механизм ввода не позволяет навести указатель на элемент, или позволяет, но это не очень-то просто (например — для имитации наведения указателя на элемент используется длительное касание экрана), или если у устройства нет основного указывающего устройства — сработает запрос, в котором применяется значение none:

@media (hover: none) {
/* ... */
}


Свойство pointer​


Разбираясь со свойством pointer, снова обратимся к стандарту:
Мультимедийная функция pointer используется для выполнения запроса на предмет наличия и точности указывающего устройства, такого, как мышь. Если имеется несколько указывающих устройств — сведения, возвращаемые запросом pointer, должны отражать характеристики «основного» указывающего устройства, определённого пользовательским агентом.

Тут, опять же, идёт речь об «основном указывающем устройстве».

Свойство pointer может иметь одно из трёх значений — coarse, fine и none.

Если основной механизм ввода данных включает в себя указывающее устройство ограниченной точности — используется значение coarse:

@media (pointer: coarse) {
/* ... */
}


Если основной механизм ввода данных включает в себя точное указывающее устройство — используется значение fine:

@media (pointer: fine) {
/* ... */
}


Если же в состав основного механизма ввода данных указывающее устройство не входит — применяется значение none:

@media (pointer: none) {
/* ... */
}


Примеры медиазапросов, ориентированных на конкретные устройства​


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

/* смартфоны, устройства с сенсорным экраном, с которым работают пальцами */
@media (hover: none) and (pointer: coarse) {
/* ... */
}
/* устройства с сенсорным экраном, с которым работают стилусом */
@media (hover: none) and (pointer: fine) {
/* ... */
}
/* контроллер Nintendo Wii, Microsoft Kinect */
@media (hover: hover) and (pointer: coarse) {
/* ... */
}
/* мышь, тачпад */
@media (hover: hover) and (pointer: fine) {
/* ... */
}


Обратите внимание на то, что если имеется несколько указывающих устройств, hover- и pointer-запросы возвращают сведения об основном указывающем устройстве.

Медиазапросы, реагирующие на все типы устройств​


Для того чтобы создавать медиазапросы, реагирующие на все типы устройств, можно пользоваться свойствами any-hover и any-pointer. Снова обратимся к документации:

Any-pointer используется для выполнения запроса на предмет наличия и точности указывающих устройств. Соответствующий запрос не принимает во внимание дополнительные устройства ввода, не являющиеся указывающими, и не может быть использован для проверки наличия других механизмов ввода данных, таких, как d-пады, или средства управления, основанные лишь на клавиатуре, которые не позволяют перемещать экранный указатель. Запрос «any-pointer: none» вернёт true только в том случае, если на исследуемом устройстве нет ни одного указывающего устройства.

/* как минимум один механизм ввода устройства включает в себя указывающее устройство ограниченной точности */
@media (any-pointer: coarse) {
/* ... */
}
/* как минимум один механизм ввода устройства включает в себя указывающее устройство высокой точности */
@media (any-pointer: fine) {
/* ... */
}
/* устройство не имеет указывающего устройства */
@media (any-pointer: none) {
/* ... */
}


Запрос «any-hover: none» вернёт true в том случае, если указывающего устройства нет, или если все имеющиеся указывающие устройства не позволяют навести указатель на элемент. В силу этого подобные запросы следует рассматривать как способ проверки наличия хотя бы одного указывающего устройства, позволяющего наводить указатель на элементы, а не проверки того, что какое-то из указывающих устройств не позволяет наводить указатель на элементы. Последняя задача в текущих условиях не может быть решена ни с помощью медиазапроса any-hover, ни с помощью какого-то другого медиазапроса, направленного на анализ возможностей по взаимодействию пользователя с устройством. Кроме того, any-hover-запросы не принимают во внимание наличие на устройстве механизмов ввода данных, не относящихся к указывающим устройствам, таких, как d-пады и клавиатуры, которые, по своей природе, не позволяют наводить указатели на элементы.

/* имеющиеся механизмы ввода данных позволяют с лёгкостью наводить указатель на элементы */
@media (any-hover: hover) {
/* ... */
}
/* имеется один или большее количество механизмов ввода данных, поддерживающих наведение указателя на элементы, но сделать это не особенно легко (например — для имитации наведения указателя на элемент используется длительное касание экрана) */
@media (any-hover: on-demand) {
/* ... */
}
/* имеющиеся механизмы ввода данных не обеспечивают функционал наведения указателя на элементы, или указывающих устройств не обнаружено */
@media (any-hover: none) {
/* ... */
}


Итоги​


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

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

74800391baa25c8d8ab34eb16afc9e76.png


Поддержка pointer, any-pointer, hover и any-hover в 2018 году

Хочется надеяться, что эти возможности войдут в официальный стандарт CSS 4.

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

Обновление 2021 года​


Этот материал написан в 2018 году. Что изменилось более чем за 2 года после его публикации?

Разработчики веб-браузеров действуют гораздо быстрее тех, кто занимается стандартами. И возникает такое ощущение, что они, скорее всего, ещё до выхода официального стандарта, сделают медиазапросы, использующие pointer, any-pointer, hover и any-hover, стандартом де-факто.

Вот свежий скриншот с CanIUse. Если сравнить его с вышеприведённым, то окажется, что ситуация значительно улучшилась.

a444a22f085fb59cee6251c4b4f3c337.png


Поддержка pointer, any-pointer, hover и any-hover в 2021 году

Я полагаю, что мы можем приступить к серьёзному использованию этих медиазапросов, даже несмотря на то, что стандарт, в котором они описаны, всё ещё пребывает в статусе черновика. Их браузерная поддержка достаточно широка, что позволяет пользоваться ими, не особенно сильно беспокоясь о том, какой именно браузер применяют пользователи некоего веб-проекта (и, пожалуйста, забудем об Internet Explorer).



Источник статьи: https://habr.com/ru/company/ruvds/blog/556156/
 
Сверху