Why absolutely positioned elements render over previous absolutely positioned element? - html

In this code,
#parent-div{
background: #B3bEb5;
border: 0.1em solid black;
}
#default{
background: #DBE9F4;
}
#centered{
background: #89CFF0;
width: 50%;
margin: auto;
}
/* text-align: left, right, center, justify */
#centered-text{
text-align: center;
}
/* Absolute Positioning : Positioning Based on the Document */
#top-left-pos{
background: #89CFF0;
border: 0.1em solid black;
position: absolute;
width: 200px;
height: 100px;
}
#bottom-right-tl-parent {
background: #DBE9F4;
position: absolute;
bottom: 0px;
right: 0px;
}
#another-pos{
background: #FF0000;
border: 0.1em solid black;
position: absolute;
width: 190px;
height: 110px;
}
<div id="parent-div">
<div id="default">Default</div>
<div id="centered">Centered</div>
<div id="centered-text">Centered Text</div>
</div>
<!-- Demonstrate Absolute Postioning -->
<div id="top-left-pos">Top Left
<div id="bottom-right-tl-parent">Bottom Right Parent</div>
</div>
<div id="another-pos">Top Right
</div>
absolutely positioned top-left-pos element, positions in next row to centered-text element, whose behaviour similar to static positioned elements.
But,
below is the output,
So, Why every new absolutely positioned element another-posis rendered over previous absolutely positioned element top-left-pos? why another-pos element is not rendered as next block element?
With the above code, am expecting another-pos element to be rendered as shown below,

So, Why every new absolutely positioned element another-posis rendered
over previous absolutely positioned element top-left-pos? why
another-pos element is not rendered as next block element?
"The absolutely positioned element is positioned relative to nearest positioned ancestor(non static). If a positioned ancestor doesn't exist, the initial container is used."
Src: CSS/position
This means that if you have 1 or 10 elements using position: absolute, they all start at the same top/left position (if you omit those values in your css rule).
As such they are also taken out of normal flow, which below sample shows, where yet another div, #another-nonpos, using normal flow starts after the previous normal flowed element.
It also shows that positioned elements have a higher z-index than non positioned, making them stay in a higher layer (on top of).
Further reading about z-index: Understanding CSS z-index
#parent-div{
background: #B3bEb5;
border: 0.1em solid black;
}
#default{
background: #DBE9F4;
}
#centered{
background: #89CFF0;
width: 50%;
margin: auto;
}
/* text-align: left, right, center, justify */
#centered-text{
text-align: center;
}
/* Absolute Positioning : Positioning Based on the Document */
#top-left-pos{
background: #89CFF0;
border: 0.1em solid black;
position: absolute;
width: 200px;
height: 100px;
}
#bottom-right-tl-parent {
background: #DBE9F4;
position: absolute;
bottom: 0px;
right: 0px;
}
#another-pos{
background: #FF0000;
border: 0.1em solid black;
position: absolute;
width: 190px;
height: 110px;
}
#another-nonpos{
background: lime;
height: 200px;
text-align: right
}
<div id="parent-div">
<div id="default">Default</div>
<div id="centered">Centered</div>
<div id="centered-text">Centered Text</div>
</div>
<!-- Demonstrate Absolute Postioning -->
<div id="top-left-pos">Top Left
<div id="bottom-right-tl-parent">Bottom Right Parent</div>
</div>
<div id="another-pos">Top Right
</div>
<div id="another-nonpos">Non absolute
</div>

Because the #top-left-pos has greater value of z-index property

When using position:absolute , the div has nothing to do with the document and and gets the parent level regardless of using z-index. in your case, the bottom-right-tl-parent is the child of top-left-pos, thus increasing z-index value wont effect its level. if you move the bottom-right-tl-parent out of top-left-pos, you will be able to apply your z-index and it will work:
<div id="top-left-pos">Top Left</div>
<div id="bottom-right-tl-parent">Bottom Right Parent</div>

The z-index is initially set to auto and applies on all positioned elements. So as the element with id "top-left-pos" has a specified z-index its value is always higher than auto. So, it always stays on top.

