2026-05-13 03:00:00
Here’s Scott Jenson in his insightful piece “The Ma of a New Machine”:
the chatbot interface [makes us] feel like deep cognitive work is happening. But the interface is fundamentally reactive. It spits complex text at you, you skim it quickly, and you immediately type a reaction to keep the momentum going.
My hypothesis is that the very structure of the chatbot interface (type, read, type again) actively discourages reflection. When you are moving too fast, you get stuck in a groove. You literally need to take a break, step back, and basically step out of this groove so you can view the problem from a new angle. We’ve all walked away from a tough problem only to have the solution arrive unbidden into our thoughts later in the day.
In my decades+ experience designing and developing software, I can’t count the number of times I’ve stepped away from a problem at the computer only to return and find the problem magically resolved in my brain.
But the human-computer interaction of prompting doesn’t encourage the use of that skill in our subconscious.
In fact, I think it actively discourages it (our tools shape us).
Scott talks about this Japanese concept called “Ma” which is about deliberately creating pauses between things. He quotes Studio Ghibli director Hayao Miyazaki who says “if you just have non-stop action with no breathing space at all, it’s just busyness.” Here’s Scott (emphasis mine):
Ma provides a framework for understanding that a pause is not a lack of work
As humans we need pauses. We need space to breathe. We need time to digest.
Pausing, breathing, synthesizing, digesting — these are all necessary work.
“Digestion” is an interesting word here.
Putting food in your body is merely the beginning of feeding yourself. Our bodies must digest that food, break it down, absorb it, and get rid of the waste.
But that’s all happening mostly without our attentive oversight, so I guess it’s not “real” work — right?
Wrong.
Building good, healthy software requires digestion.
2026-05-11 03:00:00
I’ve been posting about how you can make lots of HTML pages and leverage navigations over in-page, JS-dependent interactions.
Now I’m gonna post another example.
On my icon sites, I have a little widget that allows you to resize the icons you’re looking at.
![]()
Previously, I implemented this functionality as a web component that looked something like this:
<icon-list size="md">
<a href=""><img src="" width="128" height="128" /></a>
<a href=""><img src="" width="128" height="128" /></a>
<!-- more -->
</icon-list>
The size attribute corresponded to an enumeration like sm | md | lg | xl which mapped to actual pixel dimensions like 64×64 or 512×512.
When the little widget was clicked to render icons at a different size, JavaScript changed the size attribute on the <icon-list> custom element. From there, the web component’s JS took over changing the dimensions of the children <img> elements, their src attributes, etc.
It all worked pretty well. However, because that was a client-side solution to my otherwise entirely pre-rendered static site, it required some templating logic and data be duplicated and sent over the wire to every client.
I didn’t love that for various reasons — like “Crap, I updated this one small part of how my icon list renders on the server, but forgot to tweak it on the client, so things are slightly broken now.”
Then one day the thought hit me: instead of relying on JS to make that interaction work (click, execute JS, modify in-page DOM to a new list), what if I just made that interaction a navigation? Click, navigate to a new list.
Instead of “every list of icons ships with some JS that allows them to re-render at four different sizes” I could do “every list of icons ships in four different sizes”.
/colors/red/, with JS to re-render the icon list based on user interactions./colors/red/{sm|md|lg|xl}, each a different icon list size.So I tried it. And guess what? Once I added some code to support CSS view transitions, I got a cool effect amongst the icons for free — that’s right, by removing code!
Works nice on mobile too!
I know I’m not doing anything particularly novel here, but as we continue to get new, powerful primitives on the web — like CSS view transitions — I find it really interesting to revisit basic patterns and explore what’s possible now that wasn’t previously.
It’s fun to ask yourself: “Could I remove some client-side JS and get a better overall experience?” If the answer is yes, I’ll bet you the development experience (and maintenance burden) is much improved too!
2026-05-04 03:00:00
I wrote about building websites with LLMs — (L)ots of (L)ittle ht(M)l page(s) — and I think it’s time for a post-mortem on that approach:
I like it.
I’ve tweaked a few things from that original post but the underlying idea is still the same, which I would describe as:
Avoid in-page interactions that require JavaScript in favor of multi-page navigations that rely on HTML and are enhanced with CSS view transitions (and a dash of JS if/where prudent).
As an example, on my blog I have a “Menu”. It doesn’t “expand” or “slide out” or “pop in” or whatever else you can do with JS. Instead, it navigates to an entirely-new page that is focused on just the menu options of my site.
I say “navigates” because it’s just a link — <a href="/menu/"> — and it functions like a link, but the navigation interaction is enhanced by CSS view transitions.
Have a newer device with a modern browser? Great, you get a nicer effect.
Have an older device, or an older browser, or JS disabled, Et al.? It’ll still work.
If you can follow a link — which is the most fundamental thing a browser can do — it will work.
So how’s it all work under the hood? In essence, all the pages have a link to the menu (except the menu page). When you navigate to the menu, that link is changed to an “X” which “closes” the menu. The closing is still just a link (back to /) but it’s enhanced with JS to actually do a “back” in the browser history. This makes it so “opening/closing” the menu doesn’t add an entry to your browser history.

