How To Set Equal Margins for Entire Web Page

czmudzin picture czmudzin · Oct 4, 2014 · Viewed 10.3k times · Source

This question may have been beaten to death, but after looking through posts and Googling the heck out of it, I cannot find a functional code to get this to work and nothing I tried is doing the trick.

I'd like to set ALL (top, left, bottom, and right) page margins to 1%, but nothing I'm doing works. The only way I can get this to work is to manually size my images using height and width properties, which I'd like to avoid.

Ideally I'd like something like this:

body, html {
margin-left:1%;
margin-right:1%;
margin-bottom:1%;
margin-top:1%;
}

But that doesn't work. Any clean, straightforward suggestions on accomplishing this out there?

Answer

Daniel Rippstein picture Daniel Rippstein · Oct 4, 2014

Summary

Your margins are working correct. However, page margins do not apply to position:fixed elements.

Details

This is not a glitch, but is by design according to the W3C specs. Putting a left/right/top/bottom on a fixed element will move it relative to the viewport (your window). It won't even check for margins on <body> or any other parent element. After all, position:fixed is designed so that an element stays fixed to a part of window, even when scrolling... it needs to be fully independent of other elements to behave this way.

So why did changing the 'top' and 'left' padding/margin of body seemed to work?

Because position:fixed is calculated in basically two steps:

  1. Lock the element at its starting position, as if it was position:static.
  2. If a left/right/top/bottom is found, apply that change, but leave everything else positioned the way it started.

So here's what happens on your example:

  1. If your <div>s were position:static, they would start in the top-left corner, but be pushed down 1% and left 1% because of that <body>'s margin/padding.
  2. You don't set any left/right/top/bottom on the 1st <div>, so it stays in place permanently.
  3. The 2nd <div> has a right: 0 on it though; and as it doesn't really care about anybody's margin/padding, it goes straight to the right edge of the window like it was born to do.

Basically, the <body> gets to indirectly affect the <div>s, but setting a right: 0; blows that all away.

Solution

Don't worry about putting padding/margin on the <body>, getting hard-to-predict results. Instead, apply CSS directly to the fixed elements. For example:

* {
    -webkit-box-sizing: border-box;
    /* Safari/Chrome, other WebKit */
    -moz-box-sizing: border-box;
    /* Firefox, other Gecko */
    box-sizing: border-box;
    /* Opera/IE 8+ */
}
div.nw {
    height:50%;
    width:50%;
    position:fixed;
    top: 0;
    left: 0;
    background-color:#ff0;
    padding: 1% 0 0 1%;
}
div.ne {
  height:50%;
  width: 50%;
  right: 0;
  top: 0;
  padding: 1% 1% 0 0;
  background-color:blue;
  position:fixed;
}

See it in action here: http://codepen.io/anon/pen/isDhA

EDIT:

If you don't want the background color near the edges either, just combine the above technique with some simple inner divs. Such as in this example: http://codepen.io/anon/pen/lDebh

EDIT 2:

After further discussion in the comments, here's some other suggestions, depending on what you need.

"I want to have equal-sized divs in each corner of the window. It should be fixed to the background, so it doesn't scroll with everything else"

Use this approach: http://jsfiddle.net/fettj66r/9/

.corner {
    position: fixed;
    width: 50%;
    height: 50%;
    z-index: -1;
}
.nw {
    background: red;
    left: 1%;
    top: 1%;
}
.ne {
    background: green;
    right: 1%;
    top: 1%;
}
.sw {
    background: blue;
    left: 1%;
    bottom: 1%;
}
.se {
    background: black;
    right: 1%;
    bottom: 1%;
}

"I want to have equal-sized divs in each corner of the window. It should scroll with everything else."

Use this approach: http://jsfiddle.net/fettj66r/10/

body {
    position: relative;
    margin: 1%;
}
.corner {
    position: absolute;
    width: 50%;
    height: 50%;
    z-index: -1;
}
.nw {
    background: red;
    left: 0;
    top: 0;
}
.ne {
    background: green;
    right: 0;
    top: 0;
}
.sw {
    background: blue;
    left: 0;
    bottom: 0;
}
.se {
    background: black;
    right: 0;
    bottom: 0;
}

If you have any questions about the above techniques, or this isn't what you needed either, feel free to ask in the comments.