Skip to content

feat(blog): "Hey Elvon!" - #33

Draft
Adebesin-Cell wants to merge 8 commits into
mainfrom
blog/hey-elvon
Draft

feat(blog): "Hey Elvon!"#33
Adebesin-Cell wants to merge 8 commits into
mainfrom
blog/hey-elvon

Conversation

@Adebesin-Cell

Copy link
Copy Markdown
Owner

🔗 Linked issue

N/A

🧭 Context

New blog post about Elvon, the autonomous trash collector five of us built for a random class group assignment. It's the story side of my FUTA years: the team, the wiring disasters, the two nights lost to a speaker, the wire that burned two days before defense, and what the rest of the team had to say about it.

Adds content/blog/hey-elvon.md.

📚 Description

The post walks through the project from team selection to defense day, with the state machine and the pieces of firmware that mattered, plus quotes from each teammate. It follows the same structure as the other long-form posts on the site, so it needs no layout or component changes.

Images are not in this PR yet. The post references 15 assets under public/images/blog/hey-elvon/ (cover, team shots, the burnt wire, the prototype, and a few gifs of the first spin, first voice and obstacle avoidance) and none of them are committed, so the post will render with broken images until I add them. That's why this is a draft. I'll push the assets before marking it ready.

@vercel

vercel Bot commented Sep 1, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
lope Ready Ready Preview Sep 2, 2026 7:47pm UTC

Prose images all loaded eagerly and carried no dimensions, so a post
paid for every image on first paint and then shifted as each one landed.

Images now default to lazy via a ProseImg override, with each post's
hero opted back into eager + high fetch priority since it's the LCP.
A build transformer stamps intrinsic width/height by reading the file
headers directly, covering png, jpeg, gif and svg without an image
library. Remote images are left alone, they can't be measured here.

Also fixes code blocks rendering unhighlighted: cpp wasn't in Shiki's
default language set, and Content's theme switch keys off a .dark
descendant of <html> while color-mode puts the class on <html> itself,
so every token fell back to the light palette on a near-black block.

Tables and rules had no styling at all, and the prose gets a Clip
component so a demo can ship as a looping mp4 instead of a gif.
Seven slots filled from the shoot: the cover is the front and
three-quarter views merged so both the sensor face and the wheels are
visible at once, plus the team at the workbench, the wired breadboard,
the bare chassis, the PIR in hand, the teardown, and a stand-in for the
glue gun moment.

Each photo is cropped to drop the dead floor and ceiling the phone
caught, so they read at a sane height in the column.

Obstacle avoidance ships as an mp4 through Clip rather than a gif. The
same clip as a gif was 6.2MB at half the resolution.

Portraits, the burnt wire, defense day and the demo video link are
still to come.
A link out of a post replaced the page the reader was in the middle of,
so anything external now opens in its own tab with noopener alongside
the nofollow Content already sets.

Internal routes go through NuxtLink instead of a plain anchor, so they
navigate client-side rather than reloading. Paths that point at a file
rather than a route keep the anchor, since NuxtLink would try to
resolve /feed.xml as a page. Anchors and mailto: are untouched.
The demo video link was still pointing at a TODO placeholder. Both
recordings live on the school's OneDrive, so they ship as links rather
than inline clips.

Worth checking these open for someone signed out, they're org-scoped.
Posts shipped full-size JPEGs into a 700px column, so a reader on a
phone paid for 1337K of photos to look at maybe a third of those
pixels, and both demo clips downloaded whether or not anyone scrolled
that far.

Prose images now go through NuxtPicture: AVIF first, WebP next, the
original as fallback, with a srcset built around the column width. The
same photos come to 249K at 1x and 583K at 2x. SVGs, GIFs and remote
images skip the pipeline, since Vercel's optimizer rejects SVG and the
mention avatars aren't ours to transform.

The provider is pinned per environment. Left to autodetect it emitted
/_ipx/ URLs into the production build, which would run sharp in a
function for every variant instead of using the edge optimizer.

Clips get a poster and preload="none", and an observer attaches the
source 200px before they scroll into view, so the 888K of video costs
nothing until it's wanted. Reduced motion still gets controls and no
autoplay.

The glue gun gif is an mp4 now, 2.0MB down to 250K.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant