Menu

<Image>

補足: Next.js 13より前のバージョンを使用している場合は、コンポーネントの名前が変更されたため、next/legacy/imageのドキュメントを参照してください。

このAPIリファレンスは、Imageコンポーネントで利用可能なprops設定オプションの使い方を理解するのに役立ちます。機能と使用方法については、Imageコンポーネントのページを参照してください。

app/page.js
import Image from 'next/image'
 
export default function Page() {
  return (
    <Image
      src="/profile.png"
      width={500}
      height={500}
      alt="著者の写真"
    />
  )
}

Props

以下はImageコンポーネントで利用可能なpropsの概要です:

Propステータス
srcsrc="/profile.png"String必須
widthwidth={500}Integer (px)必須
heightheight={500}Integer (px)必須
altalt="著者の写真"String必須
loaderloader={imageLoader}Function-
fillfill={true}Boolean-
sizessizes="(max-width: 768px) 100vw, 33vw"String-
qualityquality={80}Integer (1-100)-
prioritypriority={true}Boolean-
placeholderplaceholder="blur"String-
stylestyle={{objectFit: "contain"}}Object-
onLoadingCompleteonLoadingComplete={img => done())}Function非推奨
onLoadonLoad={event => done())}Function-
onErroronError(event => fail()}Function-
loadingloading="lazy"String-
blurDataURLblurDataURL="data:image/jpeg..."String-
overrideSrcoverrideSrc="/seo.png"String-

必須のProps

Imageコンポーネントには以下のプロパティが必須です: srcaltwidthheight(またはfill)。

app/page.js
import Image from 'next/image'
 
export default function Page() {
  return (
    <div>
      <Image
        src="/profile.png"
        width={500}
        height={500}
        alt="著者の写真"
      />
    </div>
  )
}

src

以下のいずれかである必要があります:

  • 静的にインポートされた画像ファイル
  • パス文字列。loader propに応じて、絶対的な外部URLまたは内部パスのいずれかを指定できます。

デフォルトのloaderを使用する場合は、ソース画像について以下の点も考慮してください:

  • srcが外部URLの場合は、remotePatternsも設定する必要があります
  • srcがアニメーションの場合、または既知のフォーマット(JPEG、PNG、WebP、AVIF、GIF、TIFF)でない場合、画像は最適化されずにそのまま提供されます
  • srcがSVGフォーマットの場合、unoptimizedまたはdangerouslyAllowSVGが有効化されていない限りブロックされます

width

widthプロパティは、画像の本来の幅をピクセル単位で表します。このプロパティは、画像の正しいアスペクト比を推測し、読み込み中のレイアウトのシフトを防ぐために使用されます。HTMLの<img>タグのwidth属性と同様に、レンダリングされる画像のサイズはCSSによって制御され、このプロパティでは決定されません。

静的にインポートされた画像またはfillプロパティを持つ画像を除き、必須です。

height

heightプロパティは、画像の本来の高さをピクセル単位で表します。このプロパティは、画像の正しいアスペクト比を推測し、読み込み中のレイアウトのシフトを防ぐために使用されます。HTMLの<img>タグのheight属性と同様に、レンダリングされる画像のサイズはCSSによって制御され、このプロパティでは決定されません。

静的にインポートされた画像またはfillプロパティを持つ画像を除き、必須です。

補足:

  • widthheightの両プロパティを組み合わせることで、ブラウザが画像を読み込む前にスペースを確保するために使用する画像のアスペクト比が決定されます。
  • 本来のサイズは、必ずしもブラウザでレンダリングされるサイズを意味するわけではありません。レンダリングサイズは親コンテナによって決定されます。例えば、親コンテナが本来のサイズよりも小さい場合、画像はコンテナに合わせて縮小されます。
  • 幅と高さが不明な場合は、fillプロパティを使用できます。

alt

altプロパティは、スクリーンリーダーと検索エンジンのために画像を説明するために使用されます。また、画像が無効化されている場合や画像の読み込み中にエラーが発生した場合のフォールバックテキストとしても使用されます。

ページの意味を変えることなく画像を置き換えることができるテキストを含める必要があります。画像を補完することは意図されておらず、画像の上下のキャプションですでに提供されている情報を繰り返すべきではありません。

画像が純粋に装飾的であるか、ユーザー向けではない場合、altプロパティは空の文字列(alt="")にする必要があります。

詳細を学ぶ

オプションのProps

