When I am Using Uiimagepngrepresentation or Uiimagejpegrepresentation for Converting Uiimage into Nsdata, the Image Size Is Too Much Increased

Convert UIImage to NSData without using UIImagePngrepresentation or UIImageJpegRepresentation

H Bastan,

Based on your comment:

...I want to save the captured image return by device camera, through UIImagepicker delegate method in document directory...

It looks like your real goal is to save the image with EXIF data to the documents directory and not specifically getting the UIImage as an NSData object with the EXIF data. In that case, you can do the following in your implementation of imagePickerController:didFinishPickingMediaWithInfo:

// Get your image.
UIImage *capturedImage = [info objectForKey:UIImagePickerControllerOriginalImage];

// Get your metadata (includes the EXIF data).
NSDictionary *metadata = [info objectForKey:UIImagePickerControllerMediaMetadata];

// Create your file URL.
NSFileManager *defaultManager = [NSFileManager defaultManager];
NSURL *docsURL = [[defaultManager URLsForDirectory:NSDocumentDirectory
inDomains:NSUserDomainMask] lastObject];
NSURL *outputURL = [docsURL URLByAppendingPathComponent:@"imageWithEXIFData.jpg"];

// Set your compression quuality (0.0 to 1.0).
NSMutableDictionary *mutableMetadata = [metadata mutableCopy];
[mutableMetadata setObject:@(1.0) forKey:(__bridge NSString *)kCGImageDestinationLossyCompressionQuality];

// Create an image destination.
CGImageDestinationRef imageDestination = CGImageDestinationCreateWithURL((__bridge CFURLRef)outputURL, kUTTypeJPEG , 1, NULL);
if (imageDestination == NULL ) {

// Handle failure.
NSLog(@"Error -> failed to create image destination.");
return;
}

// Add your image to the destination.
CGImageDestinationAddImage(imageDestination, capturedImage.CGImage, (__bridge CFDictionaryRef)mutableMetadata);

// Finalize the destination.
if (CGImageDestinationFinalize(imageDestination) == NO) {

// Handle failure.
NSLog(@"Error -> failed to finalize the image.");
}

CFRelease(imageDestination);

From my tests the execution time was about the same or faster than doing:

NSData *data = UIImageJPEGRepresentation(capturedImage, 1.0);
[data writeToURL:outputURL atomically:YES];

...and you get to keep the EXIF data!

You could also dispatch it to a background queue if you want to make sure your UI stays responsive:

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{

// Do the image saving here...
});

Important Note: You will need to add the ImageIO.framework and the MobileCoreServices.framework to your target's build phases and import them in the class where you do the image saving:

#import <ImageIO/ImageIO.h>
#import <MobileCoreServices/MobileCoreServices.h>

Other notes
It is my understanding that in this case we're not creating a generation loss when saving the image as proposed in the example. We are using UIImage's CGImage property and as the documentation states:

The underlying Quartz image data

Image size is resized when convert it from data in swift 3

If it’s originally an image from your assets, it’s probably @2x, which means the size in pixels (real size) is double the size in pts (displayed size). So the image size isn’t actually increasing, it was 640x854 before and after the transform. It’s just that before the OS automatically scaled it because it was named @2x.

To use the original image scale you can replace 1.0 with capturedImage.scale.

Uploading NSData UIImageJPEGRepresentation too big

This method will allow you to resize an image in Objective-C programmatically.

+ (UIImage *)imageWithImage:(UIImage *)image scaledToSize:(CGSize)newSize {
UIGraphicsBeginImageContextWithOptions(newSize, YES, [UIScreen mainScreen].scale);
[image drawInRect:CGRectMake(0,0,newSize.width,newSize.height)];
UIImage* newImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return newImage;
}

Basically I recommend you resize the image and then upload it if the issue is the API you are using. That being said, using the NSURLConnection class methods, I have been able to upload files larger than 40mb. You can check out a post I just made out about how to use those methods to upload files with a PHP back-end here:

Strange issue while posting image from iPhone

Make sure to mark my answer as correct if it helps!

Convert UIImage to NSData and convert back to UIImage in Swift?

UIImage(data:imageData,scale:1.0) presuming the image's scale is 1.

In swift 4.2, use below code for get Data().

image.pngData()

convert UIImage to NSData

Try one of the following, depending on your image format:

UIImageJPEGRepresentation

Returns the data for the specified image in JPEG format.

NSData * UIImageJPEGRepresentation (
UIImage *image,
CGFloat compressionQuality
);

UIImagePNGRepresentation

Returns the data for the specified image in PNG format

NSData * UIImagePNGRepresentation (
UIImage *image
);

Here the docs.

EDIT:

if you want to access the raw bytes that make up the UIImage, you could use this approach:

CGDataProviderRef provider = CGImageGetDataProvider(image.CGImage);
NSData* data = (id)CFBridgingRelease(CGDataProviderCopyData(provider));
const uint8_t* bytes = [data bytes];

This will give you the low-level representation of the image RGB pixels.
(Omit the CFBridgingRelease bit if you are not using ARC).



Related Topics



Leave a reply



Submit