Добрый день,
Я пытаюсь создать небольшой слайдер (это учебный пример для моей будущей книжки по HTML/CSS/JS).
Всё было нормально, но в некоторый момент началось странное поведение в плане перекрытия блоков, которое я никак не могу понять. Возможно, ответ лежит где-то в недрах стандарта? Огромная просьба подсказать, в чём проблема, или хотя бы где почитать, чтобы понять это.
Итак, есть следующая разметка:
<div id="main">
<header><div id="logo"></div></header>
<nav><a href="/" class="current">Главная</a><a href="tours.html">Туры</a><a href="feedback.html">Отзывы</a><a href="about.html">О нас</a></nav>
<main>
<p>Добро пожаловать на сайт туроператора "Компас-Тур"!</p>
<div id="slider_wrap">
<div id="slider"><div class="left"></div><div class="right"></div><div class="film"></div></div>
<div class="dots"></div>
</div>
</main>
<footer></footer>
</div>
...
main {
min-height: 530px;
padding: 32px 28px 18px;
font-family: Arial;
font-size: 13px;
}
main > h1 {
font-family: Georgia;
color: #c50;
font-size: 24px;
margin: 14px 0px 18px;
}
footer {
height: 38px;
}
#slider_wrap {
width: 510px;
}
#slider {
width: 510px;
height: 290px;
position: relative;
overflow: hidden;
margin-top: 18px;
}
#slider .film {
position: absolute;
top: 0px;
left: 0px;
height: 100%;
transition: left 1s;
-moz-tranzition: left 1s;
-o-transition: left 1s;
-ms-transition: left 1s;
}
#slider .film > a {
display: block;
text-decoration: none;
border: none;
float: left;
width: 510px;
height: 290px;
position: relative;
}
#slider .film > a > .title {
position: absolute;
left: 0px;
bottom: 0px;
width: 120px;
height: 32px;
background: rgba(0, 0, 0, 0.6);
padding: 4px 16px;
transition: opacity 0.8s ease-in-out 0.2s;
}
#slider .film > a > .title > span {
color: #fff;
font-size: 20px;
font-family: Verdana;
text-shadow: 1px 0px #000;
}
#slider_wrap > .dots {
margin: -26px auto 0px;
width: 160px;
text-align: center;
z-index: 1;
position: relative;
}
#slider_wrap > .dots > div {
display: inline-block;
width: 16px;
height: 16px;
margin: 2px;
}
#slider_wrap > .dots > div > div {
display: inline-block;
border: 2px solid #fff;
border-radius: 6px;
width: 8px;
height: 8px;
margin: 0px 2px;
}
#slider_wrap > .dots > div.active > div {
background: #fff;
}
Она даёт следующий вывод:
Не буду полностью приводить все стили и скрипты, просто объясню, что происходит, и что меня не устраивает.
Изначально в элементе с классом "dots" выводились элементы, которые служили индикаторами текущей страницы слайдера. Выводились они как инлайново-блочные элементы, содержимое центрировалось через text-align. Затем я сделал их кликабельными. Потом я увидел, что кликать по ним не очень-то удобно из-за небольшого размера, и решил обернуть их в обёртки, дабы сделать допустимую область для клика чуть больше. И вот тут начались проблемы.
Дело в том, что изначально я ради гибкости (чтобы была возможность отображать эти индикаторы и вне слайдера) не стал вкладывать элемент с классом "dots" прямо в слайдер, а вложил его в специальный элемент-обёртку. Потом я всё же решил выводить его поверх слайдера, и использовал сдвиг с помощью margin-top в верхнюю сторону.
Вопрос: почему до того, как я использовал обёртки у div-ов внутри элемента "dots" элемент "dots" выводился
поверх слайдера, а как только я ввёл их - слайдер начал его перекрывать, и потребовались довольно нетривиальные операции с z-index, чтобы это поправить?
Два рабочих варианта изменений, которые я нашёл: добавить элементу c class="dots" position: relative (то есть вытащить его из нормального потока); добавить элементу c id="main" свойства z-index: -1; position: relative, а элементу с id="slider" z-index: -1 (position: relative у него уже есть, так как id="film" внутри него позиционируется абсолютно).
Вопрос 2: Я полагал, что при использовании отрицательных z-index сначала выводятся элементы с отрицательными индексами в порядке их возрастания, затем фон, затем элементы с position: static, затем элементы с нулевыми и положительными индексами. Я так думал потому, что мне удалось в тестовом примере вывести элемент
под фоном, присвоив ему z-index, равный -1 (фон был полупрозрачный).
Но теперь, произведя все манипуляции, которые потребовались, чтобы пофиксить проблему, эта теория рушится: если я присваиваю элементу "slider" z-index, равный -1, то он выводится... под фоном элемента "main" (даже если задать элементу "slider_wrap" свой собственный фон)! Почему происходит именно так? При создании элемента с z-index меньше нуля, он проваливается не только под фон своего родителя, но и под фоны всех предков (на самом деле, не совсем всех, фон элемента body остался ниже элемента "slider").
UPD: со второй частью вопроса частично прояснилось. Если добавить элементу с id="slider_wrap" position: relative; z-index: 0, а элементу с id="slider" присвоить z-index, равный -1, то оно тоже отображается правильно. При чём если выкинуть z-index: 0, то всё снова ломается. И это логично - ведь указывая z-index на этом элементе, я создаю новый контекст наложения, в противном же случае этот контекст находится выше, видимо как раз на элементе с id="main" (правда я хз, почему именно на нём - там не указан z-index, и тот элемент даже не позиционируемый).