当滚动视图子视图不在屏幕上时,手势识别器不起作用

Posted

技术标签:

【中文标题】当滚动视图子视图不在屏幕上时,手势识别器不起作用【英文标题】:Gesture recognizer not working when scrollview subview is off screen 【发布时间】:2017-02-27 16:02:11 【问题描述】:

我的视图控制器中有一个UIScrollView,其中有一个UIView(称为viewPreSeasonCard)作为内容视图,所有这些都在Interface Builder 中完成。然后我以编程方式将子视图添加到容器中,如下所示:

func displayPreSeason(preSeasons: [PreSeason]) 
    var yPos = 0
    let viewWidth = Int(viewPreSeasonCard.frame.width)
    for (index, preSeason) in preSeasons.enumerated() 
        yPos = 40 + index * 80
        let frame = CGRect(x: 0, y: yPos, width: viewWidth, height: 78)
        let preSeasonView = PreSeasonLineupView(frame: frame)
        preSeasonView.setPreSeason(preSeason: preSeason)
        preSeasonView.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(self.preSeasonClicked)))

        viewPreSeasonCard.frame.size.height += frame.height
        viewPreSeasonCard.addSubview(preSeasonView)
    

    let curSize = self.view.frame
    scrollView.contentSize = CGSize(width: curSize.width, height: curSize.height + CGFloat(yPos))

如您所见,我在添加子视图后调整scrollView.contentSize。这一切正常,我可以一直向下滚动滚动视图并查看所有子视图。

问题在于我要添加到子视图中的UITapGestureRecognizer。当子视图最初在设备屏幕上可见时(即前 3 或 4 个子视图),手势识别器正在工作。但是当我必须滚动查看子视图时,当我点击它们时,这些子视图上的手势识别器根本不会触发。好像是因为最初看不到较低的子视图,所以忽略了手势识别器。

手势识别器的方法如下:

func preSeasonClicked(_ sender: UITapGestureRecognizer) 
    if let preSeasonView = gestureRecognizer.view as? PreSeasonLineupView, let constructorId = preSeasonView.constructorId 
        presenter.preSeasonClicked(constructorId: constructorId)
    

【问题讨论】:

尝试添加preSeasonView.userInteractionEnabled = true 已经尝试过了,但没有任何效果,并且它适用于前几个视图。 @Snapper 你找到解决这个问题的方法了吗? 【参考方案1】:

我有同样的问题,我在滚动视图中有 ContentView

我发现的问题是我设置的 ContentView 其高度等于 ScrollView 父视图。我正在计算自己的 ScrollView 的 ContentSize。

所以行为是滚动视图正确滚动,但任何视图在 ViewController 的第一次显示中都处于关闭屏幕无法检测到触摸。

经过一些调试后,我尝试使 ClipToBounds 对 ContentView 是正确的。我看到了我在等待的内容,内容视图只有屏幕的高度(ScrollView 父级)

我删除了使内容视图等于滚动视图父级高度的约束。 而不是添加了新的约束来将容器视图的底部与底部大多数视图的底部对齐,并且不再计算内容大小。

目前滚动工作正常,触摸适用于所有视图。

【讨论】:

【参考方案2】:

我在内容视图中遇到了同样的问题,并且我对高度没有限制。

我最终做的是完全删除内容视图,从而解决了问题。

希望有帮助!

【讨论】:

以上是关于当滚动视图子视图不在屏幕上时,手势识别器不起作用的主要内容,如果未能解决你的问题,请参考以下文章

识别 UIView 中的滑动手势以使用手势识别器滚动滚动视图

UIButton 在子视图控制器中不起作用

如何将手势识别器添加到一系列子视图中?

当 iCarousel 包含 UITableView 作为子视图时无法滑动

当从视图启用滚动时,SWRevealViewController 平移手势不起作用

添加手势识别器 uivew 导航栏 swift 不起作用