拦截 UIScrollView 滚动
Posted
技术标签:
【中文标题】拦截 UIScrollView 滚动【英文标题】:Intercepting UIScrollView Scrolls 【发布时间】:2013-06-20 10:55:44 【问题描述】:我在 UIScrollView 中有一个 UIScrollView 和一个 UITableView。
我想拦截 UITableView 的滚动,并且仅在超级视图 (UIScrollView) 达到特定 contentOffset 时才允许滚动。
我已经创建了 UIScrollView 和 UITableView 的子类,我如何在用户仍在滚动时捕获滚动事件并拦截滚动?
我想要完成的示例: UITableView 将有一个标题,如果我向下滚动标题将折叠到原始大小的 30% 并在顶部保持可见。在我滚动回 UITableView 的顶部后,我希望标题展开。换句话说,我想使用可以折叠/展开的标题来扩展 UITableView 的滚动。
可能有更好的方法来实现这一点,我愿意接受建议。
【问题讨论】:
如何使用滚动视图委托方法scrollViewDidScroll:? 【参考方案1】:可能有更好的方法,但这个解决方案对我有用。
UITableView(我们称它为 innerScrollView)在 UIScrollView(我们称它为 scrollView)内无论主视图是什么(我们称它为 view)。 在您的视图控制器中为 innerScrollView (self.innerScrollView
) 设置一个出口。
在 XIB 或代码中设置退回:scrollView.bounces = YES
和 innerScrollView.bounces = NO
。
最初将 innerScrollView 的滚动设置为禁用。
在代码 (viewDidLoad:) 中将scrollView.contentSize.height
设置为view.frame.size.height
+ 70% 的标题要消失。调整 innerScrollView 的大小以将调整后的 contentView 填充到底部。
将您的视图控制器设置为 scrollView 的委托并实现scrollViewDidScroll:
,如下所示:
- (void)scrollViewDidScroll:(UIScrollView *)scrollView
CGFloat maxYOffset = self.scrollView.contentSize.height - self.scrollView.frame.size.height;
CGFloat minInnerYOffset = self.innerScrollView.contentInset.top;
CGFloat currentYOffset = scrollView.contentOffset.y;
CGFloat newYOffsetDelta = currentYOffset - maxYOffset;
CGFloat currentInnerYOffset = self.innerScrollView.contentOffset.y;
if (scrollView.contentOffset.y >= maxYOffset)
self.innerScrollView.scrollEnabled = YES;
self.scrollView.contentOffset = CGPointMake(0, maxYOffset);
if (currentYOffset != maxYOffset)
self.innerScrollView.contentOffset = CGPointMake(0, currentInnerYOffset + newYOffsetDelta);
else if (currentInnerYOffset > minInnerYOffset)
self.scrollView.contentOffset = CGPointMake(0, maxYOffset);
self.innerScrollView.contentOffset = CGPointMake(0, currentInnerYOffset + newYOffsetDelta);
else if (currentYOffset < scrollView.contentInset.top)
scrollView.contentOffset = CGPointMake(0, scrollView.contentInset.top);
else
self.lowerScrollView.scrollEnabled = NO;
我刚刚整理好并快速测试了它。这一切似乎都有效,但可能需要一些改进和调整。无论如何,这至少应该让你开始。
【讨论】:
【参考方案2】:嗯,你应该使用下面的 UIScrollViewDelegate 方法
- (void)scrollViewDidScroll:(UIScrollView *)scrollView
// here perform the action you need
【讨论】:
问题是当该方法被调用时视图已经被滚动,我如何禁用仅向一个方向滚动并使用该方法将其发送到超级视图?以上是关于拦截 UIScrollView 滚动的主要内容,如果未能解决你的问题,请参考以下文章
UIScrollView 不使用 RubyMotion 滚动