DEV Community

Deepika Pusala
Deepika Pusala

Posted on

CSS Foundations: Understanding the Box Model, Cascade and Specificity

CSS looks simple at first, but understanding how the browser calculates sizes and decides which style to apply is extremely important for building predictable and maintainable web pages.

Three important concepts are the CSS Box Model, Cascade, and Specificity. This blog explains these concepts in simple terms with practical examples.

  1. What is the CSS Box Model?

In CSS, every HTML element can be thought of as a rectangular box.

Whether it is a heading, paragraph, button, image, card, header, or footer, the browser treats the element as a box for layout purposes.

The CSS Box Model has four parts:

Content → Padding → Border → Margin

From the inside to the outside:

Content – The actual text, image, button, or other content inside the element.
Padding – The space between the content and the border.
Border – The visible boundary around the element.
Margin – The space outside the border that separates one element from other elements.
Example

Suppose we have a card containing the text:

"Welcome to my blog"

The text is the content.

If there is some empty space around the text before the visible border starts, that is padding.

The visible line surrounding the card is the border.

The space between this card and another card is the margin.

A simple way to remember the structure is:

Margin → Border → Padding → Content

  1. Padding vs Border vs Margin

These three are often confusing at first, so it is important to understand their exact purpose.

Padding

Padding creates space inside the element, between the content and the border.

For example:

padding: 20px;

means the element gets 20px of padding on all four sides.

So it is equivalent to:

padding-top: 20px
padding-right: 20px
padding-bottom: 20px
padding-left: 20px
Border

A border creates a visible boundary around the element.

For example:

border: 2px solid black;

means:

2px → border thickness
solid → border style
black → border color
Margin

Margin creates space outside the border.

For example:

margin-bottom: 40px;

creates 40px of space below the element.

Unlike padding, margin is outside the element's border.

  1. What is box-sizing?

The box-sizing property controls how CSS calculates the width and height of an element.

The two important values are:

content-box
border-box

Understanding these two values is extremely important when working with layouts.

  1. content-box

content-box is the default value of box-sizing.

With content-box, the declared width applies only to the content area.

For example:

.card {
width: 300px;
padding: 20px;
border: 2px solid black;
}

Here:

Content width = 300px
Left padding = 20px
Right padding = 20px
Left border = 2px
Right border = 2px

Therefore:

Total width = 300 + 20 + 20 + 2 + 2 = 344px

So even though we wrote:

width: 300px

the complete element becomes 344px wide.

This can sometimes cause unexpected overflow.

  1. border-box

With border-box, the declared width includes:

Content + Padding + Border

For example:

.card {
box-sizing: border-box;
width: 300px;
padding: 20px;
border: 2px solid black;
}

Now the entire box is 300px wide.

The padding and border are included inside those 300px.

Therefore, the content area becomes smaller to make room for the padding and border.

Conceptually:

300px total width

minus:

40px padding

minus:

4px border

equals:

256px content width

The important point is:

With border-box, the element stays 300px wide. The content area adjusts to fit the padding and border inside that width.

  1. Why is border-box commonly used?

A common practice is:

  • { box-sizing: border-box; }

The * is the universal selector, so this applies border-box to all elements.

It makes layouts easier to predict because when we say:

width: 300px

we can think:

"The entire element will be 300px wide."

This is especially useful when creating cards, forms, columns, navigation bars, and responsive layouts.

  1. Understanding the Box Model in Chrome DevTools

Chrome DevTools provides a visual representation of the Box Model.

When inspecting an element, we can see:

Margin → Border → Padding → Content

The innermost area represents the content box.

This is important because the number shown in the center of the DevTools Box Model represents the content area's dimensions, not necessarily the entire element's width.

For example, suppose the viewport is approximately 603px wide.

With:

width: 100%

and content-box:

Content = approximately 603px
Padding = 40px on each side
Border = 5px on each side

So the total width becomes approximately:

603 + 40 + 40 + 5 + 5 = 693px

Since 693px is greater than the 603px viewport, horizontal overflow can occur.

With border-box:

Entire element = approximately 603px
Padding and border are included within those 603px
The remaining space becomes the content area

So the content may be approximately 514px wide.

