How to select a portion of an image, crop, and sav

2020-02-19 08:15发布

问题:

I am trying to create an iOS app using Swift to capture images and let the user save a selected portion of the image. In many cam based apps, I noticed that a rectangular frame is offered to let the users choose the desired portion. This involves either sliding the edges of the rectangle or moving the corners to fit the required area.

Could you please guide me on how to implement that moveable rectangle and how to save only that piece of the image?

回答1:

Using Swift 3

Image cropping can be done using CGImages from CoreGraphics.

Get the CGImage version of a UIImage like this:

// cgImage is an attribute of UIImage
let cgImage = image.cgImage

CGImage objects have a method cropping(to: CGRect) that does the cropping:

let croppedCGImage: CGImage = cgImage.cropping(to: toRect)

Finally, convert back from CGImage to UIImage:

let uiImage = UIImage(cgImage: croppedCGImage)

Example function:

func cropImage(image: UIImage, toRect: CGRect) -> UIImage? {
    // Cropping is available trhough CGGraphics
    let cgImage :CGImage! = image.cgImage
    let croppedCGImage: CGImage! = cgImage.cropping(to: toRect)

    return UIImage(cgImage: croppedCGImage)
}

The CGRect attribute of cropping defines the 'crop rectangle' inside the image that will be cropped.



回答2:

Found one more solution. This time it is in Swift. The solution looks elegant and the code relative to other such solutions is written in fewer number of lines.

Here it is.. https://github.com/DuncanMC/CropImg Thanks to Duncan Champney for making his work available on github.



回答3:

https://github.com/myang-git/iOS-Image-Crop-View does something like what you are looking for..

Hope this helps.



回答4:

If you getting issue like rotating 90 after cropping image try this.
Store the original image scale and orientation property for later Use

let imgOrientation = image?.imageOrientation
let imgScale = image?.scale

Get the CGImage from UIImage:

let cgImage = image.cgImage

Pass the cropArea(CGRect) area you want to crop (incase you are using imageView.image you have find the scale and do maths to find cgRect) adding that code below if needed

let croppedCGImage = cgImage.cropping(to: cropArea)
let coreImage = CIImage(cgImage: croppedCGImage!)

Need context for rendering image (its a heavy process do check https://developer.apple.com/documentation/coreimage/cicontext if you are doing multiple times ) using this you can set the scale and orientation we created in first line so image don't rotate 90

let ciContext = CIContext(options: nil)
let filteredImageRef = ciContext.createCGImage(coreImage, from: coreImage.extent)
let finalImage = UIImage(cgImage:filteredImageRef!, scale:imgScale!, orientation:imgOrientation!)
imageView.image = finalImage