Плавающие элементы в CSS

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

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

Рассмотрим пример, в котором нам поставили задачу компактно разместить на странице: заголовок второго уровня, два изображения и определенный текст.

За дело, сформируем разметку будущей страницы:

<!DOCTYPE html>
<html>
<head>
	<title>Размещение элементов на странице</title>
<style> 
img {
width: 30%; /* ширина 30% от родительского элемента  */
} 
h2 {
text-align: center; /* выравниваем заголовок по центру */
} 
</style>
</head>
	<body>
		<h2>Панды</h2>
		<img src = "panda1.jpg" alt = "Изображение маленькой панды" title = "Изображение маленькой панды">
		<p>Большая панда, или бамбуковый медведь (лат. Ailuropoda melanoleuca) — вид млекопитающих из семейства медвежьих (Ursidae) со своеобразной чёрно-белой окраской шерсти, обладающих некоторыми признаками енотов. Единственный современный вид рода Ailuropus подсемейства Ailuropodinae.</p>
		<img src = "panda2.jpg" alt = "Изображение большой панды" title = "Изображение большой панды">
		<p>Большие панды обитают в горных регионах центрального Китая: Сычуань и Тибет.
		Со второй половины XX века панда стала чем-то вроде национальной эмблемы Китая. Его западное имя происходит от малой панды. Раньше его также называли пятнистым медведем</p>
	</body>
</html>

В данном примере мы разместили заголовок второго уровня по центру, а элементам <img> задали ширину равную 30% от родительского элемента (<body>) :

Результат нашего примера:

Рис.107 Размещение элементов на странице.
Рис.107 Размещение элементов на странице.

Хм, не кажется ли Вам, что на нашей странице слишком много пустого места и задачу о компактном размещении мы с Вами провалили? Может нам сместить текст ближе к изображению, но как этого можно добиться?


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


То, что надо, давайте внесем правки в наш документ:

<!DOCTYPE html>
<html>
<head>
	<title>Пример работы с плавающими элементами</title>
<style> 
img {
width: 30%; /* ширина 30% от родительского элемента */
} 
h2 {
text-align: center; /* выравниваем заголовок по центру */
} 
.floatLeft {
float: left; /* элемент становится плавающим и смещается по левому краю */
padding: 5px 5px 5px 0; /* устанавливаем внутренние отступы для всех сторон */
}
.floatRight {
float: right; /* элемент становится плавающим и смещается по правому краю */
padding: 5px 0 5px 5px; /* устанавливаем внутренние отступы для всех сторон */
}
p {
text-align: justify; /* горизонтально выравниваем элементы по ширине */
}
</style>
</head>
	<body>
		<h2>Панды</h2>
		<img src = "panda1.jpg" class = "floatLeft" alt = "Изображение маленькой панды" title = "Изображение маленькой панды">
		<p>Большая панда, или бамбуковый медведь (лат. Ailuropoda melanoleuca) — вид млекопитающих из семейства медвежьих (Ursidae) со своеобразной чёрно-белой окраской шерсти, обладающих некоторыми признаками енотов. Единственный современный вид рода Ailuropus подсемейства Ailuropodinae.</p>
		<img src = "panda2.jpg" class = "floatRight" alt = "Изображение большой панды" title = "Изображение большой панды">
		<p>Большие панды обитают в горных регионах центрального Китая: Сычуань и Тибет.
		Со второй половины XX века панда стала чем-то вроде национальной эмблемы Китая. Его западное имя происходит от малой панды. Раньше его также называли пятнистым медведем</p>
	</body>
</html>

И так, что мы добавили к нашему примеру:

Результат нашей работы:

Рис. 108 Пример работы с плавающими элементами.
Рис. 108 Пример работы с плавающими элементами.

С помощью CSS свойства float Вы можете не только перемещать изображения к одной из сторон экрана, но и управлять размещением любых других элементов на странице: меню навигации, боковые панели, рекламные блоки и тому подобное. У данного свойства может быть всего три значения, два из которых мы рассмотрели выше (left и right), а третее значение none, считается значением по умолчанию для всех элементов (элемент не является плавающим и отображается там, где он расположен в потоке документа).


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


Давайте рассмотрим следующий пример:

