СДЧПВС: слишком длинный чтобы поместиться в строчку
Новый день и новая велеречивая статья о CSS от сноба-приверженца JavaScript. :) Сегодня, однако, постараюсь быть краток.
В этот раз мы поговорим о переносе слов. Если конкретнее, то о том, как с помощью CSS заставить текст поместиться в контейнер, даже если придётся применить перенос в неестественных (не соответствующих границам слов) местах. Можно сказать, это задача, противоположная поставленной в моей предыдущей статье «Сокращение текста».
Пример:
http://www.urbandictionary.com/define.php?term=the%20meaning%20of%20life
Браузер добавляет перенос в длинный URL, но полученный результат оставляет желать лучшего.
Добавление переносов в текст вручную
Можно использовать хакерский подход и разместить на одинаковых отрезках длинного текста определённый элемент, который будет служить для браузера подсказкой, где следует добавлять перенос.
С помощью JavaScript в куске текста, например, твите или информационном сообщении, можно добавить элемент-подсказку после каждого энного количества символов. Однако следует учесть некоторые возможные загвоздки:
- Чаще всего перенос требуется добавить только в длинные слова (то есть,
добавление переноса в середине слова из двух символов не желательно), в таком
случае слепое помещение элемента-подсказки после каждого энного символа не
совсем подходит. Больше подошло бы указание вроде «следует найти строку,
состоящую более чем из 10 символов, отличных от пробела, и добавить в неё
элемент-подсказку». Регулярное выражение JS для этого будет выглядеть примерно
так:
text.split(/(\s*\S{10}\s*)/g).join("…")
, где"…"
— элемент-подсказка для добавления переноса. - Если перед вами не просто текст, а, к примеру, html-разметка, придётся быть
более осторожным, чтобы избежать добавления переноса в фрагменты html. В
противном случае можно повредить теги или имена атрибутов, что приведёт к их
невалидности. Из этого следует, что сначала лучше с помощью цикла перебрать
значения, которые возвращает
split(..)
и по контексту определить, нужно ли в этом месте добавлять элемент-подсказку или нет (написание соответствующего кода я оставляю читателю в качестве домашнего задания).
Если мы решим выбрать этот путь, какой элемент следует использовать в качестве подсказки для переноса?
(пробел)
Наиболее очевидным решением может показаться пробел, однако он не так уж хорош,
так как в местах где перенос по факту не добавляется, пробел будет отображаться,
что скорее всего нежелательно. И уж тем более не используйте
, ведь он
является буквально «неразрывным пробелом», что прямо противоположно тому, чего мы
добиваемся.
Можно добавить элемент <span class='break'> </span>
и в стилях прописать
ширину, с которой он будет невидимым.
<style>
p { font-family:sans-serif; font-size:15px; padding:3px; background-color:yellow; width:85px; }
.break { font-size:0px; }
</style>
<p>Пришло вре<span class="break"> </span>мя для всех достойных людей…</p>
Пришло время для всех достойных людей…
Однако этот приём откровенно отвратителен и может привести к проблемам в старых версиях браузеров (если вам, конечно, на них не наплевать!).
Новые возможности
Как насчёт тега «Возможного деления слова» <wbr>
? На первый взгляд,
подходит идеально. Это невидимый элемент, помогающий браузеру понять, где уместен
перенос.
Вы можете столкнуться с тем нюансом, что при использовании тега <wbr>
символ
переноса в месте разделения слова не будет добавлен браузером. Такой результат
может быть удобным в зависимости от обстоятельств.
Несколько лет элемент не поддерживался в Safari. Однако, команда Safari первой
ввела поддержку элемента ­
(тогда он не поддерживался другими браузерами),
который представляет собой «мягкий перенос», используемый в качестве
подсказки для браузера, предлагающей возможные позиции для переноса строки.
Если перенос добавляется в месте расположения ­
, отображается символ
переноса -
, если нет, он остаётся невидимым. Именно то, что нам нужно.
Из-за проблем с поддержкой браузерами, раньше приходилось проводить проверку на
поддержку браузера и, соответственно, выбирать, какой элемент использовать: <wbr>
или ­
. В наше время поддержка значительно улучшилась, и уже можно выбирать,
какой из них использовать, исходя из того, нужен вам символ переноса или нет.
Например, вам вряд ли потребуется символ переноса внутри URL, разделённого на
две строки, а вот в обычном тексте для читателей, особенно тех что привыкли к
разметке, имитирующей печатные издания (в онлайн журналах, газетах и т.д.),
гораздо удобнее, если символ переноса присутствует.
CSS спешит на помощь!
Раньше ручная разбивка текста была единственным вариантом. Однако, к счастью, в CSS уже есть отличное решение для этой проблемы, поэтому если поддержка браузеров, не понимающих CSS3, для вас не критична, можете переложить всю работу на CSS.
Средство word-wrap:break-word
реализует то, что нам нужно, то есть оно даст
браузеру возможность выполнить перенос в середине слова там, где сочтёт это
уместным.
<style>
#container { word-wrap:break-word; background-color:yellow; padding:10px; width:200px; }
</style>
<div id="container">
http://www.urbandictionary.com/define.php?term=the meaning of life
Примечание: Это свойство появилось уже давно, однако недавно в спецификации
CSS3 было переименовано в overflow-wrap:break-word
; новая версия
поддерживается только самыми последними версиями браузеров. Будьте осторожны,
используя его, и, наверное, стоит ещё некоторое время прописывать оба правила.
Ещё одно похожее свойство — word-break
. С точки зрения семантики, нам
стоит отдать предпочтение word-break
для управления разделением слов, о
котором идёт речь, вместо word-wrap
или overflow-wrap
, однако … не суть
важно. В любом случае, видимо во всех международных языках для управления
переносом слов используется word-break
, поэтому стоит ли вообще рассматривать
его семантику — спорный вопрос.
Что думаете вы?
Является ли запись в CSS исчерпывающей? Небольшая семантическая неувязка с
word-break
и word-wrap
не должна играть большой роли. Тем не менее, судя по
всему, CSS не даёт нам контроль над расстановкой символа переноса в том же объеме,
как ­
.
Нужно ли усовершенствовать стандарт CSS или же достаточно радоваться и тому, что уже есть? Поделитесь вашим мнением в комментариях!