Next.js Images and Fonts
In modern web development, optimizing images and fonts is crucial for improving website performance and user experience. Next.js provides a series of built-in features that help you easily handle these static assets and achieve automatic optimization.
1. Static File Serving
Next.js serves static files through the public directory, such as images, icons, robots.txt, etc. Any file in the public directory can be accessed through the application's root URL (/).
Example:
- Place an image named
logo.pngin thepublicdirectory. - You can reference this image in code via
/logo.png.
function MyLogo() {
return <img src="/logo.png" alt="My Company Logo" />;
}Note: Don't use the
publicdirectory for compiled assets or dynamically generated files. It should only be used for static assets that don't need build processing.
2. Image Optimization (next/image)
Directly using the HTML <img> tag can lead to performance issues, such as:
- Loading large images: Even on small screen devices, the original size image is loaded, wasting bandwidth.
- No lazy loading: Images outside the viewport are loaded immediately, affecting initial page load speed.
- Layout Shift: Image loading may cause sudden changes in page layout.
To solve these problems, Next.js provides the <Image> component, which is an extension of the <img> tag with automatic image optimization features.
How to Use next/image
Import the component:
jsximport Image from 'next/image';Use the component:
jsximport profilePic from '../public/me.png'; // Import local image function MyProfile() { return ( <Image src={profilePic} // Can be a statically imported image or a URL string alt="Picture of the author" width={500} // Must provide dimensions to avoid layout shift height={500} // placeholder="blur" // Optional: provide blur placeholder // blurDataURL="..." // Optional: custom blur placeholder /> ); }
Core Advantages of next/image
- Automatic Size Adjustment: Provides correctly sized images based on device screen size.
- Automatic Lazy Loading: By default, images outside the viewport are lazy loaded.
- Prevents Layout Shift: By requiring
widthandheightattributes, space is reserved for images to prevent page jumping. - Automatic Format Conversion: Can automatically convert images to modern formats (like WebP) to reduce file size.
Remote Images
If you need to load images from external CDNs or other domains, you need to configure allowed domains in the next.config.js file for security.
// next.config.js
module.exports = {
images: {
remotePatterns: [
{
protocol: 'https',
hostname: 's3.amazonaws.com',
port: '',
pathname: '/my-bucket/**',
},
],
},
}3. Font Optimization (next/font)
Web font loading can also affect performance, potentially causing FOIT (Flash of Invisible Text) or FOUT (Flash of Unstyled Text). Next.js 13 introduced the next/font module for optimizing font loading.
next/font downloads font files at build time and hosts them with other static assets. This means:
- No External Network Requests: The browser doesn't need to make additional network requests to services like Google Fonts.
- Privacy Friendly: User information isn't shared with third-party services.
- Automatic
font-display: Automatically setsfont-display: optionalfor optimal performance.
How to Use next/font
Using Google Fonts
Import fonts from
next/font/google:javascriptimport { Inter, Lusitana } from 'next/font/google';Load fonts:
javascriptconst inter = Inter({ subsets: ['latin'] }); const lusitana = Lusitana({ subsets: ['latin'], weight: ['400', '700'] });Apply fonts in components:
You can apply fonts globally or to specific elements.
Global application (in
_app.js):jsx// pages/_app.js import { Inter } from 'next/font/google'; const inter = Inter({ subsets: ['latin'] }); export default function MyApp({ Component, pageProps }) { return ( <main className={inter.className}> <Component {...pageProps} /> </main> ); }Local application:
jsxconst lusitana = Lusitana({ subsets: ['latin'], weight: ['400', '700'] }); function Heading() { return <h1 className={lusitana.className}>My Heading</h1>; }
Using Local Fonts
Import from
next/font/local:javascriptimport localFont from 'next/font/local';Load local font file:
javascriptconst myFont = localFont({ src: '../styles/my-font.woff2' });Apply in components:
jsxfunction MyComponent() { return <p className={myFont.className}>This text uses a local font.</p>; }
Summary
Next.js provides powerful built-in optimization features through next/image and next/font that can significantly improve website performance and user experience. By using these tools, you can ensure images and fonts load in the most efficient way while avoiding common performance pitfalls. In the next chapter, we'll explore how to organize and build reusable components and layouts.