Closed5

Expoで画像を使用するときのTips

大森翔吾大森翔吾

画像を使用するときのベストプラクティスチェックリスト

前提

  • PNG画像がプロジェクトに既にある。
  • CDNのような実装/維持コストがかかるものは除外。
  • 「Expoでモバイルアプリ開発、あらかじめプロジェクトに用意した画像をアプリ内に表示する」という要件。

必須TODOリスト

画像フォーマット

  • WebPへ変換する(強く推奨)
    EAS Build利用時
    eas.jsonに以下の記述を追記するとpngが自動変換される
eas.json
{
  "build": {
    "yourProfileName": { // "development" や "production" など、ビルドプロファイル名
      "ios": {
        "imageOpts": {
          "pngToWebP": true // PNGをWebPに自動変換する設定
        }
      },
      "android": { //Androidの場合も同様に設定可能
         "imageOpts": {
          "pngToWebP": true
        }
      }
    }
  }
}
  • アイコンなどはSVGを使用する
    アイコン、ロゴなど、拡大縮小する可能性のあるシンプルな図形はSVGを推奨。
    react-native-svg ライブラリを使用。

画像サイズと解像度の最適化

  • Retina対応 (必須)
    @2x, @3x サフィックス付きの画像を用意 (WebPでも必要)。
    例: image.webp, image@2x.webp, image@3x.webp

  • 画像圧縮 (WebPでも実施)
    Squoosh などのツールで、WebPの圧縮率を調整 (画質とのバランス)。
    PNGのままの場合は、ImageOptim, TinyPNG などを使用。

  • expo-image コンポーネントの使用 (必須)

import * as Image from 'expo-image';

<Image
  source={{ uri: require('./image.png').uri.replace(/\.png$/, '.webp') }} // 基本はWebP
  style={styles.image} // スタイルは必須 (後述)
  placeholder={require('./placeholder.png')} // プレースホルダー (推奨)
  transition={300} // フェードイン (任意)
  contentFit="cover" // または "contain", "scale-down" など (必須)
/>
  • contentFit プロパティの設定 (必須)
    cover, contain, scale-down, repeat, stretch から適切なものを選択。
    未設定は避ける (デフォルトの挙動が意図しない場合があるため)。
    cover はみ出す, contain 余白OK, scale-downはcontainと似ているが、元の画像より大きい時は拡大しない

  • style プロパティの設定 (必須)
    width と height を必ず設定する。設定しないと画像は表示されません
    必要に応じて resizeMode も設定 (通常は contentFit で十分)。

推奨項目

  • cachePolicy (通常はデフォルトの cache でOK)
    expo-image はデフォルトで強力なキャッシュ機能を持つ。
    頻繁に更新される画像の場合のみ、cachePolicy を変更するか、URLにクエリパラメータを追加してキャッシュを回避することを検討。
  • プレースホルダーの設定 (推奨)
    placeholder プロパティで、読み込み中に表示する画像や色を指定。
    プレースホルダー画像も最適化する。
  • accessibilityLabel の設定 (推奨)
    画像の内容を説明するテキストを設定。
    装飾的な画像の場合は空文字列 ("")。
大森翔吾大森翔吾

EASでWebPに自動変換する:についてのQ&A

  • Retina 対応、画像圧縮などの前処理は必要ですか?

    • Retina 対応
      • 必須です。
        image.png, image@2x.png, image@3x.png があれば、それぞれ image.webp, image@2x.webp, image@3x.webp が生成されます。
    • 画像圧縮
      • EAS Build の quality オプションを設定することで一括でも設定はできる
      • けど、TinyPNGとかで個別にしても良い。こっちだと、画像の劣化具体が確認できる。
  • ビルド時にってことは、アプリストアに提出する時には最適化されているけど、ローカルでデバッグする時はパフォーマンス下がるよってこと?

    • いいえ、ローカルでのデバッグ時にも WebP が使用されます。
      expo-image は、expo start や expo run:ios / expo run:android での開発時にも適用される
  • PNG で assets の中に置いておくだけでいいの?画像ファイルをコードから呼び出す場合も PNG という指定でいいの?

    • はい。EAS Build は、assets ディレクトリ (または指定したディレクトリ) 内の PNG ファイルを自動的に WebP に変換します。
    • expo-image を使用する場合は、source に通常通り .png で指定して問題ありません。
大森翔吾大森翔吾

結局どうするの?

アプリ内で使用したい画像素材がある場合

  1. 準備
    1. まずpngで素材を用意。
    2. @2x,@3xのものも用意
  2. 実装
    1. eas.jsonにwebP変換の記述を追加する(EAS Buildを使用する場合)
    2. expo-imageコンポーネントで画像を呼び出す(contentFitwidthheightを設定する )
eas.json
<!-- webP変換の記述 -->
{
  "build": {
    "yourProfileName": { // "development" や "production" など、ビルドプロファイル名
      "ios": {
        "imageOpts": {
          "pngToWebP": true // PNGをWebPに自動変換する設定
        }
      },
      "android": { //Androidの場合も同様に設定可能
         "imageOpts": {
          "pngToWebP": true
        }
      }
    }
  }
}
  1. 必要に応じて
    • より圧縮したい場合
      • EAS Build の qualityオプションで一括圧縮をする
      • または、TinyPNGなどを活用して画像を圧縮して置き換える。
    • アイコンなどはsvgで用意する。(react-native-svgで読み込む)
      • react-native-svg で作成したSVGコンポーネントの fill プロパティを currentColor に設定しておくと、親コンポーネントの color スタイルで色を制御できるようになり便利
  2. アクセシビリティを気にするなら
    • expo-image の placeholderで、読み込み中に表示するプレースホルダー画像を設置
    • expo-image の accessibilityLabel プロパティで、画像の内容を説明するテキストを設定
このスクラップは2025/02/07にクローズされました