Опубликован: 28.11.2008 | Уровень: для всех | Доступ: платный
Лекция 37:

Абсолютное и фиксированное позиционирование CSS

< Лекция 36 || Лекция 37: 12345 || Лекция 38 >

Определение позиции

При рассмотрении относительного позиционирования мы узнали, что для определения позиции бокса можно использовать свойства top, right, bottom и left. Эти же свойства используются для определения позиции абсолютно позиционированного бокса, но способ их использования совершенно другой.

Для относительно позиционированного элемента четыре свойства определяют относительное расстояние для смещения сгенерированного бокса. Помните, что в случае относительного позиционирования они дополняют друг друга, так что top:1em и bottom:-1em означают одно и то же, и не имеет смысла определять одновременно top и bottom (или left и right ) для одного и того же элемента, так как одно из значений будет проигнорировано.

Эти положения неверны в случае абсолютного позиционирования. Здесь все четыре свойства можно использовать одновременно для определения расстояния от каждого края позиционированного элемента до соответствующего края объемлющего блока. Можно определить также позицию одного из углов абсолютно позиционированного бокса - например, используя top и left - а затем определить размеры бокса, используя width и height (или вообще не использовать width и height, если вы хотите позволить боксу сжиматься в соответствии с его контентом).

Microsoft Internet Explorer версии 6 и более старые не поддерживают метод задания всех четырех ребер, но поддерживают метод задания одного угла и размеров.

/* Этот метод работает в IE6 */
#foo {
  position: absolute;
  top: 3em;
  left: 0;
  width: 30em;
  height: 20em;
}

/* Этот метод не работает в IE6 */
#foo {
  position: absolute;
  top: 3em;
  right: 0;
  bottom: 3em;
  left: 0;
}

Необходимо здесь запомнить, что значения, которые задаются для свойств top, right, bottom и left определяют расстояние от краев элемента до соответствующих краев его объемлющего блока. Это не соответствует координатной системе, где каждое значение задается относительно одной точки начала координат. Например, right:2em означает, что правый край абсолютно позиционированного бокса будет отстоять на 2em от правого края объемлющего блока.

Поэтому при использовании абсолютного позиционирования критически важно знать, что является объемлющим блоком. Именно поэтому задание position:relative на объемлющем блоке будет так полезно, даже если вы не сдвигаете позицию бокса. Это позволяет сделать элемент объемлющим блоком для его абсолютно позиционированных потомков, что обеспечивает управление.

Давайте рассмотрим пример, чтобы увидеть, как это работает.

1. Скопируйте представленный ниже код в текстовый редактор и сохраните документ как absolute.html.

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
    <title>Absolute Positioning</title>
    <link rel="stylesheet" type="text/css" href="absolute.css">
  </head>
  <body>
    <div id="outer">
      <div id="inner"></div>
    </div>
  </body>
</html>

2. Затем скопируйте следующий код в новый файл и сохраните его как absolute.css.

html, body {
  margin: 0;
  padding: 0;
}

#outer {
  margin: 5em;
  border: 1px solid #f00;
}

#inner {
  width: 6em;
  height: 4em;
  background-color: #999;
}

3. Сохраните оба файла и загрузите документ HTML в браузер. Вы увидите серый прямоугольник, окруженный достаточно широкой красной границей. Элемент #inner имеет указанную ширину и высоту и серый цвет фона. Элемент #outer, который является структурным предком #inner, имеет красную границу. Он имеет со всех сторон также поле шириной 5em, чтобы сместить его от краев окна браузера, и более четко видеть, что происходит. Пока ничего удивительного, не так ли? Высота элемента #outer задана его элементом потомком ( #inner ) и шириной горизонтальных полей.

4. Теперь посмотрим, что произойдет, если сделать элемент #inner абсолютно позиционированным! Добавьте следующее выделенное объявление в правило #inner:

#inner {
  width: 6em;
  height: 4em;
  background-color: #999;
  position: absolute;
}

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

Здесь произошли два интересных события. Прежде всего, при абсолютном позиционировании элемент #inner полностью удаляется из потока документа. Это означает, что его предок, #outer, теперь не имеет потомков в нормальном потоке документа, так что его высота схлопывается до нуля.

То, что выглядит как красная линия толщиной 2px, является в действительности границей толщиной 1px вокруг элемента с нулевой высотой - вы видите верхнюю и нижнюю границы и ничего между ними.

Второе интересное событие состоит в том, что абсолютно позиционированный бокс не смещается. Значение по умолчанию для свойств top, right, bottom и left будет auto, что означает, что абсолютно позиционированный бокс появится точно там, где он был бы, если бы не был позиционирован. Однако так как он был удален из потока, он будет перекрывать все элементы в нормальном потоке, которые следуют за ним.

На самом деле это очень полезно - можно использовать это, если вы хотите только переместить сгенерированный бокс в одном направлении. Например, в раскрывающемся меню, управляемом CSS, "раскрывающиеся" панели можно абсолютно позиционировать, определяя только свойство top. Они будут затем автоматически появляться в ожидаемой координате по оси X (также, как и их предок).

6. Затем давайте зададим высоту для элемента #outer, чтобы он снова выглядел как прямоугольник, и смещал #inner в сторону. Добавьте следующие выделенные строки в правила CSS:

#outer {
  margin: 5em;
  border: 1px solid #f00;
  height: 4em;
}

#inner {
  width: 6em;
  height: 4em;
  background-color: #999;
  position: absolute;
  left: 1em;
}

7. Сохраните и перезагрузите, и вы увидите некоторые изменения. Элемент #outer будет теперь снова прямоугольником, так как вы задали для него высоту. Элемент #inner смещается в сторону, но не туда, куда вы могли бы ожидать. Он находится на расстоянии 1em не от левой границы своего предка, а на расстоянии 1em от левого края окна!

Причина в том, как объяснялось выше, что элемент #inner не имеет позиционированного предка, поэтому его объемлющий блок является начальным объемлющим блоком. Если определить позицию отличную от auto, то она будет задана относительно соответствующего края объемлющего блока. Если задать left:1em, то левый край элемента #inner закончится на расстоянии 1em от левого края окна.

8. Если вы хотите вместо этого, чтобы он был на расстоянии 1em от левого края его элемента предка, то необходимо сделать предка объемлющим блоком. Для этого мы используем теперь прием, который упоминался ранее в статье - сделаем блок предок относительно позиционированным. Добавьте следующую выделенную строку в правило #outer:

#outer {
  margin: 5em;
  border: 1px solid #f00;
  height: 4em;
  position: relative;
}

9. Сохраните и перезагрузите документ - и вот! Серый прямоугольник теперь находится на расстоянии 1em от левой границы элемента предка. Задание position:relative в правиле #outer делает его позиционированным и задает как объемлющий блок для всех абсолютно позиционированных потомков, которые он мог бы иметь. Задание left:1em для элемента #inner теперь отсчитывается от левого края элемента #outer, а не от левого края окна браузера.

< Лекция 36 || Лекция 37: 12345 || Лекция 38 >
Марина Походаева
Марина Походаева

Помогите мне. Я ничего не понимаю в курсе ((((((   (от слова "совсем") и мне от этого очень грустно. Есть ли какие-нибудь курсы для "чайников", самые простые в объяснении. ПАМАГИТЕ!!!

Федор Антонов
Федор Антонов

Здравствуйте!

Записался на ваш курс, но не понимаю как произвести оплату.

Надо ли писать заявление и, если да, то куда отправлять?

как я получу диплом о профессиональной переподготовке?

Данила Некрасов
Данила Некрасов
Россия, Пермь, ПНИПУ
Сергей Федоров
Сергей Федоров
Россия