<!DOCTYPE html>
<html>
<head>
<title>Позиционирование плавающего элемента внутри контейнера</title>
<style> 
.container {
width: 60%; /* ширина 30% от родительского элемента */
height: 200px; /* высота элемента */
background-color: #BBB; /* устанавливаем цвет заднего фона */
margin: 0 auto; /* устанавливаем внешние отступы элемента (осуществляем центрирование) */
}
.floatRight {
float: right; /* элемент становится плавающим и смещается по правому краю */
border: 1px solid red; /* сплошная граница размером 1 пиксель красного цвета */
}
</style>
</head>
<body>
	<div class = "container">
		<div class = "floatRight">
			<p>Что появилось первым?</p>
			<ul>
				<li>Яйцо</li>
				<li>Курица</li>
				<li>Петух</li>
			</ul>
		</div>
	</div>
</body>
</html>

В данном примере мы разместили контейнер шириной 60% от родительского элемента (<body>), осуществили его центрирование и задали цвет заднего фона #BBB. Внутри этого контейнера мы разместили плавающий блок (элемент <div>), который смещен по правому краю:

Рис. 109 Позиционирование плавающего элемента внутри контейнера.
Рис. 109 Позиционирование плавающего элемента внутри контейнера.

Где ты плаваешь, ты, что границ не видишь?

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

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

Давайте рассмотрим пример, в котором рассмотрим подобный случай:

<!DOCTYPE html>
<html>
<head>
	<title>Поведение границ и фона с плавающим элементом</title>
<style> 
div {
border: 3px solid green; /* сплошная граница размером 3 пикселя зеленого цвета */
background-color: rgba(0,255,0,.3); /* устанавливаем цвет заднего фона */
}
img {
width: 30%;/* ширина 30% от родительского элемента */
}
.floatRight {
float: right; /* элемент становится плавающим и смещается по правому краю */
}
</style>
</head>
	<body>
		</div>
			<img src = "kot_pid.jpeg" alt = "кот для примера" class = "floatRight">
			- Котик-котик обормотик, Ты зачем описал ботик. Мама ботик обувала, мама котика ругала.
		</div>
	</body>
</html>

В этом примере мы установили для элемента <div> границы и фоновые значения, внутри элемента разместили изображение, которое занимает 30% от его ширины и указали, что изображение является плавающим, сместив его к правому краю (float: right).

Текстовое содержимое этого блока обтекает изображение с левой стороны, но при этом границы и фон блока отображаются под этим изображением:

Рис. 110 Поведение границ и фона с плавающим элементом.
Рис. 110 Поведение границ и фона с плавающим элементом.

В предыдущей статье этого учебника «Размеры блочных элементов в CSS» мы с вами уже рассматривали свойство overflow, которое предназначено для управления переполнением элементов. Что касается нашего документа, то для того, чтобы фон и границы блока отображались после изображения, а не за ним, необходимо применить свойство overflow со значением auto, или hidden. Это заставит браузер заново рассчитать высоту блока и изменить ее таким образом, чтобы включить и наш плавающий элемент. То есть свойство overflow отменит отображение фона и границ под плавающим элементом:

<!DOCTYPE html>
<html>
<head>
	<title>Использование автоматического переполнения с плавающими элементами</title>
<style> 
div {
border: 3px solid green; /* сплошная граница размером 3 пикселя зеленого цвета */
background-color: rgba(0,255,0,.3); /* устанавливаем цвет заднего фона */
}
img {
width: 30%; /* ширина 30% от родительского элемента */
}
.floatRight {
float: right; /* элемент становится плавающим и смещается по правому краю */
}
.fixContainer {
overflow: auto; /* переполнение будет производиться в автоматическом режиме */
}
</style>
</head>
	<body>
		<div class = "fixContainer">
			<img src = "kot_pid.jpeg" alt = "кот для примера" class = "floatRight">
			- Котик-котик обормотик, Ты зачем описал ботик. Мама ботик обувала, мама котика ругала.
		</div>
	</body>
</html>

В этом примере, мы создали дополнительный класс, в котором указали, что переполнение будет производиться в автоматическом режиме (overflow: auto) и применили этот класс к нашему блоку. Если указать значение hidden (контент, который выходит за размеры будет невидимым) результат будет аналогичен значению auto. В результате это привело к тому, что фон и границы нашего блока отображаются после изображения, а не за ним, что нам и требовалось:

