原理:
用tableView其中一个cell 来展示一个 UIScrollView, 在scrollview上很像放置子tableView
注意点: 外层tableView需要实现手势代理
/* 若重叠tableview, 内外层的都可以滑动 */ - (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer{ if(![otherGestureRecognizer.view isKindOfClass:[UITableView class]]){ return NO; } return YES; }
如图:
关键代码:
是通过监听内外层tableView的偏移量 contentOffset, 来切换哪一个tableView可以滑动, 不可以滑动的tableView 实时设置contentOffset = CGPointZero(来达到不能滚动的目的)
监听外层tableview:
- (void)scrollViewDidScroll:(UIScrollView *)scrollView{if (scrollView == self.outTableView) { CGFloat contentOffsetY = scrollView.contentOffset.y; if (contentOffsetY == 0) { [self changeOuterTableViewScrollStatus]; } CGFloat tableViewSectionY = [self.outTableView rectForSection:_horizontalSection].origin.y; if (contentOffsetY >= tableViewSectionY) {//偏移量超过headerView时候, 则偏移量一直固定为tableViewSectionY, 来达到不能滚动 scrollView.contentOffset = CGPointMake(0, tableViewSectionY); self.canScroll = NO; [self.currentItemView setTabCanScroll:YES]; }else{ if (!self.canScroll) { scrollView.contentOffset = CGPointMake(0, tableViewSectionY); } } NSLog(@"外层%f ; tbtableViewSectionY:%f",contentOffsetY, tableViewSectionY); } }
外层监听通知, 来切换外层tableView可滚动
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(changeOuterTableViewScrollStatus) name:InnerTableViewLeaveTopNotification object:nil]; - (void)changeOuterTableViewScrollStatus{ self.canScroll = YES; //leaveTop后,每个tableview偏移量恢复 for (UITableView *tb in self.itemViews) { [tb setContentOffset:CGPointZero]; } } - (void)setCanScroll:(BOOL)canScroll{ _canScroll = canScroll; for (SFHorizontalInnerTableView *tb in self.itemViews) { [tb setTabCanScroll:!canScroll]; } }
监听内层tableView:
- (void)scrollViewDidScroll:(UIScrollView *)scrollView{ CGFloat contentOffsetY = scrollView.contentOffset.y; if (contentOffsetY != 0) { NSLog(@"内层tb偏移:%f tabCanScroll:%d",contentOffsetY , self.tabCanScroll); } //外部滚动时, 内部通过设置CGPointZero 来控制不能滚动 if (!self.tabCanScroll) { scrollView.contentOffset = CGPointZero; } if (self.tabCanScroll && contentOffsetY < 0) {//切换 self.tabCanScroll = NO; scrollView.contentOffset = CGPointZero; [[NSNotificationCenter defaultCenter] postNotificationName:InnerTableViewLeaveTopNotification object:nil]; } // scrollView.showsVerticalScrollIndicator = self.tabCanScroll; }