Когда display: none, а когда visibility: hidden?
Зависит от того, что вы пытаетесь сделать. Есть и другие варианты как спрятать блок и даже специальный атрибут.
Если вам приходится что-то прятать, то лучше всего это вообще убрать: сайт легче, код чище… ошибок меньше! Но если вам нужно, чтобы оно там пряталось до поры, а потом кому-то пригодилось — это другое дело. Здесь важно не ошибиться с выбором способа.
Самый простой и популярный — display: none, он работает как топор: элемент как будто вырубают из HTML. Его не видно на странице и соседние блоки про него ничего не знают. Просто нет и всё. Его даже скринридеры игоририруют и не читают содержимое — будьте аккуратнее с этим.
/* Вырубает */
.cut-down {
display: none;
}
Что интересно, несмотря на полное вырубание элемента, браузеры всё равно загружают картинку из img с display: none. Если же картинка указана фоном, то Chrome и Edge её тоже загружают, а Firefox и Safari — нет. Ну, разные у них взгляды на оптимизацию загрузки, что поделать.
Другой способ — visibility: hidden, он работает как кольцо всевластья: элемент вроде здесь и соседние блоки его чувствуют, но его не видно. И чем это отличается от opacity: 0? Opacity просто делает элемент прозрачным (или полупрозрачным), а visibility: hidden ещё не даёт с ним взаимодействовать: навести, кликнуть, сфокусировать.
/* Прячет */
.one-ring {
visibility: hidden;
}
/* Не сработает */
.one-ring:hover {
visibility: visible;
}
У visibility: hidden есть другая приятная особенность: свойство наследуется, а значит ребёнок невидимого родителя может сменить видимость на visible. Такой трюк не пройдёт ни с display: none, ни с opacity: 0. С ним удобно делать всплывающие меню и подказки.
Иногда нужно, чтобы элемент не мешал дизайну, но при этом не прятался от скринридеров, оставаясь частью содержимого. Ну не нарисовал дизайнер здесь заголовка, а по логике документа он здесь нужен. Вот бы нам что-то вроде display: hidden или visibility: none! Это я только что придумал, в природе их не существует.
Недавно в черновике CSS Display третьего уровня появилось свойство box-suppress со значениями show, discard и hide. Оно отвязывает видимость блока от display — ведь с обратной стороны от none есть не только block, но и inline, flex, grid. Значение discard привычно вырубает элемент, а hide делает то самое волшебное комбо. Читайте подробнее у Рейчел Эндрю.
/* То, что нужно */
.combo {
box-suppress:
hide;
}
К сожалению, до box-suppress нам ещё долго ждать. Его не только ещё нет в браузерах, но уже в том черновике — недавно его перенесли в следующий уровень, чтобы закончить текущий вовремя. Так что придётся делать магию самим — следите за руками.
Есть такой паттерн «visually hidden» или «визуально спрятанный», чтобы прятать элементы из дизайна, но оставлять доступным их содержимое. Про другие нюансы со скринридерами читайте у Тима Райта. Как это работает: вы делаете универсальный служебный класс и добавляете его к элементам, которые нужно доступно спрятать. Обычно его так и называют: visually-hidden, через дефис.
<h2 class="
visually-hidden">
Важный
за головок,
которого нет
</h2>
Если посмотреть что внутри, то это обычный position: absolute плюс clip, который обрезает элемент до нуля. То есть он не влияет на соседей и становится невидимым. Все остальные свойства добавляют универсальности и кроссбраузерности, чтобы класс можно было не глядя шлёпнуть на любой элемент. Подробнее читайте в справке к ally.js Родни Рейма.
.visually-hidden {
position: absolute;
clip: rect(0 0 0 0);
width: 1px;
height: 1px;
margin: -1px;
…
}
А вы знали, что любому элементу можно добавить атрибут hidden и он пропадёт? Теперь знаете! В современных браузерах на этот атрибут повешен тот самый display: none, который вырубает элемент. Он бинарный как required или checked, так что его удобно выставлять через JavaScript. Только не забудьте добавить в стили [hidden] { display: none } для IE 10, Safari 5 и других старых браузеров.
<div hidden>
Вырублен
</div>
// JS
div.hidden = true;
Это почти всё, что вам нужно знать про прятки в CSS. Попробуйте эти способы, они все хороши в разных ситуациях. Главное, не рубите с плеча и думайте о доступном содержимом.
Видеоверсия
Вопросы можно задавать здесь
Комментарии (10)
ElianL
04.11.2017 17:24И чем это отличается от opacity: 0? Opacity просто делает элемент прозрачным (или полупрозрачным), а visibility: hidden ещё не даёт с ним взаимодействовать: навести, кликнуть, сфокусировать.
Так же что стоит заметить, что opacity создает новый контекст для расчета z-index. Плюс opactity можно анимировать
switzergirl
06.11.2017 16:14Использовал и то, и другое при верстке. Но со временем стал стараться обходить стороной такие штуки)
kahi4
Что это за серия вредных туториолов для начинающих на хабре? Вы собрались все свойства css рассказать, прикрепив ненужный видеофайл?
И влетел в бан в гугле и яндексе за это. Для доступности у html хватает аттрибутов, их и стоит использовать, а не заниматься дичью вроде top: -9999px (еще один способ, как и сделать текст такого же цвета как и фон, много их было).
И не написано, что переключение display приводит к пересчету лайаута, а visibility нет. Причем переключение каждого display будет приводить к пересчету, так что стоит избегать изменений этого свойства в цикле и все такое, но это да, не для новичков.
andreymal
Я всегда думал, что пересчёты ленивые и производятся только по необходимости, а не сразу после изменения, это не так что ли?
kahi4
Покуда сразу следующей же строчкой после переключения стиля вы можете попытаться выяснить размер/что-то еще счисляемое, браузеру попросту нет вариантов делать иначе.
Простой пример: jsfiddle. Если бы оно рассчитывалось только один раз отложено — в логе бы вывелось 7 одинаковых надписей. Однако есть вероятность, что современные браузеры достаточно умны, вызывают пересчет только если кто-то обращается к этим значениям, иначе по окончании выполнения скрипта, однако не стоит на это рассчитывать.
andreymal
Это и есть необходимость. А если убрать offsetHeight?
Ну то есть вы говорите о том, чего толком не знаете, понятно)
kahi4
Окей, я проверил. Есть набор свойств, таких как offsetHeight, которые требуют пересчета layout. Вот например список таких свойств. Только они не стандартизированы и получены для конкретного браузера, конкретной версии, неизвестно что там у себя внутри думает IE/Edge, не известно как это может измениться в будущем.
Помимо этого, нужно убедиться, что никто не навесит dom-observable и чего-то подобного (onscroll не вызывается, проверил, впрочем не уверен что справедливо для всех условий).
Хотите завязываться на неопределенное поведение? Пожалуйста. На моей практике когда речь идет о включении-выключении элементов до 1000 за раз — никаких трудностей не возникает, а когда речь идет об 50 000+ элементов — трудности возникают и приходится делать дополнительные шаги. Впрочем, задачи тоже разные бывают.
P.S. Вот почитать подробнее о том, что вызывает пересчет layout при изменении каких свойст было бы по-интереснее, чем перески "css для чайников", конечно.AlexPershin
Вы так пишете как будто бы Хабр место для элиты, вроде вас, и новичков тут нет.
Гугл точно за это не банит. Тем более, что доступность уже становится обязательным требованием. В США всё к этому идёт и для коммерческих сайтов, а раз так, то очень скоро и до нас докатится, а почувствуют это профессионалы-аутсорсеры в первую очередь. Думаю, и для них такие туториалы начального уровня будут полезны (быстрой систематизацией).
kahi4
Оф. дока. СЕО штука такая, сложная, сложно говорить что-то наверняка с пруфами (вообще это чуть ли не уникальный случай, что удалось найти пруфы в чем-то официальном, а не только сакральные знания на каком-нибудь блоке сеошников), однако я встречал людей, которых банили за это. Это связано с черным (black hat) СЕО времер до 2012 года, когда это использовали для искуственного повышения в выдаче. С тех пор если visible: hidden и display: none в целом безобидные, то трюки с clipRect расцениваются как попытка обмануть поисковики.
Повторюсь, для HTML существует целые разделы спецификации, нацеленные на решение доступности сайта. Один из них — wai-aria и использовать нужно их (по многим причинам).
Тогда вперед, давайте сюда еще по главам опубликуем весь учебник математики за 5 класс. И википедию всю переписать сюда. Грань, когда статья уместна на хабре, а когда нет — очень тонкая, но основы CSS — на мой взгляд уж точно ее переходят. Хабр для уникального опыта, уникальных знаний, чего-то, что сложно или даже порой невозможно найти в других источниках. А с visiblity и hidden новички в html/css могут познакомиться в миллионах других источников, предназначенных для этого. Впрочем, рейтинг статьи показывает, что я, похоже, не прав.
Хм, может тоже пойти что-то такое публиковать? Чур я забил учебник Атанасяна по геометрии за 7-9 класс!
Никогда не думал, что я тоже буду сидеть и говорить "хабр уже не торт".AlexPershin
Отличная ссылка на документацию, в которой говорится прямо противоположное вашим выводам:
Гугл сам говорит, что текст, спрятанный от пользователей, и предназначенный для поисковиков — это плохо. Но текст, предназначенный для пользователей с читалками (то есть в целях доступности) — это ок.
Если лень вникать в английский текст, то вот прямой ответ на форуме поддержки вебмастеров productforums.google.com/forum/#!msg/webmasters/YJcZUhtMIE4/XkOEzVakBAAJ
Такие статьи про азы на Хабре нужны не только для новичков, но и для опытных, которые в азах не разобрались в своё время, или разобрались в азах, но они поменялись.
А что касается aria-атрибутов, то можно и без них обойтись в большинстве простых случаев, если использовать теги по назначению.