UICollectionView - Herunterladen von Bildern und effektive zurückladen von Daten, wie Instagram
Bemerkte ich, dass apps wie Intagram verwendet UICollectionViews
um den feed anzuzeigen Fotos.
Mir ist auch aufgefallen, dass die Zellen für diese Fotos ist irgendwie platziert auf dem Bildschirm vor den photos, die komplett heruntergeladen worden sind. Dann, wenn ein download abgeschlossen ist, das Foto ist sehr schön dargestellt in der richtigen Zelle.
Möchte ich kopieren, dass Funktionalität, aber ich weiß nicht, wie ' s geht.
Ich bin derzeit herunterladen einer großen JSON Objekt, das ich zu transformieren, um ein array von NSDictionaries. Jeder NSDictionary
enthält Informationen über jedes Foto, und unter, dass Informationen, eine URL dargestellt wird. Bei dieser URL, die ich finden kann das entsprechende Bild, das ich brauchen, um download und die Anzeige in meinem UICollectionViewCells
Als für ich jetzt Durchlaufen Sie diese Liste, und initiieren Sie einen download für jede URL, die ich sehe. Wenn das herunterladen abgeschlossen ist, habe ich ein reload der collectionview mit [self.collectionView reloadData]
. Aber, wie Sie sich vorstellen können, wenn ich 30 Zellen, die alle will, ein Bild, es gibt eine Menge von reloadData
Anrufe.
Ich bin mit AFNetworking zu behandeln download, hier ist die Methode, das nenne ich mal anhand der URL, die ich bereits erwähnt habe:
-(void) downloadFeedImages:(NSString *) photoURL imageDescs:(NSDictionary*)imageDescs photoId:(NSString *)photoID{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
NSString *directory = [paths objectAtIndex:0];
NSString* foofile = [directory stringByAppendingPathComponent:photoID];
if([[NSFileManager defaultManager] fileExistsAtPath:foofile]){
//IF IMAGE IS CACHED
[self.collectionView reloadData];
return;
}
NSLog(@"photoURL: %@", photoURL);
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:photoURL]];
AFImageRequestOperation *operation = [AFImageRequestOperation imageRequestOperationWithRequest:request
imageProcessingBlock:nil
success:^(NSURLRequest *request, NSHTTPURLResponse *response, UIImage *image) {
//Save Image
NSLog(@"URL-RESPONSE:%@", image);
NSString *myFile = [directory stringByAppendingPathComponent:photoID];
NSData *imageData = UIImagePNGRepresentation(image);
[imageData writeToFile:myFile atomically: YES];
[self.collectionView reloadData];
}
failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error) {
NSLog(@"ERROR: %@", [error localizedDescription]);
}];
[[WebAPI sharedInstance] enqueueHTTPRequestOperation:operation];
}
So im Grunde Frage ich mich, wie ich erreichen kann, die Funktionen, die Instagram und ähnlichen Anwendungen hat, wenn es um die Anzeige eines Feeds mit Bildern.
Außerdem würde ich gerne wissen, ein guter Weg, um einen download initiieren, für jede Zelle, und wenn das download abgeschlossen ist, aktualisieren Sie die Zelle, nicht neu zeichnen die gesamte Ansicht mit [reloadData]
Dank
Du musst angemeldet sein, um einen Kommentar abzugeben.
Die Technik, die Sie umsetzen wollen, ist die sogenannte lazy loading. Da Sie über
AFNetworking
wird es leichter sein, um dies zu implementieren, in Ihrem Fall. Jede Ihrer Sammlung anzeigen-Zelle muss eineUIImageView
um das Bild anzuzeigen. Verwenden Sie dieUIImageView+AFNetworking.h
Kategorie und stellen Sie die korrekte Bild-URL durch den Aufruf der MethodePlatzhalter für das Bild angezeigt wird, bis die gewünschte Bild heruntergeladen wird. Dies wird einfach den gewünschten job für Sie.
Hinweis: standardmäßig URL-Anfragen, die ein cache policy von
NSURLCacheStorageAllowed
und einem timeout-Intervall von 30 Sekunden und sind nicht für den Umgang mit cookies. Konfigurieren von URL-Anforderungen anders, verwenden SiesetImageWithURLRequest:placeholderImage:success:failure:
.Auch, für den Sie verweisen, wenn Sie wollen, zu implementieren, faul laden von Bildern, die Sie selbst, Folgen Sie diesem Apple Beispielcode. Dies ist für
UITableView
aber die gleiche Technik kann verwendet werden, fürUICollectionView
als gut.Hoffe, das hilft!
cellForItemAtIndexPath
? Alle Operationen dazu führen würde, dass eine merkliche pause in der main-thread?setImageWithURL: placeholderImage:
. Auch müssen Sie nicht speichern Sie die Bilder separat im caches-Verzeichnis.verwenden
[self.collectionView reloadItemsAtIndexPaths:[NSArray arrayWithObject:indexPath]];
statt
[self.collectionView reloadData];
hier
indexPath
ist dieNSIndexPath
Objekt für die entsprechendeUICollectionViewCell
ObjektVerwenden folgende Bild laden Async in der Zelle in cellForItemAtIndexPath delegate-Methode
Implementieren Protokoll "UICollectionViewDataSourcePrefetching" in Sie ViewController als
class ViewController: UIViewController , UICollectionViewDataSourcePrefetching {
Stellen Sie folgende Delegierte, um Ihre Sammlung Ansicht im storyboard (siehe angehängtes Bild)
oder programmgesteuert
In ViewController ist viewDidLoad Methode
UICollectionViewDataSourcePrefetching
funktioniert nur auf iOS 10+