The important distinction is:

603px is the total border-box width, while approximately 514px is the content width.

  1. Margin Collapsing

Margin collapsing is a behavior that can happen with vertical margins of block-level elements.

For example:

.box1 {
margin-bottom: 30px;
}

.box2 {
margin-top: 20px;
}

It might seem that the gap should be:

30 + 20 = 50px

But in a normal block layout, these vertical margins can collapse into one margin.

The larger margin generally wins.

So the resulting gap can be:

30px

rather than 50px.

Margin collapsing mainly occurs with vertical margins in normal block layouts.

It does not work the same way for items inside Flexbox or Grid layouts.

  1. What is the CSS Cascade?

The word cascade refers to the process the browser uses to decide which CSS declaration should be applied when multiple CSS rules target the same element.

For example:

p {
color: blue;
}

p {
color: green;
}

Both rules target the same paragraph.

Both have the same specificity.

Therefore, the later rule wins.

The paragraph becomes:

green

This is called the source order part of the cascade.

The cascade considers several factors, including:

Origin and importance
Specificity
Source order

Understanding the cascade is much better than trying to fight CSS using !important everywhere.

  1. What is CSS Specificity?

Specificity is the system browsers use to determine which selector is more specific when multiple selectors target the same element.

You can think of specificity as a priority score for selectors.

The main selector categories are:

ID selector

Example:

contact

An ID has high specificity.

Class selector

Example:

.send-btn

Classes have lower specificity than IDs.

Attribute selector

Example:

button[type="submit"]

Attribute selectors have the same specificity level as classes.

Type selector

Example:

button

Element/type selectors have lower specificity than classes and IDs.

  1. Specificity Example

Suppose we have:

button {
background-color: gray;
}

.send-btn {
background-color: yellow;
}

contact button {

background-color: green;
Enter fullscreen mode Exit fullscreen mode

}

And our HTML contains:

Send Message

The button matches all three rules.

Now compare their specificity:

button

→ Type selector

.send-btn

→ Class selector

contact button

→ ID + type selector

The ID-based selector is more specific, so:

contact button

wins.

The button becomes:

green

  1. Specificity Score

Specificity is commonly represented using three levels:

(ID, Class, Type)

For example:

button

(0, 0, 1)

One type selector.

.send-btn

(0, 1, 0)

One class selector.

contact

(1, 0, 0)

One ID selector.

contact .send-btn

(1, 1, 0)

One ID + one class.

The browser compares the numbers from left to right.

So:

(1, 0, 0) beats:

(0, 100, 0)

because an ID is in a higher specificity category than classes.

  1. What Happens When Specificity is Equal?

Suppose we write:

.button {
background-color: blue;
}

.button {
background-color: red;
}

Both selectors have exactly the same specificity.

Therefore, source order decides the winner.

The second rule wins.

The button becomes:

red

So a simple rule to remember is:

If specificity is tied, the later applicable rule wins.

  1. Inline Styles

Inline styles are written directly inside the HTML element.

Example:


Send

Inline styles have very high priority compared with normal stylesheet rules.

They are therefore another important part of understanding CSS conflicts.

However, using inline styles everywhere can make a project harder to maintain, so stylesheets or reusable classes are generally preferred for normal styling.

  1. Why should we avoid excessive !important?

!important gives a declaration very high priority.

Example:

.button {
background-color: red !important;
}

It can be useful in specific situations, but using it repeatedly can create specificity wars.

For example, if many rules contain !important, overriding a style becomes difficult.

Instead of immediately writing:

color: red !important;

it is better to ask:

Which selector is currently winning?
Is another selector more specific?
Is the rule appearing later?
Is there an inline style?
Can I simplify the selectors?

The goal is to understand the cascade rather than fight it.

  1. Inheritance

Inheritance means that some CSS properties can automatically receive their value from a parent element.

For example:

.parent {
color: darkblue;
}

If a paragraph is inside that parent, the paragraph can inherit the text color.

Not every CSS property is inherited.

For example, properties such as:

color → commonly inherited
font-family → commonly inherited
margin → not normally inherited
padding → not normally inherited
border → not normally inherited

So inheritance depends on the specific CSS property.

  1. inherit

