Lighthouse 90+ Without Killing the Design
Keep cinema-grade brand design and still hit strong Lighthouse and Core Web Vitals on real phones. Treat 90 as a tradeoff, not a chase for a perfect 100.
William Spurlock Founder — Spurlock Studios Updated 18 MIN
A 90 on mobile Lighthouse and a film-grade fold can live on the same page. They stop living together when you lock the art direction first, then ask engineering to hide the cost. Chrome itself colors 90–100 as good and says a perfect 100 is not expected — moving 99 to 100 takes about as much metric work as moving 90 to 94, per the Lighthouse performance scoring docs. This spoke is the tradeoff map: keep the brand, budget the motion, and stop treating a green circle as the product. Parent pillar: Websites That Feel Like Films.
The short answer
- Animations are allowed. Unbudgeted animations, late LCP images, and first-load tag soup are not.
- Optimize the actual LCP node. If the fold is hidden until a JavaScript timeline runs, the plan is wrong.
- Core Web Vitals are field metrics at the 75th percentile: LCP ≤ 2.5s, INP ≤ 200ms, CLS ≤ 0.1, as published on web.dev/vitals.
- Lighthouse is a lab debugger. It cannot measure INP the way the field does; it uses Total Blocking Time as a proxy.
- Cut accidental weight first. Do not start by deleting the photography that is the brand.
What does a Lighthouse 90 actually mean?
A Lighthouse Performance score is a weighted average of lab metrics, not a ranking certificate and not a taste score. Chrome documents the current published weights under Lighthouse 10 in performance scoring:
| Lab metric | Weight | What it is actually scoring |
|---|---|---|
| Total Blocking Time (TBT) | 30% | Main-thread long tasks between FCP and TTI |
| Largest Contentful Paint (LCP) | 25% | When the largest viewport content paints |
| Cumulative Layout Shift (CLS) | 25% | Unexpected layout movement |
| First Contentful Paint (FCP) | 10% | First paint of any content |
| Speed Index | 10% | How quickly visible content fills in |
Color bands on that same page: 0–49 poor, 50–89 needs improvement, 90–100 good. That is why this post is titled 90+, not 100. A 92 with a readable cinematic fold beats a 99 that shipped as a sterile brochure because someone deleted the brand to flatten the last orange audit.
Score curves are log-normal against HTTP Archive data. The 8th percentile maps to a metric score of 90. Past ~96 you are in diminishing returns. If a stakeholder wants “100 or we failed,” show them that paragraph from Chrome, then show the filmstrip of what the 100 cost.
Desktop and mobile use different scoring curves. A desktop 96 on an M-series laptop is not a mobile 96. Celebrate the mobile run, or do not celebrate.
Is lab Lighthouse the same as Core Web Vitals?
No. Web Vitals is explicit: Core Web Vitals are field metrics. Lighthouse is a lab tool. Google’s own table says Lighthouse can report LCP and CLS in the lab, and cannot report INP — use TBT instead.
| Signal | Where it comes from | What it is for |
|---|---|---|
| Lighthouse Performance | Simulated device + throttling | Debug a build before it ships |
| CrUX / Search Console CWV | Real Chrome users, ~28-day window | The compliance picture |
Your RUM (web-vitals library) | Your visitors, your pages | Diagnose which template actually fails |
| PageSpeed Insights | CrUX on top + Lighthouse below | Compare field vs lab on one URL |
Optimize LCP says it directly: look at real users first. Lab tools explain why. They do not get to overrule CrUX when the two disagree.
A staging 95 that becomes a field 70 usually means one of these:
- Production tags were not in the lab run.
- Real phones are slower than the lab CPU throttle you assumed.
- Users land cold on the homepage; you tested a warm cache.
- The LCP element in the field is not the element you optimized in DevTools.
Test with extensions off. Then test again with the marketing tag soup that will exist in production — and fight to remove the soup. Pair both with a phone in your hand.
Can a brand site stay fast with animations?
Yes, if motion is a budgeted material, not an unlimited overlay. High-performance CSS animations is blunt: keep motion on transform and opacity so work stays on the compositor. Animating top, left, width, height, or filter forces layout or paint. That is how a “subtle” scroll scene melts a mid-range Android after twenty seconds.
The path I use on brand homepages:
- Static fold that paints from HTML — type and LCP image visible without JS.
- Modern image formats at layout widths, not a 4000px dump.
- Fonts loaded with a display strategy you chose on purpose.
- JS islands only where interaction needs them.
- Motion limited to transform/opacity, with teardown when the scene leaves the viewport.
- Measurement on a mid-tier Android, not only on a laptop lab score.
| Motion type | Usually fine | Usually expensive |
|---|---|---|
| One earned hero entrance (opacity + translate) | Yes, if LCP text is already visible | Hiding the headline until GSAP says go |
| Hover / focus micro-moves | Yes | Hover that triggers layout on every card |
| One scroll-linked scene | Maybe, if compositor-only | Multiple scrubbed timelines fighting each other |
filter: blur() on scroll | Almost never on mobile | — |
| Decorative WebGL on the homepage | Rarely | Always until proven otherwise |
If the animation plan requires hiding LCP text until a JS timeline runs, fix the plan. Motion that arrives after the brand is readable is craft. Motion that is the first paint is a metric trap.
Honor prefers-reduced-motion: reduce with a still or a single fade. That is not a performance hack. It is the same craft standard as Accessibility as Craft.
What does LCP want from a cinematic fold?
Largest Contentful Paint is the time from navigation start until the largest image or text block in the viewport is painted. Optimize LCP sets the field target: 2.5 seconds or less for at least 75% of visits.
On brand sites the LCP node is almost always the hero image or the headline block. Optimize that node. Do not optimize a logo that is not LCP while the 2.4MB shoot sits in a CSS background discovered after a stylesheet.
Chrome’s LCP request discovery insight is a three-line brief:
- Make the LCP image discoverable from the HTML (or preload it).
- Put
fetchpriority="high"on that image or its preload. - Do not put
loading="lazy"on it.
Fetch Priority explains why: in-viewport images often start at Low priority until layout proves they are visible. That delay is how a “correct” hero still loses 2.5s. An explicit high fetch priority lets the hero start earlier. Do not stamp fetchpriority="high" on three images. Chrome’s own guidance: more than one or two high-priority images makes the hint useless.
Browser-level lazy loading is equally blunt on the fold: lazy-load only what is outside the first viewport. A CMS that auto-applies loading="lazy" to every <img> will punish the hero. Override it.
| Fold pattern | LCP outcome | Use it? |
|---|---|---|
<img> in HTML, sized, AVIF/WebP, fetchpriority="high" | Best default | Yes |
CSS background-image with <link rel="preload" as="image" fetchpriority="high"> | Workable | When art direction requires a background |
| Image injected by JS after hydration | Late discovery | No |
| Autoplay film as the LCP candidate | Decode + bytes tax | Still + poster first; see hero video |
Headline hidden at opacity: 0 until a timeline | Text LCP delayed or shifted to a worse node | No |
TTFB and FCP are diagnostic, not vanity. A large TTFB-to-FCP gap often means render-blocking CSS/JS. A large FCP-to-LCP gap often means the LCP resource was not in the HTML. Read those gaps before you recrop the photograph.
Why does INP punish motion libraries and tag soup?
Interaction to Next Paint measures responsiveness across the page life, not only the first tap. Good is 200ms or less at p75 (web.dev/vitals). Lighthouse cannot click around like a person, so it scores Total Blocking Time instead.
TBT sums the blocking portion of long tasks between FCP and Time to Interactive. A task over 50ms is long. A 70ms task contributes 20ms of blocking. TBT is 30% of the Lighthouse Performance score. That is why a homepage that “looks instant” still lands orange: analytics, chat, A/B, and a motion runtime ate the main thread before anyone tapped.
| First-load guest | Typical INP / TBT damage | Default policy |
|---|---|---|
| Tag manager + four pixels | High | One container, delayed, owned |
| Chat widget | High | Click-to-load after the fold is idle |
| Motion runtime hydrating the whole page | Medium–high | Island the scene; teardown offscreen |
| Auto-rotating carousel | Medium | Static first slide; enhance on view |
| Consent banner JS | Medium | Reserved space; no layout thrash |
| Five social embeds | High | Facades; one job per page |
Chrome’s TBT doc points at the usual culprits: unnecessary JS parse/execute, unused code, and third-party scripts. On a marketing site those are process failures, not requirements of taste. A 900kb homepage bundle is almost never “the design.” It is a stack that hydrated a brochure.
Top CWV fixes put interactivity in the same conversation as LCP: defer non-critical work so the main thread can answer a tap. Yield long tasks. Do not run a scroll listener that forces layout on every frame.
- Audit third parties like they cost rent.
- Split the motion bundle from the page shell.
- Hydrate carousels, forms, and scenes on visibility or interaction.
- Kill duplicate tags. Two analytics snippets is not “coverage.”
- Re-check INP in the field after marketing adds “just one pixel.”
How do you stop CLS without flattening the layout?
Cumulative Layout Shift is unexpected movement. Good is 0.1 or less (web.dev/vitals). Brand sites fail CLS in boring ways: webfont swap on a three-line headline, a consent bar that shoves the hero, an embed that opens at 0×0 then becomes 16:9, a sticky announcement injected after paint.
Reserved space is design. It is not a compromise that makes the page “less cinematic.” A fold that jumps under a thumb feels cheap. A fold that holds its geometry while media arrives feels expensive.
| CLS source | Fix | Do not |
|---|---|---|
| Images / video posters | Width + height or aspect-ratio boxes | Naked <img> with no box |
| Webfonts | Metric-matched fallback + display strategy | Swap a condensed display face onto a system sans with no @font-face override |
| Consent / promo bars | Reserve a slot or use an overlay that does not shove | Inject 72px after first paint |
| Embeds | Sized iframe or facade with the same box | “The player will fill in” |
| Web fonts + late CSS | Preload the face that styles the LCP text | Four families, eight weights, discovered in a CSS file at the bottom |
Top CWV also flags layout-inducing animations as a CLS (and INP) problem. Animate transform. Do not animate properties that reflow the page, especially in response to a tap.
Set sizes. Avoid injecting sticky bars after load without a reserved slot. Coordinate legal and marketing before launch — last-minute banner installs are a classic vitals regression, not a surprise.
What image pipeline can designers live with?
Designers should see weight budgets the way they see color tokens. A “small tweak” that swaps in an uncompressed shoot can erase a week of performance work. The pipeline is the constraint that keeps the photograph.
| Slot | Starting budget I put in a sprint brief | Notes |
|---|---|---|
| Hero / LCP still | Agree a cap in the brief (often well under 300KB in AVIF/WebP at 1x/2x) | Art-direct the crop; do not ship unused pixels |
| Below-fold stills | Smaller; lazy-load | Same format rules |
| Decorative textures | Tiny, or CSS | Not a 2MB PNG grain overlay |
| Poster for optional video | Optimized still that is LCP | Video is extra, never the first paint |
Rules that survive contact with a brand shoot:
- Prefer AVIF/WebP with a fallback when the audience needs it.
- Widths match the layout (1x/2x), not 4000px everywhere.
- Hero is prioritized. Below-fold is lazy. Never reverse that.
- Art-direct crops so you are not shipping the unused edges of a horizontal frame into a vertical phone slot.
- Avoid PNG for photographic heroes. PNG is for sharp UI and type-on-transparent, not a grade of a live set.
If the creative requires a 4K film loop behind type, admit the metric cost or change the creative. I do not publish invented “42 to 99 overnight” stories. The honest pattern: remove accidental weight, protect the LCP path, budget motion, re-check on a phone.
How should brand fonts load without invisible text?
Two families is enough for most marketing sites. Display plus body. Extra weights are how a type system becomes a network problem.
Font best practices maps font-display to block and swap periods. That table is the decision, not a vibe:
font-display | Block | Swap | Brand-site use |
|---|---|---|---|
swap | 0ms | Infinite | Distinctive display faces, if you preload and metric-match the fallback |
optional | ~100ms | None | Body text you can live without on the first visit |
fallback | ~100ms | ~3s | Compromise when swap is too jumpy |
block | 2–3s | Infinite | Rare; FOIT risk. Pair with preload if you insist |
auto | Browser-defined | Browser-defined | Do not leave this to chance on a headline |
Optimize web fonts notes that swap shows text immediately and can shift the layout if fallback metrics differ. optional avoids that shift and may skip the webfont on a slow first visit. Preload + optional is the Chrome-documented path to kill FOIT and much of the swap jump when the face is actually needed.
Preload critical assets is the other half: preload the face that styles LCP text, not every weight in the kit. A preload without crossorigin on a font is ignored. Do not preload six files “just in case.”
- Preconnect to the font CDN if you do not self-host.
- Subset when you control the files.
- Prefer a variable font when it reduces total bytes, not when it is a fashion choice that ships a heavier file than two static cuts.
- Design the fallback stack so swap is not a layout explosion — size, line-height, and
size-adjust/ metric overrides belong in the type PR, not in a post-launch hotfix.
Invisible text during font load hurts UX and metrics. If the LCP node is a webfont headline, font-display other than auto/block keeps that text visible so LCP is not blocked on the extra request — optimize LCP calls this out.
How much JavaScript does a marketing homepage actually need?
Ship HTML for the story. Hydrate the pieces that must move.
| Need | Ship | Do not ship on first load |
|---|---|---|
| Brand story + offer | HTML + CSS | A client-rendered shell that paints a blank stage |
| Carousel | First slide in HTML | The whole slider runtime before paint |
| Form | Native form, enhance later | A 200kb forms framework for three fields |
| Motion scene | CSS or a scoped island | A page-wide timeline that imports the kitchen sink |
| Analytics | One delayed, owned container | Four tags “because the last vendor left them” |
Astro and other static-first shells make high scores easier because HTML arrives complete. Framer and Webflow can still perform when you are disciplined with assets and interactions; they punish carelessness faster. Custom React SPAs can hit 90+ but you earn it with islands, code splitting, and ruthless dependency control. None of those stacks is a moral position. They are different places the weight hides.
Preload key requests exists because JS often hides CSS and images behind a download-parse-execute chain. If the LCP image is only known after app.js runs, you already lost. Put the image in the HTML or preload it from the document head.
What should you cut first when scores slip?
Resist random thrashing. Bytes first, third parties second, layout third, motion last.
| Priority | Cut or fix | Why it is first |
|---|---|---|
| 1 | Ambient / autoplay video | Decode + bytes + main thread; see hero video |
| 2 | Extra webfont weights and unused families | Cheap win; often the CLS and LCP hit you ignored |
| 3 | Chat and extra pixels on first load | TBT / INP |
| 4 | Auto-carousels | Timers + images you did not ask for |
| 5 | Scroll libraries fighting each other | Main-thread + layout |
| 6 | Decorative WebGL | GPU + JS for a texture you could still |
| 7 | Duplicate analytics tags | Free, and somehow always there |
What not to cut first: readable type contrast, real photography that defines the brand, or primary CTA clarity. Performance theater that deletes the brand is not a win. Teams that start by deleting photography to chase a two-point gain usually regret it — and still have a 400kb JS problem they did not look at.
Failure mode I see on cinema-grade marketing sites: the fold is a JS-owned stage. The photograph is fine. The type is fine. Nothing paints until a bundle, a font kit, and a timeline agree. Lab LCP looks “close.” Field LCP is a different element, or a late one. The fix is not “less design.” The fix is HTML for the still + type, then motion as a layer.
A second failure mode is the 100-or-else recap. Someone pastes a desktop 98 into Slack, marketing adds a chat widget the same afternoon, and the phone experience is the one nobody recorded. The score was never the product. The fold that paints, the tap that answers, and the layout that holds are the product. If a two-point lab gain requires deleting the image that is the brand, you are optimizing the PDF.
Do not start a rescue by restyling the logo. Start by naming the LCP node, the long tasks, and the layout jumps. Those three names usually tell you whether the problem is design or residue.
When is hero video or WebGL the wrong spend?
When the still already does the job, or when mobile cannot pay the tax.
Autoplay background video is LCP poison if the video frame becomes the largest element or if the download starves the poster. The spoke that owns that decision is Hero Video Slowing Your Site: poster carries LCP, mobile defaults to still or tap-to-play, loop stays muted and short. This post will not re-litigate encoding. It will say: if you need a 4K loop to “feel premium,” try a graded still plus compositor motion first.
WebGL and heavy canvas are the same conversation with a different GPU bill. A decorative particle field on a homepage is rarely the offer. It is a demo. Demos belong in a lab tab or a campaign microsite with an explicit metric waiver.
| Spend | Earns its keep when | Wrong spend when |
|---|---|---|
| Graded still + CSS/GSAP | Always the default | You skipped it to jump to video |
| Short muted loop | Poster is LCP; mobile is still | Same file on a phone over LTE |
| WebGL scene | The product is the scene | It is wallpaper behind a CTA |
| Full music video in the hero | The page’s job is the video | The page’s job is a booking or a listen |
Dark cinematic UIs do not automatically score better or worse. Near-black can hide compression artifacts, which sometimes lets you use a smaller still. That is a craft bonus, not a free pass for a 3MB hero film.
How do embeds, chat, and consent banners blow the budget?
YouTube, Maps, calendars, and social embeds are convenience with a cost. Embed best practices and iframe lazy-loading are the primary docs: facade or lazy-load offscreen iframes, and reserve width/height so CLS does not eat the page when the player arrives.
A brand homepage that loads five embeds is a scrapbook. Cut until the page has one job, then bring embeds back behind facades.
| Embed | First-load policy | CLS / INP note |
|---|---|---|
| YouTube | Click-to-load facade with poster | Sized box; no live player in the fold |
| Maps | Static image linking out, or lazy iframe | Maps JS is not a decoration |
| Calendar | Below fold, lazy, or a link | Booking widgets are INP landmines |
| Social feed | Almost never on a homepage | Infinite scroll inside an iframe is not a composition |
| Chat | Idle or click-to-open | Do not hydrate Intercom-class widgets at DOMContentLoaded |
Consent banners are frequent CLS offenders. Reserve space or use an overlay that does not shove the hero. Last-minute legal installs before launch are how a green staging build goes orange on Monday.
Third parties cost rent. If marketing cannot name the decision the tag supports, it does not ship on first load.
Should you prefetch and prerender marketing pages?
Sometimes, for the next step you can name. Not for every thumbnail on the work index.
Top CWV describes Speculation Rules prerender as a way to drive next-page LCP toward zero when you guess right. It also says incorrect speculations waste server and client resources. On a media-heavy brand site, aggressive prerender is how you download a second hero film the user never asked for.
| Intent | Reasonable | Wasteful |
|---|---|---|
| Prefetch Work → Contact | High odds, light target | Prefetch every case study |
| Prerender the booking page after idle | If analytics say that is the next click | Prerender five campaign films |
| Prefetch the next article in a series | Maybe | Prefetch the whole blog index |
Prefer intentional prefetch for the most likely next step. Measure. Marketing sites with heavy media can punish users who were “helped” by speculation. Prefetch is not a substitute for a fast first page.
What optimization order protects the design?
When a brand site scores poorly, work this order. Do not start in Figma deleting the shoot.
- Measure the real LCP element in DevTools and, if you have traffic, in field tools. Optimize that asset and the server path first (optimize LCP).
- Kill duplicate tags and defer non-critical third parties. This is often the entire INP story.
- Fix CLS from fonts, banners, and embeds with reserved space and metric-matched fallbacks.
- Reduce JS on the critical path. Move motion and widgets later. Watch TBT.
- Re-encode media. Redesign only if the hero concept requires impossible weight.
- Then trim motion complexity — compositor-only, one scene, teardown.
CDN and TTFB sit under step 1. A beautiful frontend on a sleepy origin still feels slow. Cache HTML where the architecture allows. Image CDNs help when defaults are sane. Preview deploys should use comparable compression so you do not discover weight only in production.
Give design the constraints up front, in the brief, not in a week-nine “no”:
- Max hero weight
- Max font files
- Motion budget (scenes, properties, CPU time on mid Android)
- Embed policy (one player, below fold, facade)
Constraints produce better design than unlimited Figma followed by an engineer saying no. The best brand sites I ship treat performance as part of the aesthetic: snappy feels expensive. That is the same thesis as Websites That Feel Like Films.
Translate vibes into numbers. Example budget I write into a sprint: hero entrance under a stated CPU window on mid Android; motion JS under an agreed cap; no more than one scroll-scrubbed scene on the homepage; image weight caps per slot. When a new idea arrives mid-build, ask which budget line it spends. If the answer is “none, we will just add it,” that is how 90 becomes 70.
When is 90+ the wrong primary KPI?
When the page’s job cannot be a static composition.
A live-event microsite with an unavoidable stream may never match a static brochure. That can be acceptable for a 72-hour campaign if the business goal is the stream. Write the waiver down. Do not pretend the Lighthouse PDF is the product.
| Site type | Performance bar | Honesty check |
|---|---|---|
| Evergreen studio / brand / artist site | Strong mobile vitals are part of quality | 90+ on mobile lab + watch field p75 |
| Campaign with a required live player | Player is the job; stills everywhere else | Do not hide a 4MB extra film “for mood” |
| App-like booking flow | INP matters more than a hero score | Do not ship three chat widgets into checkout |
| Internal preview | Lab only | Never use this screenshot in a recap deck |
For evergreen brand and studio sites, strong vitals are part of the product quality bar, not a nice-to-have. For a 72-hour stream, say so. The failure is the team that chases 100 on the stream page by breaking the player, or the team that treats an evergreen homepage like a stream page.
Users judge speed before Lighthouse does. A clear fold that appears quickly feels faster than a blank stage that becomes perfect at 2.5s. Skeleton states help when they are honest. Fake progress bars that stall destroy trust. Optimize for meaningful paint of brand + offer, not only for a green circle in a report PDF.
How do you report the tradeoff to stakeholders?
Show the cost with eyes, not with a single desktop score.
| Artifact | Why it changes the conversation |
|---|---|
| Mobile Lighthouse before/after | Same form factor they were ignoring |
| Filmstrip of loading | They can see the blank stage |
| Phone recording, one-minute scroll | Late jank that a 4s lab run missed |
| Field CrUX / Search Console, if you have traffic | Ends the “but lab is green” argument |
| Byte table for the hero vs the still | Makes the video tax visible |
Stakeholders who approve heavy video need to see the stutter. Often they choose the still + craft move once they watch it. That is not you “winning.” That is the brief getting honest.
Same build, two checklists. Ship only when both pass.
Design
- Brand readable at the fold
- Offer / CTA clear without waiting on motion
- Spacing on the system, not on leftover magic numbers
- Hover and focus states exist
- Reduced-motion still exists
Performance
- LCP node identified and optimized (HTML + priority, no lazy)
- Lazy boundaries correct below the fold
- JS partitioned; third parties justified
- CLS boxes reserved (media, fonts, banners, embeds)
- Mid-range phone smoke test, full-page scroll, not only the first screen
Mobile CPU is part of the medium. Thermal throttle is real. A page that runs many blur filters will melt frames after twenty seconds even if the first Lighthouse sample looked fine. Scroll the homepage for a minute on device. Jank that appears late still trains users that the brand feels cheap.
Assign an owner after launch. Performance is not a certificate. When marketing adds a pixel, someone re-runs mobile Lighthouse and a phone smoke test. Put it on the monthly checklist beside content updates. Orgs that treat performance as a launch souvenir watch scores decay and then blame “the algorithm” for fewer leads.
On Spurlock Studios website sprints I do not treat Lighthouse as a vanity screenshot. We check mobile on a real phone path before calling the fold done. Hundreds of production sites have not made me worship 100. They have made me worship the fold that paints, the tap that answers, and the layout that holds.
FAQ
Can I have a fast website with animations?
Yes. Keep critical content visible without JavaScript, animate transform and opacity, budget scroll scenes, and optimize media first. Animation is rarely the only score killer — images, fonts, and third parties usually lead. If a timeline hides the LCP node, rewrite the timeline, not the brand.
Which Core Web Vitals matter most for brand sites?
All three at p75: LCP for first impression (≤ 2.5s), INP for interaction quality (≤ 200ms), CLS for layout stability (≤ 0.1), per web.dev/vitals. Brand sites often fail LCP via hero media and fail INP via tag managers and chat. Passing two and failing one still fails the assessment.
Is 90+ on desktop enough?
No. Mobile is the honest run. Desktop-only celebrations are how janky phone experiences ship. Chrome uses different scoring curves for desktop and mobile, and field Core Web Vitals are segmented by device. If you only screenshot a laptop, you do not have a performance bar.
Should I remove all motion to hit 90?
No. Remove unbudgeted motion and layout-inducing properties. Keep micro-interactions and one earned entrance if they do not harm LCP or INP. Blind deletion can make a site feel broken without fixing the real byte problems. Chrome does not ask you to ship a dead page for a 100.
Do Framer and Webflow prevent high Lighthouse scores?
They do not prevent them, but they make asset discipline mandatory. Oversized images and heavy interactions show up immediately. Custom static stacks give more control, not automatic virtue. The score follows the bytes and the main thread, not the logo on the invoice.
How often should we re-run performance checks?
At fold lock, after the motion pass, after marketing tags are added, and after launch. Re-run when a campaign pixel lands. Tags added “just for a campaign” are a classic regression. Lab plus a phone smoke test; field tools once you have traffic.
CTA
Want this bar on a site that still looks like the brand, not a Lighthouse hostage?
Explore custom websites or book a sprint at /contact?intent=websites-sprint.
What questions does this article answer?
- Can I have a fast website with animations?
- Yes. Keep critical content visible without JavaScript, animate `transform` and `opacity`, budget scroll scenes, and optimize media first. Animation is rarely the only score killer — images, fonts, and third parties usually lead. If a timeline hides the LCP node, rewrite the timeline, not the brand.
- Which Core Web Vitals matter most for brand sites?
- All three at p75: LCP for first impression (≤ 2.5s), INP for interaction quality (≤ 200ms), CLS for layout stability (≤ 0.1), per [web.dev/vitals](https://web.dev/articles/vitals). Brand sites often fail LCP via hero media and fail INP via tag managers and chat. Passing two and failing one still fails the assessment.
- Is 90+ on desktop enough?
- No. Mobile is the honest run. Desktop-only celebrations are how janky phone experiences ship. Chrome uses different scoring curves for desktop and mobile, and field Core Web Vitals are segmented by device. If you only screenshot a laptop, you do not have a performance bar.
- Should I remove all motion to hit 90?
- No. Remove unbudgeted motion and layout-inducing properties. Keep micro-interactions and one earned entrance if they do not harm LCP or INP. Blind deletion can make a site feel broken without fixing the real byte problems. Chrome does not ask you to ship a dead page for a 100.
- Do Framer and Webflow prevent high Lighthouse scores?
- They do not prevent them, but they make asset discipline mandatory. Oversized images and heavy interactions show up immediately. Custom static stacks give more control, not automatic virtue. The score follows the bytes and the main thread, not the logo on the invoice.
- How often should we re-run performance checks?
- At fold lock, after the motion pass, after marketing tags are added, and after launch. Re-run when a campaign pixel lands. Tags added "just for a campaign" are a classic regression. Lab plus a phone smoke test; field tools once you have traffic.
Last reviewed
Websites
Websites Linktree is a leak — build the house
Spotify does not send you the fan’s email. Instagram rents the following. Linktree is a hallway with no register. The House is the owned room: site, membership, checkout, follow-up.
Websites The shop site that answers the phone
A Midwest shop does not lose the job to a prettier hero. It loses the job to whoever looks real and picks up. Here is what the site has to do on a Saturday.
Websites A media kit the brand can steal in sixty seconds
Influencers need a brand-safe /media or /kit with rates and demographics you can stand behind — not a Google Doc with dead links. This is not a booker EPK.
Websites Creator Site or Business Site for the house?
Creator Site ($3,500) is tour, listen, join, buy. Business Site ($8,000) is the register. Pick after the $1,500 sprint — not before you have seen the house.
Will's Journal in your inbox.
What I learned this week building for shops, floors, and houses.
You're on the list.
Sign-up failed — try again.
By subscribing, you agree to the Privacy Policy.