Your Next.js site takes 3 seconds to load images, and fonts shift while you read. Visitors leave, and Google knows it. Every second of delay cuts conversions by 7% — a number we know well because we see it in the budgets of clients we manage. The good news? Next.js already has the tools to fix it all: next/image and next/font. Not using them to their full potential? You're paying to lose customers. Let's change that.
How to optimize images in Next.js to improve Core Web Vitals?
Images account for 50% of the average page weight. Without optimization, LCP (Largest Contentful Paint) and CLS (Cumulative Layout Shift) suffer. We at Meteora Web saw an e-commerce client halve load time just by using next/image instead of classic <img> tags. Here's how it works.
Using next/image for lazy loading and modern formats
The next/image component does three things a regular HTML tag doesn't: automatically optimizes images (WebP/AVIF), lazy loads below-the-fold images, and reserves space to prevent CLS. Without it, every image is a hit to your Core Web Vitals.
import Image from 'next/image';
export default function ProductCard({ product }) {
return (
<div>
<Image
src={product.image}
alt={product.name}
width={600}
height={400}
sizes="(max-width: 768px) 100vw, 50vw"
priority={product.isFirst}
/>
</div>
);
}
Set sizes to tell the browser how much space the image takes up depending on the viewport — it's the secret to not downloading huge images on mobile. Use priority only for the LCP image, not for all.
Sponsored Protocol
Configuring remote domains for external images
If images come from a CDN or external backend, Next.js blocks unknown domains. Configure them in next.config.js to avoid errors in production.
// next.config.js
module.exports = {
images: {
remotePatterns: [
{ protocol: 'https', hostname: 'cdn.example.com' },
],
},
};
This step is mandatory if you don't want images to break in production. We see it often in projects that come to us: everything works locally, then the deploy fails.
How to optimize fonts in Next.js to reduce CLS and speed up rendering?
Fonts are another silent enemy. Every custom font is an extra HTTP request and a potential layout shift when it loads. The solution? next/font, which loads fonts optimally and serves them from the same domain — no external requests to Google Fonts.
Sponsored Protocol
Using next/font for optimized font loading
With next/font, you can use system fonts or Google Fonts without external requests. The font is downloaded at build time and served with font-display: swap to avoid FOIT (Flash of Invisible Text).
import { Inter } from 'next/font/google';
const inter = Inter({ subsets: ['latin'], display: 'swap' });
export default function Layout({ children }) {
return <html lang="en" className={inter.className}>{children}</html>;
}
This eliminates CLS caused by fonts and improves LCP. If you use system fonts, you can define a font-family with fallbacks to depend on nothing.
Setting font fallbacks to avoid layout shift
Even with next/font, if the font hasn't loaded yet, the browser uses a fallback. Measure the size difference between font and fallback to minimize CLS. Next.js lets you adjust size-adjust with the adjustFontFallback property.
Sponsored Protocol
const inter = Inter({ subsets: ['latin'], adjustFontFallback: true });
This option aligns font metrics with the fallback, reducing CLS to zero. It's a detail that makes a difference in PageSpeed Insights scores.
How to measure and monitor Core Web Vitals in Next.js?
Optimizing without measuring is like driving in the dark. Next.js has a built-in component to track Core Web Vitals in real time. We use it to know where to intervene before the client notices.
Using the useReportWebVitals component for monitoring
You can create a component that sends data to Google Analytics or a custom endpoint. This gives you real data from your users, not just lab tests.
'use client';
import { useReportWebVitals } from 'next/web-vitals';
export function WebVitals() {
useReportWebVitals((metric) => {
console.log(metric); // Send to GA or other service
});
return null;
}
Integrate this component into your layout and start collecting data. Without these numbers, every optimization is an opinion, not a fact.
What are common mistakes to avoid in image and font optimization?
Even with the right tools, we all make mistakes. Here are the errors we see most often in projects that come to us, and how to avoid them.
Sponsored Protocol
Not optimizing hero images
The hero image is the first thing seen — it's the LCP. If you don't load it with priority and correct sizes, you lose 90% of the benefit. We treat it as a critical element, not a detail.
Using too many fonts and weights
Every extra font is a hit to performance. Limit weights to 2-3 and use variable fonts if possible. With next/font, if you import a font with multiple weights, Next.js generates only the necessary files.
const inter = Inter({ subsets: ['latin'], weight: ['400', '700'] });
This keeps the bundle light and rendering fast.
How to integrate image and font optimization with your stack?
Optimization isn't an island: it integrates with the rest of your stack. If you use a CDN for images, you can combine it with next/image for the best of both worlds. If you have a custom backend, you can generate optimized images at runtime.
Combining next/image with CDN and external storage
The next/image component supports custom loaders. You can point to a CDN like Cloudinary or Imgix and let it do the heavy lifting.
Sponsored Protocol
import Image from 'next/image';
const customLoader = ({ src, width, quality }) => {
return `https://cdn.example.com/${src}?w=${width}&q=${quality || 75}`;
};
export default function OptimizedImage(props) {
return <Image loader={customLoader} {...props} />;
}
This gives you total flexibility without sacrificing performance.
In summary
Optimizing images and fonts in Next.js isn't a luxury: it's the foundation for a site that converts. Here are the immediate actions to take:
- Replace all
<img>tags withnext/imageand setsizesandprioritycorrectly. - Configure
next/fontfor all custom fonts and useadjustFontFallbackto eliminate CLS. - Measure Core Web Vitals with
useReportWebVitalsand connect data to Google Analytics. - Check your homepage with PageSpeed Insights and compare scores before and after.
If you need a hand, we at Meteora Web work on these details every day. Your site deserves to be fast — and your customers deserve not to wait.