Magic Numbers in CSS

Magic numbers are numbers that appear in source code without any explanation of what they mean. This makes the code difficult to understand and maintain.

In CSS, it's harder to tell if a value is a magic number than in other languages. This is mostly because there are more numbers that don't require additional explanation.

Refactoring CSS to remove magic numbers

Let's look at this example design.

Box design implemented using Magic Numbers

The layout contains two elements: an outer box with the class summary and a blue button with the class expand.

We can implement the design with this CSS code:

.summary {
    position: relative;
    height: 200px;
    width: 550px;

    padding: 40px;
    padding-right: 140px;
}

.summary .expand {
    position: absolute;
    width: 60px;
    height: 60px;
    top: 110px;
    right: 40px;
}

(The snippet only includes the layout styling, not colors or fonts.)

The design is based on a 40px padding around each element. But why is padding-right 140px and top 110px? These are both magic numbers that have an explanation that isn't included in the code.

If you wanted to increase the padding to 50px, you wouldn't immediately know how to update these two numbers.

Explaining padding-right

Two sizes are relevant for our layout: the 40px padding and the size of the expand box (60px).

To get rid of the magic numbers, we need to expose the relationship between these values in our code.

Layout image showing how the padding-right value is composed

In modern browsers we can use the CSS calc function to calculate the value:

padding-right: calc(40px + 60px + 40px);

Or we can use Sass to run the calculation when we generate the CSS file:

padding-right: 40px + 60px + 40px;

The code now makes it clear what the role of the two sizes is in deciding what the padding-right value should be.

We can use Sass variables to further explain the relationship between the different layout sizes (try it here).

$padding: 40px;
$buttonSize: 60px;

.summary {
    position: relative;
    height: 200px;
    width: 550px;

    padding: $padding;
    padding-right: $padding + $buttonSize + $padding;
}
.summary .expand {
    position: absolute;
    width: $buttonSize;
    height: $buttonSize;
    top: 110px;
    right: $padding;
}

Giving names to the values also makes it easier to change the sizes in the future.

Explaining the top value

The calculation for the top property of the button looks like this:

top: (200px + 2 * $padding - $buttonSize)/2;

We can refactor it for increased readability by introducing a few more variables:

$contentHeight: 200px;
$boxHeight: $contentHeight + 2 * $padding;

// ... 
.summary .expand {
    top: ($boxHeight - $buttonSize)/2;
}

By subtracting the button height from the box height, we calculate the amount of vertical whitespace in the box. Dividing that by two means we have an equal amount of space below the button and above the button. In other words, the button is now beautifully centered.

Why isn't the width a magic number?

The CSS sets the width of the box to 550px. Why don't we need to refactor this by moving the number into a variable?

In this case, the variable name would be something like $contentWidth. But that doesn't tell us anything that width: 550px doesn't already tell us.

It's actually the same situation with $contentHeight. It's only worth putting in a variable because we re-use the value to calculate the top property.

Many values in CSS are self-explaining. Only create a variable if it adds new information or to avoid repetition.

What to do when finding a number by trial and error

Sometimes you'll determine a value purely by trial and error, maybe when checking that two elements align.

In those cases, you can't replace the magic number with a calculation or variable name, because you don't know how to calculate it.

When you can't avoid introducing a magic number you should use comments to explain the process you used to determine the value.

Write that you found the value by trial and error and describe what the success condition was. For example, a success condition might be that the top of box A aligns with the bottom of box B.