모바일 기기로 촬영한 이미지를 워드프레스로 만든 웹사이트에 업로드했을 때, 이미지들이 엉뚱한 방향으로 뒤집히거나 회전되었던 적 있으신가요?
결론부터 말씀드리자면, 워드프레스가 서브사이즈 이미지를 생성하는 과정에서 원본 이미지 파일이 가지고 있던 EXIF를 누락하면서 발생되는 문제입니다. 사진에 관심이 있는 분들은 EXIF에 대해서 잘 아실텐데요, 이미지 파일에는 Camera, Credit, Aperture, Orientation 등 다양한 메타데이터들이 포함될 수 있습니다. 여기서 우리가 눈여겨 보아야할 것이 Orientation. 8가지 방향에 대한 값이 각각 숫자로 할당됩니다.
* 2, 4, 5, 7은 플립된 상태.(셀카모드?)
모바일 기기로 사진촬영을 하면, 실제 데이터는 항상 같은 방향으로 기록되고, EXIF에 촬영 방향이 저장됩니다. 그리고 이미지 뷰어(웹브라우저, 탐색기 등)는 이 값을 체크하여 보정된 결과를 우리에게 보여주는 것입니다.(단, 기기/환경에 따라 다름)
따라서 워드프레스 처럼 자동으로 서브사이즈 이미지를 생성하는 경우, 그 전에 원본 파일의 Orientation을 미리 확인하여 방향을 교정해주어야 합니다.
안타깝게도 워드프레스가 현재 이런 이슈를 고려하고있지는 않지만, 이미지를 다루는데 있어서 유용한 많은 기능들을 제공하고 있기 때문에, 단 몇 줄의 코드만로 쉽게 구현할 수 있습니다.
아, 그 전에, PHP의 EXIF 익스텐션을 사용할 수 있는지 미리 체크해보세요. 사용할 수 없다면… 동작하지 않습니다.
우선, 파일 업로드 처리 함수인 wp_handle_upload를 찾아서, 어떤 액션 훅을 이용할 수 있는지 찾아봅니다.
wp-admin/includes/file.php에 함수가 정의되어 있는데요, 처리 결과를 반환하기 직전에 ‘wp_handle_upload’라는 훅이 걸려있는 것을 확인할 수 있습니다. 이 부분에서 EXIF Orientation을 확인하여 값이 1보다 큰 경우, flip 또는 rotate 되도록 훅을 걸어봅시다.
add_filter( 'wp_handle_upload', 'fix_image_orientation' ); function fix_image_orientation($upload){ extract($upload); if( ! isset($file) || ! isset($type) || 0 !== strpos( $type, 'image/' ) ) return $upload; $image = wp_get_image_editor($file); if ( is_wp_error( $image ) ) return $upload; if ( ! function_exists('wp_read_image_metadata') ) require_once(ABSPATH . 'wp-admin/includes/image.php'); if ( ! $image_meta = wp_read_image_metadata($file) ) return $upload; $orientation = 0; $degree = 0; $flip_horz = false; $flip_vert = false; $changed = false; if ( isset($image_meta['orientation']) ){ $orientation = $image_meta['orientation']; }else{ list( , , $sourceImageType ) = getimagesize( $file ); if ( is_callable( 'exif_read_data' ) && in_array( $sourceImageType, apply_filters( 'wp_read_image_metadata_types', array( IMAGETYPE_JPEG, IMAGETYPE_TIFF_II, IMAGETYPE_TIFF_MM ) ) ) ) { $exif = @exif_read_data( $file ); if ( ! empty( $exif['Orientation'] ) ) $orientation = $exif['Orientation']; } } switch ( $orientation ) { case 2: $flip_vert = true; break; case 3: $degree = 180; break; case 4: $flip_horz = true; break; case 5: $flip_vert = true; $degree = 90; break; case 6: $degree = -90; break; case 7: $flip_vert = true; $degree = -90; break; case 8: $degree = 90; break; } if( $flip_horz || $flip_vert ) if( ! is_wp_error( $image->flip( $flip_horz, $flip_vert ) ) ) $changed = true; if( $degree ) if( ! is_wp_error( $image->rotate( $degree ) ) ) $changed = true; if( $changed ) $image->save( $file, $type ); return $upload; }
라인 6-7: 변수 체크, 마임타입 체크.
라인 9-11: GD 또는 Imagic PHP 모듈 인스턴스 생성.
라인 13-17: EXIF를 비롯한 메타데이터 가져오기.
라인 25-35: EXIF Orientation 값은 워드프레스 4.0부터 포함되었으므로 이전 버전을 고려하여 값을 가져옴.
라인 37-67: Orientation 값에 따라 회전 각도와 플립 방향을 정해줌.
라인 69-78: 회전, 플립, 저장
아래 이미지는 워드프레스의 미디어 라이브러리를 캡쳐한 것입니다.(테스트용 이미지는 여기에서 가져왔습니다.)
보정전 업로드 결과
보정후 업로드 결과
← home