Project/Record

SwiftUI 이미지가 회전되는 이유와 해결 방법

내일은개발천재🎵 2023. 1. 30. 02:13

 

우선 전체적인 이슈의 원인

현재 이미지를 coreData로 저장하기 위해 Image가 아닌, Data 형식으로 저장해야했다.
이에 사용자가 갤러리에서 선택한 이미지를 pngData()를 이용해 Data로 변환해서 저장했다.
그런데 4:3 이미지를 저장하면, 이미지가 회전해서 저장되는 이슈가 존재했다! (원인을 찾은 팀원 최고다)
팀원이 pngData -> jpegData()로 함수를 바꾸면, 이미지를 제대로 저장할 수 있다는 것을 발견하였다.

이게 너무 궁금해서 찾아봤다! 


 

PNG와 JPEG(=JPG)의 차이점

  1. JPEG (Joint Photographic Experts Group)
  2. 압축 손실 방식으로, 압축률이 매우 뛰어나 파일 용량에 비해 우수한 품질의 이미지를 구현한다. 작고 호환성이 좋아서 웹 사이트나 카메라에 저장하는 용도로 사용한다. 하지만 압축 과정에서 품질저하는 발생한다. 이에 많은 선이 존재하거나, 문자가 많은 경우는 JPEG를 사용하는 것을 추천하지 않는다.
  3. PNG (Portable Network Graphics)
  4. 비손실 압축 방식으로, 이미지 데이터를 모두 유지할 수 있다. JPEG의 단점을 보완해주는 파일로 용량은 크지만 품질 저하가 없고, 투명도를 지원하기 때문에 합성이나 웹 그래픽 이미지에 적합하다.

 

그렇다면 왜 SwiftUI에서 이미지 회전이 발생했을까?

  • 글을 저장할 때, imageOrientation.rawValue를 통해 값을 확인해봤다.

image

- 4:3 비율의 이미지에서 image orientation이 3임을 발견할 수 있었다. (이 이유는 애플만 알겠..지?)
- 즉, 이미지의 방향이 `right`이며 시계 방향으로 90도 회전된 모습을 볼 수 있다.

 

image orientation?

출처: 애플 공식문서


 

결론

정리하자면 우리는 코어데이터로 이미지를 저장하기 위해서 UIImage -> Data로 변환해서 저장해야했다.
이때 4:3 이미지의 경우 imageOrientation이 3이었다. (90도 회전된 상태)

(참고 함수의 내부적인 동작은 확인을 하지 못한다!! -> 예상해보자면)

jpegData(compressionQuality: ) -> Image orientation을 고려하여 Image를 Data로 변환하여 리턴한다.
pngData() -> image orientation을 고려하지 않고 회전된 그대로 Data를 리턴한다.

 

회고

jpeg와 png 차이를 알아보지 않고 무작정 Data로 변환시키며 불러온 문제..!

이래서 개발자는 공부가 끝이 없나보다~


 

무조건 png를 사용해야하는 상황이라면?

func rotatedCopy() -> UIImage {
    if self.imageOrientation == UIImage.Orientation.up {
        return self
    }

    UIGraphicsBeginImageContext(size)

    //draws the image in current context respecting orientation
    draw(in: CGRect(origin: CGPoint.zero, size: size))
    let copy = UIGraphicsGetImageFromCurrentImageContext()

    UIGraphicsEndImageContext()

    return copy!
 }
  • 이런식으로 imageOrientation이 up (0)일 때에는 그대로 return하고, 그렇지 않을 때에는 방향을 맞춰 이미지를 그리는 방식으로 저장하면 된다고 한다!

 

출처

  1. png와 jpeg의 차이점
    Tistory
    Tistory
  2. Image Orientation
    애플 공식 문서
  3. 무조건 png를 사용해야한다면?
    stack overflow
    stack overflow