Рис. 111 Использование автоматического переполнения с плавающими элементами.
Рис. 111 Использование автоматического переполнения с плавающими элементами.

Ты сюда не обтекай, ты сюда обтекай (или отмена правил обтекания).

При работе с плавающими элементами вам рано или поздно потребуется, чтобы определенный элемент не взаимодействовал с плавающими элементами и существующие правила обтекания не распространялись на него.

Например, мы составляем какой-то список из блоков, которые содержат в себе изображение и поясняющий текст, при этом изображения являются плавающими и смещаются к правому краю (float: right):

<!DOCTYPE html>
<html>
<head>
	<title>Пример обтекания плавающих элементов</title>
<style> 
div {
border-top: 1px solid red; /* сплошная граница размером 1 пиксель красного цвета */
background-color: rgba(255,0,0,.3); /* устанавливаем цвет заднего фона */
}
img {
width: 25%; /* ширина 25% от родительского элемента */
}
.floatRight {
float: right; /* элемент становится плавающим и смещается по правому краю */
}
</style>
</head>
	<body>
		<div>
			<img src = "kot_pid.jpeg" alt = "кот для примера" class = "floatRight">
			- Котик-котик обормотик, Ты зачем описал ботик. Мама ботик обувала, мама котика ругала.
		</div>
		<div>
			<img src = "kot_pid.jpeg" alt = "кот для примера" class = "floatRight">
			- Котик-котик обормотик, Ты зачем описал ботик. Мама ботик обувала, мама котика ругала.
		<div>
	</body>
</html>

Обратите внимание, какая при этом у нас возникает проблема: второй текстовый блок с изображением начинает обтекать первый блок вместо того, чтобы быть ниже изображения:

Рис. 112 Пример обтекания плавающих элементов.
Рис. 112 Пример обтекания плавающих элементов.

Чтобы решить нашу проблему, необходимо воспользоваться CSS свойством clear, которое определяет с какой стороны текущего элемента не допускаются плавающие элементы.

Это свойство имеет следующие значения:

ЗначениеОписание
noneРазрешает наличие плавающих элементов с обоих сторон элемента. Значение по умолчанию.
leftПлавающие элементы не разрешены с левой стороны.
rightПлавающие элементы не разрешены с правой стороны.
bothПлавающие элементы не разрешены с обоих сторон элемента (как с левой, так и с правой стороны).

Давайте рассмотрим применение этого свойства на нашем примере:

<!DOCTYPE html>
<html>
<head>
	<title>Пример использования свойства clear</title>
<style> 
div {
background-color: rgba(0,255,0,.3); /* устанавливаем цвет заднего фона */
clear: right; /* плавающие элементы не разрешены с правой стороны */
}
img {
width: 25%; /* ширина 25% от родительского элемента */
}
.floatRight {
float: right; /* элемент становится плавающим и смещается по правому кра */
margin-bottom: 15px; /* устанавливаем внешние отступы снизу */
}
</style>
</head>
	<body>
		<div>
			<img src = "kot_pid.jpeg" alt = "кот для примера" class = "floatRight">
			- Котик-котик обормотик, Ты зачем описал ботик. Мама ботик обувала, мама котика ругала.
		</div>
		<div>
			<img src = "kot_pid.jpeg" alt = "кот для примера" class = "floatRight">
			- Котик-котик обормотик, Ты зачем описал ботик. Мама ботик обувала, мама котика ругала.
		</div>
	</body>
</html>

В данном примере мы запретили для блоков <div> плавающие элементы с правой стороны (отменили правила обтекания), что позволило нам выстроить блоки один за одним. Кроме того, для тематического разрыва мы указали для изображений внешние отступы снизу равными 15px.

Рис. 113 Пример использования свойства clear (отмена правил обтекания).
Рис. 113 Пример использования свойства clear (отмена правил обтекания).

Верстка главной страницы сайта плавающими элементами

Чтобы закрепить полученные знания и рассмотреть еще некоторые приемы верстки, давайте рассмотрим следующий пример, который формирует простую разметку главной страницы для сайта:

