将 UIImage 的大小调整为200x200pt/px

我一直在努力调整图像的大小。 基本上,我偶然发现: 如何缩小一个 UIImage,并使它清晰/锐利的同时,而不是模糊?

这似乎是一个合法的解决方案,但不知何故,它没有正常工作。

我的应用程序可以处理来自相机滚动的照片。这张照片的大小应该调整到200x200左右,而宽度是重要的,而不是高度。

不幸的是,我没有一个示例代码,因为我丢弃了我的愤怒,非工作解决方案,对不起。

98272 次浏览

Here is my code. The Image is in width 850 px and not 200 px:

 func resizeImage(image: UIImage, newWidth: CGFloat) -> UIImage {


let scale = newWidth / image.size.width
let newHeight = image.size.height * scale
UIGraphicsBeginImageContext(CGSizeMake(newWidth, newHeight))
image.drawInRect(CGRectMake(0, 0, newWidth, newHeight))
let newImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()


return newImage
}




@IBAction func chooseImage(sender: AnyObject) {




var myPickerController = UIImagePickerController()
myPickerController.sourceType = UIImagePickerControllerSourceType.PhotoLibrary
myPickerController.delegate = self;
self.presentViewController(myPickerController, animated: true, completion: nil)




}


func imagePickerController(picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [NSObject : AnyObject])


{
var imagenow = info[UIImagePickerControllerOriginalImage] as? UIImage


imageImage.image = resizeImage(imagenow!, newWidth: 200)






pimg2 = imageImage.image!


cidnew2 = textFieldCID!.text!
pname2 = textFieldName!.text
pmanu2 = textFieldMan!.text
pnick2 = textFieldNick!.text
podate2 = textFieldPODate!.text
pno2 = textFieldArtNo!.text






self.dismissViewControllerAnimated(true, completion: nil)


}

If you're dealing with PNG images that contain transparencies, then the accepted answer function will actually convert the transparent areas to black.

If you wish to scale and keep the transparencies in place, try this function:

SWIFT 4

extension UIImage {
func scaleImage(toSize newSize: CGSize) -> UIImage? {
var newImage: UIImage?
let newRect = CGRect(x: 0, y: 0, width: newSize.width, height: newSize.height).integral
UIGraphicsBeginImageContextWithOptions(newSize, false, 0)
if let context = UIGraphicsGetCurrentContext(), let cgImage = self.cgImage {
context.interpolationQuality = .high
let flipVertical = CGAffineTransform(a: 1, b: 0, c: 0, d: -1, tx: 0, ty: newSize.height)
context.concatenate(flipVertical)
context.draw(cgImage, in: newRect)
if let img = context.makeImage() {
newImage = UIImage(cgImage: img)
}
UIGraphicsEndImageContext()
}
return newImage
}
}

This function will return an image with width you specified:

func scaleImage(image: UIImage, maximumWidth: CGFloat) -> UIImage {
let rect: CGRect = CGRectMake(0, 0, image.size.width, image.size.height)
let cgImage: CGImageRef = CGImageCreateWithImageInRect(image.CGImage!, rect)!
return UIImage(CGImage: cgImage, scale: image.size.width / maximumWidth, orientation: image.imageOrientation)
}

Swift 3.0

func scaledImage(_ image: UIImage, maximumWidth: CGFloat) -> UIImage {
let rect: CGRect = CGRect(x: 0, y: 0, width: image.size.width, height: image.size.height)
let cgImage: CGImage = image.cgImage!.cropping(to: rect)!
return UIImage(cgImage: cgImage, scale: image.size.width / maximumWidth, orientation: image.imageOrientation)
}
func getScaledDimension(width: CGFloat, height: CGFloat,new_width: CGFloat, new_height: CGFloat)->CGPoint {


let widthAspect =  (width / new_width)
let heightAspect = (height / new_height)
if widthAspect == 0 || heightAspect == 0 {
return CGPoint(x: width, y: height)
}
var width1 : CGFloat = 0
var height1 : CGFloat =  0
if widthAspect > heightAspect {
width1 = (width) / heightAspect
height1 = (height) / heightAspect
} else {
width1 = (width) / widthAspect
height1 = (height) / widthAspect
}


return CGPoint(x: width1, y: height1 )
}






func ResizeImage(image: UIImage, targetSize: CGSize) -> UIImage {


let rect = CGRectMake(0, 0, targetSize.width, targetSize.height)


UIGraphicsBeginImageContextWithOptions(targetSize, false, 1.0)
image.drawInRect(rect)
let newImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()


return newImage
}




let imagesize =  getScaledDimension(image.size.width, height: image.size.height , new_width: Width, new_height: Hieght)


print("Image Size Scaled Dimension -> H:\(imagesize.x) W:\(imagesize.y)")


let newImage = ResizeImage(image, targetSize: CGSizeMake(imagesize.x,imagesize.y))
print("Resize Image Size -> H\(newImage.size.height) W\(newImage.size.width) ")

Based on swift_dan's answer, an update for Swift 3

func resizeImage(image: UIImage, newWidth: CGFloat) -> UIImage? {


let scale = newWidth / image.size.width
let newHeight = image.size.height * scale
UIGraphicsBeginImageContext(CGSize(width: newWidth, height: newHeight))
image.draw(in: CGRect(x: 0, y: 0, width: newWidth, height: newHeight))


let newImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()


return newImage
}

For Swift 3.0

simply add this snippet as extension to UIImage. However, remember that is not going to make the image in square form but if it was in that form, the result will be square.

extension UIImage {
func resizeImage(newWidth: CGFloat) -> UIImage {


let scale = newWidth / self.size.width
let newHeight = self.size.height * scale
UIGraphicsBeginImageContext(CGSize(width: newWidth, height: newHeight))
self.draw(in: CGRect(x: 0, y: 0, width: newWidth, height: newHeight))
let newImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()


return newImage!
} }

