This question already has answers here:
Why does this CSS margin-top style not work?
(14 answers)
CSS margin terror; Margin adds space outside parent element [duplicate]
(7 answers)
Closed 1 year ago.
I don't understand why there is a scroll in the body and a space after the block .example. According to my logic, I make the margin-bottom 100px and then subtract these 100px from the block height max-height: calc(100% - 100px);
<!DOCTYPE html>
<html>
<head>
<title></title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<style>
* {
padding: 0;
margin: 0;
box-sizing: border-box;
}
html,
body {
height: 100%;
}
.example {
padding: 20px;
width: 60%;
margin: 100px auto 0;
max-height: calc(100% - 100px);
border: 1px solid black;
overflow-y: scroll;
}
p{
padding: 100vh 0;
}
</style>
</head>
<body>
<div class="example">
<div class="text">
<p>Lorem</p>
<p>Lorem</p>
</div>
</div>
</body>
</html>
You're running into wildly inherited margins problem derived from the popular collapsed margins - issue (which is better known for when two elements with vertical margins, the two colliding margins collapse into one) - not your exact case but same in nature.
Read more on w3.org Collapsing Margins
Since you used html, body {height: 100%} and the tall .example element has margin-top 100% - the body element moved, collapsed 100px down! It basically "wildly" inherited (at least visually) those 100px margin.
An element with vertical margin can cause unwanted results with ancestors flow. One common way to fix this is to smartly avoid vertical margin, or to add overflow: auto to the ancestor that's being affected by that problem html, body in your specific case.
html, body {
height: 100%; /* Why would you want this? */
overflow: auto; /* FIX for wild margins */
}
The other solution (I'm sure there are many others) is to not use html, body {height: 100%}
Rather min-height (if really needed) on html and body and vh (viewport height) unit on the .example element
html, body {
/* min-height: 100%; /* use min-height, but not needed */
}
.example {
/* .... other styles */
margin: 100px auto 0;
height: calc(100vh - 100px); /* 100vh minus 100px margin-top */
}
Long story short - Be careful when using margin. I personally use it only when working with flexbox, or in the horizontal space (often when using inline-block elements) otherwise I always use wrappers with padding to create desired spacings which are perfectly controlled thanks to box-sizing: border-box (no need to calculate anything) - or when really necessary- I treat them with special care.
Get rid of the padding on the p elements:
<!DOCTYPE html>
<html>
<head>
<title></title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<style>
* {
padding: 0;
margin: 0;
box-sizing: border-box;
}
html,
body {
height: 100%;
}
.example {
padding: 20px;
width: 60%;
margin: 100px auto 0;
max-height: calc(100% - 100px);
border: 1px solid black;
overflow-y: scroll;
}
</style>
</head>
<body>
<div class="example">
<div class="text">
<p>Lorem</p>
<p>Lorem</p>
</div>
</div>
</body>
</html>
Right answer its a Collapsing margins xD. To solve the problem, you can add one of the following to the body:
border
padding
overflow
Related
With this simple HTML/CSS template below, I expected BODY to be contained within HTML element. Why is it not? I separated the css for HTML and BODY to give different colors.
https://jsfiddle.net/jwinnd/w95ngLqc/3/
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>demo</title>
<style>
html {
width: 100%;
height: 100%;
border: solid 30px red;
}
body {
width: 100%;
height: 100%;
border: solid 30px blue;
}
</style>
</head>
<body>
<script>
</script>
</body>
</html>
This is what you want. Don't overthink it. The box-sizing property is the most important in this scenario. The box-sizing will measure the element's width and height with the border included.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8"/>
<title>demo</title>
<style>
html {
border: solid 30px red;
box-sizing: border-box;
height: 100%;
margin: 0;
padding: 0;
width: 100%;
}
body {
border: solid 30px blue;
box-sizing: border-box;
height: 100%;
margin: 0;
padding: 0;
width: 100%;
}
</style>
</head>
<body>
<script>
</script>
</body>
</html>
Your Question:
In short; you're asking why the body element is not directly on top of the html parent as you would expect.
Explanation:
The fact is, IT IS, but the way that the CSS is set out, is that some CSS rules and some default styling factors offset this direct layering.
In this case, the HTML and the body 'boxes' are only by default measured by the system in terms of it's "content area" rather than it's whole "margin" + "border" + "content" area.
Read about CSS box-sizing.
You have a border on both, so the child element is offset against the border, but the child element has also been told to be 100% width, so it must overflow the parent because the true total size of the child element is "border" (30px x 2) + "padding" (0px) + "content" (100%)
As well as this, the <body> element has a default margin value of 8px (0.5rem standard font size) on all edges so this as well is not accounted for by the sizing system because the margin (like the border) is not in the "content area" and so causes a further offset.
However, the child element is forced to being 100% of its parent so it has to "overflow" at the far end of the parent (<html>) box; causing your borders to overlap.
From the above you can see your body element actually has a TOTAL width of:
margin: 16px
border: 60px
content: 100%
So the body is 100% + 76px of the parent element's size.
CSS can't not show any part of the display, so it is forced to overflow the parent to keep everything viewable (You can change this with: overflow:hidden;)
Further to the above, the <body> element overflows the parent <html> element because the parent has been set to a width of 100% as well, so it will be the maximum width of the child (body) "content area" rather than the area it actually effects on the screen. This is why the border on the bottom right of your example has blue outside the red; because the system thinks:
This container [the screen size] has a width of X so I need to be X wide for my contents and then I can add my border and my margin
the child element meanwhile processes:
I must take up all the width of my parent, plus my border and plus my margin that I have.
Be default <body> has a natural margin on it, and the border itself set on <html> will force its child elements to be within the border rather than on top of the border.
My fixes to remove default settings and browser inherited styles, and force the box model to respect all areas of the box not just the contents.
Tweaked Version of your HTML:
html {
width: 100%;
height: 100%;
border: solid 30px red;
box-sizing: border-box;
}
body {
margin: 0; /* Added to body */
width: 100%;
height: 100%;
border: solid 30px blue;
box-sizing:border-box;
/* often added to the *{ .. } element to apply to all elements on a page */
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8"/>
<title>demo 2</title>
<style>
</style>
</head>
<body>
Hello 2
</body>
</html>
CSS Changes made:
Removed default margin on the body element.
Changed box-sizing to border box whereby the DOM Box model is set to the border rather than simply the box contents.
Yeah! If sometimes you see a web developer pulling his hair or gnashing his teeth, he is probably messing up with this problem. You may think that when you determine the height of a block-level element it includes the content box to the outer side of the border. But it is not! When you set the height of an element you only set its content's size, and not the borders and paddings. It is really common for developers to set all element to have box-sizing of border-box. You can do this by adding this peace of code to the top of your css style. :
*{
box-sizing: border-box;
}
So, here is your code result after adding this property. Also, note that the body element has a default margin. Be sure to disable that too:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>demo</title>
<style>
*{
box-sizing: border-box;
}
html {
width: 100%;
height: 100%;
border: solid 30px red;
}
body {
width: 100%;
height: 100%;
margin:0;
border: solid 30px blue;
}
</style>
</head>
<body>
<script>
</script>
</body>
</html>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>demo</title>
<style>
html {
box-sizing:border-box;
width: 100%;
height: 100%;
border: solid 30px red;
}
body {
margin:0;
box-sizing:border-box;
width: 100%;
height: 100%;
border: solid 30px blue;
}
</style>
</head>
<body>
<script>
</script>
</body>
</html>
This code working fine
<!DOCTYPE html>
<html lang="en">
<head>
<style>
html {
width: 100%;
height: 100%;
background-color: red;
margin: 0px;
padding: 0px;
}
body {
background-color: chartreuse;
width: 100%;
height: 100%;
padding: 0px;
margin: 0px;
}
</style>
<title>Document</title>
</head>
<body>
</body>
</html>
but then this code doe not work when i try to add margin 5% to each side of body....
why there is vertical scrolling bar....
height 90% + 2 * 5% margin = 100% height
but there is scrolling bar....
i think when body height is 100% then is not be any scrolling bar present
<!DOCTYPE html>
<html lang="en">
<head>
<style>
html {
width: 100%;
height: 100%;
background-color: red;
margin: 0px;
padding: 0px;
}
body {
background-color: chartreuse;
width: 90%;
height: 90%;
padding: 0px;
margin: 5%;
}
</style>
<title>Document</title>
</head>
<body>
</body>
</html>
Try this. Maybe it will point you in the right direction
<style>
html, body {
height: 100%; /* keep these full height to avoid push or pull */
margin: 0; /* remove default margin on body */
}
body {
background-color: red; /* your background color */
}
#page {
width: 90vw; /* use 90/100 of view width */
height: 90vh; /* use 90/100 of view height */
/* top margin 5/100 of view height + auto margin on left/right */
margin: 5vh auto 0 auto;
background-color: chartreuse; /* your background color */
}
</style>
<body>
<div id="page">
<!-- here your content in the #page container -->
</div>
</body
In order to achieve the first case you need to increase the padding rather than the margin because margin is used for creating space around elements ,outside of any defined borders and here space is created around body tag thus,pushing the body element.Now to fill the green background over red you need to use padding which creates space inside the element's defined borders around the content thereby increasing height and width of the element.
Padding properties can have following values:
Length in cm, px, pt, etc.
Width % of the element.
Now when you assigned padding:5% that will be equal to 5% of the width and height of body element that is 5% of 90% of html tag's width and height and this is how your math went wrong .I tried some values and got what you needed.
<!DOCTYPE html>
<html lang="en">
<head>
<style>
*{
margin:0px;
padding:0px;
}
html {
width:100%;
height:100%;
background-color: red;
}
body {
background-color: chartreuse;
width:90%;
height:90%;
padding-right:5%;
padding-left:5%;
padding-top:2.3%;
padding-bottom:2.3%;
}
</style>
<title>Document</title>
</head>
<body >
</body>
</html>
This question already has answers here:
How wide is the default `<body>` margin?
(4 answers)
CSS position absolute and full width problem
(7 answers)
Closed 3 years ago.
Please see the code below. The footer is not touching the edges. if I poot footer width to 100% or 100vw i see a horizontal scrollbar in the browser. 99% falls short. Instead of finding a hardcoded value like 99.4% etc. is their way to touch the edges perfectly?
.main .footer {
border: 1px solid black;
background-color: #d4d4d4;
text-align: center;
position: absolute;
bottom: 0;
height: 40px;
width: 99%;
}
<div class="main">
<div class="footer"></div>
</div>
Every browser has its own default ‘user agent’ stylesheet, that it uses to make unstyled websites appear more legible. For example, most browsers by default make links blue and visited links purple, give tables a certain amount of border and padding, apply variable font-sizes to H1, H2, H3, etc. and a certain amount of padding to almost everything.
In your current example, the default body will have a margin set. To make the body of the document touch the edges, you will need to add a reset to the body margin, margin: 0;
Read more about it here. https://cssreset.com/what-is-a-css-reset/
You need to remove the margin on the body element. Then since you're using absolute positioning, remove the width declaration and use left/right:
body {
margin:0;
}
.main .footer {
border: 1px solid black;
background-color: #d4d4d4;
text-align: center;
position: absolute;
bottom: 0;
right: 0;
left: 0;
height: 40px;
}
body {
margin: 0;
}
<div class="main">
<div class="footer"></div>
</div>
Apply a CSS reset, by default, it have padding and margin setted, that why it not fit the edge:
*{
margin:0;
padding:0;
}
.main {
border: 1px solid black;
background-color: #d4d4d4;
height: 90vh;
}
.footer {
border: 1px solid black;
background-color: #d4d4d4;
height: 10vh;
}
<body>
<div class="main">
Your content
</div>
<div class="footer">
Your Footer
</div>
</body>
You should add the left attribute too, and you put a border, that border occupies a space, i used box-sizing: border-box; option to use the inside space of the element.
I attached some useful links for you:
box-sizing,
box-model
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
<title>Document</title>
<style>
.main .footer {
border: 1px solid black;
box-sizing:border-box;
background-color: #d4d4d4;
text-align: center;
position: absolute;
bottom: 0;
left:0;
height: 40px;
width: 100%;
}
</style>
</head>
<body>
<div class="main">
<div class="footer"></div>
</div>
</body>
</html>
Firstly I would recommend to use the new tags <header>, <main>& <footer> instead div with class.
Secondly the problem is that the body have a initial margin so try:
body{ margin:0; }
After that you will still have a scrollbar because of the border.
So you have two options:
Set border-top instead of left and right.
Give all elements the style * {box-sizing: border-box;} which means padding and border is included of the elements total width and height.
I tried to style container full width and height border line, in pc version it is ok, but test on iPhone, there is a little space(10px) in right side.
But only in vertical mode will see this happen, rotate to horizontal is ok.
Why? How to solve it?
UPDATE
I tried add box-sizing:border-box not work.
And right now I'm using overflow: hidden (Responsive website on iPhone - unwanted white space on rotate from landscape to portrait) to not let user scroll to see white space, but the space between container border line and content, right side is smaller. So I set content margin-right bigger than left make it still looks like center.
But I want to know why and find perfect way
Is it something wrong related I using meta tag? if I remove meta tag it is fine both vertical and horizontal mode
html, body {
width: 100%;
height: 100%;
}
.container {
width: 100%;
min-height: 100%;
border: 10px solid #000000;
}
.content {
width: 100%;
margin: 0 auto;
}
html
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=0">
</head>
<body>
<div class="container">
<div class="content"></div>
</dvi>
</body>
</html>
Html
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=0">
</head>
<body>
<div id="solution" class="container">
<div class="content"></div>
</div>
</body>
</html>
CSS
html, body {
width: auto;
height: 100%;
}
.content {
width: 100%;
margin: 0 auto;
background:#000;
height:200px;
}
.container {
width: 100%;
padding: 10px;
border: 30px solid #999;
}
#solution {
box-sizing: border-box;
}
check below fiddle http://jsfiddle.net/manjunath_siddappa/53grcpdv/,
i hope, it may help you.
Your container has 100% width + 1px border on each side thus making it bigger than 100%.
Try one of these solutions:
.container{
box-sizing: border-box;
}
.container{
width: calc(100% - 2px);
}
.container{
max-width: 100%;
}
From what I've seen in other answers, CSS viewport units can't be used in calc() statements yet. What I would like to achieve is the following statement:
height: calc(100vh - 75vw)
Is there some workaround way I can achieve this using purely CSS even though the viewport units can't be used in the calc() statement? Or just CSS and HTML? I know I can do it dynamically using javascript, but I'd prefer CSS.
Before I answer this, I'd like to point out that Chrome and IE 10+ actually supports calc with viewport units.
FIDDLE (In IE10+)
Solution (for other browsers): box-sizing
1) Start of by setting your height as 100vh.
2) With box-sizing set to border-box - add a padding-top of 75vw. This means that the padding will be part f the inner height.
3) Just offset the extra padding-top with a negative margin-top
FIDDLE
div
{
/*height: calc(100vh - 75vw);*/
height: 100vh;
margin-top: -75vw;
padding-top: 75vw;
-moz-box-sizing: border-box;
box-sizing: border-box;
background: pink;
}
As a workaround you can use the fact percent vertical padding and margin are computed from the container width. It's quite a ugly solution and I don't know if you'll be able to use it but well, it works: http://jsfiddle.net/bFWT9/
<!DOCTYPE html>
<html>
<head>
<title></title>
</head>
<body>
<div>It works!</div>
</body>
</html>
html, body, div {
height: 100%;
}
body {
margin: 0;
}
div {
box-sizing: border-box;
margin-top: -75%;
padding-top: 75%;
background: #d35400;
color: #fff;
}
<div>It's working fine.....</div>
div
{
height: calc(100vh - 8vw);
background: #000;
overflow:visible;
color: red;
}
Check here this css code right now support All browser without Opera
just check this
Live
see Live preview by jsfiddle
See Live preview by codepen.io
Doing this with a CSS Grid is pretty easy. The trick is to set the grid's height to 100vw, then assign one of the rows to 75vw, and the remaining one (optional) to 1fr. This gives you, from what I assume is what you're after, a ratio-locked resizing container.
Example here: https://codesandbox.io/s/21r4z95p7j
You can even utilize the bottom gutter space if you so choose, simply by adding another "item".
Edit: StackOverflow's built-in code runner has some side effects. Pop over to the codesandbox link and you'll see the ratio in action.
body {
margin: 0;
padding: 0;
background-color: #334;
color: #eee;
}
.main {
min-height: 100vh;
min-width: 100vw;
display: grid;
grid-template-columns: 100%;
grid-template-rows: 75vw 1fr;
}
.item {
background-color: #558;
padding: 2px;
margin: 1px;
}
.item.dead {
background-color: transparent;
}
<html>
<head>
<title>Parcel Sandbox</title>
<meta charset="UTF-8" />
<link rel="stylesheet" href="src/index.css" />
</head>
<body>
<div id="app">
<div class="main">
<div class="item">Item 1</div>
<!-- <div class="item dead">Item 2 (dead area)</div> -->
</div>
</div>
</body>
</html>