<!DOCTYPE html>
<html>
<head>
	<title>Пример верстки сайта плавающими элементами</title>
<style>
header {
background-color: #777; /* устанавливаем цвет заднего фона */
}
header ul {
list-style-type: none; /* убираем маркеры */
margin: 0; /* устанавливаем внешние отступы для всех сторон */
padding: 0; /* устанавливаем внутренние отступы для всех сторон */
overflow: auto; /* переполнение будет производиться в автоматическом */
}
header li {
float: left; /* элемент становится плавающим и смещается по левому краю */
}
header li a {
display: inline-block; /* устанавливаем, что элементы становятся блочно-строчными (строчным элементам не задать отступы) */
color: orange; /* устанавливаем цвет элемента */
padding: 10px; /* устанавливаем внутренние отступы для всех сторон */
text-decoration: none; /* убираем подчеркивание */
}
header li a:hover {
background-color: #888; /* устанавливаем цвет заднего фона при наведении */
}
footer {
background-color: #888; /* устанавливаем цвет заднего фона */
clear: both; /* плавающие элементы не разрешены с обеих сторон */
min-height: 30px; /* устанавливаем минимальную высоту элемента */
}
nav {
margin-top: 2%; /* устанавливаем внешние отступы сверху */
float: left; /* элемент становится плавающим и смещается по левому краю */
width: 15%; /* ширина 15% от родительского элемента */
border: 1px solid #888; /* сплошная граница размером 1 пиксель светло-серого цвета */
}
nav ul {
list-style-type: none; /* убираем маркеры */
padding: 0; /* устанавливаем внутренние отступы для всех сторон */
}
nav li a {
color: orange; /* устанавливаем цвет элемента */
padding: 10px; /* устанавливаем внутренние отступы для всех сторон */
text-decoration: none; /* убираем подчеркивание */
}
nav li a:hover {
color: #777; /* устанавливаем цвет элемента при наведении */
}
section {
margin: 2% 0 0 16%; /* устанавливаем внешние отступы для всех сторон */
border: 1px solid #888; /* сплошная граница размером 1 пиксель светло-серого цвета */
}
img {
width: 13%; /* ширина 13% от родительского элемента */
margin: 2% 10%; /* устанавливаем внешние отступы для всех сторон */
float: left; /* элемент становится плавающим и смещается по левому краю */
border: 1px solid orange; /* сплошная граница размером 1 пиксель оранжевого цвета */
}
.clearCats {
clear: left; /* плавающие элементы не разрешены с левой стороны */
}
</style>
</head>
	<body>
		<header> /* шапка сайта начало */
			<ul>
				<li><a href = "#">Домой</a>|</li>
				<li><a href = "#">Раздел 1</a>|</li>
				<li><a href = "#">Раздел 2</a>|</li>
				<li><a href = "#">Раздел 3</a></li>
			</ul>
		</header> /* шапка сайта конец */
		<nav> /* дополнительная навигация начало */
			<ul>
				<li><a href = "#">Домой</a></li>
				<li><a href = "#">Раздел 1</a></li>
				<li><a href = "#">Раздел 2</a></li>
				<li><a href = "#">Раздел 3</a></li>
			</ul>
		</nav> /* дополнительная навигация конец */
		<section> /* основное содержимое начало */
		- Котик-котик обормотик, Ты зачем описал ботик.<br> Мама ботик обувала, мама котика ругала.
		</section>
		<section>
		- Котик-котик обормотик, Ты зачем описал ботик.<br> Мама ботик обувала, мама котика ругала.
		</section>
		<div class = "clearCats">  
			<img src = "kot_pid.jpeg" alt = "кот для примера">
			<img src = "kot_pid.jpeg" alt = "кот для примера">
			<img src = "kot_pid.jpeg" alt = "кот для примера">
		</div> /* основное содержимое конец */
		<footer>2016, Все права принадлежат коту и сайту basicweb.ru.</footer> /* подвал сайта */
	</body>
</html>

