PHP处理上传图片出现旋转问题

小寒、 / 2024-03-05 / 原文

相关参考链接:

  图像生成和处理(可交换图像信息):https://www.php.net/manual/zh/book.exif.php(包含相关扩展需求以及安装)

一、EXIF 方向参数 Orientation 简介:

  EXIF Orientation 参数让你随便照像但都可以看到正确方向的照片而无需手动旋转(前提要图片浏览器支持,Windows 自带的不支持)。这个参数在有的照片是自带的(也可能没有),看照片时不能自动旋转,修正的方法有两个,一个看不顺眼就旋转,另一个是修改 EXIF 中的 Orientation 参数(XnView 浏览器查看缩略图时可以修改)

  Orientation 参数:其中1、3、6、8照片会比较常见,其余参数普通照片基本不会出现

参数
旋转方向
1
2
水平翻转
3
180°
4
垂直翻转
5
顺时针90°+水平翻转
6
顺时针90°
7
顺时针90°+垂直翻转
8
逆时针90°

示意图:

二、代码示例

1、PHP.ini开启 exif、gd2相关扩展

2、检测是否存在图片旋转代码示例: 

$path = "图片原图地址或上传图片时的临时地址"; //$_FILES['file']['tmp_name']
//>>检测原图是否经过旋转、有些图片可能没有exif信息exif_read_data会抛出异常
try {
    $exif_data = exif_read_data($path);
}catch (\Exception $e){
    //>>遇到无法解析的图片
    $exif_data = [];
}
$img_is_rotate = isset($exif_data['Orientation'])?(int)$exif_data['Orientation']:'';

//>>上述检测 此处判断保存的图片是否需要进行旋转
if(in_array($img_is_rotate,[3,6,8],true)){
    try {
        //>>旋转图片 此处$path 为原图地址或已将上传文件保存后的地址
        imgturn($path,$img_is_rotate);
    }catch (\Exception $e){
       //对应异常处理
       die('旋转图片异常!');
    }
}

 

3、旋转代码示例(仅供参考):

if (!function_exists('imgturn')) {
    /**
     * 旋转图片
     * @param $src
     * @param string $direction
     */
    function imgturn($src,$direction = ''){
        $ext = strtolower(pathinfo($src)['extension']);
        switch ($ext) {
            case 'gif':
                $img = imagecreatefromgif($src);
                break;
            case 'jpg':
            case 'jpeg':
                $img = imagecreatefromjpeg($src);
                break;
            case 'png':
                $img = imagecreatefrompng($src);
                break;
            default:
                die('图片格式错误!');
                break;
        }
        $width = imagesx($img);
        $height = imagesy($img);
        $img2 = imagecreatetruecolor($height,$width);
        switch ($direction){
            case 6:
                //顺时针90°
                for ($x = 0; $x < $width; $x++) {
                    for ($y = 0; $y < $height; $y++) {
                        imagecopy($img2, $img, $height - 1 - $y, $x, $x, $y, 1, 1);
                    }
                }
                break;
            case 8:
                //逆时针90°
                for ($x = 0; $x < $height; $x++) {
                    for ($y = 0; $y < $width; $y++) {
                        imagecopy($img2, $img, $x, $y, $width - 1 - $y, $x, 1, 1);
                    }
                }
                break;
            case 3:
                //180°
                $img2 = imagerotate($img, 180, 0);
                break;
        }
        switch ($ext) {
            case 'jpg':
            case "jpeg":
                imagejpeg($img2, $src, 100);
                break;

            case "gif":
                imagegif($img2, $src, 100);
                break;

            case "png":
                imagepng($img2, $src, 100);
                break;

            default:
                die('图片格式错误!');
                break;
        }
        imagedestroy($img);
        imagedestroy($img2);
    }
}