Friday, October 10, 2025
HomeWeb development"If" CSS Will get Inline Conditionals

“If” CSS Will get Inline Conditionals


A couple of sirens went off a few weeks in the past when the CSS Working Group (CSSWG) resolved so as to add an if() conditional to the CSS Values Module Degree 5 specification. It was Lea Verouโ€™s X publish that very same day that caught my consideration:

Lea is the one who opened the GitHub subject resulting in the dialogue and in a stroke of coincidence โ€” or serendipity, maybe โ€” the decision got here in on her birthday. That needed to be fairly a whirlwind of a day! What did you get on your birthday? โ€œOh, you already know, simply an accepted proposal to the CSS spec.โ€ Wild, simply wild.

The accepted proposal is a inexperienced gentle for the CSSWG to work on the thought with the intent of circulating a draft specification for additional enter and concerns en path to, hopefully, develop into a advisable CSS function. So, itโ€™s gonna be a scorching minute earlier than any of that is baked, that’s, if it will get totally baked.

However the concept of making use of kinds based mostly on a conditional requirement is tremendous thrilling and value an early have a look at the thought. I scribbled some notes about it on my weblog the identical day Lea posted to X and thought Iโ€™d distill these right here for posterity whereas rounding up extra particulars which have come up since then.

This isnโ€™t a brand new concept

Many proposals are born from beforehand rejected proposals and if() isn’t any totally different. And, certainly, we’ve gained a number of CSS options in latest days that enable for conditional styling โ€” :has() and Container Type Queries being two of the extra apparent examples. Lea even cites a 2018 ticket that appears and reads quite a bit just like the accepted proposal.

The distinction?

Type queries had already shipped, and we may merely reference the identical syntax for circumstances (plusย media()ย andย helps()ย fromย Tabโ€™sย @whenย proposal) whereas within the 2018 proposal how circumstances would work was largely undefined.

Lea Verou, โ€œInline conditionals in CSS?โ€

I like how Lea factors out that CSS goes on to explain how CSS has at all times been a conditional language:

Of usโ€ฆ CSS had conditionals from the very starting. Each selector is actually a conditional!

Lea Verou, โ€œInline conditionals in CSS?โ€

True! The Cascade is the car for evaluating selectors and matching them to HTML parts on a web page. What if() brings to the desk is a strategy to write inline circumstances with selectors.

Syntax

It boils right down to this:

<if()> = if( <container-query>, [<declaration-value>]{1, 2} )

โ€ฆthe place:

  • Values will be nested to provide a number of branches.
  • If a 3rd argument is just not supplied, it turns into equal to an empty token stream.

All of that is conceptual in the intervening time and nothing is ready in stone. Weโ€™re more likely to see issues change because the CSSWG works on the function. However because it at the moment stands, the thought appears to revolve round specifying a situation, and setting one among two declared kinds โ€” one because the โ€œdefaultโ€ type, and one because the โ€œup to dateโ€ type when a match happens.

.component {
  background-color:
    /* If the type declares the next customized property: */
    if(type(--variant: success),
      var(--color-green-50), /* Matched situation */
      var(--color-blue-50);  /* Default type */
    );
}

On this case, weโ€™re in search of a type() situation the place a CSS variable known as --variant is asserted and is ready to a worth of success, and:

  • โ€ฆif --variant is ready to success, we set the worth of success to --color-green-50 which is a variable mapped to some greenish shade worth.
  • โ€ฆif --variant is just not set to success, we set the worth of the success to --color-blue-50 which is a variable mapped to some bluish shade worth.

The default type could be optionally available, so I believe it may be omitted in some instances for barely higher legibility:

.component {
  background-color:
    /* If the type declares the next customized property: */
    if(type(--variant: success),
      var(--color-green-50) /* Matched situation */
    );
}

The syntax definition up high mentions that we may assist a 3rd argument along with the matched situation and default type that enables us to nest circumstances inside circumstances:

background-color: if(
  type(--variant: success), var(--color-success-60), 
    if(type(--variant: warning), var(--color-warning-60), 
      if(type(--variant: hazard), var(--color-danger-60), 
        if(type(--variant: main), var(--color-primary)
      )
    ),
  )
);

Oomph, appears like some wild inception is going on in there! Lea goes on to counsel a syntax that may lead to a a lot flatter construction:

<if()> = if( 
  [ <container-query>, [<declaration-value>]{2}  ]#{0, },
  <container-query>, [<declaration-value>]{1, 2} 
)

In different phrases, nested circumstances are rather more flat as they are often declaredย outdoorsย of the preliminary situation. Identical idea as earlier than, however a special syntax:

