Добавить скрытый UIView в UITableView, аналогичный UIRfreshControl.

Очень похоже на UIRfreshControl, я пытаюсь поместить UIView поверх UITableView. Перетаскивание табличного представления должно открыть представление и оставить его там. Перетаскивание вверх должно снова скрыть его, а затем прокрутить представление таблицы. Когда скрытый вид таблицы должен прокручиваться нормально. Прокрутка вверх должна либо снова показать скрытый вид, либо привязаться к скрытому состоянию. В конечном итоге отображаемое представление должно содержать несколько кнопок или сегментированный элемент управления. Оно должно выглядеть и вести себя очень похоже на приложение OmniFocus.

Скрытый вид в OmniFocus Скрытый вид в OmniFocus

Открытое представление в OmniFocus Открытый вид в OmniFocus

Вот как далеко я зашел. Особенно не работает возврат к скрытому состоянию, когда прокручивается табличное представление. Если вы правильно рассчитаете время, вы застрянете в середине вида сверху, а это совсем не то, чего я хочу.

static CGFloat const kTopViewHeight = 40;

@interface ViewController ()
@property (nonatomic, weak) UIView *topView;
@property (nonatomic, assign) CGFloat dragStartY;
@end

@implementation ViewController

#pragma mark - View Lifecycle

- (void)viewDidLoad
{
    CGRect topViewFrame = CGRectMake(0.0, -kTopViewHeight, 320, kTopViewHeight);

    UIView *myView = [[UIView alloc] initWithFrame:topViewFrame];
    myView.backgroundColor = [UIColor greenColor]; // DEBUG
    self.topView = myView;
    [self.tableView addSubview:myView];
}

#pragma mark - UIScrollViewDelegate

- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView
{
    NSLog(@"scrollViewWillBeginDragging %@", NSStringFromCGPoint(scrollView.contentOffset));
    self.dragStartY = scrollView.contentOffset.y;
}

- (void)scrollViewDidScroll:(UIScrollView *)scrollView
{
    NSLog(@"scrollViewDidScroll %@", NSStringFromCGPoint(scrollView.contentOffset));
    if (scrollView.contentOffset.y > 0) {
        // reset the inset
        scrollView.contentInset = UIEdgeInsetsZero;
    } else if (scrollView.contentOffset.y >= -kTopViewHeight) {
        // set the inset for the section headers
        scrollView.contentInset = UIEdgeInsetsMake(-scrollView.contentOffset.y, 0, 0, 0);
    } else if (scrollView.contentOffset.y < -kTopViewHeight) {
        // don't scroll further when the topView's height is reached
        scrollView.contentInset = UIEdgeInsetsMake(-kTopViewHeight, 0, 0, 0);
        scrollView.contentOffset = CGPointMake(0, -kTopViewHeight);
    }
}

- (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate
{
    NSLog(@"scrollViewDidEndDragging %@", NSStringFromCGPoint(scrollView.contentOffset));
    CGFloat yOffset = scrollView.contentOffset.y;

    if (yOffset < 0) {
        BOOL dragDown = self.dragStartY > yOffset;
        CGFloat dragThreshold = 10;

        if (dragDown) {
            if (yOffset <= -dragThreshold) {
                [self snapDown:YES scrollView:scrollView];
            } else {
                [self snapDown:NO scrollView:scrollView];
            }
        } else if (!dragDown) {
            if (yOffset >= dragThreshold - kTopViewHeight) {
                [self snapDown:NO scrollView:scrollView];
            } else {
                [self snapDown:YES scrollView:scrollView];
            }
        }
    }
}

- (void)snapDown:(BOOL)down scrollView:(UIScrollView *)scrollView
{
    [UIView animateWithDuration:0.3
                          delay:0
                        options:UIViewAnimationOptionAllowUserInteraction|UIViewAnimationOptionCurveEaseOut|UIViewAnimationOptionBeginFromCurrentState
                     animations:^{
                         if (down) {
                             // snap down
                             scrollView.contentOffset = CGPointMake(0, -kTopViewHeight);
                             scrollView.contentInset = UIEdgeInsetsMake(kTopViewHeight, 0, 0, 0);
                         } else {
                             // snap up
                             scrollView.contentOffset = CGPointMake(0, 0);
                             scrollView.contentInset = UIEdgeInsetsZero;
                         }
                     }
                     completion:nil];
}

person Simon    schedule 13.10.2014    source источник


Ответы (1)


person    schedule
comment
Возможно, я не совсем ясно выразился, но я НЕ собираюсь заменять UIRefreshControl и мне не нужны какие-либо функции обновления. Это должно быть просто статическое представление с UISegmentedControl, которое выглядит как UIRefreshControl с точки зрения того, что оно находится поверх UITableView и раскрывается при панорамировании вниз. - person Simon; 17.10.2014