Styling with Classy CSS (2006)(thedailywtf.com) |
Styling with Classy CSS (2006)(thedailywtf.com) |
Instead of .f-green in your HTML you can do --f-green in your CSS.
<header class="f-green"></header>
would become
header { color: var(--f-green); }
or if you really hate CSS and must stay in HTML
<header style="var(--f-green)"></header>
Though the literal naming is a touch too specific anyway. Something like this is wonderful:
--f1-color: green;
header { color: var(--f1-color); }
then you don't have to do confusing things like
header .f-green { color: red; }
because you can do
header { --f1-color: red; }
So we can be less specific AND more modular... because you can have that f1 (font1) color be red in your header, and still do:
footer { --f1-color: green; }
We can make really flexible and extensible systems with modern vanilla CSS. No frameworks or preprocessors needed.
Also, if your company rebrands from green to red you can just `.f-green {color:#f00;}` - it's so efficient!
I find it's helped for a few reasons, but the big one is just that it's easier to keep the colours in my head - I'm not thinking in terms of "tertiary-alt-3" or something, I'm looking at a design and going "that's green, which green? This green". I have more discussions talking about colours in terms of the standard English colour names than I do in terms of those colours' purposes in the design system, so the colour names seem more practical.
That said, I agree that spending some time switching the colours to whatever design system you're using us very useful. Another trick I've found is starting off a project just using raw CSS values (the `p-[8px]` syntax), and then when the basic designs are done based on whatever the designer has sent, getting a list of all the custom classes you've got and using this to define what the standard units are. This is helpful when the design guide isn't specific on these details, and the designer is being more freeform.
That way you can define your company's --brand-colour at the top of the file.
Oh, we didn't? Well, time to learn a new syntax. (Was it `dark:md:hover:text-slate-400` or `hover:md:dark:text-slate-400` again?) At least Tailwind arguably has more benefits than its predecessors.
At my current job, I work on a legacy application which is still actively developed and released. I spend a lot of my time cleaning up inline styles, styles that are applied via javascript calls, and style blocks on individual pages. I wish the inline styles would have been utility classes, because at least then they would be easy to find and replace, instead, there are "margin-top: 3px" and "margin: 4px 0 0" and "padding-top: 2px" and dozens of variations on that that had they just done something like ".mt-small { margin-top: 3px }" there wouldn't be so many variations and inconsistent looking pages. This company would have benefited greatly from Bootstrap or Tailwinds. I hate both of those, but there is no denying how easy they are to use and abuse.
But when you want to redesign a whole site after the fact, or if you want to keep your component library logic & templates, and port it to a new system, Tailwind might be more trouble than it's worth.
It's just that... Atomic CSS has its benefits, BEM has its benefits, etc etc etc.
Personally I'm using Tailwind for 90% of the styling. If I keep repeating a certain combination of classes often, I'll group it with a custom class. (Edit: See colejohnson66's comment for an example)
Two advantages of tailwind that I didn't see before I started using it:
- It's often easier to find what I want in the tailwind documentation, and it comes with nice examples. MDN is great, but with Tailwind I get reasonable presets.
- TailwindUI: Saves me a lot of time and looks good without feeling as generic as bootstrap.
I completely rewrote the CSS for my website and I did not need to touch the templates. An .error is an error and a . collapsible is a collapsible. Their exact style is not dictated by the markup.
I also like that it keeps the markup small and easy to read, because it's not peppered with CSS.
It also avoids situations where two widgets look different because I forgot to copy one class over. A .collapsible is a collapsible.
Then you can do things like `color1` (or `primary1` or `secondary2`) etc, keeping them generic. With this setup you can then re-theme any area instantly, no dark-x or light-x, no green-x. You can inverse an area to be light on dark, you can change the color out if need be.
We even go one step further (as an optional feature) where you can avoid the `color1` for many cases and instead use `color`, `colorHover` etc, which allows for having themes that change contrast or the strength of their various alternate states, but that's another story.
The site itself shows off some of this, but it's really quite nice. Now your "Notice" box can be alert style, or success style, with just a single `<Theme name="alert">`.
I agree but found that Bootstrap (>v4) to be better at this. Instead of every possible color and tweakie, Bootstrap has pretty decent utility classes that are semantic, and in addition to all the basic components like button, etc:
Restyling a website without changing any of the markup is a pipe dream from the CSS Zen Garden days when websites were much simpler and more static. Apart from small/personal/static websites, it just never happens in practice today.
Why do we need all these different classes? One CSS class can handle the presence or absence of a hide button just fine, and lots of frameworks just have .danger set variables or override colors, staying pretty much universal.
.myFancyTable td {
@apply p-4;
}
The advantage of Tailwind, IMO, is that styles for one-off components (like a breadcrumb bar) can just be written inline instead of in a separate file. But reused components like table cells should be using CSS selectors.CSS variable libraries like open-props also do this, only without the controversial use of utility classes. Add editor snippets to that and you have nearly the same ease of use as tailwind.
Class definitions are not CSS. They're markup. The CSS selector language does let you target them (with a leading dot, as in .foo)—just like CSS lets you target other things defined in markup with special syntax: element IDs (#bar), attributes ([foo=bar]), etc. It's not as if HTML existed without classes and without CSS, and then CSS was invented and with it came classes, too.
(This isn't to say that you're alone. A frighteningly high number of people reveal through their choice of language an apparent belief that `class` was invented by the CSS working group (or something). That when you're writing HTML, evidently 95% of it is HTML proper, but then when you get to the part where you type out 'c', 'l', 'a', 's', 's', that you're shifting into CSS and it's like, "This last piece with these "classes" was contributed by the CSS folks, and so that's why/how CSS leaked in," without ever seeming to realize that... they're not actually writing CSS. It's still just markup—using the ordinary syntax for specifying attributes and their values. The CSS only happens when you, uh, start writing CSS...)
These are things that CSS literally solved with the web2.0/semantic-web movement 20 years ago. I get the convenience of Tailwind but a lot of it feels like a massive step backwards.
That way there is no repeated rules like in the final compiled @extend/@apply operations.
But yeah take say a dashboard layout with a lot of cards of different sizes. They're going to have the same underlying design, padding, rounded edges, background colors, etc -- and usually only vary on maybe size and breakpoints.
This is all very well solved in semantic web, but it feels to me like the JS + Tailwind apporach is creating new problems and thus new solutions to accompany.
If it was solved with "semantic web" (whatever that means), we wouldn't have people attempting to solve this again, and again, and again.
All "semantic web" can provide is a flat CSS namespace and a bunch of nested divs.
Even if you do everything right there's nothing semantic about it: https://inclusive-components.design/cards/