Because both the elements have same z index and you have not specified the left and top parameters.If both of them have same z-index and also no coordinates are specified the second one would be placed over the previous one .
#top-left-pos {
top: 0;
}
Set top property to a number will solve the issue
https://jsfiddle.net/00s3f6gj/

Related

Static positioned elements affect Absolute position of subsequent sibling elements

I understand that any element with position: absolute will be positioned relative to the nearest ancestor with a positional attribute such as absolute or relative. This is mentioned in various answers for example here. Also on the w3schools site here...
An element with position: absolute; is positioned relative to the
nearest positioned ancestor (instead of positioned relative to the
viewport, like fixed).
However, inserting a static element appears to disrupt this rule and shifts the absolute element. I'd like to understand why that happens. See code snippet below.
If the static element is chaged to absolute, the subsequent elements are displayed as expected (according to the nearesst positional ancestor rule).
div.relative {
position: relative;
width: 440px;
height: 600px;
border: 3px solid #73AD21;
}
div.static {
position: static;
width: 200px;
height: 100px;
border: 3px solid #73ADff;
}
div.absolute {
position: absolute;
width: 200px;
height: 100px;
border: 3px solid #73AD21;
}
div.absolute2 {
left:210px;
position: absolute;
width: 200px;
height: 100px;
border: 3px solid #ffAD21;
}
<div class="relative">This div element has position: relative;
<div class="static">This div element has position: static</div>
<div class="absolute">This div element has position: absolute, but is positioned relative to the preceding static element, not the first positional ancestor.;</div>
<div class="absolute2">This div element also has position: absolute;</div>
</div>
As this answer explains, if there is no (top, left, right, bottom) attributes the position: absolute element will be positioned by default as if it was part of the normal flow , this is helpful in case you want to maintain a position: absolute next to its sibling like a tool tip would, and manipulate it with margin property, let say:
margin-top:-40px;
margin-left:30px;
but if you set any (top,left,right, bottom), this will reset the default position and will be relative to the parent.
top:0
When W3Schools (and the CSS spec) says that an element is "positioned relative to" something, it is never referring to the element's siblings. It's referring to the element's containing block.
The reason a non-positioned element (position: static) affects the layout of subsequent absolutely positioned elements with auto offsets is because absposed elements with auto offsets will assume their static position (see this answer as well as this one RenzoCC links to), and an element's static position, by nature, is influenced by the layout of surrounding elements, especially preceding siblings.
What absolutely positioning an element without changing any of its offsets does, is cause elements that follow it to be laid out as if that element itself were not there. This is what taking an element out of the flow means.
Static position doesn't affect the Absolute position when it comes to the ancestor position which "position: relative".
But the "position: absolute" has a power to position itself whenever you want inside of the (see the additional code I made) "position: relative;" while the "position: static" don't have the ability to used the Top, Right, Bottom and Left because is it a default position where it is only located at the left side.
div.relative {
position: relative;
width: 440px;
height: 600px;
border: 3px solid #73AD21;
}
div.static {
position: static;
width: 200px;
height: 100px;
border: 3px solid #73ADff;
}
div.absolute {
position: absolute;
width: 200px;
height: 100px;
border: 3px solid #73AD21;
/* Absolute Location inside the Relative Position */
top: 0;
left: 0;
}
div.absolute2 {
left:210px;
position: absolute;
width: 200px;
height: 100px;
border: 3px solid #ffAD21;
/* Absolute Location inside the Relative Position */
top: 0;
}
<div class="relative">This div element has position: relative;
<div class="static">This div element has position: static</div>
<div class="absolute">This div element has position: absolute, but is positioned relative to the preceding static element, not the first positional ancestor.;</div>
<div class="absolute2">This div element also has position: absolute;</div>
</div> <!-- / .relative -->

Setting an absolute positioned div to overlap one regular div but not another