<Image />コンポーネントは、必須のプロパティ以外にも多くの追加プロパティを受け入れます。このセクションでは、Imageコンポーネントの最も一般的に使用されるプロパティについて説明します。より一般的でないプロパティについては、高度なPropsセクションで詳細を確認してください。

loader

画像URLを解決するためのカスタム関数です。

loaderは以下のパラメータを受け取り、画像のURL文字列を返す関数です:

以下はカスタムローダーを使用する例です:

import Image from 'next/image'
 
const imageLoader = ({ src, width, quality }) => {
  return `https://example.com/${src}?w=${width}&q=${quality || 75}`
}
 
export default function Page() {
  return (
    <Image
      loader={imageLoader}
      src="me.png"
      alt="著者の写真"
      width={500}
      height={500}
    />
  )
}

あるいは、next.config.jsloaderFile設定を使用して、propを渡すことなくアプリケーション内のすべてのnext/imageインスタンスを設定することもできます。

fill

fill={true} // {true} | {false}

画像を親要素に合わせて表示するブール値で、widthheightが不明な場合に便利です。

親要素にはposition: "relative"position: "fixed"、またはposition: "absolute"スタイルを割り当てる必要があります。

デフォルトでは、img要素に自動的にposition: "absolute"スタイルが割り当てられます。

画像にスタイルが適用されていない場合、画像はコンテナに合わせて拡大されます。コンテナに合わせてレターボックス化され、アスペクト比を維持する場合は、object-fit: "contain"を設定することをお勧めします。

あるいは、object-fit: "cover"を使用すると、画像はコンテナ全体を埋め、アスペクト比を維持するためにトリミングされます。

詳細については、以下も参照してください:

sizes

メディアクエリに似た文字列で、異なるブレークポイントでの画像の幅に関する情報を提供します。fillを使用する画像やレスポンシブサイズにスタイリングされた画像のパフォーマンスに大きく影響します。

sizesプロパティは、画像のパフォーマンスに関連する2つの重要な目的を果たします:

  • 第一に、sizesの値は、ブラウザがnext/imageが自動生成するsrcsetからどのサイズの画像をダウンロードするかを決定するために使用されます。ブラウザが選択する際、まだページ上の画像のサイズを知らないため、ビューポートと同じサイズまたはそれより大きい画像を選択します。sizesプロパティを使用すると、画像が実際には全画面よりも小さくなることをブラウザに伝えることができます。fillプロパティを持つ画像でsizes値を指定しない場合、デフォルト値として100vw(全画面幅)が使用されます。
  • 第二に、sizesプロパティは自動生成されるsrcset値の動作を変更します。sizes値が存在しない場合、固定サイズの画像(1x/2x/など)に適した小さなsrcsetが生成されます。sizesが定義されている場合、レスポンシブ画像(640w/750w/など)に適した大きなsrcsetが生成されます。sizesプロパティにビューポート幅のパーセンテージを表す50vwなどのサイズが含まれている場合、必要とされることのない小さすぎる値を含まないようにsrcsetがトリミングされます。

例えば、スタイリングによって画像がモバイルデバイスで全幅、タブレットで2列レイアウト、デスクトップディスプレイで3列レイアウトになることがわかっている場合、以下のようなsizesプロパティを含める必要があります:

components/author.js
import Image from 'next/image'
 
export default function Author() {
  return (
    <div className="grid-element">
      <Image
        fill
        src="/example.png"
        alt="著者の写真"
        sizes="(max-width: 768px) 100vw, (max-width: 1200px) 50vw, 33vw"
      />
    </div>
  )
}

このsizesの例は、パフォーマンス指標に劇的な影響を与える可能性があります。33vwのsizesがない場合、サーバーから選択される画像は必要な幅の3倍になってしまいます。ファイルサイズは幅の2乗に比例するため、sizesがない場合、ユーザーは必要以上に9倍大きい画像をダウンロードすることになります。

srcsetsizesについて詳しく学ぶ:

quality

quality={75} // {1-100の数値}

最適化された画像の品質を、1から100の整数で指定します。100が最高品質で、したがって最大のファイルサイズとなります。デフォルトは75です。

priority

priority={false} // {false} | {true}

trueの場合、画像は高優先度とみなされ、プリロードされます。priorityを使用する画像については、遅延読み込みは自動的に無効化されます。loadingプロパティも使用されており、lazyに設定されている場合、priorityプロパティは使用できません。loadingプロパティは高度なユースケース用です。priorityが必要な場合はloadingを削除してください。

