Image 组件和图片优化

示例

10.0.0 版本开始,Next.js 内置了图片组件和自动图片优化功能。

Next.js 的 Image 组件(即 next/image)是对 HTML 的 <img> 元素的扩展,跟进了最新的 web 技术。

自动图片优化功能(Automatic Image Optimization)能够调整图片尺寸、优化图片并以最新的 WebP 格式传输图片(如果浏览器支持 WebP 格式的话)。这样就可以避免将较大的图片传送到视口(viewport)较小的设备上。此功能还允许 Next.js 自动采用未来的图片格式,并将其传输给支持这些格式的浏览器。

自动图片优化功能可以支持任何图片来源。即使是托管在外部数据源上(例如,CMS),仍可对图片进行优化。

Next.js 无需在构建时优化图片,而是根据用户的请求按需优化图片。与静态站点生成器和纯静态解决方案不同,无论发布 10 张还是 1000 万张图片,构建时间都不会增加。

图片默认是延迟加载的。这意味着你的页面不会因为加载视口(viewport)外的图片而影响页面的加载速度。当图片进入视口(viewport)时才加载。

始终以这种方式渲染图片是为了避免 累计布局偏移(Cumulative Layout Shift),此 Core Web Vital 被 Google 作为参数用于 搜索排名

图片组件

要在应用中添加图片的话,首先导入(import)next/image 组件:

import Image from 'next/image'

function Home() {
  return (
    <>
      <h1>My Homepage</h1>
      <Image
        src="/me.png"
        alt="Picture of the author"
        width={500}
        height={500}
      />
      <p>Welcome to my homepage!</p>
    </>
  )
}

export default Home

查看 next/image 组件的所有属性

配置

除了使用 next/image 组件的 属性 外,你还可以通过 next.config.js 来针对图片优化功能配置更高级的用法。

域名

要为外部网站上托管的图片启用图片优化功能,请先将图片的 src 地址设置完整的网址(即,带域名的地址),然后指定哪些 域名 需要开启优化功能。这是为了确保不会误伤其它外部网址。当 loader 被设置为外部图片服务时,此选项将被忽略。

module.exports = {
  images: {
    domains: ['example.com'],
  },
}

Loader

如果希望使用第三方云服务来优化图片,而不是 Next.js 的内置图片优化功能时,则需要配置 loader 和路径前缀参数。这让你可以为图片设置相对路径的 src,并自动为你所选择的云服务生成正确的完整网址。

module.exports = {
  images: {
    loader: 'imgix',
    path: 'https://example.com/myaccount/',
  },
}

目前支持以下云服务提供商:

  • Vercel: Works automatically when you deploy on Vercel, no configuration necessary. Learn more
  • Imgix: loader: 'imgix'
  • Cloudinary: loader: 'cloudinary'
  • Akamai: loader: 'akamai'
  • Default: Works automatically with next dev, next start, or a custom server

如果你需要支持其它云服务提供商,你可以为 next/image 设置 loader 属性。

缓存

下面介绍默认 loader 的缓存算法。对于所有其它的 loader,请参考响应的云服务提供商的文档。

图片根据用户的请求进行动态优化,并存储到 <distDir>/cache/images 目录下。优化过的图片文件将用于后续的请求,直到过期为止。当用户请求一个已经过期的图片文件时,将首先删除先前缓存的文件,然后生成新的经过优化的文件。

过期时间(或者最长寿命)由上游服务器的 Cache-Control 标头确定。

如果在 Cache-Control 中找到 s-maxage,则使用 s-maxage。如果没有找到 s-maxage,则使用 max-age。如果没有找到 max-age,则设置为 60 秒。

你可以设置 deviceSizesimageSizes 来减少可能生成的图片总数。

高级设置

以下是高级设置示例,通常不需要。如果你选择设置以下属性,则将来 Next.js 更新时会覆盖 Next.js 的默认值。

设备尺寸

在某些情况下,如果你预先知到网站用户的设备宽度,则可以通过 deviceSizes 属性指定设备宽度的列表。当 next/image 组件设置了 layout="responsive"layout="fill" 时将使用这个宽度列表,在某个设备访问你的网站时,将向该设备传输列表中列出的图片尺寸。

如果不自定义配置,则使用如下的默认值。

module.exports = {
  images: {
    deviceSizes: [640, 750, 828, 1080, 1200, 1920, 2048, 3840],
  },
}

图片尺寸

你可以通过 imageSizes 属性来指定图片宽度列表。这些宽度应该不同于(通常是小于) deviceSizes 属性中设置的宽度值,因为这两个属性值所对应的数组将被合并。当 next/image 组件设置了 layout="fixed"layout="intrinsic" 时,将使用这些宽度值。

如果不自定义配置,则使用如下的默认值。

module.exports = {
  images: {
    imageSizes: [16, 32, 48, 64, 96, 128, 256, 384],
  },
}

相关内总

以下是我们建议接下来需要学习的内容: