/ Ako porovnávať PHAsset s UIImage - ios, objektív-c, uiimage, phasset

Ako porovnávať PHAsset s UIImage - ios, objektív-c, uiimage, phasset

Prekonal som niektoré PHAsset na 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];
}];

Teraz chcem urobiť niečo také:

[selectedAssets removeObject:image];

kde selectedAssets je pole PHAsset a image je UIImage

tak som implementoval isEqual takto:

- (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];
}

Ale to nefunguje!

odpovede:

6 pre odpoveď č. 1

Nemali by ste porovnávať obrázky, namiesto toho by ste mali porovnávať PHAssety alebo ich iba užitočnú časť s názvom localIdentifier.

Tá vec, ktorú hľadáte na rozlíšenie medzi aktívami, sa nazýva localIdentifier majetok spoločnosti PHAsset.

Aplikácie Apple Docs ju definujú ako:

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

Ospravedlňujeme sa, že táto odpoveď bude trochu široká, pretože sa tu nepáči.

Keby som bol vy, urobil by som to takto:

Najprv vytvorte vlastnú triedu, nechajte ju nazvaťPhotoInfo. (Nemáte to naozaj robiť, ak nemáte záujem uchovávať veľa informácií o svojich fotografiách.Ak je to prípad, použite PFFetchResults z PHAssets priamo, ak chcete, ale budem ísť s CustomClass) ,

v PhotoInfo.h:

#import <Foundation/Foundation.h>
@interface PhotoInfo : NSObject

@property NSString *localIdentifier;

@end

Teraz namiesto použitia množstva obrázkov použite túto vytvorenú vlastnú triedu, ktorá bude obsahovať localIdentifier. Ako toto:

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

Povedzme, že chcete odobrať obrázky z galérie, urobíte niečo takéto:

-(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;
}

Ak chcete načítať zdroj údajov, urobíte niečo ako:

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];

}

Teraz povoľte, aby ste tieto obrázky zobrazili niekde a potrebujete skutočný obrázok, aby ste urobili niečo také, aby ste získali obrázok:

-(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);
}
}
}];
});

}

Teraz povieme, že zobrazujete tieto obrázky v tabuľke, v bunkeForRowAtIndexPath, zavolajte na vyššie uvedenú metódu takto:

  //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;
});
}];

Teraz s asynchrónnym vkladaním obrázkovhladký používateľ Skúsenosti a úspory pamäte zobrazením iba potrebných záberov namiesto ich ukladania. (Účinnosť môžete dosiahnuť ešte lepšie zavedením ukladania do vyrovnávacej pamäte, ale to tu nie je bod.

Nakoniec sa dostanete k vašej otázke, ak chcete odstrániť určitý obrázok, ktorý potrebujete, potrebujete len localIdentifier, pretože je jedinečný pre každý PHAsset alebo index.

Predpokladajme, že ste vymazali nejakú bunku vo vašom tableView, ktorá zobrazuje konkrétny obrázok, ktorý teraz chcete odstrániť.

- (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];


}
}

Ak nepoužívate TableView / CollectionViewa nepoznáte index objektu, môžete použiť rýchle vyčíslenie na poli, ale potom musíte poznať localIdentifier objektu, ktorý chcete vymazať:

-(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];
}
}];

}