Largest Contentful Paint (LCP)要素として検出された画像には、priorityプロパティを使用する必要があります。異なるビューポートサイズで異なる画像がLCP要素となる可能性があるため、複数の優先画像を持つことが適切な場合があります。

フォールド上に表示される画像にのみ使用してください。デフォルトはfalseです。

placeholder

placeholder = 'empty' // "empty" | "blur" | "data:image/..."

画像の読み込み中に使用するプレースホルダーです。blurempty、またはdata:image/...のいずれかを指定できます。デフォルトはemptyです。

blurの場合、blurDataURLプロパティがプレースホルダーとして使用されます。src静的インポートからのオブジェクトで、インポートされた画像が.jpg.png.webp、または.avifの場合、画像がアニメーション化されているとして検出された場合を除き、blurDataURLは自動的に設定されます。

動的な画像の場合は、blurDataURLプロパティを提供する必要があります。Plaiceholderのようなソリューションはbase64の生成に役立ちます。

data:image/...の場合、画像の読み込み中にData URLがプレースホルダーとして使用されます。

emptyの場合、画像の読み込み中にプレースホルダーはなく、空のスペースのみが表示されます。

試してみる:

高度なProps

場合によっては、より高度な使用方法が必要になることがあります。<Image />コンポーネントは、以下の高度なプロパティをオプションで受け入れます。

style

基礎となる画像要素にCSSスタイルを渡すことができます。

components/ProfileImage.js
const imageStyle = {
  borderRadius: '50%',
  border: '1px solid #fff',
}
 
export default function ProfileImage() {
  return <Image src="..." style={imageStyle} />
}

必須の幅と高さのpropsは、スタイリングと相互作用する可能性があることに注意してください。スタイリングを使用して画像の幅を変更する場合は、本来のアスペクト比を維持するために高さもautoにスタイリングする必要があります。そうしないと、画像が歪んでしまいます。

onLoadingComplete

<Image onLoadingComplete={(img) => console.log(img.naturalWidth)} />

警告: Next.js 14以降ではonLoadに置き換えられ、非推奨となりました。

画像が完全に読み込まれ、placeholderが削除された時に呼び出されるコールバック関数です。

コールバック関数は、基礎となる<img>要素への参照を1つの引数として受け取ります。

onLoad

<Image onLoad={(e) => console.log(e.target.naturalWidth)} />

画像が完全に読み込まれ、placeholderが削除された時に呼び出されるコールバック関数です。

コールバック関数は、基礎となる<img>要素への参照を含むtargetを持つEventを1つの引数として受け取ります。

onError

<Image onError={(e) => console.error(e.target.id)} />

画像の読み込みに失敗した場合に呼び出されるコールバック関数です。

loading

loading = 'lazy' // {lazy} | {eager}

画像の読み込み動作です。デフォルトはlazyです。

lazyの場合、ビューポートからの計算された距離に達するまで画像の読み込みを遅延させます。

eagerの場合、画像を直ちに読み込みます。

loading属性について詳しく学ぶ。

blurDataURL

Data URLで、src画像が正常に読み込まれるまでのプレースホルダー画像として使用されます。placeholder="blur"と組み合わせた場合にのみ有効です。

base64エンコードされた画像である必要があります。拡大されぼかされるため、非常に小さな画像(10px以下)を推奨します。より大きな画像をプレースホルダーとして含めると、アプリケーションのパフォーマンスに悪影響を与える可能性があります。

試してみる:

また、単色のData URLを生成することで、画像に合わせることもできます。

unoptimized

unoptimized = {false} // {false} | {true}

trueの場合、ソース画像は品質、サイズ、フォーマットを変更せずにそのまま提供されます。デフォルトはfalseです。

import Image from 'next/image'
 
const UnoptimizedImage = (props) => {
  return <Image {...props} unoptimized />
}

Next.js 12.3.0以降、このpropはnext.config.jsに以下の設定を追加することで、すべての画像に割り当てることができます:

next.config.js
module.exports = {
  images: {
    unoptimized: true,
  },
}

overrideSrc

<Image>コンポーネントにsrc propを提供する場合、結果として生成される<img>srcsetsrc属性は自動的に生成されます。

input.js
<Image src="/me.jpg" />
output.html
<img
  srcset="
    /_next/image?url=%2Fme.jpg&w=640&q=75 1x,
    /_next/image?url=%2Fme.jpg&w=828&q=75 2x
  "
  src="/_next/image?url=%2Fme.jpg&w=828&q=75"
/>

場合によっては、src属性を自動生成させたくない場合があり、overrideSrc propを使用して上書きすることができます。