The keyword inherit tells an element:

"Use the value from my parent."

Example:

.parent {
box-sizing: border-box;
}

.child {
box-sizing: inherit;
}

The child takes the parent's box-sizing value.

If the parent uses border-box, the child also uses border-box.

If the parent changes to content-box, the child follows it.

  1. initial

initial means:

"Use the property's initial value defined by CSS."

For box-sizing, the initial value is:

content-box

Therefore:

box-sizing: initial;

sets it back to:

content-box

  1. unset

unset works differently depending on whether the property normally inherits.

It means:

If the property normally inherits, inherit it. Otherwise, use its initial value.

Since box-sizing is not normally inherited:

box-sizing: unset;

results in its initial value:

content-box

  1. revert

revert tells the browser to step back in the cascade and use the value that would have applied from an earlier cascade origin.

In simple terms:

"Undo the styling from this CSS level and go back to the previous applicable value."

It is useful when we want to remove an author-level override without manually specifying another value.

  1. revert-layer

revert-layer is related to CSS Cascade Layers.

It means:

"Undo the value from the current cascade layer and use the value from an earlier applicable layer."

For example, modern CSS can organize styles into layers such as:

Reset
Components
Utilities

revert-layer can move the property back to what an earlier layer specified.

This is a more advanced feature and is mainly useful when a project is using CSS cascade layers.

  1. CSS Custom Properties

CSS custom properties are commonly called CSS variables.

They allow us to store reusable values.

Example:

:root {
--main-color: #173b6c;
--spacing: 16px;
}

We can then use them with:

.card {
color: var(--main-color);
padding: var(--spacing);
}

Instead of writing the same value repeatedly, we can store it once and reuse it.

If we later change:

--main-color

the elements using that variable can automatically use the new value.

  1. Why Simple CSS is Better

When working on a real project, CSS can become difficult to maintain if selectors are overly complicated.

For example, this is unnecessarily specific:

body div.sidebar ul li a {
color: red;
}

A simpler class-based selector is often easier to understand:

.sidebar-link {
color: red;
}

Simple selectors make the cascade easier to predict and reduce the need for !important.

  1. Using Chrome DevTools for CSS Debugging

Chrome DevTools is extremely useful when something doesn't look right.

A useful workflow is:

Open the webpage.
Right-click the element.
Select Inspect.
Look at the Styles panel.
Look at the Computed styles when necessary.
Look at the Box Model diagram.
Check which rules are active.
Check which declarations are crossed out.
Temporarily uncheck a CSS property to see what changes.

This helps us understand why a style is being applied instead of guessing.

  1. Final Practical Summary

The most important concepts to remember are:

Box Model

Content → Padding → Border → Margin

Content is the actual material inside the element.

Padding is space inside the border.

Border is the visible boundary.

Margin is space outside the border.

content-box

Width = Content width

Padding and border are added outside.

border-box

Width = Entire border-box width

Padding and border fit inside the declared width.

Cascade

The browser uses the cascade to decide which competing CSS declaration wins.

Specificity

A selector with higher specificity normally wins.

The basic order is:

ID → Class/Attribute/Pseudo-class → Type

If specificity is tied:

Later rule wins.

Inheritance

Some properties can pass from a parent to its children.

Global Keywords
inherit → use parent's value
initial → use property's initial value
unset → inherit if normally inherited, otherwise use initial
revert → step back through the cascade
revert-layer → step back through the current cascade layer
!important

Use carefully. Understanding the cascade is better than repeatedly forcing styles with !important.

CSS Variables

Use custom properties such as:

--main-color

and access them with:

var(--main-color)

Conclusion

Understanding CSS is not about memorizing hundreds of properties. It is about understanding how the browser thinks.

The Box Model explains how an element occupies space.

The Cascade explains how competing CSS rules are resolved.

Specificity explains which selector has more priority.

Inheritance explains how some styles move from parent to child.

And box-sizing: border-box helps make element dimensions more predictable.

Once these fundamentals are clear, debugging CSS becomes much easier because instead of randomly changing properties, we can inspect the element, understand the box model, check the cascade, and identify exactly why a particular style is winning.

Top comments (0)