According to Mozilla Developer Network's article on CSS position property, setting position as absolute has the following behavior:
absolute
Do not leave space for the element. Instead, position it at a specified position relative to its closest positioned ancestor if any, or otherwise relative to the initial containing block. Absolutely positioned boxes can have margins, and they do not collapse with any other margins.
However, in the official CSS specification as of 2015 I cannot find where does it states the constraint that the containing box or closest ancestor needs to be positioned (i.e. has to have a computed positioned property of either relative, absolute, fixed or sticky). How is it deduced or implied?
It's in the spec (you were looking at the wrong document):
9.8.4 Absolute
positioning
The containing block for a positioned box is established by the
nearest positioned ancestor (or, if none exists, the initial
containing block).
This is relevant, as well:
9.3.2 Box offsets: top, right, bottom,
left
An element is said to be positioned if its position property has a
value other than static.
From the official CSS specification as of 2015 is:
This document collects together into one definition all the specs that together form the current state of Cascading Style Sheets (CSS) as of 2015. The primary audience is CSS implementers, not CSS authors, as this definition includes modules by specification stability, not Web browser adoption rate.
Inside the above link you can find a link to the CSS2, where inside you can find this:
9.6 Absolute positioning
In the absolute positioning model, a box is explicitly offset with respect to its containing block. It is removed from the normal flow entirely (it has no impact on later siblings). An absolutely positioned box establishes a new containing block for normal flow children and absolutely (but not fixed) positioned descendants. However, the contents of an absolutely positioned element do not flow around any other boxes. They may obscure the contents of another box (or be obscured themselves), depending on the stack levels of the overlapping boxes.
Related
I am reading the "Positioning Techniques" of this article on MDN.
It talks about "Absolute positioning elements can be fixed to a position relative to its nearest positioned ancestor element".
My understanding of "positioned ancestor" is an ancestor with any position property other than static. But I need expert opinions to verify my thought.
When referring to positioned ancestor we mean the closest ancestor to the element with a set position value, other than static (which is default).
So there are two assumptions here:
In case there are more than one positioned ancestors we mean the closest.
In case there is an ancestor with a set position:static (presumably set by JavaScript, in order to change the "positioned ancestor") we don't mean that ancestor.
Why is this important? Because the "positioned ancestor" is the reference from which properties like left and top are calculated, when the descendant is given position:absolute. It's also called "the reference element/parent" of the descendant.
Also, if this closest ancestor has a set z-index (other than auto), it creates a stacking context for its descendants.
From the W3C:
In this case the containing block is the nearest positioned ancestor.
By “positioned” I mean an element whose position property is set to
relative, absolute or fixed—in other words, anything except normal
static elements.
Long description for example illustrating positioning with respect to a positioned ancestor
a containing block established by a relatively positioned ancestor
("outer").
And CSS Module 3, search for "positioned ancestor" on that page.
I have a problem understanding absolute positioning, when the parent is not either absolute or relative. I understand that absolute positioning will place itself based on the offsets with respect to it's parent, which can relative or absolute. If the parent is not absolute or relative? Will it position itself to the nearest absolute or relative element. Or will it position itself relative to the body?
I do not have a problem when the parent is relative or absolute. I have a problem in understanding what is gonna happen if the parent is static. How the absolute element is gonna place itself
This is defined here: http://www.w3.org/TR/css3-positioning/#def-cb
Relevant blurbs from that reference:
For fixed, absolute, center and page, it is defined as follows:
If the element has 'position: absolute', the containing block is
established by the nearest ancestor with a position other than static,
in the following way:
1. In the case that the ancestor is block-level, the containing block is formed by the padding edge of the ancestor.
2. In the case that the ancestor is inline-level, the containing block depends on the direction property of the ancestor ...
and
If there is no such ancestor, the containing block is the initial
containing block
More details here: http://www.w3.org/TR/CSS2/visudet.html#containing-block-details
So, to answer your question directly - the containing block is established by the nearest ancestor with a position other than static. If there is no such ancestor, then the containing block is the initial containing block. This incidentally happens to be html. This is the reason why many developers choose to provide position: relative to body in order to avoid confusion with the viewport.
Assigning an element as absolute essentially takes it out of the "normal" flow of the webpage.
This essentially means that absolutely positioned elements can be placed anywhere on the page by instructing them to be at certain points in accordance with their nearest relative parent.
By default, most elements inherit the position of static, meaning they form on the page as they "should" (basically meaning, they follow one after the other depending on where they're specified). To quote Chris Coyier at CSS Tricks, position relative pretty much means "relative to itself", so merely assigning an element to be relative is basically the same as leaving it as static, unless you instruct it position itself otherwise.
Remember, if you set an element to be absolute, it will look for it's closest relative parent - it will progressively look higher and higher up the DOM tree till it finds one, that can sometimes be the <html> tag itself if no others are defined as relative.
The following link explains this topic much better than I can, please check it out: https://css-tricks.com/absolute-relative-fixed-positioining-how-do-they-differ/
I remember reading somewhere, a long time ago, that absolutely positioning an element withoout giving it any top, right, bottom or left property will (as any positioned element) take it out of the flow, but keep it inside the same containing block (the one it's supposed to be in when statically positioned).
On the example below (jsFiddle), elements #2 and #3 are absolutely positioned, but #2 hasn't any additional properties.
I've been looking for documentation explaining that behavior so that I could continue using this without fearing for possible backslashes, but haven't been lucky on Gooogle or SO. Could someone point me in the right direction?
For absolutely positioned elements, the default values for the offsets (top, left and so on) are auto.
In this case, the element remains in the position it would have it had position: static even though the content is taken out of the document flow.
References to the 'static position' concept include:
http://www.w3.org/TR/CSS2/visudet.html#abs-non-replaced-width
http://www.w3.org/TR/CSS2/visudet.html#abs-non-replaced-height
http://www.w3.org/TR/CSS2/visuren.html#position-props
To quote:
10.3.7 Absolutely positioned, non-replaced elements
For the purposes of this section and the next, the term "static position" (of an element) refers, roughly, to the position an element would have had in the normal flow. More precisely:
The static-position containing block is the containing block of a hypothetical box that would have been the first box of the element if its specified 'position' value had been 'static' and its specified 'float' had been 'none'.
It won't keep it inside the containing block, as once it's absolutely positioned it's always outside of the document flow. What it does do (without setting top/bottom/left/right) is keep it in the default position it would have been if it was still position static.
To force it to be inside the parent container, set the parent as position: relative and the top/bottom/left/right as needed.
I am creating a website here. In the HTML I have two lines:
<span class="header_text">Trapped in payday loans?</span>
<span class="header_text2">We can help you!</span>
The class .header_text and .header_text2 are defined in css.css with the attribute position: absolute.
Would it be more professional if I changed CSS position from absolute to relative?
How do I change position from absolute to relative? When I do so the text appears in wrong parts of the page.
You change it for functionality - neither is more professional.
position: relative. Though it will probably appear in wrong parts of page because its offsets no longer apply.
It depends what you want to achieve, there is no more professional, both values serve their purpose but they are different. You cannot just change one for the other.
But if you change absolute for relative, most likely you have to place the elements in question somewhere else in your HTML to achieve the same effect (if even possible).
For completeness:
relative
Lay out all elements as though the element were not positioned, and then adjust the element's position, without changing layout (and thus leaving a gap for the element where it would have been had it not been positioned). The effect of position:relative on table-*-group, table-row, table-column, table-cell, and table-caption elements is undefined.
absolute
Do not leave space for the element. Instead, position it at a specified position relative to its closest positioned ancestor or to the containing block. Absolutely positioned boxes can have margins, they do not collapse with any other margins.
The biggest difference is that elements positioned with absolute are taken out of the normal page flow (that is why it is said do not leave space).
Always stick to absolute, relative is not very professional and normally dumb people use this just to show off they can use odd layout to impress others.
what is the containing block of an absolutely positioned element? it seems the rule can be a bit complicated...
the spec should be here:
http://www.w3.org/TR/CSS21/visudet.html#containing-block-details
i want to verify if the following is true:
for simplicity, assume the containing block is a block element (not inline element)...
1) if the absolute positioned element has a closest ancestor that is positioned "non static" (relative, fixed, or absolute), then that ancestor is the containing block. the absolute positioned element is relative to it.
2) if there is no such ancestor, then the viewport is the containing block, and so the absolute positioned element is relative to the viewport.
no matter what the containing block is above, the width:100% or n% and height:100% or n% are both relative to the containing block.
that's why a
<div style="position:absolute;width:100%;height:100%;background:green"></div>
right under <body> will cover up the whole viewport exactly -- no more, no less.
we could also use position: fixed, except IE 6 doesn't support it... and so the poor programmer need to use position: absolute instead... (well, not a big deal)
Is that an accurate description of an absolute positioned element? If so, i think IE 6 and above, FF, Safari, Chrome all follow this behavior accurately?
You are correct. The containing block is the last positioned element. so if you want to explicitly set the container then give it position:relative. Most browsers get this right. CSS doesn't really have a 'viewport', I think the top is the HTML element though don't hold me to that. IE prior to 7 had an unnamed element above HTML though.
Summary:
position: relative
Does nothing except set the positioning context for all the elements contained within it. You can then position: absolute any element it contains by setting (typically one or two) values from the possible top, right, bottom or left.
If you give an element with position: relative a top, right, bottom or left value, it will shift position accordingly but leave a blank space where it would be by default. In other words, it remains within the document flow but offset.
position: absolute
To position something absolutely, you need to ask 'absolutely, but relative to which containing element'? It will either be the entire body (the default) or some other element on the page that is already positioned (usually with relative or absolute - fixed is also useful and supported in IE 7 but see this bug). It is then taken out of the document flow - other elements might appear beneath it, but won't flow around it. If it appears behind another element, you need to set the z-index property to move it in front.
A common solution is to have a centred container (margin: 0 auto) with position: relative within which other items are placed with position: absolute.
Finally, I like this little interactive CSS positioning demo.