Веб-разработка

индекс
236,88

Динамическая висячая пунктуация в HTML

Наверняка вы видели на многих сайтах свешивающиеся в начале строк кавычки и скобки. И хотя на бумаге такое полное свешивание в простых текстах (не заголовках) как минимум спорно, на вебе это выглядит отлично. Такое поведение текста называется «висячая пунктация», и на текущий момент есть ровно один способ её реализации в (X)HTML/CSS — добавление парных стилей. Этот способ, скажем, применён на сайте Артемия Лебедева.

Главный минус классической «лебедевской» реализации висячей пунктуации на вебе — её статичность. Поясню, как у них это сделано.

В CSS прописаны парные стили: .h[symbol] и .s[symbol], например, .slaquo и .hlaquo. Для каждого из них прописан отвес через margin. При использовании свешивающихся символов в тексте к пробелу перед символом добавляется стиль s[symbol], а к самому символу — h[symbol]. Соответственно, когда и пробел, и символ, находятся в одной строке, отвесы взаимно компенсируются, и текст выглядит как обычно. А когда свешивающийся символ по каким-то причинам сносится на следующую строку — первый стиль (балансирующий второй блок) остаётся на предыдущей строке, поэтому нужный символ свешивается влево на заданный отвес.

Реализация по сути хорошая, с одним «но» — шрифты. Для каждого шрифта отвес, скажем, открывающей кавычки-ёлочки или открывающей скобки разный. Да, конечно, мы можем его вычислить вручную и прибить в таблице стилей гвоздями (так и сделано у Лебедева на сайте), но для этого придётся быть уверенным, что как минимум у 90% посетителей сайта будет именно этот шрифт. В случае, если браузер покажет это каким-то иным шрифтом, начнутся проблемы с разъезжающимися строками.

Что было сделано?

В начало документа помещаются три заведомо невидимых блока: блок с открывающей ёлочкой, блок с открывающей скобкой, и блок размером 1em (если есть необходимость свешивать ещё какие-либо символы — добавляем нужные блоки, там могут быть любые символы). Далее вызывается несложная функция на JavaScript, вычисляющая размеры этих невидимых блоков, конвертирующая их из пикселей в «эмы» (не зря же мы сделали блок размером 1em), и динамически вписывающая их в основной CSS документа. Использование самих отвесов при этом совершенно не отличается от оригинального способа, отличается только задание стилей.

Этот не очень сложный по реализации способ позволяет гарантировать правильное отображение висячей пунктуации во всех современных браузерах и операционных системах, вне зависимости от используемого пользователем шрифта; также этот способ уменьшает затраты на кодирование стилей вебмастеру, т. к. более не требуется вычислять отвесы вручную.

Напоследок приведу пример конечной реализации (за текстовый материал спасибо «Яндекс.Рефератам»). Не стесняйтесь использовать данную функцию в своих сайтах, но, пожалуйста, уважайте копирайты. Пример гарантированно работает в «Фаерфоксе», «Опере», «Интернет эксплорере», и «Сафари». Естественно, после внедрения динамической висячей пунктуации статические стили из CSS необходимо удалить.
+48
1 июня 2008, 19:37
116

комментарии (44)

