it-roy-ru.com

UICollectionview Скроллинг при загрузке ячеек

В моем приложении есть галерея, использующая переменную 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 быстрее?

31
Avner Barr

Таким образом, любой, у кого есть проблемы с прокруткой, должен сделать это

добавить эти 2 строки после вашей очереди

cell.layer.shouldRasterize = YES;
cell.layer.rasterizationScale = [UIScreen mainScreen].scale;
95
Avner Barr

Я бы предположил, что «изменчивость» происходит из распределения 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

19
preynolds

Загрузите ваши изображения, используя sendAsynchronousRequest:queue:completionHandler: NSURLConnection

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]];
}];
8
Beau Hankins

Установите флажок для подпредставлений клипа и непрозрачность в инспекторе атрибутов, а также включите подкачку.

2
A.G

У меня были проблемы с прокруткой UICollectionView.

То, что сработало (почти) как очарование для меня: я заполнил клетки пиктограммами png 90x90. Я говорю почти потому, что первая полная прокрутка не так гладко, но больше не рухнула ...

В моем случае размер ячейки составляет 90х90. 

У меня было много оригинальных размеров png раньше, и это было очень изменчиво, когда оригинальный размер png был больше чем ~ 1000x1000 (много падений при первой прокрутке).

Поэтому я выбираю 90x90 (или подобное) в UICollectionView и отображаю исходные pngs (независимо от размера). Надеюсь, что это помогает другим.

0
Paulo Souto

Если кто-то использует 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!
    })
0
NoWhereToBeSeen