Программная прокрутка UITableView с ускорением и замедлением

#iphone #ios #uitableview #scroll

#iPhone #iOS #uitableview #прокрутка

Вопрос:

Я пытаюсь программно прокрутить UITableView, нажав кнопку. Такой же эффект должен быть при выполнении вручную или даже немного дольше по времени прокрутки.

Сначала я попытался использовать scrollToRowAtIndexPath:atScrollPosition:animated: однако это слишком быстро и фиксировано во времени. Также у него нет ускорения и замедления.

Есть идеи, как программно прокручивать UITableView, поскольку он был прокручен вручную? Я думал отправить ему несколько пользовательских штрихов. Как вы думаете, это может сработать?

Любые идеи и помощь приветствуются! Спасибо!

Ответ №1:

UITableView является подклассом UIScrollView. Как и в UIScrollView, вы можете программно задать положение прокрутки UITableView, установив свойство contentOffset.

Вы изменяете значение этого свойства внутри блока анимации, чтобы иметь больше контроля над временем. Вам нужно будет вычислить положение точки Y. Допустим, вы хотите прокрутить до 50-й строки, это может быть высота 50 * RowHeight (при условии, что это одинаковая высота).

Например:

 CGFloat calculatedPosY = 50 * rowHeight // do you own calculation of where you'd like it.
[UIView animateWithDuration:0.2
     animations:^{theTableview.contentOffset = CGPointMake(0.0, calculatedPosY);}
     completion:^(BOOL finished){ }];
  

Есть еще один метод, который вы могли бы использовать, который также предоставляет больше возможностей

Взгляните на этот метод:

   (void)animateWithDuration:(NSTimeInterval)duration delay:(NSTimeInterval)delay options:(UIViewAnimationOptions)options animations:(void (^)(void))animations completion:(void (^)(BOOL finished))completion
  

Комментарии:

1. Спасибо! Однако я уже пробовал это. Проблема в том, что ячейки табличного представления не загружаются.

2. Звучит как проблема с чем-то другим. Возможно, после завершения анимации с параметром contentOffset вы можете запросить у tableview видимые строки с помощью метода: «indexPathsForVisibleRows». А затем вызовите reloadRowsAtIndexPaths:withRowAnimation: с этими видимыми индексными путями. Но я думаю, что здесь может возникнуть проблема более высокого уровня.

Ответ №2:

Установите свою кнопку в подвид ячейки и используйте этот код для программной прокрутки таблицы по событию касания кнопки. И если вы не устанавливаете кнопку в качестве подвида ячейки таблицы, измените этот код по мере необходимости.

   CGPoint point = [button.superview convertPoint:button.frame.origin toView:self.tableView];
  CGPoint contentOffset = self.tableView.contentOffset;
  contentOffset.y  = (point.y - contentOffset.y - self.navigationController.navigationBar.frame.size.height); // Adjust this value as you need
  [self.tableView setContentOffset:contentOffset animated:YES];
  

Ответ №3:

Что ж, это всего лишь пара «неожиданных ответов», но вы могли бы попробовать использовать этот метод (в UIScrollView , который UITableView является подклассом):

 -(void)setContentOffset:(CGPoint)contentOffset animated:(BOOL)animated
  

После того, как -(CGRect) rectForRowAtIndexPath: вы получите координаты ячейки, вы сможете анимировать местоположение ячейки. Но вместо того, чтобы вызывать его один раз, вызовите его пару раз с меньшим смещением, затем со все большими и большими смещениями, а затем снова с меньшими. Я беспокоюсь, что будет сложно сделать его гладким.

Тем не менее, если это не сработает, возможно, изменение contentOffset значения внутри UIView animateWithDuration:delay:options:animations:completion блока сработает. Возможно, если вы используете UIViewAnimationOptionCurveEaseInOut, вы можете получить желаемый эффект, просто вызвав его один раз. Если нет, запустите несколько анимаций на каждой части пути и покрывайте все большие расстояния, прежде чем замедляться.

Комментарии:

1. Спасибо! Я пробовал это. Однако содержимое TableView загружается не таким образом. Я действительно не могу поверить, что это так сложно сделать.