例えば、既存のウェブサイトを<img>から<Image>にアップグレードする際に、画像ランキングや再クロールを避けるためなど、SEO目的で同じsrc属性を維持したい場合があります。

input.js
<Image src="/me.jpg" overrideSrc="/override.jpg" />
output.html
<img
  srcset="
    /_next/image?url=%2Fme.jpg&w=640&q=75 1x,
    /_next/image?url=%2Fme.jpg&w=828&q=75 2x
  "
  src="/override.jpg"
/>

decoding

画像のデコードを待ってから他のコンテンツの更新を表示するかどうかをブラウザに示すヒントです。デフォルトはasyncです。

指定可能な値は以下の通りです:

  • async - 他のコンテンツが画像のデコードが完了する前にレンダリングされることを許可し、非同期的に画像をデコードします。
  • sync - 他のコンテンツと同時に表示するため、同期的に画像をデコードします。
  • auto - デコードモードの設定をブラウザに任せ、特に選好しません。

decoding属性について詳しく学ぶ。

その他のProps

以下を除き、<Image />コンポーネントの他のプロパティは基礎となるimg要素に渡されます:

  • srcSet。代わりにDevice Sizesを使用してください。

設定オプション

propsに加えて、next.config.jsでImageコンポーネントを設定することができます。以下のオプションが利用可能です:

localPatterns

next.config.jsファイルでlocalPatternsを設定して、特定のパスの最適化を許可し、他のすべてのパスをブロックすることができます。

next.config.js
module.exports = {
  images: {
    localPatterns: [
      {
        pathname: '/assets/images/**',
        search: '',
      },
    ],
  },
}

補足: 上記の例では、next/imagesrcプロパティが/assets/images/で始まり、クエリ文字列を持たない必要があることを保証します。それ以外のパスを最適化しようとすると、400 Bad Requestで応答します。

remotePatterns

アプリケーションを悪意のあるユーザーから保護するために、外部画像を使用する場合は設定が必要です。これにより、Next.js Image Optimization APIから提供できる外部画像がアカウントからのものに限定されます。これらの外部画像は、以下のようにnext.config.jsファイルのremotePatternsプロパティで設定できます:

next.config.js
module.exports = {
  images: {
    remotePatterns: [
      {
        protocol: 'https',
        hostname: 'example.com',
        port: '',
        pathname: '/account123/**',
        search: '',
      },
    ],
  },
}

補足: 上記の例では、next/imagesrcプロパティがhttps://example.com/account123/で始まり、クエリ文字列を持たない必要があることを保証します。他のプロトコル、ホスト名、ポート、またはマッチしないパスは400 Bad Requestで応答します。

以下は、next.config.jsファイルのremotePatternsプロパティでhostnameにワイルドカードパターンを使用する例です:

next.config.js
module.exports = {
  images: {
    remotePatterns: [
      {
        protocol: 'https',
        hostname: '**.example.com',
        port: '',
        search: '',
      },
    ],
  },
}

補足: 上記の例では、next/imagesrcプロパティがhttps://img1.example.comhttps://me.avatar.example.comなど、任意の数のサブドメインで始まる必要があります。ポートやクエリ文字列は持てません。他のプロトコルやマッチしないホスト名は400 Bad Requestで応答します。

ワイルドカードパターンはpathnamehostnameの両方で使用でき、以下の構文を持ちます:

  • * 単一のパスセグメントまたはサブドメインにマッチします
  • ** 末尾の任意の数のパスセグメントまたは先頭のサブドメインにマッチします

**構文はパターンの途中では機能しません。

補足: protocolportpathname、またはsearchを省略した場合、ワイルドカード**が暗黙的に指定されます。これは、意図しないURLの最適化を許可する可能性があるため推奨されません。

以下は、next.config.jsファイルのremotePatternsプロパティでsearchを使用する例です:

next.config.js
module.exports = {
  images: {
    remotePatterns: [
      {
        protocol: 'https',
        hostname: 'assets.example.com',
        search: '?v=1727111025337',
      },
    ],
  },
}

補足: 上記の例では、next/imagesrcプロパティがhttps://assets.example.comで始まり、正確なクエリ文字列?v=1727111025337を持つ必要があることを保証します。他のプロトコルやクエリ文字列は400 Bad Requestで応答します。

domains

警告: アプリケーションを悪意のあるユーザーから保護するため、Next.js 14以降では厳格なremotePatternsに置き換えられ、非推奨となりました。domainsはドメインのコンテンツがすべて自分のものである場合にのみ使用してください。