As a simplified example, the code looks like this:
<!-- Normal page -->
<nav>
<a href="/menu/">
<svg>...</svg>
</a>
</nav>
<!-- Menu page -->
<nav>
<a href="/" onclick="document.referrer ? history.back() : window.location.href = '/'; return false;">
<svg>...</svg>
</a>
</nav>
The document.referrer checks whether we came to this page as a navigation (mostly likely from within the blog itself) or via a direct visit (i.e. somebody typed it into the URL bar, unlikely but possible) which is how I suss out whether there’s a meaningful history.back() run or not.
Here’s a video of how it all works, if that’s your thing:
While this solution seems simplistic, it was not a simple thing to arrive at. It required me to spend time thinking about what was essential to navigation, how that interaction could work across multiple pages, and how I could ensure page size stayed small so the interaction was both fast and robust while remaining intuitive to use.
In other words, the approach shaped the design.
Turns out, if you have a website and you think of the browser as a way to navigate documents — rather than a runtime to execute arbitrary code and fetch, compile, and present them — things can be a lot simpler than our tools often prime us to make them.
Reply via: Email · Mastodon · Bluesky
Related posts linking here: (2026) Out With the JS, In With the HTML
2026-04-27 03:00:00
I’ve been thinking about speed which is why Chris Coyier caught my attention in his latest piece discussing how AI might be 10✕ing the speed with which we code, but it’s not making our software 10✕ better:
Faster individuals don’t make a fast company
My mind immediately went to the 4✕100 relay at the Olympics.
(Not sure which race that is? Watch the London 2012 one.)
Imagine you were put in charge of winning the 4✕100 relay.
All you gotta do is find the four faster sprinters in your country — right?
I’m no track and field expert, but I doubt it’s that simple.
In a relay race, the baton is arguably the most critical element. Passing it cleanly is vital because if you fumble it you’re easily behind a few meters or maybe even disqualified.
So, one could argue, a sprinter’s ability to pass and receive the baton is more important than speed because all the speed in the world won’t help you overcome a dropped baton.
(There are other considerations too, like which leg each runner takes, which sequence works best given individual pairings and rapport, and whether a slower veteran might perform better in the heat of the moment.)
Faster runners won’t guarantee a faster team.
And faster coders won’t guarantee a faster company.
Like a relay race, it might be worth giving some thought to the relationships and interfaces between people.
2026-04-20 03:00:00
In the early 2000’s, my parents took us on a road trip to Glacier National Park in Montana.
We made the journey in our new (used) family van: a green Dodge Caravan whose reputation was soon to become “a lemon”.
I was a teenager and didn’t pay a lot of attention to the details of what was happening around me, but I do remember how the van kept overheating. It ran fine on the interstate, but anything under 40MPH had the car’s temperature gauge rising into unsafe zones.
I remember stopping in some small town in Montana to get it checked out by a mechanic. He checked it out, took it for a test drive, etc., and told my Dad the reason the car was overheating was because the idling fan wasn’t turning on. At higher speeds, like on the interstate, that was fine because there was enough airflow to keep the engine cool but at lower speeds the car would overheat. The mechanic said he didn’t know why the fan wasn’t turning on. There was nothing wrong mechanically from what he could see. But he couldn't fix it. He told my Dad that this was one of those increasingly common “computerized” cars that you have to hook up to another computer to diagnose the source of the issue. And he didn’t have one of those computers.
So we continued on our way. The rest of the trip required my Dad taking “the long way around”, like back roads where he could keep up his speed in order to avoid the car overheating. It was all very amusing to us as kids, almost thrilling because Dad had a legitimate excuse to drive fast (suffice it to say, Mom did not like this).
Once the trip was over and we returned home, my Dad was able to get the car in to a dealer where they hooked up the car’s computer to another computer to diagnose and fix the issue. I don’t really remember the specifics, but the issue was seemingly some failed digital sensor that prevented the idling fan from turning on. Once the sensor was replaced, things worked again.
Computers talking to computers.
Growing up in an era that shifted so many things from analog to digital, mechanical to electronic, I’ve thought about this trip a lot.
And I’m thinking about it again in this new era of building software with LLMs.
I think about that mechanic. This guy who grew up around mechanical cars that could be physically inspected, diagnosed, and repaired. So much of his experience and knowledge unusable in the face of a computerized car.
You can tell when a mechanical switch has failed with your eyes, but not a digital one. You need a computer to help you understand the computer.
Will this be my future?
If a codebase was made with the assistance of an LLM, will its complexity and bugs only be inspectable, understandable, diagnosable, and fixable with an LLM?
“Hey, can you help me, there’s a problem with my codebase?”
“Ok, I can confirm the issue, but I can’t fix it without hooking your codebase up to an LLM.”
2026-04-16 03:00:00
Speed has become the primary virtue of the modern world. Everything is sacrificed to it.
Move fast (and break things, not as a goal but as a consequence).
Wisdom requires allowing yourself to be undone by experience:
Experiencing these can be slow and uncomfortable, but if you keep up your speed you can outrun them — never reflecting on what happened in your wake.
Speed is how you avoid reckoning. It guarantees you miss things, and you can’t learn from what you don’t notice.
Wisdom’s feedback loop is slow.
Wise people I’ve met seem unhurried. I don’t think it’s because they’re slow thinkers or actors. I think it’s because they’ve learned that important things take the time they take, no amount of urgency changes that.
Wisdom is chasing all of us, but we’re going too fast to notice what it’s trying to teach us.
Reply via: Email · Mastodon · Bluesky
Related posts linking here: (2026) Collective Speed Is Not the Summation of Individual Speed