【问题标题】:touches methods not getting called on UIView placed inside a UIScrollView触摸放置在 UIScrollView 内的 UIView 上未调用的方法
【发布时间】:2012-03-05 13:39:25
【问题描述】:

我有一个自定义滚动视图,子类化 UIScrollView。我在 viewcontroller nib 文件中添加了一个滚动视图,并将其类更改为 CustomScrollView。现在,这个自定义滚动视图(由 xib 制成)作为子视图添加到 self.view。

在这个滚动视图中,我从 xib 添加了 3 个文本字段和 1 个 UIImageView(命名为 signImageView)。单击UIImageView(添加了TapGestureRecogniser)后,自定义滚动视图上会添加一个名为signView 的UIView。我想允许用户在这个视图上签名,所以我创建了一个类 Signature.m 和 .h,子类化 UIView 并实现了触摸方法(touchesBegan、touchesMoved 和 touchesEnded),并将 signView 初始化如下:

signView = [[Signature alloc]initWithFrame:signImageView.frame];
    [customScrollView addSubview:signView];

但是当我开始在 signView 上签名时,视图会滚动,因此不会调用 touches 方法。

我尝试在 self.view 上添加 signView 而不是自定义滚动视图,但在这种情况下,当我开始滚动时,视图仍然粘在固定位置。 (在这种情况下,它的框架保持固定)

【问题讨论】:

    标签: ios uiview uiscrollview touches


    【解决方案1】:

    尝试将scrollView 中的canCancelContentTouches 设置为NO,将delaysContentTouches 设置为YES

    编辑:

    我看到Drag & sweep with Cocoa on iPhone这里回答了类似的问题(答案完全一样)。

    如果用户点击-n-按住 signView(大约 0.3-0.5 秒),则视图的 touchesBegan: 方法被触发,并且从那一刻起的所有事件都转到 signView 直到调用 touchesEnded: .

    如果用户快速扫过signView,则UIScrollView 会接管。

    由于您已经使用 touchesBegan: 方法实现了 UIView 的子类化,也许您可​​以以某种方式向用户表明您的应用已准备好让他签名('绿灯'等效)。

    您也可以使用touchesEnded: 关闭此绿灯

    如果您将signImageView 添加为signViewsubView(而不是customScrollView)并在touchesBegan: 被触发时隐藏它可能会更好)。您可以将signView 添加到customScrollview,而在现有代码中添加signImageView 的位置。

    这样你就可以实现在那个地方实际上只有一个subView(为了提高触摸传递效率。你可以通过取消隐藏signImageView来实现绿灯效果touchesBegan:/touchesEnded:

    如果此应用程序行为(0.3-0.5 秒延迟)是不可接受的,那么您还需要子类化 UIScrollView。 Vignesh 覆盖UIScrollViewtouchesShouldBegin: 的方法可能会派上用场。在那里你可能会检测到触摸是否在signView 中发生并立即将其传递给该视图。

    【讨论】:

    • 感谢 rokjarc。虽然当我尝试在视图上签名时,有时视图会滚动,但它仍然比以前我无法在视图上绘制短线的情况要好。如果你知道如何让签名变得更好,那么请建议我为实现这一目标而必须做出的改变。
    • @anshul:我现在不在 mac,所以我无法测试任何东西。我会尽快回复的
    【解决方案2】:

    当您在视图层次结构中添加滚动视图时,它会吞下所有触摸。因此您没有开始触摸。因此,要在您的登录视图中获得触摸,您必须将触摸传递给登录视图。 This 就是你的做法。

    【讨论】:

      【解决方案3】:

      我们通过UIScrollView 子类实现了这一点,该子类为您提供的视图列表禁用平移手势识别器。

      class PanGestureSelectiveScrollView: UIScrollView {
      
        var disablePanOnViews: [UIView]?
      
        override func gestureRecognizerShouldBegin(_ gestureRecognizer: UIGestureRecognizer) -> Bool {
          guard let disablePanOnViews = disablePanOnViews else {
            return super.gestureRecognizerShouldBegin(gestureRecognizer)
          }
      
          let touchPoint = gestureRecognizer.location(in: self)
          let isTouchingAnyDisablingView = disablePanOnViews.first { $0.frame.contains(touchPoint) } != nil
      
          if gestureRecognizer === panGestureRecognizer && isTouchingAnyDisablingView {
            return false
          }
          return true
        }
      }
      

      【讨论】:

        猜你喜欢
        • 2012-08-27
        • 2012-10-12
        • 2014-09-23
        • 1970-01-01
        • 2011-06-18
        • 1970-01-01
        • 2014-01-12
        • 2011-02-10
        • 2017-05-17
        相关资源
        最近更新 更多