0
Markovnin #
круто, давно искал реализацию. спасибо )
+1
daduda #
В Opera 9.5 (9972) почему-то не работает. :(
+5
kostos #
Думаю, это все доработается. Тут же показан сам смысл.
P.S.: Опера вообще странный броузер, вроди и стандарты поддерживает, но в некоторых случаях ведет себя довольно глупо (не про данный пример).
+1
Archon #
Спасибо, сегодня посмотрю на данной версии и попробую исправить.
0
cyberbobs #
Ну, возможно, не имеет смысла всерьёз над этим работать. Opera 9.5 ещё пока что очень beta. Текст-то никуда в результате не разъезжается, просто нет висячей пунктуации (что совершенно не смертельно).

P.S. Не работает и на самой последней beta-сборке оперы, 1997 под intel-linux.
0
Archon #
Подозреваю, дело в том, что в последних версиях «Оперы» они исправили тот глюк, из-за которого требовались строки, помеченные в коде как «dirty hack», и она отображает код более валидно (но неправильно с точки зрения предыдущих версий «Оперы»).
0
SamDark #
Уже не очень бета…
0
pxx #
Да-да, и в ИЕ6 отваливается с JS-ошибкой. Но В фоксе смотрится прекрасно. Сарсибо за скрипт. Если будет homepage скрипта - с удовольствием добавлю его в закладки. И желаю оптимизации и доточки.
0
Novikov #
Народ с "Оперой" 9.5 уже замучал слегка ;-) Мне вот только ленивый не сообщил "аа, ваш сайт не работает в последней нестабильной версии нашего любимого глюкобраузера".
+6
yaad #
Пользуясь вашим скриптом, можно реализовать и другие идеи,
например, висячие союзы в заголовках:
ffffound.com
В русском это односимвольные «и», «а».
–2
ESQUELETO #
Спасибо огромнейшее!
Плюсанул в карму, в топик, в комментарии :-)
+7
DmitryBaranovskiy #
По-хорошему надо бы и эти три элемента создавать в JavaScript чтобы не захламлять код.
0
XXXVII #
Тогда этот скрипт действительно будет крайне полезен!
0
SpeCT #
Особенно учитывая то, что среднестатистический «контент-менеджер» ака «копирайтер» знать не знает, что такое типографика, классы и стили :(
0
Archon #
Сделано. Ссылка та же. Добавляет кусок в самое начало тела, где кусок по идее не должен никому помешать.
+3
kosiakk #
а ещё бы и span .slaquo и .hlaquo создавать автоматически! Это же халява.
Банально - через body.innerHTML заменить все ' «' на '[span class="slaquo"] [/span][span class="hlaquo]«[/span]'.

В итоге: все у кого JS включён получают красивую типографику. Остальные - работюащий сайт без изысков, как и хотели.

я категорически за 100% автоматическую расстановку всего этого при добавлении единственной строчки [script src="tipografy.js"] в head.
+1
rubyrabbit #
да, это было бы законченное, полностью динамическое решение )
+2
SpeCT #
Типографика это конечно замечательно, но мне (подчеркну — мне) всё время казалось, что не всё то, что применимо для бумаги, нужно делать и на вебе. Поясню — читая книжки я уже привык к висячей пунктуации, она не режет глаз, подсознательно она воспринимается как что-то естественное и гармоничное. Но вот в браузере Ваша страничка с примером у меня вызывает какое-то отторжение. Глаз не привык к такой роскоши на просторах интернета, но привык к прямым границам, которые стали (для меня) неким символом стройности контента. А потому текст в примере моим глазом воспринимается как в «корявый какой-та».

PS: Тем не менее спасибо за статью, сам давно пассивно интересовался описанным вопросом (с чисто технической точки зрения).
0
Spunk #
Далеко не во всех книгах есть «висячая пунктуация». Прочитал ваш коммент, проверил в 5-ти книгах :)
0
SpeCT #
Давно уже думаю, что мне надо прокачивать скилл копирайтера, не умею мысли ясно выражать :(

Я имел в виду, что в книжках висячая пунктуация встречается намного чаще, чем в интернете. И в книжках свисающие «ёлочки да скобочки» уже примелькались.
0
Heath #
В русской типографике висячая пунктуация вообще традиционно не использовалась, как мне кажется.
0
Archon #
Использовалась, но для мелких символов — точек, запятых, дефисов и переносов, с правого края. Свешивание «ёлочек» и скобок, действительно, до недавнего времени практически не применялось.
0
Heath #
Приведите примеры изданий. Дело в том, что в ручном наборе делать свешивающуюся пунктуацию довольно дорого (по трудозатратам), потому что полосы должны быть чётко прямоугольными, а со свешивающейся пунктуацией у них был бы рваный правый край, который нужно было бы выравнивать шпациями. Возможно, в строкоотливном наборе с этим стали справляться, но я не уверен, что в СССР кто-то этим занимался.
0
Archon #
Сейчас, увы, добраться до примеров не представляется возможным, но не так давно смотрел несколько книг, свёрстанных (если я правильно помню) в конце восьмидесятых годов, с немного «рваным» правым краем (если смотреть на него, приложив линейку).

Соглашусь с вами, что технологически при ручном наборе это весьма проблематично, особенно учитывая свешивание переносов наполовину. Возможно, с моей стороны имеет место путаница с годами издания.
+1
Heath #
Я не к тому, чтобы поспорить — просто очень интересно, и вообще для общего образования. :) Если удастся найти ссылки — сообщите, пожалуйста.
0
Heath #
Он кажется корявым именно потому, что свисающие элементы слишком далеко свисают — я написал об этом в комментарии ниже. Если свисание уполовинить, всё сразу станет более гармоничным.
0
yaad #
Интересно, в русской типографике можно свешивать номера пунктов в списке?
0
Heath #
У нас это не было принято, но я ничего плохого в таком свешивании не вижу. В русской традиции и ненумерованные списки особо не использовались. Но это же не повод продолжать их не использовать.

Я планировал написать статью про списки в блоге «Типографика», подниму там и этот вопрос.
+1
dab512 #
Если автоматически проставлять все служебные символы, и невидимые блоки, а в функцию передавать список css классов для которых нужно отработать висячую пунктуацию и список символов которые нужно свешивать, то можно продавать рекламу на сайте, на который ринется толпа почитателей веб типографики.
0
Nicomashi #
Красивая реализация, спасибо.
0
Heath #
Переносите в «Типографику». :) Очень хочется, чтобы запись не затерялась в дебрях Хабра.
0
Archon #
Думаю, это всё-таки ближе к веб-разработке, чем к типографике как таковой, хотя и имеет завязки на обе тематики.
0
Heath #
Я написал до того, как топик был в веб-разработку перенесён, так тоже нормально. :) Спасибо.
0
monsterzz #
Правильнее было бы разбирать текст в нужном блоке и окружать нужные span'ами автоматически.
+1
Heath #
А теперь по делу — что касается висячей пунктуации, даже в бумажной вёрстке при её использовании (что бывает о-о-очень редко) висячий символ не свешивается за границу полосы набора целиком — свешивается только частично. В данном варианте и скобка, и кавычка слишком отстранены от полосы набора. Если их наполовину задвинуть обратно, выглядеть это станет значительно лучше.
+1
h8every1 #
В js-коде <div id="1em" style="width: 1em;"> изменить на <div id="1em" style="width: 2em;">
0
khayrov #
На мой взгляд, здесь и половина ширины символа — слишком много. Скобки визуально «вываливаются», что противоречит самой идее оптического выравнивания текста.
Например, в диссертации Хан Те Фана по микротипографике предлагается величина свеса для скобок всего в 5% от их ширины. Это, конечно, зависит от шрифта. В приведённом примере мне близкими к оптимальными показались значения около 0.1em для скобок и 0.2em для кавычек.
Ну это я так, со своей технической (и TeXнической) колокольни, ни разу не специалист по типографике :-)
0
Heath #
Спасибо, диссер интересный, буду изучать. Я сам математик по образованию и диплом в ТеХе набирал. :) Насчёт оптимального свешивания я не экспериментировал, возможно вы и правы. Но что символ не должен свешиваться целиком, по-моему, очевидно.
0
utk #
Странно, у меня в Safari 3.1.1 на маке пример не работает. В FireFox 3 RC1 все отлично.
Консоль при этом выдает:

SyntaxError: Parse error
http://archon.name/trash/quotes/ (line 43)
0
rassadin #
Дорогой мой, Archon, вы просто не застали момент появления висящей пунктуации на artlebedev.ru три года назад, вместе с появлением очередного параграфа в ководстве за номером 120, ей посвященного.

Изначально, мой дорогой друг, реализация висящей пунктуации на artlebedev.ru была выполнена именно на JavaScript, очень схожим с вашим способом.

Следом было обсуждение сего факта и его реализации в ЖЖ. И как вы видите сотрудники студии согласились с приведенными аргументами бессмыслености использования JavaScript в этом вопросе и перенесли код расставления оберток для реализации плавающей пунктуации в парсер сайта.

И, да, еще имейте ввиду, что Times New Roman, он и в Африке Times New Roman. Остальное мне как-то лень пытаться донести, умные люди в предыдущих коментариях намекнули вам на все огрехи, осталось только домыслить немного.
НЛО прилетело и опубликовало эту надпись здесь
+1
tick #
в IE 7 не работает
http://i25.tinypic.com/sx0tif.jpg
0
tot_ra #
Помоему если это невозможно реализовать через css, то на js генерировать тоже не стоит — у людей бывает отключенным js. На мобильниках например. Как и с подсветкой кода, это надо делать на стороне сервера.
0
r3s3t #
Показалось интересным. Открыл пример, ничего висячего не увидел. Нашёл комментарии про Оперу. Ах, вот оно в чём дело… А вы пишете: «Пример гарантированно работает в …, “Опере”, …»

Только зарегистрированные пользователи могут оставлять комментарии. Войдите, пожалуйста.