Flutter: image_pickerで撮影した写真データが、縦横逆で(90度回転して)表示されてしまう

結論:「flutter_image_compress」パッケージを使う

2022/9/2  Flutter エラー・バグ日記 

 

「image_picker」のカメラ機能で撮った写真が、ファイル情報では、縦幅2160ピクセル、横幅3840ピクセル(つまり横幅の方が長い状態)で記録されているのに、アプリ内で表示させると、90度回転した状態つまり縦幅の方が長い状態)で表示されてしまう。

 

本記事はライトな日記思考で書いているので、詳細説明はしておらず、基本、テキストのみで画像とかはあまり載せておりません。。m(_ _)m

解説記事ではないため、解決していない内容や、その時々の間違った解釈を述べてしまっている可能性が大いにありますので、何卒、ご了承ください。

 

以前は「RotatedBoxクラス」で対処

以前も同じ状況に遭遇し、その時は、表示後に、手動で画像を回転させる仕様を入れることで(RotatedBoxクラスの導入)対処した。

 

↓そのときの対応記録

 

しかし、今回は手動で調整するのではなく、初めから正しい向きで表示させたい

 

毎回、90度回転して表示されるなら、事前に画像の縦横比を把握して、あらかじめ回転させて表示すれば良いが、正しく表示される場合も多く、単純には補正できない。。

 

「decodeImage」は遅すぎるので使いたくない

以前も参考にした下記StackOverflowの記事

 

 

では、いったん「decodeImage」メソッドでImage型に変換し、その後、「bakeOrientation」メソッドを実行して修正する、という方法が一番人気となっている。

 

しかし、この「decodeImage」メソッドは、とてつもなく時間がかかるので、使いたくない。。

 

実際、上記記事内でも、この方法は一番人気ではあるものの、よく見ると「解決」のマークが付いていなかった。

 

「flutter_exif_rotation」パッケージを使う方法

「解決」マークが付いていたのが、この方法。

 

 

このパッケージを使い、「FlutterExifRotation.rotateImage」メソッドに掛けてやると、画像の向きが適正化されるようだが、iOSの対応が不十分らしく、バージョン番号も0番始まり(現時点でバージョン0.5.1)で安定版化していないので、導入するのをやや躊躇。

 

「flutter_image_compress」パッケージで解決

上記StackOverflowで、かなり下の方に回答されていたのが、この方法。

 

 

「flutter_image_compress」は、画像ファイルを圧縮する目的で、一般的に使用されているパッケージだが、これを使うことで、画像の向きも補正できるらしい。

 

「flutter_image_compress」は安定版のパッケージになっており(現時点でバージョン1.1.2)、かつ、自分は画像圧縮も同時に実行したかったこともあり、早速導入。

 

確かに使ってみたら、画像の圧縮と同時に、向きも適正化された

 

コードも非常に簡単。下記のように書くことで、向きが適正化された画像のFile型インスタンスを作成できた。

 

プロパティの設定は、「rotate」0「keepExif」false「autoCorrectionAngle」trueにするのがポイント。

 

// クラス・メソッド・プロパティについて、筆者が作成したものには、末尾に大文字のオー「O」をつけて表記
// ※パッケージで予め決められているものとの区別しやすくするため

        final Uint8List? fixedImageBytesO = await FlutterImageCompress.compressWithFile(
          // ↓画像ファイルのパス
          pickedFilePathO.path,

          // ↓設定しないとこの値になる
          minWidth: 1920,
          minHeight: 1080,

          rotate: 0, // 必要
          quality: 100,
          keepExif: false, // 必要
          autoCorrectionAngle: true, // 必要
          format: CompressFormat.jpeg,
        );

        returnFileO = File("※パス名の文字列");
        // 画像を File クラスのインスタンスに格納
        returnFileO.writeAsBytesSync(fixedImageBytesO!);

 

処理も高速だったので、今後はこの方法を活用していこう。

 

\ Flutterの学習で役立ったコンテンツ・書籍 /

 

 

 


Dart入門 – Dartの要点をつかむためのクイックツアー

タイトルとURLをコピーしました