[英]iOS Photokit - PHAsset pixelWidth and pixelHeight does not match high-resolution image
我的公司在通过获取PHAssets获取正确大小的元数据时遇到了一个大问题。 我们开发了一个iOS应用程序,客户可以从库中选择图片,获取每张图片的大小(以像素为单位),计算坐标以适应我们出售的小工具,然后将高质量版本的图片上传到我们的服务器以打印小工具。 对于我们的某些客户而言,问题在于所发送的某些高质量版本图片的像素大小与PHAsset对象提供的pixelWidth和pixelHeight不匹配。 举一个例子,我们有一张图片:
图片不在iCloud中,而是由运行iOS 10.2的iPhone 6 SE发送的。 这是获取完整尺寸图像版本的代码:
PHImageRequestOptions *imgOpts = [[PHImageRequestOptions alloc] init];
imgOpts.deliveryMode = PHImageRequestOptionsDeliveryModeHighQualityFormat;
imgOpts.networkAccessAllowed = YES;
imgOpts.resizeMode = PHImageRequestOptionsResizeModeExact;
imgOpts.version = PHImageRequestOptionsVersionCurrent;
PHCachingImageManager *imageManager = [[PHCachingImageManager alloc] init];
[imageManager requestImageForAsset:imageAsset targetSize:PHImageManagerMaximumSize contentMode:PHImageContentModeDefault options:imgOpts resultHandler:^(UIImage * result, NSDictionary * info) {
NSData * imageData = UIImageJPEGRepresentation(result, 0.92f);
//UPLOAD OF imageData TO SERVER HERE
}]
还尝试了requestImageDataForAsset方法,但是没有运气:
PHImageRequestOptions *imgOpts = [[PHImageRequestOptions alloc] init];
imgOpts.deliveryMode = PHImageRequestOptionsDeliveryModeHighQualityFormat;
imgOpts.networkAccessAllowed = YES;
imgOpts.resizeMode = PHImageRequestOptionsResizeModeExact;
imgOpts.version = PHImageRequestOptionsVersionCurrent;
PHCachingImageManager *imageManager = [[PHCachingImageManager alloc] init];
[imageManager requestImageDataForAsset:imageAsset options:imgOpts resultHandler:^(NSData * imageData, NSString * dataUTI, UIImageOrientation orientation, NSDictionary * info) {
//UPLOAD OF imageData TO SERVER HERE
}]
在上传之前,从每张图片的高分辨率版本获取准确的大小对我们来说不是一个选择,因为从库中选择大量资产时,这会降低很多性能。
我们是失踪还是做错了什么? 有没有办法在不将全分辨率图像加载到内存的情况下获得以像素为单位的资产大小? 感谢您的帮助
这是由于Photos
框架中的错误所致。 有关该错误的详细信息,请参见此处 。
有时,在编辑照片后,会创建较小的版本。 这仅适用于一些较大的照片。
尝试检索已编辑的版本( PHImageRequestOptionsVersionCurrent
)时,调用requestImageForAsset:
带有PHImageManagerMaximumSize
)或requestImageDataForAsset:
带有PHImageRequestOptionsDeliveryModeHighQualityFormat
)将读取较小文件版本的数据。
上述方法的回调中的info
将指向图像的路径。 举个例子:
PHImageFileURLKey = "file:///[...]DCIM/100APPLE/IMG_0006/Adjustments/IMG_0006.JPG";
检查该文件夹后,我可以找到另一张图像FullSizeRender.jpg
该图像具有完整的尺寸并包含最新的编辑内容。 因此,一种方法是尝试从FullSizeRender.jpg
读取(如果存在)。
PHAssetResourceManager
以高分辨率获取最新的编辑:
// if (@available(iOS 9.0, *)) { // check if a high quality edit is available NSArray<PHAssetResource *> *resources = [PHAssetResource assetResourcesForAsset:_asset]; PHAssetResource *hqResource = nil; for (PHAssetResource *res in resources) { if (res.type == PHAssetResourceTypeFullSizePhoto) { // from my tests so far, this is only present for edited photos hqResource = res; break; } } if (hqResource) { PHAssetResourceRequestOptions *options = [[PHAssetResourceRequestOptions alloc] init]; options.networkAccessAllowed = YES; long long fileSize = [[hqResource valueForKey:@"fileSize"] longLongValue]; NSMutableData *fullData = [[NSMutableData alloc] initWithCapacity:fileSize]; [[PHAssetResourceManager defaultManager] requestDataForAssetResource:hqResource options:options dataReceivedHandler:^(NSData * _Nonnull data) { // append the data that we're receiving [fullData appendData:data]; } completionHandler:^(NSError * _Nullable error) { // handle completion, using `fullData` or `error` // uti == hqResource.uniformTypeIdentifier // orientation == UIImageOrientationUp }]; } else { // use `requestImageDataForAsset:`, `requestImageForAsset:` or `requestDataForAssetResource:` with a different `PHAssetResource` }
您可以尝试以此来获取相机胶卷照片吗:
__weak __typeof(self) weakSelf = self;
PHFetchResult<PHAssetCollection *> *albums = [PHAssetCollection fetchAssetCollectionsWithType:PHAssetCollectionTypeSmartAlbum subtype:PHAssetCollectionSubtypeSmartAlbumSelfPortraits options:nil];
[albums enumerateObjectsUsingBlock:^(PHAssetCollection * _Nonnull album, NSUInteger idx, BOOL * _Nonnull stop) {
PHFetchOptions *options = [[PHFetchOptions alloc] init];
options.wantsIncrementalChangeDetails = YES;
options.predicate = [NSPredicate predicateWithFormat:@"mediaType == %d",PHAssetMediaTypeImage];
options.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"creationDate" ascending:NO]];
PHFetchResult<PHAsset *> *assets = [PHAsset fetchAssetsInAssetCollection:album options:options];
if(assets.count>0)
{
[assets enumerateObjectsUsingBlock:^(PHAsset * _Nonnull asset, NSUInteger idx, BOOL * _Nonnull stop) {
if(asset!=nil)
{
[[PHImageManager defaultManager] requestImageForAsset:asset targetSize:PHImageManagerMaximumSize contentMode:PHImageContentModeAspectFill options:nil resultHandler:^(UIImage *result, NSDictionary *info)
{
dispatch_async(dispatch_get_main_queue(), ^{
[weakSelf addlocalNotificationForFilters:result];
// [weakSelf.buttonGalery setImage:result forState:UIControlStateNormal];
});
}];
*stop = YES;
}
else{
[weakSelf getlatestAferSelfie];
}
}];
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.