Why does my element not align properly? The box-sizing problem

Maciej Sawicki - Nov 1 '20 - - Dev Community

I have a code snippet element that I want to stretch to 100% of its parent. Easy peasy. Here's the code:

<div class="container">
  <div class="box">
    Code snippet
  </div>
</div>
Enter fullscreen mode Exit fullscreen mode
.container {
  width: 400px;
  border: 5px solid black;
  margin: 10px;
}

.box {
  background-color: #407AA4;
  border: 3px solid red;
  line-height: 100px;
  color: #fff;
  text-align: center;

  width: 100%;
  padding: 0 10px;
}
Enter fullscreen mode Exit fullscreen mode

Rendered element with overflowed content

Wait! Why does it overflow like that? When we inspect the element we can see that its width is 426px meanwhile its parent is 400px. What is going on?

Rendered element with overflowed content and displayed size

This, my friend, is a CSS box-sizing problem. But before we fix it we need to understand why it happens. In order to do that first we need to make friends with CSS Box Model.

Box model

CSS Box Model is a way the browser represents each and every HTML element in the DOM Tree.

HTML element Box Model

It consists of 4 layers, where the previous one is surrounded with the following one, just like the onion:

  • content (blue) - changed by: font-size, line-height, height, etc.
  • padding (green) - changed by: padding, padding-left, padding-top, etc.
  • border (orange) - changed by: border-width
  • margin (brown) - changed by: margin, margin-left, margin-top, etc.

How can I see the Box Model of a given element?

Fortunately, every major browser has a way to visually represent the model in their DevTools, which we can open in a couple of steps:

  1. Hit Ctrl + Shift + C when in browser and click on the element of choice.
  2. Inside opened DevTools in the Elements tab click Computed tab.
  3. Bam. That's all.
  4. You can repeat from step 1 to pick a new element or just click the tag in the Elements tab DOM Tree.

Gif
Alt Text

The box-sizing problem

Now that we know the basics we can say hi to the CSS box-sizing property. It can have one of 2 values:

  • content-box (default)
  • border-box

content-box

When we tell the browser that we want an element to have 100% width, like in our case, the browser:

  1. Gets the width of the parent, in our case 400px.
  2. Sets the elements content width to 400px.
  3. Adds 20px of padding (to left and right). Now width is 420px.
  4. Adds 6px of border (to left and right). Now width is 426px.
  5. Puts the element inside the parent.

Our calculation matches the width measured empirically.

How can we fix it?

border-box

The solution is to set the box-sizing: border-box to the .box element.

Element with applied border-box value

The browser now:

  1. Gets the width of the parent, in our case 400px.
  2. Sets the elements content width to 400px.
  3. Subtracts 20px of padding (to left and right). Now width is 380px.
  4. Subtracts 6px of border (to left and right). Now width is 374px.
  5. Puts the element inside the parent.

The steps remained almost the same, but in steps 3 and 4 instead of adding padding and border the browser now subtracts them.

If we take a look at the elements Box Model now we can see that the calculations checkout.

Box Model of the element with applied border-box property

Measured Element with applied border-box value

How to avoid this kind of problems in the future?

The very first thing I do at the beginning of every project is I add this piece of CSS code:

* {
    box-sizing: border-box;
}
Enter fullscreen mode Exit fullscreen mode

This selector applies border-box value to every element in the DOM Tree, so that we don't have to worry this specific case anymore.

But be careful when you do this in your existing codebase, because all the layouts had been adjusted to the content-box calculations and there is a high chance that something might break.

Conclusion

In this article we've made friends with CSS Box Model and box-sizing property. We now know how the browser performs calculations regarding content-box and border-box properties. We've also learned what to do at the start of every project.

The full example can be explored here.

In the next articles we will get to know the lonely wanderer called quirk modes and flirt with rendering layers concept.

See you around.

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Terabox Video Player