PHP
ImageMagick
exif
Imagick

アップロードした写真(画像)が回転して表示されるのを直す方法

More than 1 year has passed since last update.

iPhoneからWebでHTMLのフォームから写真をアップロードしてもらったときなど、画像が回転して表示されてしまう場合があるようです。原因はExifのOrientationの値が「1」以外になっていること。

画像の向きの情報がExifに埋め込まれているけれど、ファイル自体は回転していない(=撮影した向きになっていない)ために表示がおかしくなるのです。

ブラウザーの仕様によりますが、ExifのOrientationの値を無視して、ファイルを表示しようとすると撮影した向きとは合わない表示になってしまうことになります。

解決するには、アップロードされたときにExifのOrientationを見て、サーバー側で画像を回転させてしまうのがオススメ。回転して、ExifのOrientationの値を正しい向きに補正します。

以下、PHPのimagick拡張を使った場合の例。

<?php
$imagick = new \Imagick();
$imagick->readImage('test.jpg');
$format = strtolower($imagick->getImageFormat());

if ($format === 'jpeg') {
    $orientation = $imagick->getImageOrientation();
    $isRotated = false;
    if ($orientation === \Imagick::ORIENTATION_RIGHTTOP) {
        $imagick->rotateImage('none', 90);
        $isRotated = true;
    } elseif ($orientation === \Imagick::ORIENTATION_BOTTOMRIGHT) {
        $imagick->rotateImage('none', 180);
        $isRotated = true;
    } elseif ($orientation === \Imagick::ORIENTATION_LEFTBOTTOM) {
        $imagick->rotateImage('none', 270);
        $isRotated = true;
    }
    if ($isRotated) {
        $imagick->setImageOrientation(\Imagick::ORIENTATION_TOPLEFT);
    }
}

ちなみにExifのOrientationのテストをするには http://www.galloway.me.uk/2012/01/uiimageorientation-exif-orientation-sample-images/ にあるようなテスト画像を用意するのがいいかも。

2016年9月9日追記

imagick拡張のバージョン3.4.1から、ImagickクラスにautoOrientメソッドが実装されました。これはImageMagickのconvertコマンドにauto-orientオプションを付けて実行するのと同じ効果をもたらします。

つまり、上で記述したのと同じ内容がこう書けるようになりました。

<?php
$imagick = new \Imagick();
$imagick->readImage('test.jpg');
$imagick->autoOrient();

簡単ですね。PHPも拡張も、できるだけ新しいバージョンを使うことをおすすめします。