И так по порядку, что мы сделали в этом примере:

  1. Для шапки сайта (HTML тег <header>html5) мы установили следующие свойства:

    • Цвет заднего фона элемента (#777).
    • Для маркированного списка (HTML тег <ul>) убрали маркеры (list-style-type: none), установили внутренние и внешние отступы равными нулю, для того, чтобы панель отображалась со всеми плавающими элементами установили переполнение в автоматическом режиме (overflow: auto). Эту важную особенность работы с плавающими элементами мы рассматривали выше (запрещали отображение границ и фон блока под изображением).
    • Указали, что элементы маркированного списка (<li>) будут плавающими и сместили их по левому краю.
    • Определили, что ссылки будут как блочно-строчные элементы, для того, чтобы задать им размеры (display: inline-block). Указали, что цвет ссылок будет оранжевый, внутренние отступы со всех сторон будут 10px и убрали нижнее подчеркивание (text-decoration: none). При наведении на ссылку курсором мыши задний фон элемента изменяется на светло-серый #888 (псевдокласс :hover).
  2. Для подвала сайта (HTML тег <footer>html5) мы установили следующие свойства:

    • Цвет заднего фона элемента (#777).
    • Минимальную высоту элемента (min-height: 30px).
    • Указали, что плавающие элементы не разрешены с обеих сторон элемента (как с левой, так и с правой стороны). Это сделано для того, чтобы элемент не мог подняться (в нашем случае достаточно и значения left).
  3. Разместили дополнительную навигацию с правой стороны HTML элементом <nav>html5 и установили для него следующие значения:

    • Внешний отступ сверху равный 2%.
    • Указали, что элемент является плавающим и сместили по левому краю.
    • Определили ширину для элемента равной 15% от родительского элемента (в нашем случае <body>).
    • Задали вокруг элемента сплошную границу размером 1px светло-серого цвета (#888).
    • Для маркированного списка (HTML тег <ul>) убрали маркеры (list-style-type: none), установили внешние отступы равными нулю.
    • Указали, что цвет ссылок будет оранжевый, внутренние отступы со всех сторон будут 10px и указали, что нижнее подчеркивание отсутствует (text-decoration: none). При наведении на ссылку курсором мыши цвет ссылок изменяется с оранжевого на серый #777 (псевдокласс :hover).
  4. Предполагается, что информационное содержимое будет размещаться в элементах <section>html5, для которых мы установили следующие значения:

    • Интересный момент здесь заключается в том, что мы указываем внешние отступы слева 16% для элемента. У элемента <nav>html5, напомню, ширина установлена 15%, то есть элемент будет обтекать навигационную панель, но при этом будет выдерживаться отступ 16%, формируя ровный столбец при наполнении, верхний отступ установлен 2%, для других сторон 0 (margin: 2% 0 0 16%).
    • Установили вокруг элемента сплошную границу размером 1px светло-серого цвета (#888).
  5. Элементы <img> (изображения) мы поместили в отдельный блок с классом .clearCats, для которого установили, что плавающие элементы не разрешены с левой стороны, тем самым данный блок не будет обтекать навигационную панель (отменяем правила обтекания).

  6. Для самих изображений (HTML элемент <img>) мы установили следующие свойства:

    • Определили ширину для элементов равной 13% от родительского элемента.
    • Внешние отступы для верха и низа элемента 2%, для левой и правой стороны 10% (margin: 2% 10%;).
    • Определили, что изображения будут плавающими и сместили по левому краю.
    • Добавили вокруг изображений границу оранжевого цвета размером 1px.

Результат нашей работы представлен на изображении:

Рис. 114 Пример верстки сайта плавающими элементами.
Рис. 114 Пример верстки сайта плавающими элементами.


Вопросы и задачи по теме

Перед тем как перейти к изучению следующей темы пройдите практическое задание:

  • Для выполнения задания вам понадобится скачать архив и скопировать содержимое архива (HTML файл) в любую папку на вашем жестком диске:

  • Используя полученные знания составьте следующий документ, применяя плавающие элементы (внимательно изучите страницу перед выполнением):

    Практическое задание № 27.

    Практическое задание № 27.

    Подсказка: для боковой панели указана ширина 15% от родительского элемента, а высота 400px. В документе использованы цвета #333, #999, #fff. Вы можете использовать произвольные значения для элементов в документе. Обращаю Ваше внимание, что для выполнения этого задания Вам необходимы знания из прошлых статей учебника.

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