2016-03-22 7 views
0

У меня около 14 элементов в моей коллекцииПросмотр и прокрутка не совсем гладкая. Я использую автоматический макет (мои ограничения не регистрируют ошибки), и я использую свойство cornerRadius (это приложение для обмена сообщениями).UICollectionView Прокрутка Производительность Ужасно

Я попытался проанализировать его с помощью инструмента Time Profiler, и это было то, что я вижу, когда я прокручиваю:

enter image description here

К сожалению, «Reveal в Xcode» неактивна, поэтому я не могу точно, какую линию занимает навсегда. Однако я вычисляю размер каждого элемента. Мне интересно, какова была бы огромная задержка в 9377 мс? Если я правильно помню, я не использую упорядоченные наборы.

Вот мой cellForItemAtIndexpath метод:

- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath { 

    //Define Message 
    Message *message = (Message *)[self.messages objectAtIndex:indexPath.item]; 

    //Check Message Type 
    switch (message.type) { 
     case MessageTypeText: { 

      //Initialize Cell 
      TextMessageItem *cell = (TextMessageItem *)[collectionView dequeueReusableCellWithReuseIdentifier:kTextMessageItemIdentifier forIndexPath:indexPath]; 

      //Return Cell 
      return cell; 

      break; 
     } 
    } 

    return nil; 
} 

Вот как я расчета высоты:

- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath { 

    //Retrieve the right message 
    Message *message = (Message *)[self.messages objectAtIndex:indexPath.row]; 

    //Check Message Type 
    switch (message.type) { 
     case MessageTypeText: { 

      //Create a temporary cell to get the correct size 
      TextMessageItem *tempCell = [[TextMessageItem alloc] init]; 

      //Configure the cell 
      [self collectionView:collectionView configureTextCell:tempCell atIndexPath:indexPath]; 

      CGSize s = [tempCell systemLayoutSizeFittingSize:UILayoutFittingCompressedSize withHorizontalFittingPriority:UILayoutPriorityDefaultHigh verticalFittingPriority:UILayoutPriorityDefaultLow]; 

      //Return Content Size 
      return CGSizeMake(self.collectionView.bounds.size.width, s.height); 

      break; 
     } 
    } 

    //Return 
    return CGSizeMake(0, 0); 
} 

Мой WillDisplayCell Метод:

- (void)collectionView:(UICollectionView *)collectionView willDisplayCell:(UICollectionViewCell *)cell forItemAtIndexPath:(NSIndexPath *)indexPath { 

    //Retrieve message from our array of messages 
    Message *message = (Message *)[self.messages objectAtIndex:indexPath.row]; 

    //Check Message Type 
    switch (message.type) { 
     case MessageTypeText: { 

      //Cast Cell 
      TextMessageItem *textItem = (TextMessageItem *)cell; 
      [self collectionView:collectionView configureTextCell:textItem atIndexPath:indexPath]; 

      break; 
     } 
    } 
} 

И, наконец, это мой заказ configureTextCell способ:

- (void)collectionView:(UICollectionView *)collectionView configureTextCell:(TextMessageItem *)item atIndexPath:(NSIndexPath *)indexPath { 

    //Retrieve Message 
    Message *message = (Message *)[self.messages objectAtIndex:indexPath.item]; 

    //Display Timestamp if Needed 
    [self displayTimestampForItemIfNeeded:item atIndex:indexPath.item]; 

    //Update Top Message Padding Based On Who Sent The Previous Message 
    [self updateDistanceFromPreviousMessageForItem:item atIndex:indexPath.item]; 

    //Display Delivery Status if Needed (e.g. Delivered) 
    [self displayDeliveryStatusForItemIfNeeded:item atIndex:indexPath.item]; 

    //Set Message 
    [item setMessage:message]; 
} 
+0

Может ли быть так, что мой «cellForItemAtIndexpath» не реализован правильно? Мой подкласс UICollectionViewCell выполняется программно (без файлов раскадровки или xib), и я замечаю, что при начальной загрузке его метод initWithFrame вызывается для каждого элемента в моем массиве self.messages. Это нормально? – KingPolygon

ответ

0

Использование угловых радиусов или масок слоев - хороший способ убить прокрутку, поскольку компоновка дороже. Вместо этого вы можете использовать CAShapeLayer с закругленными углами, чтобы поддержать ваш взгляд или как подуровень вашего представления. Или вы можете нарисовать свой контент с закругленными углами в изображение, которое вы добавляете к своему представлению. Вы также должны избегать просмотра клипа. (Я печатаю это на своем телефоне от своего компьютера, поэтому я не могу вставлять какие-либо фрагменты прямо сейчас.)

+0

Спасибо Мустанг. Позвольте мне попытаться внести несколько изменений, которые вы предлагаете, и посмотреть, есть ли какая-либо заметная разница. – KingPolygon

+0

Я пробовал то, что вы предлагаете, и хотя это немного помогает, оно все еще заметно отсталое. Время профайлера снизилось с 9377 до 8800 мс. Итак, реальный вопрос: что может быть за 8800 мс? Это показывает только когда я прокручиваю, а не на viewDidLoad, если это помогает сузить его. – KingPolygon

+0

Когда я получу второй, я буду более внимательно смотреть на ваш код. Еще одна вещь, которую вы никогда не хотите делать, - это ограничения изменений в время подготовкиForReuse или время dequeueReusableCellWithReuseIdentifier. Установите их во время init. – Mustang