If you are using kingfisher lib for loading images in you project and want to resize it here is the way:

  • Xcode 8
  • Swift 3x

    let imageUrl = URL(string: "your image url")
    //Size refer to the size which you want to resize your original image
    let size = CGSize(width: 60, height: 60)
    let processImage = ResizingImageProcessor(targetSize: size, contentMode: .aspectFit)
    cell.courseTitleImage.kf.setImage(with: imageUrl! , placeholder: UIImage(named: "placeholder"), options: [.transition(ImageTransition.fade(1)), .processor(processImage)], progressBlock: nil, completionHandler: nil)
    

    OR

    Resize Local Image:- you can refer to the answer of @Christoph R

  • Reduce image size by 1024, you can always convert according server capacity

    func resizeImage(image: UIImage) -> UIImage {
    
    
    if image.size.height >= 1024 && image.size.width >= 1024 {
    
    
    UIGraphicsBeginImageContext(CGSize(width:1024, height:1024))
    image.draw(in: CGRect(x:0, y:0, width:1024, height:1024))
    
    
    let newImage = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext()
    
    
    return newImage!
    
    
    }
    else if image.size.height >= 1024 && image.size.width < 1024
    {
    
    
    UIGraphicsBeginImageContext(CGSize(width:image.size.width, height:1024))
    image.draw(in: CGRect(x:0, y:0, width:image.size.width, height:1024))
    
    
    let newImage = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext()
    
    
    return newImage!
    
    
    }
    else if image.size.width >= 1024 && image.size.height < 1024
    {
    
    
    UIGraphicsBeginImageContext(CGSize(width:1024, height:image.size.height))
    image.draw(in: CGRect(x:0, y:0, width:1024, height:image.size.height))
    
    
    let newImage = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext()
    
    
    return newImage!
    
    
    }
    else
    {
    return image
    }
    
    
    }
    

    Swift 4.0 -

    If you're dealing with images that contain transparencies, then the accepted answer function will actually convert the transparent areas to black.

    If you wish to scale and keep the transparencies in place, try this function:

    func resizeImageWith(image: UIImage, newSize: CGSize) -> UIImage {
    
    
    let horizontalRatio = newSize.width / image.size.width
    let verticalRatio = newSize.height / image.size.height
    
    
    let ratio = max(horizontalRatio, verticalRatio)
    let newSize = CGSize(width: image.size.width * ratio, height: image.size.height * ratio)
    var newImage: UIImage
    
    
    if #available(iOS 10.0, *) {
    let renderFormat = UIGraphicsImageRendererFormat.default()
    renderFormat.opaque = false
    let renderer = UIGraphicsImageRenderer(size: CGSize(width: newSize.width, height: newSize.height), format: renderFormat)
    newImage = renderer.image {
    (context) in
    image.draw(in: CGRect(x: 0, y: 0, width: newSize.width, height: newSize.height))
    }
    } else {
    UIGraphicsBeginImageContextWithOptions(CGSize(width: newSize.width, height: newSize.height), isOpaque, 0)
    image.draw(in: CGRect(x: 0, y: 0, width: newSize.width, height: newSize.height))
    newImage = UIGraphicsGetImageFromCurrentImageContext()!
    UIGraphicsEndImageContext()
    }
    
    
    return newImage
    }
    

    This code uses UIGraphicsImageRenderer introduced in iOS 10: in my testing it was 10-40% faster than earlier samples with UIGraphicsBeginImageContext (Swift 4 / Xcode 9):

    extension UIImage {
    func renderResizedImage (newWidth: CGFloat) -> UIImage {
    let scale = newWidth / self.size.width
    let newHeight = self.size.height * scale
    let newSize = CGSize(width: newWidth, height: newHeight)
    
    
    let renderer = UIGraphicsImageRenderer(size: newSize)
    
    
    let image = renderer.image { (context) in
    self.draw(in: CGRect(origin: CGPoint(x: 0, y: 0), size: newSize))
    }
    return image
    }
    }
    

    Further improving on @rommex's answer using a maximum size, in Swift 4.2:

    private extension UIImage {
    func scaled(to maxSize: CGFloat) -> UIImage? {
    let aspectRatio: CGFloat = min(maxSize / size.width, maxSize / size.height)
    let newSize = CGSize(width: size.width * aspectRatio, height: size.height * aspectRatio)
    let renderer = UIGraphicsImageRenderer(size: newSize)
    return renderer.image { context in
    draw(in: CGRect(origin: CGPoint(x: 0, y: 0), size: newSize))
    }
    }
    }
    

    This is a continuation to @Christoph R 's answer posted for Swift 3.0. This code works for Swift 5.0.1.

    static func resizeImage(image: UIImage, newWidth: CGFloat) -> UIImage {
    
    
    let scale = newWidth / image.size.width
    let newHeight = image.size.height * scale
    UIGraphicsBeginImageContext(CGSize(width: newWidth, height: newHeight))
    image.draw(in: CGRect(x: 0, y: 0, width: newWidth, height: newHeight))
    let newImage = UIGraphicsGetImageFromCurrentImageContext()
    UIGraphicsEndImageContext()
    
    
    return newImage!
    }
    

    at callers site

    TaskUtilties.resizeImage(image: rawImage!, newWidth: CGFloat(50))
    

    This code works excellently on square image and won't lose the quality

    extension UIImage {
    
    
    func resize(targetSize: CGSize) -> UIImage {
    return UIGraphicsImageRenderer(size:targetSize).image { _ in
    self.draw(in: CGRect(origin: .zero, size: targetSize))
    }
    }
    
    
    }
    

    Answer From: Resize Image without losing quality