iOS:从磁盘加载PNG,向其添加PixelPerMeter属性,并将其保存到相册

时间:2012-10-18 00:16:28

标签: objective-c ios png dpi

显然,使用CGImages,你可以将kCGImagePropertyPNGXPixelsPerMeter和kCGImagePropertyPNGYPixelsPerMeter属性添加到图像中,它们将被添加到png的pHYs块中。但是UIImageWriteToSavedPhotosAlbum不直接接受CGImage。

我一直在尝试将图像作为UIImage加载,然后从中创建CGImage,添加属性,然后根据该数据创建一个新的UIImage并将其保存到相册。

图像正在写入相册,但没有PPM设置。我可以在MacOS上的预览应用中验证这一点,或者使用ImageMagick的identify

ObjC不是我的域名,所以这是我从类似的stackoverflow问题拼凑而成的。

UIImage *uiImage = [UIImage imageWithContentsOfFile:path];

NSDictionary* properties = [NSDictionary dictionaryWithObjectsAndKeys:
                            [NSDictionary dictionaryWithObjectsAndKeys:
                               [NSNumber numberWithInt:5905], (NSString *)kCGImagePropertyPNGXPixelsPerMeter, /* this doesn't work */
                               [NSNumber numberWithInt:5905], (NSString *)kCGImagePropertyPNGYPixelsPerMeter, /* this doesn't work */
                                @"This works when saved to disk.", (NSString *)kCGImagePropertyPNGDescription,
                               nil],(NSString*) kCGImagePropertyPNGDictionary,
                            nil];

NSMutableData* imageData = [NSMutableData data];
CGImageDestinationRef imageDest =  CGImageDestinationCreateWithData((CFMutableDataRef) imageData, kUTTypePNG, 1, NULL);

CGImageDestinationAddImage(imageDest, uiImage.CGImage, (CFDictionaryRef) properties);
CGImageDestinationSetProperties(imageDest, (CFDictionaryRef) properties); /* I'm setting the properties twice because I was going crazy */
CGImageDestinationFinalize(imageDest);

UIImageWriteToSavedPhotosAlbum( [UIImage imageWithData:imageData], nil, NULL, NULL );

// This is a test to see if the data is getting stored at all.
CGImageDestinationRef diskDest = CGImageDestinationCreateWithURL(
    (CFURLRef)[NSURL fileURLWithPath:[NSString stringWithFormat:@"%@.dpi.png",path]], kUTTypePNG, 1, NULL);

CGImageDestinationAddImage(diskDest, uiImage.CGImage, (CFDictionaryRef) properties);
CGImageDestinationSetProperties(diskDest, (CFDictionaryRef) properties);
CGImageDestinationFinalize(diskDest);

更新:修改并简化了代码。仍然将图像保存到相册和磁盘,但每米的像素值不能保存。描述块保存到磁盘,但在写入相册时似乎被剥离。

更新2:通过将文件保存为jpeg并向其添加TIFF X / Y Resolution标签,我已经能够将版本保存到磁盘以存储除72之外的PPI值。此信息仍被删除保存到相册时。

比较通过iOS相机应用拍摄的照片,一张通过Instagram拍摄的照片,以及一张通过我的代码保存的照片,我注意到相机应用程序版本有大量的TIFF / EXIF标签,Instagram和我的相同限制一组标签。这让我得出结论,iOS有意地剥离了这些标签。一个确定的答案可以帮助我在晚上睡觉。

1 个答案:

答案 0 :(得分:0)

答案是不要使用UIImageWriteToSavedPhotosAlbum。

有一个ALAssetsLibrary方法 [writeImageDataToSavedPhotosAlbum:metadata:completionBlock:]

元数据是一个字典,格式与传递给CGImageDestinationSetProperties的字典相同。 PNG和JFIF密度设置可能会被破坏,我正在使用kCGImagePropertyTIFFXResolution。