UIScrollView中的UITableView在滚动后没有收到第一次点击 [英] UITableView inside UIScrollView not receiving first tap after scrollling

查看:100
本文介绍了UIScrollView中的UITableView在滚动后没有收到第一次点击的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在 UIScrollView <中遇到 UITableView 的问题/ code>。当我滚动外部 scrollView 时,没有收到 willSelect / didSelect 第一次触摸事件,但第二次触摸事件。更奇怪的是,即使委托没有,单元格本身也能获得触摸和突出显示的状态。

I am having an issue with a UITableView inside a UIScrollView. When I scroll the external scrollView, the table does not receive the willSelect/didSelect event on the first touch, but it does on the second one. What is even more strange, the cell itself gets the touches and the highlighted state, even when the delegate does not.

我的视图层次结构:

UIView
  - UIScrollView  (outerscroll)
      - Some other views and buttons
      - UITableView (tableView)

在滚动视图中,我有一些额外的视图可以动态扩展/关闭。表格视图需要与视图中的其他元素一起固定在顶部,这就是我创建此布局的原因,这使我可以通过使用转换以类似于Apple推荐的方式轻松移动元素。滚动发生。

Inside the scroll view I have some extra views that get expanded/closed dynamically. The table view needs to get "fixed" on top, together with some other elements of the view, so that is why I created this layout, that allows me to easily move elements in a similar way than Apple recommends by the use of transformations when the scroll happens.

当outerscroll像这样移动时,表格视图将转换为平移效果:

The table View is transformed with a translation effect when the outerscroll moves like this:

- (void)scrollViewDidScroll:(UIScrollView *)scrollView {
    if (scrollView == self.outerScrollView) {

        CGFloat tableOffset = scrollView.contentOffset.y - self.fixedHeaderFrame.origin.y;
        if (tableOffset > 0) {
            self.tableView.contentOffset = CGPointMake(0, tableOffset);
            self.tableView.transform = CGAffineTransformMakeTranslation(0, tableOffset);
        }
        else {
            self.tableView.contentOffset = CGPointMake(0, 0);
            self.tableView.transform = CGAffineTransformIdentity;
        }

        // Other similar transformations are done here, but not involving the table

}

在我的单元格中,如果我实现这些方法:

In my cell, if I implement these methods:

- (void)setSelected:(BOOL)selected {
    [super setSelected:selected];
    if (selected) {
        NSLog(@"selected");
    }
}

- (void)setHighlighted:(BOOL)highlighted animated:(BOOL)animated
{
    [super setHighlighted:highlighted animated:animated];
    if (highlighted) {
        NSLog(@"highlighted");
    }
}

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
    [super touchesBegan:touches withEvent:event];
    NSLog(@"touchesBegan");
}

- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
    [super touchesEnded:touches withEvent:event];
    NSLog(@"touchesEnded");
}

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event {
    [super touchesCancelled:touches withEvent:event];
    NSLog(@"touchesCancelled");
}

Y失败时可以看到此输出(第一次点击):

Y can see this output when fails (first tap):

2014-02-10 13:04:40.940 MyOrderApp[5588:70b] highlighted 
2014-02-10 13:04:40.940 MyOrderApp[5588:70b] touchesBegan 
2014-02-10 13:04:40.978 MyOrderApp[5588:70b] touchesEnded

当这个工作时(第二次点击):

And this one when works (second tap):

2014-02-10 13:05:30.359 MyOrderApp[5588:70b] highlighted 
2014-02-10 13:05:30.360 MyOrderApp[5588:70b] touchesBegan 
2014-02-10 13:05:30.487 MyOrderApp[5588:70b] touchesEnded 
2014-02-10 13:05:30.498 MyOrderApp[5588:70b] expanded

在第一次和第二次点击之间不进行任何其他帧更改,动画或任何其他视图交互。此外,只有当滚动大量时才会出现错误,但只有几个像素的滚动,一切都按预期工作。

No other frame change, animation or any other view interaction is done between the first and the second tap. Also, only when scrolling large amounts the bug appears, but with scrollings of just a few pixels everything keeps working as expected.

我也尝试改变一些属性,但是没有运气。我做的一些事情:

I experimented changing some properties as well, but with no luck. Some of the things I did:


  • 从滚动以外的视图中删除 userInteractionEnabled 和表

  • 在表格上添加对 setNeedsLayout 的调用,在 scrollViewDidScroll 发生。

  • 从表中删除转换(仍然发生)

  • Remove userInteractionEnabled from views other than the scroll and table
  • Add a call to setNeedsLayout on the table, scroll and main view when scrollViewDidScroll occurs.
  • Remove the transformations from the table (still happens)

我已经看到一些关于在 UIScrollViews 中嵌入 UITableViews 的意外行为的评论,但我看不到这样的警告Apple的官方文档,所以我希望它能够正常运行。

I have seen some comments about the unexpected behaviour of embedding UITableViews inside UIScrollViews but I can not see such a warn in the official documentation by Apple, so I am expecting it to work.

该应用仅限iOS7 +。

The app is iOS7+ only.

有没有人遇到类似问题?为什么会这样,我该如何解决??我认为我可以截取单元格上的点击手势,并通过自定义委托或类似方式传递,但我希望表格能够接收正确的事件,所以我的 UITableViewDelegate 按预期收到。

Has anyone experienced similar issues? Why is this and how can I solve it? I think that I could be able to intercept the tap gesture on the cell and pass it with a custom delegate or similar, but I would like the table to receive the proper events and so my UITableViewDelegate receives it as expected.


  • 我尝试按照评论中的建议禁用单元格重用,但它仍然以相同的方式发生。

推荐答案

Apple文档中,你不应该'在 UIScrollView 中嵌入 UITableView

From Apple Documentation, you shouldn't embed a UITableViewinside a UIScrollView.


重要提示:您不应在
UIScrollView对象中嵌入UIWebView或UITableView对象。如果你这样做,意外的行为可能导致
,因为两个对象的触摸事件可能混淆而且错误地处理

Important: You should not embed UIWebView or UITableView objects in UIScrollView objects. If you do so, unexpected behavior can result because touch events for the two objects can be mixed up and wrongly handled.

你的问题与 UIScrollView 的问题有关。

Your problem is really related to what your UIScrollView does.

但如果只是为了隐藏在需要时(就我的情况而言),你可以在超级视图中移动 UITableView

But if it's just to hide the tableview when needed (that was my case), you can just move the UITableView in its superview.

I在这里写了一个小例子: https://github.com/rvirin/SoundCloud/

I wrote a small example here : https://github.com/rvirin/SoundCloud/

这篇关于UIScrollView中的UITableView在滚动后没有收到第一次点击的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