I have a page that's set up with a split pane - top and bottom (divs using calc() for their height), with the top div having an absolutely positioned div that overlays the top div. HTML + CSS below from https://jsfiddle.net/b2mb79ev/1/
<div id="everything">
<div id="top">
<div id="free"></div>
</div>
<div id="bottom"></div>
</div>
</div>
#everything {
width: 400px;
height: 400px;
}
#top {
height: calc(50%);
width: 100%;
background: blue;
}
#free {
position: absolute;
top: 50px;
left: 300px;
height: 200px;
width: 50px;
background: yellow;
border: 3px solid black;
}
#bottom {
height: calc(50%);
width: 100%;
background: rgba(0,255,0,0.6);
}
However I want the absolutely positioned div not to intrude into the bottom div. I want the bottom div to always be in a 'higher' layer. In the jsfiddle I don't want the yellow bit going into the green bit.
But from what I can gather the top and bottom divs always have the same level because they are just regularly flowed elements and won't take any notice of z-index. I can use z-index to have the absolutely positioned div above both or beneath both, but not one above and one underneath?
Is there a way to do what I'd like?
You just need to set a non-static position (e.g. position:relative) on the #bottom div to give the stacking context you're after.
jsFiddle example
#bottom {
height: calc(50%);
width: 100%;
background: rgba(0, 255, 0, 0.6);
position:relative;
}

Why is an absolutely positioned element placed by its sibling instead of at the top corner of the page?

I don't understand why my absolutely positioned element appears after my child_static div. I always thought that absolutely positioned elements are taken out of the flow. So why doesn't child_absolute cover the child_static div?
.parent {
position: relative;
}
.child_static {
height: 20px;
background: blue;
}
.child_absolute {
position: absolute;
height: 20px;
width: 100%;
background: green;
}
<div class='parent'>
<div class='child_static'></div>
<div class='child_absolute'></div>
</div>
http://jsfiddle.net/4v4eLtp1/
I always thought that absolute positioned elements are out of the flow.
Yes, they are removed from normal flow.
I don't understand why absolute positioned element appeared after child_static div.
Just because absolute positioning removes elements from normal flow, it doesn't mean it does alter the position of the elements as well.
In other words, absolutely positioned elements would be at the same place as they are not positioned absolutely unless their top, left, ... offsets are set.
So what happens is that they would overlap next sibling elements, because they are not part of document flow anymore.
For instance have a look at the following example where the gold <div> element is covered by absolutely positioned element.
.parent {
position: relative;
}
.child_static {
height: 20px;
background: blue;
}
.child_absolute {
position: absolute;
height: 20px;
width: 100%;
background: green;
}
.child_static ~ .child_static {
background: gold;
}
<div class='parent'>
<div class='child_static'>Green</div>
<div class='child_absolute'>Blue</div>
<div class='child_static'>Gold</div>
</div>
You forgot to set from which sides your DIV is positioned.
Something like:
top: 0;
left: 0;
http://jsfiddle.net/Paf_Sebastien/uqprmkwo/
(I changed the 2nd DIV dimensions so you can see both.)

How to make the div inside wrapper bigger than wrapper itself without change the structure

