I wouldn't be surprised if this ended with a smirky one-liner presented in a popular CSS framework, making a full circle from (early HTML):
<H1><FONT COLOR=red>...</FONT></H1>
to (Tailwind CSS)
<h1 class="text-red-500">...</h1>
I totally acknowledge the accomplishments that the Web standards and their implementations have made since the early days.
On the other hand, while I am no Tailwind proponent, for many applications "worse is good" and Tailwind is a bridge to the straightforward beginnings of the web design.
What do you mean by 'worse is good'? Remember the 'separation of concerns' wrt HTML/CSS was at a time when JSX, lit-html, web components et al did not exist. There was no easy way on the front end to do something like this:
function PrimaryHeader({children}){
return <h1 className="text-red-500">{children}</h1>
}
<PrimaryHeader>...</PrimaryHeader>
Thus, the 'separation of concerns' and many thousands of hours of developer toil ensued to both completely separate, yet still closely bind, style to markup by way of class names. There's no point to have a .PrimaryHeader class in a world of web components and atomic CSS (Tachyons, Tailwind, etc.)
Even absent of an atomic CSS library, I still prefer inline CSS to making up arbitrary class names; my entire codebase can be JSX files, and every component is self encapsulating. I don't see this as 'worse' in any way.
Having recently dabbled with Tailwinds, I can't express how nice it is to have control over most styling within the JSX/HTML without having to jump between CSS class definitions. At just a glance from the class names I can figure out what everything is doing, and it feels much more productive.
Generally, we now have awesome levels of abstraction available for developers (and counting, for example see CSS Logical Properties). On the other hand, for simple solutions, less abstraction is the way to go. Luckily, there is still inline style for that.
Technically, the choices are vastly more improved now.
You could always have a global style variable in a framework like react, that in the end renders the "text-red-500" part. Changes are pretty easy too.
And, React has been the framework that brought this new paradigm to the forefront. The amalgamation of programming and UI design. As long as designers were at the helm of web-sites, we had tools like Adobe Dreamweaver. Once programmers were forced to do UI stuff, we had stuff like React / Vue / Angular on the horizon.
I now realize that HTML is a platform. No human should ever directly write an HTML file. We must build software that builds HTML.
I realize the "in the horizon" is hedging for this reply, but I just had to mention that there was about a decade in-between where Dreamweaver was absolete and yet React / Vue / Angular were just random (non-)words.
> I totally acknowledge the accomplishments that the Web standards and their implementations have made since the early days.
I don't. It's taken all this time for CSS to catch up with table-based layouts, and it still doesn't really offer significant advantages if you're generating your markup from code (which we all are now). Video and audio tags are not noticeably better than HTML3-style embed; indeed in practice they're worse for the user (all that autoplaying video on news sites).
CSS exists to make it easier to DRY your hand-written HTML, which no-one does anymore. It's time to kill it.
Sure, the CSS standard supported CSS tables since the IE6 days, but IE6 didn’t support CSS tables. It wasn’t until IE8 had a decent browser share, around 2011, that it was feasible to use CSS tables. Even here, there were still enough IE6 and IE7 users that I still had stuff like this on my website in 2011:
There was a huge disconnect between what the standards documents supported and what browsers actually supported. There’s a reason they made that “smiley face” Acid2 test in the mid-2000s, because standards support was so bad back then: http://acid2.acidtests.org/ — https://en.wikipedia.org/wiki/Acid2
> CSS supported table-based layouts since CSS 2.0 which is more than 20 years old at this point.
IE only supported them from v8, so more like 10 years old in practice (a lot of CSS 2.x was "standardised" before it was implemented, and some of it turned out to not even be possible to implement). Though I was actually thinking of flexbox rather than table-layout, though I don't remember what (if any) the difference was.
Yeah IE6 being abandonware held back the web for a decade, no doubt about that.
But it was not CSS that had trouble catching up, it was a deliberate strategy by Microsoft because they considered the web a threat to its desktop dominance.
I share your opinion, But I would also like to mention that those "worse is good" applications are limited to certain niche.
I prefer vanilla HTML, CSS and minimal or no JS websites and my audience to a large part don't mind either and as long as I keep building to such niche audience then it's fine.
But if I try to compete in a market where the audience expect shiny layouts, fresh animations and don't mind waiting a minute for those to load; with a late 90s-esque website then I will certainly fail.
Remember that text-red-500 can be changed in one place across the application and allows you to apply general design ideas to quickly build layout. I don't personally use anything like tailwind, but the self-rolled css library I do use has a whole section of one liners like "flex" or "vertical-center" that saves me hours.
That’s an odd concern. Programmers have always been able to rework things maliciously. I can redefine console.log to wipe your hard drive if I wanted to. Redefining “red” is for if you want to tweak the shade. For example, changing it from ff0000 (or whatever) to, say, cc0000. Then all the darkness values (100-900) update automatically.
If “red-500” is your company color, it should be redefined in your config as “company” and write “text-company-500”. That way, if your company branding changes, you don’t have to “hack” red-500 to be blue-400; you just change the definition of “company”.
The “config” is just tailwind.config.json next to your package.json. The most basic file is literally just:
module.exports = {}
That alone gives you all the Tailwind defaults. But it’s customizable to infinity. tailwindcss.com’s documentation on individual classes is extensive on customization.
OK but you still haven't given any example of the part that actually does something, the part where you somehow go from "text-company-500" to red and whatever.
Why? We're discussing Tailwind in this thread. If you aren't aware that Tailwind isn't just the classes, but also a CSS preprocessor, we can't have a productive conversation.
But if you insist: https://tailwindcss.com/docs/adding-custom-styles There you can see that the example config file there defines custom colors (which could be your company branding colors). They don't have to be named actual colors; I could use `"mygreen": "#8FB68F"` (random color I just generated) if I so desired. Then, during my website's build process (into static HTML), any usages of "text-mygreen-500", for example (colors are 100-900), will generate a CSS selector automagically.
We're discussing how to set up a maintainable website where you can do things like change your company's brand colour from red to blue in one place and apply that consistently across your website. "Use Tailwind" isn't an answer to that any more than "Use CSS" or "Use HTML" is.
If your point is "I can write some code to output HTML with the appropriate styling" then... yes, but at that point why use HTML as the input format? (Because you can edit it in an HTML editor? Yes, but you undermine that if your styling isn't working at that point, in the same way as the Apache SSI problem described in the article). I think the article is talking about the kind of HTML that gets rendered by a web browser rather than the kind that's used as an internal representation in some other system.
When I write layout, I do it in a way that requires as little new css as possible. To do that, I rely on one liners that do the heavy lifting. When I was new, I would assign a class to a div, then write the padding and margins for that class. I would try to make general classes, like a class I can assign to all buttons, but I didn't have the right mindset.
Now, I can define my flex boxes, vertical flex boxes in a snap. Apply one of several common padding and margins to an element in a one-liner. Throw "vertical-center" onto an element to make it align-items:center. 80% of the layout I need to do can be composed in one shot without new css. Then I can make fine-tune adjustments using variables.
I don't remember what the exact text of any of the 4 box shadows I use. I know I apply two shadows (one shallow dark one and one further light one), but I couldn't tell you what the opacity is on either. I don't need to. I either apply it in the class or @extend .shadow-1;
OK, so what's the thing that actually does this? Clearly you're not talking about CSS as implemented in the browser, the thing that the article and this comment are about, because "@extend .shadow-1;" is not CSS syntax. And assuming that thing is some kind of processor that generates HTML/CSS, what do you gain from having the input to this processor be pseudo-HTML/pseudo-CSS rather than whatever format is most suitable for expressing things?
I know several different things that use a syntax like what you quoted. What I don't know is what workflow you're advocating or what you're trying to say at all.
You, sir, deserve a Pulitzer Prize for this. I smiled and yet shed tears of pain reading this. I worked for a web dev studio in the mid ‘90s. That was so rare. We had a partnership with a design and marketing firm because we were really the only ones in quite a wide area that knew how to code. To top it off, we were an Oracle database partner and would service big and upcoming companies. A database tied to a website, that was next level. LOL.
Those were the days. I kinda miss them. Everything was new and unexplored.
Small quibble: at least according to her twitter account linked from the sidebar of the linked post, the author of the linked post ("Eevee a.k.a. Evelyn Woods") goes by "she/her"
Even after reading the Wikipedia article to find out who "Peppermint Patty" is, I don't quite understand the reference but get the impression that it may be slightly disrespectful?
Those are sad times when the new generation doesn't intimately know about the Peanuts anymore.
Peppermint Patty´s best frient, Marcie, tends to eccentrically call her "sir", which may be due to Marcie´s bad eyesight and Patty´s slightly tomboyish behaviours. Patty at first is hugely annoyed by that, but eventually starts to accept - or better, less obviously discourages - that behaviour.
Peppermint Patty is a character in the Peanuts comic strip, there are probably only 4 characters in the strip that if you say someone is like that character it would be taken as disrespectful.
I don't think Peppermint Patty is disrespectful personally.
I gotten off the frontend train ten years ago. Then just the other day I decided that generating some stuff for printing in HTML should be way easier than fussing around with spreadsheets (and was right)—so finally looked up how one positions things with the flexbox. Where back in the day things were like literal masochism and still even selling your soul wouldn't get you far, now it's just ‘put these properties on your divs to tell the browser which way each of them goes’. Whoa daddy.
So these days there are 3 layout choices. Table, Flexbox and Grid. The one you pick is ultimately determined by how you want it to work relative to screen size.
Table is still good for making tables, that won't change layout based on screen or printer size. Very useful. For a spreadsheet type view, with strict columns and rows, regardless of screen, this might be a good option.
Grid is the best alternative where the grid must adapt to screen size, but there are still clear rows and columns in the layout.
Flex is more 1D than 2D, but can (easily) be coerced into 2D. It's great for things that should "flow" to fill the page.
So now instead of 1 (almost always bad) option, we have 3 distinct options, but it does take some experience to figure out when to use one, and when the other.
I recommend the guides at css-tricks for quick reference - I have them on speed dial.
> this company Netscape had been selling its Navigator browser (to businesses;
> it was free for personal use), and then Microsoft entered the market with its
> completely free Internet Explorer browser, and then Microsoft had the
> audacity to bundle IE with Windows. Can you imagine?
I believe the larger problem was that Microsoft offered companies and OEMs discounts on their Windows license fees if they agreed to stop purchasing any Netscape software, client and server, thereby collapsing Netscape's revenue from both ends.
Basically, MS offered discounts for anybody that wouldn't sell alternative OSes too. That includes OS2 (well I imagine it as aimed at it, and Be was unintentional), that IBM developed in a partnership with MS.
After they settled that case, they stopped offering discount, instead they just billed Windows copies by computer sold, independently of the OS.
This is indeed something I've noticed. The discussion about browser engines seems to draw heavily on late-90s folklore while entirely missing the point: browser engines today are extremely easy to work with, in the sense that it's entirely possible to develop something on, say, Safari, and expect it to work flawlessly on Chrome and Firefox, as well.
Back in the days, you had to budget twice the time to make something work in two browsers that it took for one. This is not hyperbole. You'd gain a bit from doing something the second time, but lose just as much trying to make it work in more-or-less the same way.
Then, there are the complaints about Chrome: there is absolutely nothing wrong with the way Google manages Chrome, with the possible exception of what they are doing to adblocking. Their approach is to try to make the browser platform an equal among the walled gardens they fear, primarily iOS and, to a lesser degree these days, Facebook. None of the lessons of Internet Explorer apply, because the problem with IE was that it was using Windows-only extensions such as ActiveX.
Two jobs ago when I used to work as a full-stack dev, the rule was to develop in Safari and test in Chrome and Firefox. We pulled the logs and there were way too many people using iPads that the site must work in Safari.
This is not a fair comparison. IE had several non-standard features and different implementations of standards. Developing in older versions of IE was almost a guarantee that it would be broken in all other browsers, even when you didn't use proprietary features.
It was even worse than that: you often had to budget for different version numbers of the same browser, or even different versions of a single version number. I'm a little foggy on the details, but I believe IE7 would force pages into "compatibility mode" if they were hosted via intranet. I was working for the government at the time and our apps were all hosted on the agency network. It was hell.
Especially if you were doing anything clever with Javascript. You pretty much had to code from scratch for several versions of every browser. Some you could do client-side and others would have to be rendered server-side. As poster above said, you would spend half your design time on getting the thing to look/run the same everywhere. Things are a lot closer now.
Man! That was a really, long and funny read. It brought me so much memories.
I remeber seeing a great site around 2003 and spending night-time reading its code and trying to grab all the details on how they did it. Copy pasting its code to the Notepad and trying to replicate it in Microsoft FrontPage.
I still have an old personal website[1] that uses Server Side Includes. I’ve been meaning to convert it to something newer for many years, but it chuggs along.
Next time I switch servers I won’t setup Apache so then it would need to be solved.
I also tend to stick with web safe colors everywhere. At the very least for my "base" colors. I also always expand them to the full pair of hex characters thanks to a bug in one of the 3.x or 4.x browsers that didn't support shortening hex colors when the characters in the pair were the same.
I am pretty much shit at using CSS correctly. I am working on a 38 page site and looking at the CSS is disgusting. The html is clean, the back end is simple and easy to understand, and the database is something to be proud of (well except where I used those seductive postgresql arrays instead of relations.) Some day though I am going to come back to make a change and that CSS is going confound me to no end.
Tailwind is great, but ironically it is full circle in regards to OP's post. You describe the page structure in HTML using classes, much the same before CSS was a thing. This is ideologically opposed to semantic HTML where you describe what the structure is, and not how it is. Using server side frameworks hides this, as long as you don't need to write static HTML. Tailwind has plenty of hype behind it and it's good, but it also has plenty of downsides too. As long as you're aware of where it's be suited for. I think Tailwind is a CSS framework for people who don't want to do CSS.
Semantic HTML is about using the write HTML tags for the right things, like <article>, <figure>, etc. The strings you put inside the class attribute are completely orthogonal to this — Tailwind has absolutely no influence on whether your HTML is semantic or not.
We worked with several accessibility experts when building Tailwind UI for example, and I am very confident in the semantics of all of that markup and how it performs in situations where that actually matters like when using assistive technology, because we tested it ourselves.
> The strings you put inside the class attribute are completely orthogonal to this — Tailwind has absolutely no influence on whether your HTML is semantic or not.
To add to this, screen readers for accessibility and search engine bots don't read CSS class names because they don't have standardised semantics (unlike HTML tags). Minifiers are allowed to mangle CSS class names because of this.
I think the problem here is it's common for people to confuse semantic HTML with semantic CSS class names. The latter are really to help your developers. If you're using utility classes though, you tend to use custom components to wrap + reuse styles versus using custom CSS classes so semantic class names aren't as important anymore. For others, this is explained well here:
I think the OP article is a good story on how we shouldn't cling on to current best practices. CSS was invented before complex single-page-applications were even a thing so it shouldn't be surprising at all if it turns out the old way doesn't scale well to our current needs.
I wonder how HTML would have developed if it would have been a 'compile target' (via static site generators) right from the start instead of being mainly written by hand. I bet that CSS could have been a lot simpler (similar to how RISC can be "simpler" than CISC if it no longer needs to support special instructions that make writing assembly code by hand more convenient).
People were already generating html back then and the output of those programs was "simpler" in the sense the html would just have tons of complicated inline formatting attributes on each element (that was completely opaque and impossible to edit by hand), so that's what it looks like when you don't need the output to be human editable.
Side note: the comments in this are all almost as valuable as the content itself. Remember when comments were a way people used to enhance content rather than attack or degrade it?
I saw the examples like `<img border=0>` and kept thinking "wtf why are they using styled-system here? Is this supposed to be pseudo code?" until I realized it must be something browsers supported (and probably still do). That should date me as a web developer.
What's "styled-system"? What's even unusual about this code? The border attribute is deprecated. And it's pretty uncommon to see un-quoted element attributes. Is it that?
What‘s unusual is that I had no idea there was ever a border html attribute, as someone who entered web dev around the time html5 was a buzzword.
styled-system is a css-in-js tool that puts the css properties right on the element, just like this. A bunch of popular tools in the space do the same thing.
It‘s funny in an "everything that‘s old is new again" way.
As someone who lived through the first round of CSS evangelism, this is amazing. That's how styling was done before it was even called "styling". It was all "bgcolor", <font>, and <table>.
That early image of Internet Explorer is very advanced. The page has a white background. When I first got into web design the page background was whatever the default color of the window control was. Usually light grey. I don't remember being able to change it?
If your website color scheme is dark, and you want to support the user's dark/light preference, what can you do to keep the default dark theme instead of simply inverting it?
To me it's the other way around. If you have a class that's only used once, is it better than inline styles? To me it's worse. You've just moved it to a different file.
With Tailwind, I work from the bottom up, with small composable classes, I notice common combinations and bundle them together in new classes. The end result is a lot better.
Utility classes are typically fewer characters, can contain multiple declarations and benefit from cascading, can benefit from responsive selectors, and can be updated in one place in the code when changes are required.
fair point, i was thinking about tailwind actually .. i guess it just provide shorter encoding and a few shortcuts to get done quickly (at the cost of ad-hoc names)
Proper use of chrome dev tools will help you here. Instant feedback based on modifying css in the page is about as good as you get when debugging. The computed tab really helps also.
All browser dev tools are good for that. I like Firefox's slightly more that Chrome's for it, Safari's is third. I don't know if Edge is different than Chrome for write, debugging CSS.
Yeah, I did not notice it was not a new post (although it was new, and a good read, for me). For some reason, it jumped at me as new in my RSS reader. Thanks to whichever mod added the tag! :)
> You see, a box (the rectangular space taken up by an element) has several measurements: its own width and height, then surrounding whitespace called padding, then an optional border, then a margin separating it from neighboring boxes. CSS specifies that these properties are all additive.
I never understood why CSS picked the obviously wrong way to define the box model. Who in their right mind would ever think that "width" would refer to the inner width of a box? I'm glad they finally added box-model: border-box, but the fact that there needed to be a switch at all is ridiculous.
It's pretty silly to claim that one way or the other is "obviously" wrong. A primary objective of defaults on the web is to never hide content; if "width" specifies the width of the content itself (i.e. box-sizing: content-box), when I say "div { width: 100px }" and put an image that's 100px in that div, I never crop/lose content. You can argue one way or the other, but neither is "obviously" more correct.
Two decades of work on CSS features, frameworks, best practices, preprocessors, etc, ....and the net value add can most generously be described as "below zero". Most content is perfectly fine as plain black text on a plain white background; the rare content that actually isn't is either a media file or requires proper graphics rendering tech like canvas or WebGL, and everything in between is just a turd-polishing trash tornado void
On the other hand, while I am no Tailwind proponent, for many applications "worse is good" and Tailwind is a bridge to the straightforward beginnings of the web design.