Ответ 1
Поэтому любой, кто имеет проблемы с прокруткой, должен this
добавить эти 2 строки после вашего удаления
cell.layer.shouldRasterize = YES;
cell.layer.rasterizationScale = [UIScreen mainScreen].scale;
У меня есть галерея в моем приложении, использующая UICollectionView
. Ячейки имеют размер приблизительно 70,70. Я использую ALAssets
из ALAssetLibrary
в галерее, которую я сохранил в списке.
Я использую обычный шаблон для заполнения ячеек:
-(UICollectionViewCell*)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
mycell = [collectionView dequeueReusableCellWithReuseIdentifier:cellIdentifier forIndexPath:indexPath];
mycell.imageView.image = [[UIImage imageWithCGImage:[alassetList objectAtIndex:indexpath.row] thumbnail]];
return mycell;
}
Моя галерея прокручивается. Я не понимаю, почему это так. Я попытался добавить NSCache для кэширования миниатюр (возможно, создание изображений было дорого), но это не помогло для производительности.
Я бы ожидал, что пользовательский интерфейс будет таким же масляным, как и приложение для акций.
Теперь я подозреваю, что это может быть что-то в UICollectionViewCell prepareForReuse
, которое может поддерживать метод dequeueReusableCellWithReuseIdentifier
, но используя инструменты, которые я не смог найти.
Любая другая вещь, которая может быть причиной этого? Есть ли "более быстрый" способ для более быстрого создания UICollectionViewCell
или dequeue
?
Поэтому любой, кто имеет проблемы с прокруткой, должен this
добавить эти 2 строки после вашего удаления
cell.layer.shouldRasterize = YES;
cell.layer.rasterizationScale = [UIScreen mainScreen].scale;
Я бы предположил, что "choppyness" исходит из распределения UIImage, а не с помощью метода dequeueReusableCellWithReuseIdentifier
. Я бы попытался сделать выделение изображения в фоновом потоке и посмотреть, делает ли это что-то более маслянистым.
-(UICollectionViewCell*)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
mycell = [collectionView dequeueReusableCellWithReuseIdentifier:cellIdentifier forIndexPath:indexPath];
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^(void) {
// Load image on a non-ui-blocking thread
UIImage *image = [[UIImage imageWithCGImage:[alassetList objectAtIndex:indexpath.row] thumbnail]];
dispatch_sync(dispatch_get_main_queue(), ^(void) {
// Assign image back on the main thread
mycell.imageView.image = image;
});
});
return mycell;
}
Более подробную информацию можно найти здесь: https://developer.apple.com/library/ios/documentation/Cocoa/Conceptual/Multithreading/Introduction/Introduction.html
Загрузите изображения с помощью NSURLConnection sendAsynchronousRequest:queue:completionHandler:
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:urlString]];
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *error) {
[cell.imageView setImage:[UIImage imageWithData:data]];
}];
Отметьте подпункты клипов и непрозрачные в инспекторе атрибутов и отключите пейджинг.
У меня были проблемы с прокруткой UICollectionView
.
Что работало (почти) как прелесть для меня: я заполнил ячейки с помощью png thumbnails 90x90. Я говорю почти потому, что первый полный свиток не настолько гладкий, но никогда больше не разбился...
В моем случае размер ячейки 90х90.
Раньше у меня было много оригинальных размеров png, и это было очень прерывисто, когда первоначальный размер png был больше ~ 1000x1000 (много сбоев при первом прокрутке).
Итак, я выбираю 90x90 (или тому подобное) на UICollectionView
и показываю оригинальные png (независимо от размера). Надеюсь, это поможет другим.
Если кто-то использует PhImageManager, выключение синхронного решения проблемы. (deliveryMode =.FastFormat также может дать дополнительное повышение производительности, но компромисс - это миниатюра будет более низкого качества)
let option = PHImageRequestOptions()
option.deliveryMode = .Opportunistic
option.synchronous = false
PHImageManager().requestImageForAsset(phAsset, targetSize: CGSizeMake(2048, 2048), contentMode: .AspectFit, options: option, resultHandler: { (image, objects) in
self.imageView.image = image!
})
Я поделюсь своим опытом работы с коллекцией просмотров.
Swift 5
Если вы используете iOS 10+, производительность уже должна быть выше, чем в предыдущих версиях iOS. Я настоятельно рекомендую вам посмотреть это видео WWDC - Что нового в UICollectionView в iOS 10
Одна очень простая вещь, которая улучшила мою производительность, заключалась в реализации делегата предварительной выборки. Я буквально ничего не сделал, кроме как просто реализовать это!
Сначала убедитесь, что ваш collectionView соответствует делегату,
yourCollectionView.prefetchDataSource = self
Затем просто реализуйте делегат предварительной выборки,
extension YourViewController: UICollectionViewDataSourcePrefetching {
func collectionView(_ collectionView: UICollectionView, prefetchItemsAt indexPaths: [IndexPath]) {
// You could do further optimizations here.
}
}