0

I have been met with a bit of surprise today, I have the bellow HTML markup. In my CSS I set the container to position: fixed; z-index: 3, and then I provided a z-index of 1 to div#1 and div#3 giving div#2 z-index: 2. My expectation is that when I move div#3 up that it will go behind div#2 but to my greatest surprise it always stays above it no matter the value of its z-index or that of div#2, I am confused why this is, maybe I don't just understand the stacking context as much as I think I do. Any help? Below I have the css.

* {
  box-sizing: border-box;
}

body, html, .container {
  height: 100%;
  width: 100%;
}

.container {
  position: fixed;
  z-index: 300;
}

#div1, #div2, #div3 {
  opacity: 0.7;
  padding: 10px;
}

#div1 {
  border: 1px dashed #996;
  background-color: #ffc;
  height: 33.333%;
  z-index: 1;
}

#div2 {
  border: 1px dashed #900;
  background-color: #fdd;
  height: 33.333%;
  z-index: 2;
}

#div3 {
  border: 1px dashed #696;
  background-color: #cfc;
  height: 33.333%;
  z-index: 1;
  transform: translateY(-40px)
}
<div class='container'>
  <div id="div1">DIV#1 </div>
  <div id="div2">DIV#2</div>
  <div id="div3">DIV#3</div>
</div>
George
  • 3,757
  • 9
  • 51
  • 86

4 Answers4

3

Your element need to be at least position:relative to use z-index as this property doesn't work with static position (the default value)

as you can read here :

Note: z-index only works on positioned elements (position:absolute, position:relative, or position:fixed).

* {
  box-sizing: border-box;
}

body, html, .container {
  height: 100%;
  width: 100%;
}

.container {
  position: fixed;
  z-index: 300;
}

#div1, #div2, #div3 {
  position:relative;
  opacity: 0.7;
  padding: 10px;
}

#div1 {
  border: 1px dashed #996;
  background-color: #ffc;
  height: 33.333%;
  z-index: 1;
}

#div2 {
  border: 1px dashed #900;
  background-color: #fdd;
  height: 33.333%;
  z-index: 2;
}

#div3 {
  border: 1px dashed #696;
  background-color: #cfc;
  height: 33.333%;
  z-index: 3;
  transform: translateY(-40px)
}
<div class='container'>
  <div id="div1">DIV#1 </div>
  <div id="div2">DIV#2</div>
  <div id="div3">DIV#3</div>
</div>
Temani Afif
  • 245,468
  • 26
  • 309
  • 415
3

In order to create a stacking context using the z-index property, the element in question must be a positioned element.

The z-index CSS property specifies the z-order of a positioned element and its descendants.

Ref: z-index -CSS | MDN

Positioned elements are any elements with a position property declared, other than static; which is the default positioning of any element.

Example of positioned elements:

  1. relative (relative)
  2. absolute (absolute)
  3. fixed (absolute)
  4. sticky (stickily)

Ref: position -CSS | MDN (Types of positioning)

To demonstrate this, declare relative positioning on the nested div elements of the containing parent element .container, e.g:

.container > div {
  position: relative;
}

Code Snippet Demonstration:

/* Additional */

.container > div {
  position: relative;
}

* {
  box-sizing: border-box;
}

body, html, .container {
  height: 100%;
  width: 100%;
}

.container {
  position: fixed;
}

#div1, #div2, #div3 {
  opacity: 0.7;
  padding: 10px;
}

#div1 {
  border: 1px dashed #996;
  background-color: #ffc;
  height: 33.333%;
  z-index: 1;
}

#div2 {
  border: 1px dashed #900;
  background-color: #fdd;
  height: 33.333%;
  z-index: 2;
}

#div3 {
  border: 1px dashed #696;
  background-color: #cfc;
  height: 33.333%;
  z-index: 1;
  transform: translateY(-40px)
}
<div class="container">
  <div id="div1">DIV#1 </div>
  <div id="div2">DIV#2</div>
  <div id="div3">DIV#3</div>
</div>

For further information: Understanding CSS z-index - CSS | MDN

UncaughtTypeError
  • 8,226
  • 4
  • 23
  • 38
2

add position: relative to the divs

* {
  box-sizing: border-box;
}

body, html, .container {
  height: 100%;
  width: 100%;
}

.container {
  position: fixed;
  z-index: 300;
}

#div1, #div2, #div3 {
  opacity: 0.7;
  padding: 10px;
}

#div1 {
  border: 1px dashed #996;
  background-color: #ffc;
  height: 33.333%;
  z-index: 1;
  position: relative;
}

#div2 {
  border: 1px dashed #900;
  background-color: #fdd;
  height: 33.333%;
  position: relative;
  z-index: 2;
}

#div3 {
  border: 1px dashed #696;
  background-color: #cfc;
  height: 33.333%;
  z-index: 1;
  position: relative;
  transform: translateY(-40px)
}
<div class='container'>
  <div id="div1">DIV#1 </div>
  <div id="div2">DIV#2</div>
  <div id="div3">DIV#3</div>
</div>
fab
  • 1,189
  • 12
  • 21
0

You've got it right, just add position: relative; to the elements so the z-index setting will take effect.

The z-index CSS property specifies the z-order of a positioned element and its descendants. MDN - CSS z-index A positioned element is an element whose computed position value is either relative, absolute, fixed, or sticky. (In other words, it's anything except static.) MDN - CSS position

* {
  box-sizing: border-box;
}

body, html, .container {
  height: 100%;
  width: 100%;
}

.container {
  position: fixed;
  z-index: 300;
}

#div1, #div2, #div3 {
  opacity: 0.7;
  padding: 10px;
  position: relative;
}

#div1 {
  border: 1px dashed #996;
  background-color: #ffc;
  height: 33.333%;
  z-index: 1;
}

#div2 {
  border: 1px dashed #900;
  background-color: #fdd;
  height: 33.333%;
  z-index: 2;
}

#div3 {
  border: 1px dashed #696;
  background-color: #cfc;
  height: 33.333%;
  z-index: 1;
  transform: translateY(-40px);
}
<div class='container'>
  <div id="div1">DIV#1 </div>
  <div id="div2">DIV#2</div>
  <div id="div3">DIV#3</div>
</div>
JasonB
  • 6,243
  • 2
  • 17
  • 27