How to make the <div> inside wrapper bigger than wrapper itself without change the structure?
HTML
<div class="page row1">
<div class="home-wrapper row2">
<div class="home-slider row3"></div>
</div>
<div>
CSS
.page { width: 100%; height: 400px; border: 1px solid #000; background: #eee; }
.home-wrapper { width: 90%; height: 400px;border: 1px solid red; background: #ccc; margin: 0 auto;}
.home-slider{ width: 100%; height: 200px; border: 1px solid blue; background:#000; }
http://jsfiddle.net/46vpqmgh/1/
I want the black box is same width with the page <div> without change the structure, using only CSS.
Thanks
Add:
position: absolute to .home-slider to pull it out of the normal flow
top: 0 and left: 0 to .home-slider to position it correctly
position: relative to .page to make it's children absolute positioned elements relative to it
Percentage height and width will be calculated based on the size of .page.
Have a fiddle!
Added CSS
.page {
position: relative;
}
.home-slider {
position: absolute;
left: 0;
top: 0;
}
Read more about the CSS position property over on the MDN
Absolute positioning
Elements that are positioned relatively are still considered to be in the normal flow of elements in the document. In contrast, an element that is positioned absolutely is taken out of the flow and thus takes up no space when placing other elements. The absolutely positioned element is positioned relative to nearest positioned ancestor. If a positioned ancestor doesn't exist, the initial container is used.
In our example above, the nearest positioned "ancestor" is .page
Add the following properties. Looks fair to me.
.home-slider {
/* ... */
z-index: 1;
margin-left: -5%;
position: fixed;
}
Change the following class:
.home-slider {
width: 100%;
height: 200px;
border: 1px solid blue;
background:#000;
position: absolute;/*Add position absolute*/
left: 0;/*Add left to 0*/
}
fiddle

IE6 and IE7 absolute positioned div on top of multiple relative divs

Is it possible to make multiple absolute-positioned divs overlap multiple relative-positioned divs in IE6 & IE7?
See this jsFiddle for more information: http://jsfiddle.net/btker/1/
HTML
<div class="wrapper">
<div class="relative_div">Relative div.
<div class="absolute_div">This div have absolute position and is placed in a relative positioned div. This div should always be on top of all relative divs.</div>
</div>
</div>
<div class="wrapper">
<div class="relative_div">Relative div.
<div class="absolute_div">This div have absolute position and is placed in a relative positioned div. This div should always be on top of all relative divs.</div>
</div>
</div>
CSS
.wrapper{
height: 100%;
width: 100%;
}
.relative_div {
height: 75px;
width: 200px;
border: 1px solid #000;
padding: 10px;
background: #e6e6e6;
margin: 0 0 35px 0;
position: relative;
}
.absolute_div {
height: 100px;
width: 250px;
border: 1px solid #000;
background: #c6c6c6;
padding: 10px;
position: absolute;
top: 40px;
left: 100px;
z-index: 100;
}
There are two relative <div>s (placed in identical wrappers) containing each one a absolute <div> that overlap all the relative <div>s. This works great without any problems in updated versions of Chrome, Firefox etc, the absolute <div> with z-index is always placed on top.
In IE6 and IE7 this is not working. The different between this problem and the standard "dropdown in header display its menus behind the page content" is that in those situations its often fixed by give the parent element of that specific menu other z-index etc. In this case the both absolute <div>s are put in identical <div>s.
Can this be solved so the absolute <div>s are always on top of all relative <div>s in IE6 & IE7? Conditional comments for IE can be used to make the solution cross-browser.
It is possible but only by decreasing the z-index of the second .wrapper or increasing the z-index of the first .wrapper.
On a simple level, each positioned element with a non-auto z-index creates a new stacking context, although there are other circumstances in which a new stacking context is created - see The stacking context.
The problem is one that affects IE <= 7, from quirksmode.org
In Internet Explorer positioned elements generate a new stacking context, starting with a z-index value of 0. Therefore z-index doesn't work correctly.
CSS
.wrapper{
height: 100%;
width: 100%;
}
.lower {
position: relative;
z-index: -1;
}
.higher {
position: relative;
z-index: 2;
}
.relative_div {
height: 75px;
width: 200px;
border: 1px solid #000;
padding: 10px;
background: #e6e6e6;
margin: 0 0 35px 0;
position: relative;
}
.absolute_div {
height: 100px;
width: 250px;
border: 1px solid #000;
background: #c6c6c6;
padding: 10px;
position: absolute;
top: 40px;
left: 100px;
z-index: 1;
}
HTML
<div class="wrapper"> <!-- add higher class here -->
<div class="relative_div">Relative div.
<div class="absolute_div">This div have absolute position and is placed in a relative positioned div. This div should always be on top of all relative divs.</div>
</div>
</div>
<div class="wrapper"> <!-- or add lower class here -->
<div class="relative_div">Relative div.
<div class="absolute_div">This div have absolute position and is placed in a relative positioned div. This div should always be on top of all relative divs.</div>
</div>
</div>