Losing image orientation while converting an image to CGImage

后端 未结 7 2114
爱一瞬间的悲伤
爱一瞬间的悲伤 2020-12-31 04:30

I\'m facing an image orientation issue when cropping a square portion of an image out of a rectangular original image. When image is in landscape, it\'s fine. But when it is

7条回答
  •  天命终不由人
    2020-12-31 05:14

    @JGuo has the only answer that has actually worked. I've updated only a little bit to return an optional UIImage? and for swift-er syntax. I prefer to never implicitly unwrap.

    extension UIImage {
    
        func crop(to rect: CGRect) -> UIImage? {
            func rad(_ degree: Double) -> CGFloat {
                return CGFloat(degree / 180.0 * .pi)
            }
    
            var rectTransform: CGAffineTransform
            switch imageOrientation {
            case .left:
                rectTransform = CGAffineTransform(rotationAngle: rad(90)).translatedBy(x: 0, y: -self.size.height)
            case .right:
                rectTransform = CGAffineTransform(rotationAngle: rad(-90)).translatedBy(x: -self.size.width, y: 0)
            case .down:
                rectTransform = CGAffineTransform(rotationAngle: rad(-180)).translatedBy(x: -self.size.width, y: -self.size.height)
            default:
                rectTransform = .identity
            }
            rectTransform = rectTransform.scaledBy(x: self.scale, y: self.scale)
    
            guard let imageRef = self.cgImage?.cropping(to: rect.applying(rectTransform)) else { return nil }
            let result = UIImage(cgImage: imageRef, scale: self.scale, orientation: self.imageOrientation)
            return result
        }
    }
    

    Here's its implementation as a computed property in my ViewController.

    var croppedImage: UIImage? {
        guard let image = self.image else { return nil }
    
        let ratio = image.size.height / self.contentSize.height
        let origin = CGPoint(x: self.contentOffset.x * ratio, y: self.contentOffset.y * ratio)
        let size = CGSize(width: self.bounds.size.width * ratio, height: self.bounds.size.height * ratio)
        let cropFrame = CGRect(origin: origin, size: size)
        let croppedImage = image.crop(to: cropFrame)
    
        return croppedImage
    }
    

提交回复
热议问题