# Image & Asset Strategy
> Serve the smallest correct image; preload the LCP one.
Frontend architecture guidance from fearchitect, written by Abas Turabli and last reviewed 2026-06-21. Source: https://fearchitect.com/topics/image-and-asset-strategy
Use it as reference for the task at hand. Before changing code, check this guidance against the codebase: where the code already makes a different, deliberate choice, flag the conflict instead of rewriting it. Library APIs move faster than this guide, so confirm exact signatures in the official docs linked at the end.
## Summary
Images and fonts are the biggest drag on LCP and CLS. Modern formats (AVIF, WebP) cut payload 30–50% over JPEG. Responsive `srcset`/`sizes` delivers the right resolution per viewport. The LCP image needs `fetchPriority="high"` and a preload link; everything below the fold gets `loading="lazy"`. Width and height attributes prevent CLS.
## What controls image performance
- AVIF compresses 40–50% smaller than JPEG at equal quality; WebP saves ~30% and decodes faster.
- `next/image` defaults to WebP only — opt into AVIF with `formats: ['image/avif', 'image/webp']` in `next.config`.
- `fetchPriority="high"` raises the LCP image's fetch priority; pair with `preload` to discover it before `
` parses.
- The `priority` prop is deprecated in Next.js 16 — use `preload` and `fetchPriority` as separate props.
- Without `sizes`, the browser assumes 100vw and downloads a full-screen image on every device.
- Explicit `width`/`height` attributes (or `aspect-ratio`) let the browser reserve space before the image loads, preventing CLS.
- `font-display: swap` renders text in a fallback face immediately; pair with `` to cut DNS + TLS time.
## LCP hero with preload + fetchPriority (Next.js 16)
Use `preload` to emit `` and `fetchPriority="high"` to raise request priority. The deprecated `priority` prop did both; in Next.js 16 they are separate.
**Hero image with preload + fetchPriority (next/image, Next.js 16)**
```tsx
import Image from "next/image";
// LCP image: preload emits ; fetchPriority raises fetch priority.
// priority is deprecated in Next.js 16 — use preload + fetchPriority instead.
export function Hero() {
return (
in
fetchPriority="high" // raises request from low to high priority
sizes="(max-width: 768px) 100vw, 1200px"
quality={75} // default qualities allowlist is [75]; other values snap to nearest
className="w-full h-auto"
/>
);
}
```
`preload` emits ``; `fetchPriority="high"` raises priority. `sizes` stops a 1200 px download on a 375 px phone.
## Diagram
```mermaid
sequenceDiagram
participant Browser
participant Server
Browser->>Server: GET /page HTML
Server-->>Browser: HTML (LCP img has fetchpriority=high)
Note over Browser: Preload scanner finds LCP img immediately
Browser->>Server: Fetch LCP image (HIGH priority)
Browser->>Server: Fetch below-fold images (lazy — deferred)
Server-->>Browser: LCP image bytes
Note over Browser: LCP image paints → LCP recorded
Browser->>Server: Fetch lazy images as user scrolls
```
fetchPriority=high raises the LCP image from low to high priority in the preload scanner; lazy images are deferred until near-viewport.
## Format and priority trade-offs
**Pros**
- AVIF/WebP reduce image payload 30–50%, directly improving LCP on slow connections.
- `fetchPriority="high"` on the LCP image can cut LCP by 200–500 ms without code changes.
- Native lazy-loading is zero-JS: the browser handles deferral and intersection natively.
- `next/image` automates format negotiation and srcset generation.
- Width/height attributes eliminate image-driven CLS at the HTML level.
**Cons**
- AVIF encoding is slow; build-time generation at multiple sizes raises deploy times.
- Misconfigured `sizes` causes the browser to fetch a larger image than needed.
- Preloading too many images wastes bandwidth and delays more important resources.
- `font-display: swap` causes a flash of unstyled text (FOUT) until the web font loads.
## Watch out: Never lazy-load the LCP image
`loading="lazy"` defers the fetch until the image is near-viewport — the LCP image is already in the viewport, so this delays it past the measurement window. Add `fetchPriority="high"` instead. Also avoid adding high priority to more than one or two images; it loses meaning if overused.
## Key terms
- **LCP (Largest Contentful Paint)**: The time until the largest above-fold image or text block renders.
- **fetchpriority / fetchPriority**: HTML attribute (JSX prop) that raises ("high") or lowers ("low") a resource fetch priority.
- **srcset / sizes**: HTML attributes that list candidate image URLs and layout widths so the browser picks the best fit.
- **CLS (Cumulative Layout Shift)**: Score for unexpected layout movement; images without dimensions are a top cause.
- **font-display: swap**: CSS descriptor that renders text in a fallback font immediately, swapping the web font when loaded.
## Related topics
- [Core Web Vitals](https://fearchitect.com/topics/core-web-vitals.md): Google's three user-experience metrics: LCP, INP, and CLS.
- [Network Performance](https://fearchitect.com/topics/network-performance.md): Hint, prioritize, and pre-navigate to cut request latency.
- [SEO for Frontend](https://fearchitect.com/topics/seo.md): Rendering choices, metadata, structured data, and CWV for search ranking.
- [Bundle Architecture & Code Splitting](https://fearchitect.com/topics/bundle-architecture-code-splitting.md): Ship only the JS a route needs, cache the rest long-term.
- [Caching Strategies](https://fearchitect.com/topics/caching-strategies.md): Layer browser, CDN, and app caches to serve responses without re-fetching.
- [Render Performance](https://fearchitect.com/topics/render-performance-patterns.md): Skip renders, defer slow work, and virtualize long lists.
## Further reading
- [Next.js — Image Optimization](https://nextjs.org/docs/app/api-reference/components/image)
- [web.dev — Largest Contentful Paint](https://web.dev/articles/lcp)
- [web.dev — Optimize Cumulative Layout Shift](https://web.dev/articles/optimize-cls)
- [web.dev — Best practices for fonts](https://web.dev/articles/font-best-practices)