Какое-то древнее дерьмо

Живёт тупо потому, что за хостинг уплачено на годы вперед

Семантическая верстка — советы и решения. Часть V. Навигация по сайту или укрощение списков

8 февраля 2008 · Комментариев: 18 · HTML/CSS, Рецептарий

Навигация — это то, с чего начинается любой сайт, ведь без нее пользователь просто не сможет им пользоваться. Не удивительно, что мы заострим на ее организации свое внимание.

Представим себе кусочек макета, присланного нам дизайнером. На нем изображено главное меню будущего сайта:

Иллюстрация 1

Пункт меню «Обратная связь» показывает поведение при наведении мышкой.

Если забыть на время про семантику, то наше меню можно представить в HTML приверно так:

<table id=”main-nav”><tr>
        <td><a href=””>Новости</a></td>
	  …
    </tr>
</table>

Набросать небольшой CSS, использовать Javascript для подсветки пункта при наведении мышкой и жить счастливо. Но не правильно.

При таком подходе мы теряем первичный структурный смысл нашей навигации. Любое меню — прежде всего список. Не даром мы говорим именно «пункт меню» и читаем книги, в которых оглавление более всего похоже именно на список.

Поэтому, вспомнив о семантике документа мы напишем код нашей навигации следующим образом:

<ul id=”main-nav”>
    <li><a href=””>Новости</a></li>
    …
</ul>

Первый шаг к светлому будущему. Однако наше горизонтальное меню в данный момент выглядит в браузере следующим образом:

Иллюстрация 2

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

Немного магии CSS

Начнем с решения двух вышеназванных проблем:

* {margin:0;padding:0;}
body {
    padding:40px;
    background:#FFF;
    font:100.01% Tahoma,Helvetica,sans-serif;
    color:#000;
    }
ul#main-nav {
    float:left; /* Предотвращаем эффект, при котором список не охватит внутри себя свои пункты. Это будет видно, если задать ul видимые границы */
    font:bold .75em Tahoma,Helvetica,sans-serif; /* Устанавливаем параметры шрифта */
    }
ul#main-nav li {
    float:left; /* «Прижимаем» элементы списка налево, эмулируя горизонталь */
    list-style:none; /* Убираем маркеры у пунктов списка */
    }

Я не буду здесь останавливаться на механизмах работы правила float, так о нем можно писать целые книги. Подробное объяснение на русском можно почепнуть в статье Ивана Сагалаева «Раскладка в CSS: float».

В итоге мы получили следующий результат:

Иллюстрация 3

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

Javascript? Не наш метод

В стандарте CSS 2.1, который является текущим, предусмотрен псевдоселектор :hover, благодаря которому мы можем менять стиль элемента по тому же принципу, как делаем при onmouseover при помощи Javascript. Одна проблема — IE шестой версии и ниже применяет :hover только к ссылкам. Флагманы технического прогресса, что уж тут скажешь.

Но не стоит отчаиваться. Поскольку наш список все-таки является навигацией, в нем совершенно очевидным образом находятся ссылки, к которым :hover в IE 5 и 6 можно применить без лишних проблем. Заодно на ссылки мы навесим и другие элементы оформления, такие как оступы, границы и цвет.

ul#main-nav li a {
    display:block; /* Делаем ссылки блочным элементом, чтобы они могли нативно работать с внутренними полями */
    position:relative; /* Небольшой «хак», чтобы в IE кликабельная область распространилась на внутренние поля */
    padding:4px 8px; /* Внутренние поля */
    background:#FFF; /* Цвет фона */
    border:1px solid #CCC; /* Границы */
    border-width:1px 0 1px 1px;
    color:#47AAE9; /* Цвет шрифта */
    }
    ul#main-nav li a:hover {
        background:#F2F2F2; /* Цвет фона при наведении на ссылку */
        color:#000; /* Цвет шрифта при наведении на ссылку */
        }

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

ul#main-nav {
    float:left;
    border-right:1px solid #CCC;
    font:bold .75em Tahoma,Helvetica,sans-serif;
    }

Иллюстрация 4

Отлично, не правда ли? Мы добились не только нужного визуального отображения, но и поведения, при этом используя лишь семантически верную HTML-разметку и CSS.

У данного решения есть один минус — в Opera седьмых версий элементы списка не выстроятся линию, пока мы не зададим списку конкретную ширину. Это проблема продвинутого уровня и я не буду на ней останавливаться. Попытайтесь найти решение самостоятельно.

Комментариев: 18 ↓

  • FX Poster

    Мдя… Неинтересно. Лучше пример верстки форм приведи. Я хочу что-то типа этого, только чтобы js’а не нужно было.

    Hint: если вместо inline-block использовать float – получается фигня с выравниванием по вертикали label’ов и input’ов (при изменении размеров шрифтов).

  • Flack

    Это серия статей для начинающих, о чём уже говорилось.
    А про формы я уже достаточно написал, задолбало.

  • егор

    а действующий пример?

  • Flack

    Чего. Тут вроде и так всё понятно.

  • егор

    понятно-то, понятно, но иногда хочется по ссылкам поводить курсором, посмотреть как цвета меняются

  • Flack

    Собрались тут любители дзена :)

  • Amiego

    Долго же я ждал продолжения) Дождался, спасибо огромное! Пожалуй, нигде в рунете такую информацию не найти…

  • h4

    > в Opera седьмых версий элементы списка не выстроятся линию

    Насколько сейчас это востребовано – поддержка Opera 7?

  • Flack

    Нахуй никому не надо.

  • Ivan

    Учтем ваши замечания .пишите ещё уважаемый

  • Max

    А как быть с тэгом див?

  • Flack

    В каком смысле?

  • Дмитрий

    Вообще, эта тема достаточно давно раскрыта в массе разных статей. Напишите про каике-нибудь фишки с использованием CSS3. Это было бы очень интересно.

  • Евгений

    Спасибо! Очень хорошая статья. Никак не мог найти более лучшего объяснения про выравнивание списков по горизонтали

  • Юрий

    Актуально ли оптимизировать верстку для КПК-шного IE5? Или это уже совсем архаизм?..

  • alexissss

    В иллюстрациях я бы еще добавил картинки для сравнения с возможными альтернативами. Подобных статей действительно немало. А так было бы совсем наглядно и тем ценно.

  • Антон

    Спасибо за статью!.
    Мне оч нравиться меню на сайте http://www.fantesca.com.
    скачал сайт, но никак не могу его воспроизвести, посоветуйте пожалуйста, ресурс или книгу, в которой были бы описаны тонкости создания подобной навигации средствами css . заранее спасибо!

Оставить комментарий