remotePatternsと同様に、domains設定は外部画像の許可されたホスト名のリストを提供するために使用できます。

ただし、domains設定はワイルドカードパターンのマッチングをサポートせず、プロトコル、ポート、パス名を制限することもできません。

以下はnext.config.jsファイルでのdomainsプロパティの例です:

next.config.js
module.exports = {
  images: {
    domains: ['assets.acme.com'],
  },
}

loaderFile

Next.jsの組み込みImage Optimization APIの代わりにクラウドプロバイダーを使用して画像を最適化する場合、以下のようにnext.config.jsloaderFileを設定できます:

next.config.js
module.exports = {
  images: {
    loader: 'custom',
    loaderFile: './my/image/loader.js',
  },
}

これはNext.jsアプリケーションのルートからの相対パスを指定する必要があります。ファイルは文字列を返すデフォルト関数をエクスポートする必要があります。例:

my/image/loader.js
export default function myImageLoader({ src, width, quality }) {
  return `https://example.com/${src}?w=${width}&q=${quality || 75}`
}

あるいは、loader propを使用してnext/imageの各インスタンスを設定することもできます。

例:

高度な設定

以下の設定は高度なユースケース用であり、通常は必要ありません。以下のプロパティを設定することを選択した場合、将来のアップデートでのNext.jsのデフォルトへの変更を上書きすることになります。

deviceSizes

ユーザーの予想されるデバイス幅がわかっている場合、next.config.jsdeviceSizesプロパティを使用してデバイス幅のブレークポイントのリストを指定できます。これらの幅はnext/imageコンポーネントがsizes propを使用する際、ユーザーのデバイスに適した画像が提供されることを保証するために使用されます。

設定が提供されない場合、以下のデフォルトが使用されます。

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

imageSizes

next.config.jsファイルのimages.imageSizesプロパティを使用して、画像の幅のリストを指定できます。これらの幅はデバイスサイズの配列と連結され、画像のsrcsetを生成するために使用される完全なサイズ配列を形成します。

2つの別々のリストがある理由は、imageSizesがsizesプロパティを提供する画像にのみ使用され、これは画像が画面の全幅よりも小さいことを示すためです。したがって、imageSizesのサイズはすべてdeviceSizesの最小サイズよりも小さくする必要があります。

設定が提供されない場合、以下のデフォルトが使用されます。

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

formats

デフォルトの画像最適化APIは、リクエストのAcceptヘッダーを通じてブラウザがサポートする画像フォーマットを自動的に検出し、最適な出力フォーマットを決定します。

Acceptヘッダーが設定された形式の複数にマッチする場合、配列の最初のマッチが使用されます。したがって、配列の順序は重要です。マッチがない場合(または元の画像がアニメーションの場合)、画像最適化APIは元の画像のフォーマットにフォールバックします。

設定が提供されない場合、以下のデフォルトが使用されます。

next.config.js
module.exports = {
  images: {
    formats: ['image/webp'],
  },
}

以下の設定で、AVIFサポートを有効にしつつWebPにフォールバックすることができます。

next.config.js
module.exports = {
  images: {
    formats: ['image/avif', 'image/webp'],
  },
}

補足:

  • AVIFは一般的にエンコードに50%長い時間がかかりますが、WebPと比較して20%小さく圧縮されます。つまり、画像が最初にリクエストされる際は通常遅くなり、その後のキャッシュされたリクエストは高速になります。
  • Next.jsの前にプロキシ/CDNを使用してセルフホストする場合、プロキシがAcceptヘッダーを転送するように設定する必要があります。

キャッシュの動作

以下はデフォルトのloaderのキャッシュアルゴリズムについて説明します。他のすべてのローダーについては、クラウドプロバイダーのドキュメントを参照してください。

画像はリクエストに応じて動的に最適化され、<distDir>/cache/imagesディレクトリに保存されます。最適化された画像ファイルは、有効期限に達するまで、その後のリクエストに提供されます。キャッシュされているが期限切れのファイルにマッチするリクエストがあった場合、期限切れの画像はすぐに古い状態で提供されます。その後、画像はバックグラウンドで再度最適化され(再検証とも呼ばれます)、新しい有効期限日でキャッシュに保存されます。

画像のキャッシュ状態は、x-nextjs-cacheレスポンスヘッダーの値を読み取ることで判断できます。可能な値は以下の通りです:

  • MISS - パスがキャッシュにない(最初の訪問時に最大1回発生)
  • STALE - パスはキャッシュにあるが再検証時間を超過したため、バックグラウンドで更新される
  • HIT - パスはキャッシュにあり、再検証時間を超過していない