background-color: if(
  type(--variant: success), var(--color-success-60), 
  type(--variant: warning), var(--color-warning-60),
  type(--variant: hazard), var(--color-danger-60), 
  type(--variant: main), var(--color-primary)
);

So, relatively than one if() assertion inside one other if() assertion, we will lump the entire attainable matching circumstances right into a single assertion.

Weโ€™re making an attempt to match an if() situation by querying a componentโ€™s kinds. There isn’t any corresponding measurement() operate for querying dimensions โ€” container queries implicitly assume measurement:

.component {
  background: var(--color-primary);

  /* Situation */
  @container dad or mum (width >= 60ch) {
    /* Utilized kinds */
    background: var(--color-success-60);
  }
}

And container queries develop into type queries after we name the type() operate as an alternative:

.component {
  background: orangered;

  /* Situation */
  @container dad or mum type(--variant: success) {
    /* Utilized kinds */
    background: dodgerblue;
  }
}

Type queries make much more sense to me after theyโ€™re considered within the context of if(). With out if(), itโ€™s simple to query the overall usefulness of fashion queries. However on this gentle, itโ€™s clear that type queries are a part of a a lot greater image that goes past container queries alone.

Thereโ€™s nonetheless loads of issues to suss out with the if() syntax. For instance, Tab Atkins describes a attainable state of affairs that might result in confusion between what’s the matched situation and default type parameters. So, who is aware of how this all shakes out in the long run!

Circumstances supporting different circumstances

As weโ€™ve already famous, if() is way from the one sort of conditional verify already supplied in CSS. What wouldn’t it appear to be to write down an inline conditional assertion that checks for different circumstances, akin to @helps and @media?

In code:

background-color: if(
  helps( /* and so forth. */ ),
  @media( /* and so forth. */ )
);

The problem could be container supporting measurement queries. As talked about earlier, there isn’t any expressย measurement()ย operate; as an alternative itโ€™s extra like an nameless operate.

@andruudย has aย succinctly describes the problem within the GitHub dialogue:

I donโ€™t see why we couldnโ€™t doย helps()ย andย media(), however measurement queries would trigger cycles with format which might be laborious/unimaginable to even detect. (Thatโ€™s why we wanted the restrictions we at the moment have for measurement CQs within the first place.

โ€œCanโ€™t we already do that with [X] strategy?โ€

After we had been trying on the syntax earlier, you might have observed that if() is simply as a lot about customized properties as it’s about conditionals. A number of workarounds have emerged over time to imitate what weโ€™d achieve if() we may set a customized property worth conditionally, together with:

  • Utilizing customized properties as a Boolean to use kinds or not relying on whether or not it is the same asย 0ย orย 1. (Ana has an exquisite article on this.)
  • Utilizing a placeholder customized property with an empty worth thatโ€™s set when one other customized property is ready, i.e.ย โ€œthe customized property toggle trickโ€ย as Chris describes it.
  • Container Type Queries!ย The issue (in addition to lack of implementation) is that containers solely apply kinds to their descendants, i.e., they can’t apply kinds to themselves after they meet a sure situation, solely its contents.

Lea will get deep into this in a separate publish titled โ€œInline conditional statements in CSS, now?โ€ that features a desk that outlines and compares approaches, which Iโ€™ll merely paste beneath. The reasons are stuffed with advanced CSS nerdery however are extraordinarily useful for understanding the necessity for if() and the way it compares to the intelligent โ€œhacksโ€ weโ€™ve used for years.

Technique Enter values Output values Execs Cons
Binary Linear Interpolation Numbers Quantitative Can be utilized as a part of a worth Restricted output vary
Toggles var(--alias)ย (precise values are too bizarre to show uncooked) Any Can be utilized in a part of a worth Bizarre values that have to be aliased
Paused animations Numbers Any Regular, decoupled declarations Takes overย animationย property

Cascade weirdness

Sort Grinding Key phrases Any worth supported by theย syntaxย descriptor Excessive flexibility for uncovered APIGood encapsulation Should insert CSS into gentle DOM

Tedious code (although will be automated with construct instruments)

No Firefox assist (although thatโ€™sย altering)

Variable animation identify Key phrases Any Regular, decoupled declarations Impractical outdoors of Shadow DOM as a result of identify clashes

Takes overย animationย property

Cascade weirdness

Completely happy birthday, Lea!

Belated by two weeks, however thanks for sharing the spoils of your huge day with us! ๐ŸŽ‚

References


Direct Hyperlink โ†’



RELATED ARTICLES

LEAVE A REPLY

Please enter your comment!
Please enter your name here

Most Popular

Recent Comments