Alejandro Cantero Jódar
Alejandro Cantero Jódar

CSS is now a programming language

· CSS Alejandro Cantero Jódar

CSS is now a programming language

CSS has significantly evolved in recent years, integrating features that were previously only possible through preprocessors like Sass or Less. Now, with the arrival of if() and @function, styles can dynamically adapt without relying on external tools. These new functionalities bring CSS one step closer to being a fully-fledged programming language within frontend development.

Understanding Drafts and Context

To understand where we stand, it's important to note that both if() and @function are part of the W3C drafts. A CSS draft is a specification in development within the CSS Working Group (CSSWG). This means that full browser support is not yet available, but the direction is clear: at some point, these features will be standardized and commonly used in production.

if(): Conditional Logic in CSS

One of CSS's historical limitations has been the lack of conditional structures. Until now, any conditional logic in styles required preprocessors or JavaScript. With if(), CSS can evaluate conditions and modify properties accordingly, similar to a ternary structure in other languages.

More details on the if() specification can be found in the official draft by the W3C.

Code Example

.foo {
  color: if(lightness(currentColor) < 50%, white, black);
}

This code adjusts the text color based on the background color's lightness. If the lightness is below 50%, it uses white; otherwise, it uses black. This eliminates the need for JavaScript to handle these dynamic changes.

More information on browser implementation status is available on Chrome Status.

@function: Creating Functions in CSS

Until now, CSS has allowed some predefined functions like calc(), min(), and max(), but it has never offered the ability to define custom functions. With @function, developers can encapsulate reusable logic, similar to mixins in preprocessors.

Code Example

The following example defines a --shadow function that enables reusable shadow effects. If no color is passed, it inherits the --shadow-color value or defaults to black.

@function --shadow(--shadow-color <color> : inherit) {
  result: 2px 2px var(--shadow-color, black);
}

.foo {
  --shadow-color: blue;
  box-shadow: --shadow();
  box-shadow: --shadow(blue);
}

This simplifies repetitive style definitions and ensures greater design consistency without relying on preprocessors.

Future, Flexibility, and Complexity: The End of Less and Sass?

With the introduction of if() and @function, CSS is absorbing features that were historically exclusive to Less and Sass. The question is whether this marks the end of preprocessors. In many cases, CSS's new capabilities will reduce the need for them, but some advanced features in preprocessors still lack a direct equivalent in native CSS.

What is clear is that CSS is evolving to handle more complex logic without external dependencies. This reduces frontend project complexity and enables more efficient development. As these features gain browser support, we will see a shift in how styles are structured and managed in modern applications.

Related posts

Alejandro Cantero Jódar

Made with ♥ by a passioned developer © 2025