有効期限(あるいは最大期間)は、minimumCacheTTL設定または上流の画像のCache-Controlヘッダーのいずれか大きい方によって定義されます。具体的には、Cache-Controlヘッダーのmax-age値が使用されます。s-maxagemax-ageの両方が見つかった場合、s-maxageが優先されます。max-ageはCDNやブラウザを含む下流のクライアントにも引き継がれます。

  • 上流の画像にCache-Controlヘッダーが含まれていない場合や値が非常に低い場合、minimumCacheTTLを設定してキャッシュ期間を延長できます。
  • deviceSizesimageSizesを設定して、生成される可能性のある画像の総数を減らすことができます。
  • formatsを設定して、複数のフォーマットを無効にし、単一の画像フォーマットを優先することができます。

minimumCacheTTL

最適化された画像のキャッシュ有効期間(Time to Live、TTL)を秒単位で設定できます。多くの場合、ファイルの内容を自動的にハッシュ化し、Cache-Controlヘッダーがimmutableの画像を永続的にキャッシュする静的画像インポートを使用する方が良いでしょう。

next.config.js
module.exports = {
  images: {
    minimumCacheTTL: 60,
  },
}

最適化された画像の有効期限(あるいは最大期間)は、minimumCacheTTLまたは上流の画像のCache-Controlヘッダーのいずれか大きい方によって定義されます。

画像ごとにキャッシュの動作を変更する必要がある場合、headersを設定して上流の画像(/_next/image自体ではなく、例えば/some-asset.jpg)にCache-Controlヘッダーを設定できます。

現時点ではキャッシュを無効化するメカニズムがないため、minimumCacheTTLを低く保つのがベストです。そうでない場合、手動でsrc propを変更するか、<distDir>/cache/imagesを削除する必要があるかもしれません。

disableStaticImages

デフォルトの動作では、import icon from './icon.png'のような静的ファイルのインポートを許可し、それをsrcプロパティに渡すことができます。

場合によっては、他のプラグインがインポートが異なる動作をすることを期待している場合、この機能を無効にすることができます。

next.config.js内で静的画像のインポートを無効にできます:

next.config.js
module.exports = {
  images: {
    disableStaticImages: true,
  },
}

dangerouslyAllowSVG

デフォルトのloaderはいくつかの理由でSVG画像を最適化しません。第一に、SVGはベクター形式であり、ロスレスでリサイズできます。第二に、SVGはHTML/CSSと同様の機能を多く持っており、適切なコンテンツセキュリティポリシー(CSP)ヘッダーがない場合、脆弱性につながる可能性があります。

したがって、srcプロパティがSVGであることがわかっている場合は、unoptimizedプロパティを使用することを推奨します。これはsrc".svg"で終わる場合、自動的に行われます。

しかし、デフォルトの画像最適化APIでSVG画像を提供する必要がある場合は、next.config.jsdangerouslyAllowSVGを設定できます:

next.config.js
module.exports = {
  images: {
    dangerouslyAllowSVG: true,
    contentDispositionType: 'attachment',
    contentSecurityPolicy: "default-src 'self'; script-src 'none'; sandbox;",
  },
}

加えて、ブラウザに画像をダウンロードさせるためのcontentDispositionTypeの設定と、画像に埋め込まれたスクリプトの実行を防ぐためのcontentSecurityPolicyの設定を強く推奨します。

contentDispositionType

デフォルトのloaderは、APIが任意のリモート画像を提供できるため、保護のためにContent-Dispositionヘッダーをattachmentに設定します。

デフォルト値はattachmentで、直接訪問時にブラウザに画像をダウンロードさせます。これは特にdangerouslyAllowSVGが真の場合に重要です。

オプションでinlineを設定して、直接訪問時にブラウザが画像をダウンロードせずにレンダリングすることを許可できます。

next.config.js
module.exports = {
  images: {
    contentDispositionType: 'inline',
  },
}

アニメーション画像

デフォルトのloaderは、アニメーション画像を自動的に検出し、画像最適化をバイパスしてそのまま画像を提供します。

アニメーションファイルの自動検出はベストエフォートで、GIF、APNG、WebPをサポートしています。特定のアニメーション画像で画像最適化を明示的にバイパスしたい場合は、unoptimizedプロパティを使用してください。

レスポンシブ画像

