UIScrollView inside a UITableViewCell - No didSelect call

匿名 (未验证) 提交于 2019-12-03 03:10:03

问题:

I have a tableviewCell, where the user can scroll horizontally. Since the scrollView covers nearly the whole cell, the tableView method didSelectRow gets not called if the user clicks the cell.

So I thought, I could pass the touch event of the UIScrollView to the cell, but still the didSelectRow doesnt gets called. I subclassed UIScrollView to pass the touch event only, if the touch was not a drag:

- (void) touchesEnded: (NSSet *) touches withEvent: (UIEvent *) event {     NSLog(@"touch scroll");     // If not dragging, send event to next responder     if (!self.dragging)         [self.superview touchesEnded: touches withEvent:event];     else         [super touchesEnded: touches withEvent: event]; } 

Any ideas on how to pass the click to the table, to get the delegate-methods called and keep the scrolling inside the scrollview?

回答1:

You can actually do this without subclassing UIScrollView. Whether you have a custom cell, or are setting properties in cellForRowAtIndexPath in the UITableView, you can do the following:

[cell.contentView addSubview:yourScrollView]; yourScrollView.userInteractionEnabled = NO; [cell.contentView addGestureRecognizer:yourScrollView.panGestureRecognizer]; 

The reason you can do this is because scrollView has its own panGestureRecognizer that's accessible to the programmer. So, just adding it to the cell's view will trigger the scrollview's gesture delegates.

The only drawback of this approach is that subviews of the scroll view are unable to receive any touch input. If you need this you will have to chose a different approach.



回答2:

I just encountered the same problem.
In your subclass make sure to include the full set of methods:

-(void) touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event {     if (!self.dragging)         [self.superview touchesCancelled: touches withEvent:event];     else         [super touchesCancelled: touches withEvent: event]; }  -(void) touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {     if (!self.dragging)         [self.superview touchesMoved: touches withEvent:event];     else         [super touchesMoved: touches withEvent: event]; }  -(void) touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {     if (!self.dragging)         [self.superview touchesBegan: touches withEvent:event];     else         [super touchesBegan: touches withEvent: event]; }  -(void) touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {     if (!self.dragging)         [self.superview touchesEnded: touches withEvent:event];     else         [super touchesEnded: touches withEvent: event]; } 


回答3:

try set this

_scrollView.canCancelContentTouches = NO 

also, it is bad to partially forward touch events



回答4:

The selected answer is correct, but I updated the code based on a bug I was getting.

- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {     if (self.dragging) {         [super touchesMoved:touches withEvent:event];     } else {         if ([self.delegate isKindOfClass:[UITableViewCell class]]) {             [(UITableViewCell *)self.delegate touchesCancelled:touches withEvent:event];         }          [self.superview touchesMoved:touches withEvent:event];     } } 

If your self.delegate is not the UITableViewCell, than replace that property with a property to your cell.

The cell needs to retrieve the cancel touch event during movement to prevent the undesired results. It can be easily reproducible as follows.

  • Highlight the cell (assuming the scroll view is over the whole cell, if not highlight the scroll view)
  • While the cell is highlighted, drag the table view
  • Select any other cell and now the previously highlighted cell will retrieve the didSelectCell state

Another point to mention is that order matters! If the self.delegate is not called before the self.superview then the highlighted state wont happen.



回答5:

Swift 3

scrollView.isUserInteractionEnabled = false contentView.addGestureRecognizer(scrollView.panGestureRecognizer) 


易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!