Ios 在UIScrollView和UIView'上检测触摸事件;s组件[放置在UIScrollView中]

Ios 在UIScrollView和UIView'上检测触摸事件;s组件[放置在UIScrollView中],ios,uiscrollview,uitapgesturerecognizer,Ios,Uiscrollview,Uitapgesturerecognizer,我在我的简单故事板IPad项目中有UIViewController,其中包含放置在整个表面上的UIScrollView(1024 x 768)。我已经创建了3个XIB文件,它们是我的应用程序在viewDidLoad中启动时加载的UIVIEW,并将它们添加到UIScrollView中。这3个XIB文件中的每个文件只包含一个UIButton 这是层次结构: ~UIViewController(UIViewControllerClass是用于此的类 UIViewController) ~~UIScro

我在我的简单故事板IPad项目中有UIViewController,其中包含放置在整个表面上的UIScrollView(1024 x 768)。我已经创建了3个XIB文件,它们是我的应用程序在viewDidLoad中启动时加载的UIVIEW,并将它们添加到UIScrollView中。这3个XIB文件中的每个文件只包含一个UIButton

这是层次结构:

~UIViewController(UIViewControllerClass是用于此的类 UIViewController)

~~UIScrollView(包含3个相同的UIView)

~~~UIView(UIViewClass是此XIB文件的文件所有者)

~~~~~~按钮

我希望我的UIViewControllerClass能够同时感知这两种情况:触摸UIScrollView组件上的任意位置,如果触摸了UIScrollView,如果触摸了UIScrollView中UIView内部的UIButton,那么就可以获得触摸该按钮的确切信息

我在UIViewClass中为触摸UIScrollView中UIView中的UIButton而进行了iAction,当我在所有元素(UIViewController、UIView和UIScrollView)上设置用户交互启用=是时,此方法按其应该的方式调用

但此时,我的UIViewControllerClass并没有意识到在UIScrollView中的UIButton上发生了触摸。我制作了如下触摸识别器:

UITapGestureRecognizer *touch = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(handleTouch)];
touch.numberOfTouchesRequired = 1;
并将其添加到UIScrollView组件。通过这种方式,我能够在UIViewControllerClass中的UIScrollView组件上检测到触摸事件,但不再调用UIView中UIButton的触摸事件处理程序,它位于UIScrollView中

因此,我需要在UIViewControllerClass中提供这两个信息:

  • 触摸UIScrollView组件
  • 触摸UIView中的UIView按钮,该按钮位于UIScrollView内(如果触摸此按钮)
我认为将触摸事件识别器附加到整个UIScrollView组件不是解决方案,因为它禁用了我在UIViewClass中编写的所有触摸事件处理程序

我认为解决方案是,在UIScrollView内部的UIView组件上进行的某种触摸应该发送到UIViewControllerClass,但我并没有找到一种方法来做到这一点

如果有人能帮助我,我将非常感激。提前谢谢


[编辑#1:郑的回答]

点击手势必须将取消触摸视图选项设置为否

对于我上面的例子,这一行解决了所有问题:

touch.cancelsTouchesInView = NO;

非常感谢Zheng。

您可以对UIScrollView进行子类化,并覆盖方法
-hitTest:withEvent:
,该方法由系统调用,以确定哪个视图将处理事件。无论何时调用它,您都可以假设在scroll视图中发生了触摸事件,通过调用super实现,您可以获得通常会处理该事件的视图。

我不知道这是否适用于您,但我在这里给出了scrollview中视图的触摸事件的答案:

这样做的目的是告诉scrollView不要吞下scroll view区域内的所有点击手势

我将把代码粘贴到这里,希望它能解决您的问题:

UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(hideKeyboard)];

// prevents the scroll view from swallowing up the touch event of child buttons
tapGesture.cancelsTouchesInView = NO;    

[pageScrollView addGestureRecognizer:tapGesture];

[tapGesture release];

...

// method to hide keyboard when user taps on a scrollview
-(void)hideKeyboard
{
    [myTextFieldInScrollView resignFirstResponder];
}

您可以在UIscrollView中捕获任何类型的手势。确保还处理一些默认属性,如将cancelsTouchesInView属性设置为false,默认情况下为true。同时为子视图提供一些标记号,以便在选择器中进行区分也使他们的用户交互成为现实

让点击=UITapGestureRecognitor(目标:自我,操作:

选择器(didTapByUser(:))


非常感谢您的回答,但我检查了我的问题的答案,当时张也回答了我,我尝试了他的解决方案,这对我很有效。再次感谢!非常感谢你!您的这个问题与我的问题无关,但它包含了一条对我来说非常重要的行,我不知道UITapGestureRecognizer有一个选项—cancelsTouchesInView。我不知道默认情况下该选项设置为“是”,现在当我将其设置为“否”时,我能够在UIScrollView上检测触摸,并且如果在UIScrollView中触摸的元素具有触摸处理程序,则也会调用该处理程序。再次感谢你,你用那句话解决了我的问题。