在UIScrollView上平移对象

Vic*_*gel 5 uiscrollview uigesturerecognizer ios

我正在开发一个应用程序,其中有几个UIView对象是UIScrollView对象上的子视图.我以编程方式创建子视图,并根据关联对象的属性将它们放在滚动视图上.允许用户在滚动视图上移动这些子视图.通常这可行,但有时滚动视图抓取平移手势.

我想做的是如果触摸位置在其中一个子视图内,则禁止​​滚动视图手势识别器.

我可以通过查看滚动视图的手势识别器数组并查找UIScrollViewPanGestureRecognizer对象来找到滚动视图手势识别器.我假设只能有一个.

我的想法是让我的视图控制器成为这个手势识别器的委托,然后如果触摸位于其中一个子视图的范围内,则委托会禁止它.

这是处理这种情况的最佳方式,还是有更好的方法?

我做了类似的事情,在我对这个问题的回答中有所描述. 如何让步进和长按共存?

嗯.看起来比我预想的更难识别scrollview的UIScrollViewPanGestureRecognizer.任何关于这样做的提示将不胜感激.

我的想法不起作用.为了编码我的想法,我不得不让我的VC成为scrollview的pan手势识别器的代表.但是,当我这样做时,我收到此错误:

*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'UIScrollView's built-in pan gesture recognizer must have its scroll view as its delegate.'

这是我使用的代码.在viewDidLoad我调用了一个方法,它获得了scrollview的平移手势识别器并将self设置为委托(self.scrollViewPanGestureRecognizer只是一个存储它的属性):

self.scrollViewPanGestureRecognizer = [self.scrollView panGestureRecognizer];
self.scrollViewPanGestureRecognizer.delegate = self;
Run Code Online (Sandbox Code Playgroud)

然后我实现了这个委托方法:

-(BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch
{
   //Disable touch if touch location is in a subview.
   BOOL enableGestureRecognizer = YES;

   if (gestureRecognizer == self.scrollViewPanGestureRecognizer) {
      CGPoint touchLocation = [touch locationInView:self.scrollView];
      for (UIView *s in self.scrollView.subviews) {
         if (CGRectContainsPoint(s.frame, touchLocation)) {
            enableGestureRecognizer = NO;
         }
      }
   }
   return enableGestureRecognizer;
}
Run Code Online (Sandbox Code Playgroud)

看起来像个好主意,但看起来我不能让我的VC成为代表.

只是尝试设置scrollEnabledNO上滚动视图.这成功禁用了滚动,但它没有解决问题.视图仍然偶尔不响应手势.想到可能有些错误导致手势识别器从对象上掉下来,我让调试器显示有问题视图的手势识别器.他们还在那里.我很难过.

更新:新信息.我终于意识到没有响应的子视图是屏幕右侧的子视图.仔细测试后,似乎只在横向方向上发生这种情况,并且只有当手指位置在portraite的右边缘右侧时,即320点.显然,当旋转到风景时,某些东西不被处理.一切看似正常,但手势没有得到认可.

只是为了笑容,我决定在方法中显示帧和边界以及内容区域viewDidLayoutSubviews.我得到的是:

self.view.frame             is {{0, 0}, {480, 320}} 
self.view.bounds            is {{0, 0}, {480, 320}} 
self.scrollView.frame       is {{0, 0}, {480, 320}} 
self.scrollView.bounds      is {{0, 0}, {480, 320}}
self.scrollView.contentSize is {480, 320}
Run Code Online (Sandbox Code Playgroud)

我好像错过了什么.旋转时还需要设置什么?

Vic*_*gel 1

我找到了解决方案。我忘记了子视图没有直接放置到滚动视图中。有一个视图最初占据了滚动视图的边界,子视图放置在该滚动视图上。层次结构是这样的:

self.view
    scroll view
        UIView (fills whole scroll view)
            subview1
            subview2
            subviewn
Run Code Online (Sandbox Code Playgroud)

在我处理旋转的代码中,我没有调整放置子视图的 UIView 的大小。纠正此问题解决了问题。

我最初尝试将没有 UIView 超级视图的子视图放置在它们和滚动视图之间,但由于某种原因它不起作用。添加这个额外的层解决了这个问题,但我忘记在旋转时处理调整大小。

所以我猜手势识别器没有响应,因为虽然它们是可见的,但它们超出了超级视图的范围。