I'm getting strange behaviour from margins. A vertical scrollbar appears even though I'm no where near the bottom. I assume this is the desired behaviour, considering that I tested this and got the same results in the latest versions of Chrome, IE11 and Firefox.
The following code results in a scrollbar
<html>
<head>
<style>
body {
margin: 0;
height: 100%;
padding: 1px;
}
div {
margin: 15px;
}
</style>
</head>
<body>
<div>Hmm</div>
</body>
</html>
Changing the body's padding to 0.1px results in no margin.
Changing the body's padding to 0px also results in a margin.
Also, adding box-sizing: border-box to the body removes the scrollbar as long as the padding is not zero.
I haven't added a Fiddle because I can't replicate it there. You need to test this in a simple html file.
Is this actually the expected behaviour? Is there a logical explanation why they implemented it like this?
Looks like the reason you're seeing the scrollbar is a combination of defining a height and setting a padding value. The height property dictates the height of an element's content, excluding the margin and padding added onto that value. The scrollbar appears after adding padding because you've set the content of the element's height to 100% of the page, plus the padding, causing the element's entire height to overflow.
Additionally, applying box-sizing to an element makes the height and width properties include padding in the value. Funny thing is, it doesn't include margin. So if you were to apply:
body {
box-sizing: border-box,
margin: 1px,
padding: 0
}
You'd still see the scrollbar. Once understanding that an element's height property, by default, only dictates the height of the content within the element, it makes a little more sense.
Hope this helps :)
Setting the height of the body to 100% makes it take all of the height of it's parent element which is the html element. The html element's width and height in turn are governed by the window it is in. Adding a margin or a border would increase the dimensions beyond the available space thus inducing the scroll.
However, the other issue is that adding the margin to the div is pushing the body down by 15px. This has to do with collapsing margins.
Check out https://stackoverflow.com/a/2680515/6184852 for further information.
Related
I have the following html:
<style>
body {
margin: 0;
height: 100vh;
}
div {
margin: 1px;
}
</style>
<body>
<div>feck</div>
</body>
The div's margin causes scroll bars, even tho the div itself is nowhere near the height of the page. Without the div's margin, there is no scroll bar. What's going on? Is this a browser bug?
Collapsing margins. Because the div is the topmost element in the body, the div's margin is collapsed with the body's margin. That is, the body gets the same margin too.
You may think that "collapsing" isn't the right word for this behaviour, and you'd be right, but that's the word they've chosen. Sorry.
There are several solutions:
Sean's solution of simply moving the div a pixel downwards
Your own solution of using calc for the body height
Set a padding on the body, and use box-sizing:border-box for it.
Because a div is a block element. It has positioning in the Dom, therefore takes up space. When you add a margin to the top, you are pushing its space down, therefore increasing the overall amount of space it occupies.
If you want to push the div down, without changing the overall container (body) height, you can give the div a position of relative, and a top of 1px.
div {
position: relative;
top: 1px;
}
Check out this answer it should be clear enough.
The main point is that margins of adjacent elements (in this case your div and body) are collapsing taking the maximum value of the two margins.
I've set my html body tag heigth to be 100% but in Firefox that shows as a few more pixels than the screen has, so a nav scroll bar appears. How can I adjust that other than specifiying an arbitrary height :98%? I've set padding and margin to zero.
I'm using only bootstrap for css, if that's of any importance.
Check elements inside the body. One of it probably has margins or even content goes outside the body element. Just try to delete all inner elements one by one in Firefox's dev.tools and notice what element deletion will solve the problem.
Just to follow up the answer above, I noticed that padding can cause the same effect, but can only be noticed when inspecting the elements.
<button class="sbtn">
<span class="text">
my btn
</span>
</button>
.sbtn {
height: 5vh;
background-color: red;
}
.text {
padding: 10vh;
color: white;
}
Try adding this to your main CSS file.
/* CSS */
* {
box-sizing: border-box;
}
border-box tells the browser to account for any border and padding in the values you specify for an element's width and height. If you set an element's width to 100 pixels, that 100 pixels will include any border or padding you added, and the content box will shrink to absorb that extra width. This typically makes it much easier to size elements.
CSS box sizing
I came across a strange issue when testing a site in FF.
The situation is this:
box-sizing: border-box is applied to everything.
I have a floated wrapper <div>, with a fixed height.
Inside the wrapper is an <img> with height: 100%.
When I add padding to the wrapper, I expect the wrapper to remain the same height, and the image to remain the same aspect ratio, but shrink to fit the height minus the padding. The width of the wrapper should change to match the new width of the image, plus the padding.
This behaves as expected in Chrome and IE on both OSX and Win7, but in FF the width of the wrapper seems to remain the same as if no padding was added.
Am I missing something, or is this a bug in the implementation of box-sizing in Firefox?
This fiddle demonstrates the issue:
http://jsfiddle.net/3j43Y/1/
Screenshots:
First image is the result in Firefox, the second one is Chrome.
This appears to be a bug, but it's not calculating the width as if no padding is applied. It's calculating the width as if the content (the <img> tag) has the width it would have were there no padding applied. It's then adding padding on top of this incorrectly calculated content width.
i.e. With no padding, the <img> element has a width of 167px. If you then add padding it should shrink (because of the height constraint) and .wrapper's width should now be the width of the shrunken <img> width plus the padding. Instead, (in FF at least) .wrapper's width is the width of the unshrunken <img> width plus the padding (167 + 16).
At least, that's what I'm seeing.
Also, it looks like you can see the same in Chrome (35.0.1916.114) if you toggle the padding rule on/off in dev tools. Initially Chrome gets it right, but then you see the same erroneous behaviour after toggling padding.
#BYossarian's answer is correct. The answer below is a possible workaround when coming across the issue.
Since .wrapper is set to a specific height, we can add the padding to the image and get the desired effect we are looking for.
Demo:
<style type="text/css">
* {
-moz-box-sizing: border-box;
box-sizing: border-box;
}
.wrapper {
float: left;
height: 100px;
background: #99ccff;
}
.wrapper img {
height: 100%;
padding: 8px;
}
</style>
<div class="wrapper">
<img src="http://placehold.it/250x150" alt="">
</div>
Another way to analyze, it is also necessary to be careful with the statement of the doctype of the document.
If you have an old doctype,
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
Firefox will not consider box-sizing: border-box;
For html 5,
it is necessary to declare the doctype as follows:
<!doctype html>
it will fix Firefox, it will take the box-sizing correctly.
When I put width: 100% for my ul, its border flies off the edge of the page. I tried setting margin-right: 2px to see if that would make a difference, but to no avail. What I thought would happen is that the border would occupy the right edge of the screen, and setting the margin-right would bring it to the left, but this didn't work. Why does it behave this way?
<!doctype html>
<html>
<head>
<style>
#nav {
border: 1px solid black;
width: 100%;
margin-right: 2px;
}
</style>
</head>
<body>
<ul id="nav">
<li>Home</li>
<li>Local</li>
<li>Weather</li>
<li>Sports</li>
<li>Politics</li>
</ul>
</body>
</html>
You can see the page here: http://www.noetherherenorthere.com/practice/2013-1-5-02.html.
Answers
Browsers use box-sizing: content-box; use border-box instead ~ setek
Choose a smaller percentage ~ Damien Black
Use width: auto ~ Josiah
This happens because the box is being generated using the content-box model: with an explicit width, and then add border and padding to it.
And uls have a left-padding by default, to account for the bullets.
Removing the left padding will stop this, but you won't be able to see the bullets anymore: you could always add a margin onto the lis to counteract this.
Alternatively, if you don't have to support older browsers (IE 6/7) you could use the property: box-sizing: border-box; which will cause the box to render by subtracting the padding and border from the explicit width, rather than adding to it like the content-box model.
EDIT: It's worth noting that IE 6 (and 7, I believe) will generate all boxes as if they were border-boxes anyway. This causes inconsistencies when you start setting widths and applying padding in those browsers vs. modern browsers.
Setting width to 100% does something a little odd in html, it makes the width 100% and the padding, border and margin will all appear outside of that full width.
You'll have to do less then 100% to leave room for the border and margin.
Using 100% will make the main box fill the whole screen, but padding and margin will be excluded. Instead of width: 100% use width: auto. That will make the box fit comfortably and takes into account margin and padding.
Fiddle: http://jsfiddle.net/kfWvr/
I have a container which creates a colored column down page from top to bottom. I am using the below CSS. This code will cause the vertical scrollbar to appear, however if I remove the padding property it works fine. It seems to be adding the padding to the height. I would expect this when using margin since it is outside of container, but padding is inside it and should not affect the size of it as far as I am aware. This container has no parent elements and contains only one word as content.
How do I make it 100% height while retaining the padding and without having to create any additional child element? Thank you in advance.
#container
{
background-color : #eee;
max-width : 910px;
min-height : 100%;
padding : 65px 15px;
}
You can add box-sizing: border-box; to the container to get the desired results;
http://jsfiddle.net/Svkp8/
Here is a detailed article by Paul Irish about box-sizing that was provided by steveax in the comments.