デフォルトで生成されるsrcsetは、異なるデバイスのピクセル比をサポートするために1x2xの画像を含みます。ただし、ビューポートに合わせて伸縮するレスポンシブ画像をレンダリングしたい場合があります。その場合、sizesとともにstyle(またはclassName)を設定する必要があります。

以下のいずれかの方法を使用してレスポンシブ画像をレンダリングできます。

静的インポートを使用したレスポンシブ画像

ソース画像が動的でない場合、静的インポートを使用してレスポンシブ画像を作成できます:

components/author.js
import Image from 'next/image'
import me from '../photos/me.jpg'
 
export default function Author() {
  return (
    <Image
      src={me}
      alt="著者の写真"
      sizes="100vw"
      style={{
        width: '100%',
        height: 'auto',
      }}
    />
  )
}

試してみる:

アスペクト比を持つレスポンシブ画像

ソース画像が動的またはリモートURLの場合、レスポンシブ画像の正しいアスペクト比を設定するためにwidthheightも提供する必要があります:

components/page.js
import Image from 'next/image'
 
export default function Page({ photoUrl }) {
  return (
    <Image
      src={photoUrl}
      alt="著者の写真"
      sizes="100vw"
      style={{
        width: '100%',
        height: 'auto',
      }}
      width={500}
      height={300}
    />
  )
}

試してみる:

fillを使用したレスポンシブ画像

アスペクト比がわからない場合は、fillプロパティを設定し、親要素にposition: relativeを設定する必要があります。必要に応じて、希望の伸縮対トリミングの動作に応じてobject-fitスタイルを設定できます:

app/page.js
import Image from 'next/image'
 
export default function Page({ photoUrl }) {
  return (
    <div style={{ position: 'relative', width: '300px', height: '500px' }}>
      <Image
        src={photoUrl}
        alt="著者の写真"
        sizes="300px"
        fill
        style={{
          objectFit: 'contain',
        }}
      />
    </div>
  )
}

試してみる:

テーマ検出CSS

ライトモードとダークモードで異なる画像を表示したい場合、CSSメディアクエリに基づいて正しい画像を表示する2つの<Image>コンポーネントをラップする新しいコンポーネントを作成できます。

components/theme-image.module.css
.imgDark {
  display: none;
}
 
@media (prefers-color-scheme: dark) {
  .imgLight {
    display: none;
  }
  .imgDark {
    display: unset;
  }
}
components/theme-image.tsx
TypeScript
import styles from './theme-image.module.css'
import Image, { ImageProps } from 'next/image'
 
type Props = Omit<ImageProps, 'src' | 'priority' | 'loading'> & {
  srcLight: string
  srcDark: string
}
 
const ThemeImage = (props: Props) => {
  const { srcLight, srcDark, ...rest } = props
 
  return (
    <>
      <Image {...rest} src={srcLight} className={styles.imgLight} />
      <Image {...rest} src={srcDark} className={styles.imgDark} />
    </>
  )
}

補足: デフォルトのloading="lazy"の動作により、正しい画像のみが読み込まれることが保証されます。両方の画像が読み込まれてしまうため、priorityloading="eager"は使用できません。代わりにfetchPriority="high"を使用できます。

試してみる:

getImageProps

より高度なユースケースでは、getImageProps()を呼び出して基礎となる<img>要素に渡されるpropsを取得し、それらを別のコンポーネント、スタイル、canvas等に渡すことができます。

これにより、React useState()の呼び出しを避けることができるため、より良いパフォーマンスにつながりますが、プレースホルダーが削除されることがないためplaceholderプロパティとは使用できません。

テーマ検出Picture

ライトモードとダークモードで異なる画像を表示したい場合、<picture>要素を使用してユーザーの優先カラースキームに基づいて異なる画像を表示できます。

app/page.js
import { getImageProps } from 'next/image'
 
export default function Page() {
  const common = { alt: 'テーマの例', width: 800, height: 400 }
  const {
    props: { srcSet: dark },
  } = getImageProps({ ...common, src: '/dark.png' })
  const {
    props: { srcSet: light, ...rest },
  } = getImageProps({ ...common, src: '/light.png' })
 
  return (
    <picture>
      <source media="(prefers-color-scheme: dark)" srcSet={dark} />
      <source media="(prefers-color-scheme: light)" srcSet={light} />
      <img {...rest} />
    </picture>
  )
}

アートディレクション

モバイルとデスクトップで異なる画像を表示したい場合(アートディレクションとも呼ばれます)、異なるsrcwidthheightqualityプロパティをgetImageProps()に提供できます。

