We can do a lot of logic in CSS. I’m thinking specifically of scenarios which take the form “if this, then that”.
There are media queries which will let us control the appearance of elements based on a variety of factors. Probably the most common is screen width, so we get things like “if the width is 1024px or higher, then show an extra element”.
There are pseudo selectors like :empty, :checked, :valid, :disabled which let us control appearance based on state, giving us, for example, “if the parent element has no children (:empty), then change its opacity”.
We can also do logic based on combinations of elements or selectors, like li + li, for example, “if the list item follows another list item, then give it a top border.”
I’m sure there are plenty more ways of applying logic but you get the idea. Each of these is equivalent to writing a conditional statement in a programming language – if this, then that.
I started thinking about this when I was designing a UI with a lot of logic going on. We had a busy table where we show some additional columns at wider screen resolutions. At smaller widths the user would be able to toggle between different groups of columns and save a preference. But then these additional columns are only offered if they contain data. So, we had logic around the screen width, user preference and presence of data, which, multiplied out, meant 8 permutations.
I initially tried to do it all with CSS. I set up media queries for the narrower and wider screen widths. Within each of these I then read a class for the user preference and then I used :empty to see if table cells contained any data. I managed it and it worked. Just.
However, I realised that it was really not scalable. Every time I added a new condition it doubled the amount of CSS I was having to write. If we wanted to add more logic in future it would create more and more work and be harder and harder to maintain.