如何比较PHAsset到UIImage

我已经将一些PHAsset转换为UIImage

  PHImageManager *manager = [PHImageManager defaultManager]; [manager requestImageForAsset:asset targetSize:PHImageManagerMaximumSize contentMode:PHImageContentModeDefault options:requestOptions resultHandler:^void(UIImage *image, NSDictionary *info) { convertedImage = image; [images addObject:convertedImage]; }]; 

现在我想要做这样的事情:

 [selectedAssets removeObject:image]; 

其中selectedAssetsPHAsset的数组, imageUIImage

所以我实现了这样的isEqual:

 - (BOOL)isEqual:(id)other { if (other == self) return YES; if (!other || ![[other class] isEqual:[self class]]) return NO; NSData *data1 = UIImagePNGRepresentation(self.image); NSData *data2 = UIImagePNGRepresentation(((TINSelectedImage*)other).image); return [data1 isEqual:data2]; } 

但它不工作!

您不应该比较图像,而应该比较PHAssets或其唯一有用的名为localIdentifier的部分。

您正在寻找的区分资产的东西叫做PHAsset的localIdentifier属性。

Apple Docs将其定义为:

 A unique string that persistently identifies the object. (read-only) 

对不起,这个答案会有点宽泛,因为我不喜欢你的方法。

如果我是你,我会这样做:

首先创build一个自定义类,我们将其命名为PhotoInfo。 (如果你不想保留大量有关你的照片的信息,你并不需要这么做,如果是这样的话,可以直接使用PHAssets的PFFetchResults,但是我会使用CustomClass)。

在PhotoInfo.h中:

 #import <Foundation/Foundation.h> @interface PhotoInfo : NSObject @property NSString *localIdentifier; @end 

现在不要使用图像数组,而是使用您创build的将包含localIdentifier的自定义类。 喜欢这个:

 PhotoInfo *photo = [[PhotoInfo alloc] init]; photo.localIdentifier = asset.localIdentifier; 

假设你想从图库中获取图像,你可以这样做:

 -(PHFetchResult*) getAssetsFromLibrary { PHFetchResult *allPhotos; PHFetchOptions *allPhotosOptions = [[PHFetchOptions alloc] init]; allPhotosOptions.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"creationDate" ascending:NO]]; //Get images sorted by creation date allPhotos = [PHAsset fetchAssetsWithMediaType:PHAssetMediaTypeImage options:allPhotosOptions]; return allPhotos; } 

要填充你的数据源,你需要做如下的事情:

 NSMutableArray *yourPhotoDataSource = [[NSMutableArray alloc] init]; PHFetchResult * assets = [self getAssetsFromLibrary]; for(PHAsset *asset in assets) { PhotoInfo *photo = [PhotoInfo new]; photo.localIndentifier = asset.localIdentifier; [yourPhotoDataSource addObject:photo]; } 

现在让我们说,你必须在某处显示这些图像,你需要一个实际的图像,所以你会做这样的事情来获取图像:

 -(void) getImageForAsset: (PHAsset *) asset andTargetSize: (CGSize) targetSize andSuccessBlock:(void (^)(UIImage * photoObj))successBlock { dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ PHImageRequestOptions *requestOptions; requestOptions = [[PHImageRequestOptions alloc] init]; requestOptions.resizeMode = PHImageRequestOptionsResizeModeFast; requestOptions.deliveryMode = PHImageRequestOptionsDeliveryModeFastFormat; requestOptions.synchronous = true; PHImageManager *manager = [PHImageManager defaultManager]; [manager requestImageForAsset:asset targetSize:targetSize contentMode:PHImageContentModeDefault options:requestOptions resultHandler:^void(UIImage *image, NSDictionary *info) { @autoreleasepool { if(image!=nil){ successBlock(image); } } }]; }); } 

现在让我们假设你在一个tableView中显示这些图像,在你的cellForRowAtIndexPath中,像这样调用上面提到的方法:

  //Show a spinner // Give a customizable size for image. Why load the memory with full image if you don't need to show it? [self getImageForAsset:asset andTargetSize:yourDesiredCGSizeOfImage andSuccessBlock:^(UIImage *photoObj) { dispatch_async(dispatch_get_main_queue(), ^{ //Update UI of cell //Hide the spinner cell.thumbNail.image = photoObj; }); }]; 

现在,您可以通过平滑的用户体验asynchronous加载图像,并可以只显示需要的图像而不是存储全部图像。 (你可以通过引入caching来使性能更好,但这不是重点)。

最后得到你的问题 ,要删除一个特定的图像,你将只需要localIdentifier,因为它是唯一的每个PHAsset或索引。

假设你正在删除tableView中的某个单元格,它正在显示你现在想删除的特定图像。

 - (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath { if (editingStyle == UITableViewCellEditingStyleDelete) { PhotoInfo *photo = [yourPhotoDataSource objectAtIndex:indexPath.row]; [yourPhotoDataSource removeObject:photo]; [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade]; } } 

如果您不使用TableView / CollectionView并且不知道对象的索引,则可以在数组上使用快速枚举,但是您必须知道要删除的对象的localIdentifier:

 -(void) deletePhotoWithIdentifier:(NSString *) identifierStr{ NSMutableArray *dummyArray = [[NSMutableArray alloc] initWithArray:yourPhotoDataSource]; //created because we can't modify the array we are iterating on. Otherwise it crashes. [dummyArray enumerateObjectsWithOptions:NSEnumerationReverse usingBlock:^(PhotoInfo *p, NSUInteger index, BOOL *stop) { if ([p.localIndentifier isEqualToString:idenfierStr]) { [yourPhotoDataSource removeObjectAtIndex:index]; } }]; }