复制UIScrollView的scrollToTop不会在iOS 11中的UITabBar点击上展开UINavigationBar

时间:2017-12-11 19:17:46

标签: uiscrollview uitabbarcontroller uinavigationbar ios11 uitabbar

(与此问题类似,未回复:Tableview scroll to top not going all the way,以及此问题,也未得到答复:Show navigation bar's large title and search bar on scroll to top collection view iOS 11 Swift 4

我试图在状态栏点击时将滚动复制到UITableView的顶部,但是当我点击UITabBar项目并且我已经在该视图中时。我有点击部分工作,但滚动到顶部不能按我的意愿工作。

tableview嵌入在具有大标题的navigationbar中,searchbar位于标题中,因此它会随着滚动(默认行为)展开和折叠。

我正在使用以下内容滚动,按预期滚动到第一个表格视图单元格,而不是展开导航栏和/或搜索栏:

[tv scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:0 inSection:0]
          atScrollPosition:UITableViewScrollPositionTop animated:YES];

我似乎无法弄清楚如何滚动到顶部并展开导航栏和搜索栏。手动计算tableview的内容偏移量不起作用,因为当tableview滚动时tableview的偏移量明显不同。此外,我无法存储偏移量,因为不同的屏幕尺寸对于展开的navigationbarsearchbar具有不同的内容偏移。

有没有人能够解决这个问题?

2 个答案:

答案 0 :(得分:1)

嗯,我在这里的行动有点晚了但是为了将来参考:

对于iOS 10+(足够,因为11中引入了增长的navigationBars),您可以使用

scrollView.perform(NSSelectorFromString("_scrollToTopIfPossible:"), with: true)

这是私有API 。我已经搜索了几个小时并尝试了很多东西,但最终这是唯一有用的东西。请注意,WhatsApp似乎使用相同的方法。也许他们与Apple有特殊协议或隐藏api电话( cough base64 cough )。

答案 1 :(得分:0)

@implementation UIWindow (SCROLL)

- (void)performScrollToTop {

    SEL selector = NSSelectorFromString(@"_scrollToTopViewsUnderScreenPointIfNecessary:resultHandler:");

    if ([self respondsToSelector:selector] == false) {
        return;
    }

    NSMethodSignature *signature = [UIWindow instanceMethodSignatureForSelector:selector];

    if (signature == nil) {
        return;
    }

    NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:[UIWindow instanceMethodSignatureForSelector:selector]];

    [invocation setTarget:self];

    [invocation setSelector:selector];

    CGRect statusBarFrame = UIApplication.sharedApplication.statusBarFrame;

    CGPoint point = CGPointMake(statusBarFrame.size.width / 2.0, statusBarFrame.size.height + 1.0);

    [invocation setArgument:&point atIndex:2];

    [invocation invoke];
}

@end