如何取消LongPressGestureRecognizer?

时间:2019-01-03 11:28:17

标签: ios swift uigesturerecognizer

我有一个分配了LongPressGestureRecognizer的视图,该视图调用以下方法:

@IBAction func longPressOnView1Recognized(_ sender: UIGestureRecognizer) {

    if sender.state == .began {
        // this runs when user's finger is down a "long time"
    }
    if sender.state == .ended {
        // this runs when user's finger goes up again after the .began state 
    }

}

这一切都按预期工作,但是我试图找到一种(好的/正确的)方法,可以在用户的​​手指仍不放下的情况下以编程方式cancel(在某些情况下)长按识别器。

也就是说,当 时,用户的手指仍在视图上,并且识别器已进入.began状态(但之前,用户已举起手指-在识别器进入.end状态之前)...我们是否可以运行一些代码来防止用户抬起手指时触发上述方法...就像过早地告诉IOS不再侦听UP事件这个手势的其余部分?

我已经阅读了这些docs,但是我对IOS touch的了解不多,而且似乎找不到用于此目的的任何方法。

我的GestureRecognizer.reset()似乎不符合我的描述。

我可以想到两种可能性:

1)一个布尔型标志,它将放在if sender.state == .ended {}闭包

2)这个:

myLongPressRecognizer.isEnabled = false
myLongPressRecognizer.isEnabled = true

这两项工作都不错,但看起来并不那么好。

3 个答案:

答案 0 :(得分:2)

通过禁用和重新启用手势识别器,您都很好。

myLongPressRecognizer.isEnabled = false
myLongPressRecognizer.isEnabled = true

完全正确。

我担心的是您不完全了解手势识别器。处理手势识别器时,应始终使用switch语句。检查评论:

func handleLongPressGestureRecognizer(_ sender: UIGestureRecognizer) {

    switch sender.state {
    case .began:
        // This will be called only once when the gesture starts
        print("Long press did begin at \(sender.location(in: sender.view))")
    case .changed:
        // This will be called whenever your finger moves (at some frequency obviously).
        // At this point your long press gesture is acting exactly the same as pan gesture
        print("Long press changed position to \(sender.location(in: sender.view))")
    case .ended:
        // This is when user lifts his finger assuming the gesture was not canceled
        print("Long press ended at \(sender.location(in: sender.view))")
    case .cancelled:
        // This is equally important as .ended case. You gesture may be canceled for many reasons like a system gesture overriding it. Make sure to implement logic here as well.
        print("Long press canceled at \(sender.location(in: sender.view))")
    case .failed, .possible:
        // These 2 have been added additionally at some point. Useless as far I am concerned.
        break
    }

}

因此,至少您应该处理已取消的状态。但也请注意,无论何时移动手势,都会触发更改后的状态。

答案 1 :(得分:1)

您已经有了解决方案。切换UILongPressGestureRecognizer isEnabled是最好的方法。无法设置state属性,因为它是一个只能获取的属性。

open var state: UIGestureRecognizer.State { get } // the current state of the gesture recognizer

isEnabled属性记录为:

  

默认为是。禁用的手势识别器将不会收到触摸。如果更改为“否”,则手势识别器如果当前正在识别手势,则将被取消。

答案 2 :(得分:1)

您可以导入手势识别器标题:

import UIKit.UIGestureRecognizer

这将使state属性成为可读写属性。因此,要取消手势,只需将其state更改为.cancelled

例如,您可以在长按手势识别器被识别后一秒钟取消,例如:

weak var timer: Timer?

@objc func handleLongPress(_ gesture: UILongPressGestureRecognizer) {
    switch gesture.state {
    case .began:
        print("began")
        timer?.invalidate()
        timer = Timer.scheduledTimer(withTimeInterval: 1, repeats: false) { _ in
            gesture.state = .cancelled
        }

    case .ended, .cancelled:
        print(gesture.state == .ended ? "Ended" : "Cancelled")
        timer?.invalidate()

    default:
        break
    }
}