app/page.js
import { getImageProps } from 'next/image'
 
export default function Home() {
  const common = { alt: 'アートディレクションの例', sizes: '100vw' }
  const {
    props: { srcSet: desktop },
  } = getImageProps({
    ...common,
    width: 1440,
    height: 875,
    quality: 80,
    src: '/desktop.jpg',
  })
  const {
    props: { srcSet: mobile, ...rest },
  } = getImageProps({
    ...common,
    width: 750,
    height: 1334,
    quality: 70,
    src: '/mobile.jpg',
  })
 
  return (
    <picture>
      <source media="(min-width: 1000px)" srcSet={desktop} />
      <source media="(min-width: 500px)" srcSet={mobile} />
      <img {...rest} style={{ width: '100%', height: 'auto' }} />
    </picture>
  )
}

バックグラウンドCSS

srcSet文字列をimage-set() CSS関数に変換して、バックグラウンド画像を最適化することもできます。

app/page.js
import { getImageProps } from 'next/image'
 
function getBackgroundImage(srcSet = '') {
  const imageSet = srcSet
    .split(', ')
    .map((str) => {
      const [url, dpi] = str.split(' ')
      return `url("${url}") ${dpi}`
    })
    .join(', ')
  return `image-set(${imageSet})`
}
 
export default function Home() {
  const {
    props: { srcSet },
  } = getImageProps({ alt: '', width: 128, height: 128, src: '/img.png' })
  const backgroundImage = getBackgroundImage(srcSet)
  const style = { height: '100vh', width: '100vw', backgroundImage }
 
  return (
    <main style={style}>
      <h1>Hello World</h1>
    </main>
  )
}

既知のブラウザのバグ

このnext/imageコンポーネントはブラウザネイティブの遅延読み込みを使用します。これはSafari 15.4より前の古いブラウザでは即時読み込みにフォールバックする可能性があります。ブラー効果のプレースホルダーを使用する場合、Safari 12より前の古いブラウザでは空のプレースホルダーにフォールバックします。width/heightautoに設定したスタイルを使用する場合、アスペクト比を保持しないSafari 15より前の古いブラウザでレイアウトシフトを引き起こす可能性があります。詳細については、このMDNビデオを参照してください。

  • Safari 15 - 16.3は読み込み中にグレーの境界線を表示します。Safari 16.4はこの問題を修正しました。可能な解決策:
    • CSS @supports (font: -apple-system-body) and (-webkit-appearance: none) { img[loading="lazy"] { clip-path: inset(0.6px) } }を使用する
    • 画像がフォールド上にある場合はpriorityを使用する
  • Firefox 67+は読み込み中に白い背景を表示します。可能な解決策:

バージョン履歴

バージョン変更内容
v15.0.0decoding propが追加されました。contentDispositionTypeのデフォルト設定がattachmentに変更されました。
v14.2.0overrideSrc propが追加されました。
v14.1.0getImageProps()が安定化されました。
v14.0.0onLoadingComplete propとdomains設定が非推奨になりました。
v13.4.14placeholder propがdata:/image...をサポートするようになりました
v13.2.0contentDispositionType設定が追加されました。
v13.0.6ref propが追加されました。
v13.0.0next/imageのインポートがnext/legacy/imageに名前が変更されました。next/future/imageのインポートがnext/imageに名前が変更されました。インポートを安全に自動的に名前変更するコードモッドが利用可能です。<span>ラッパーが削除されました。layoutobjectFitobjectPositionlazyBoundarylazyRootプロパティが削除されました。altが必須になりました。onLoadingCompleteimg要素への参照を受け取ります。組み込みのloader設定が削除されました。
v12.3.0remotePatternsunoptimized設定が安定化されました。
v12.2.0実験的なremotePatternsと実験的なunoptimized設定が追加されました。layout="raw"が削除されました。
v12.1.1style propが追加されました。layout="raw"の実験的サポートが追加されました。
v12.1.0dangerouslyAllowSVGcontentSecurityPolicy設定が追加されました。
v12.0.9lazyRoot propが追加されました。
v12.0.0formats設定が追加されました。
AVIFサポートが追加されました。
ラッパー<div><span>に変更されました。
v11.1.0onLoadingCompletelazyBoundaryプロパティが追加されました。
v11.0.0src propが静的インポートをサポートするようになりました。
placeholder propが追加されました。
blurDataURL propが追加されました。
v10.0.5loader propが追加されました。
v10.0.1layout propが追加されました。
v10.0.0next/imageが導入されました。