UTapGestureRecognizer doesn't work for .began state
UTapGestureRecognizer doesn't work for .began state
I've added two gesture recognizers to my UIView
:
UIView
func tap(sender: UITapGestureRecognizer)
if sender.state == .began
print("snapping photo")
func longPress(sender: UILongPressGestureRecognizer)
if sender.state == .began
print("snapping video")
When both are set to state == .began
, only longPress
fires. When I set tap to .ended
, both fire.
state == .began
longPress
.ended
Why doesn't tap work when its state is set to .began
?
.began
1 Answer
1
UITapGestureRecognizer
is a discrete gesture, and as such, your event handler is called only once when the gesture was recognized. You don't have to check the state
at all (if your gesture recognizer was called, the gesture was recognized). Certainly you won't receive a call for the state
of .began
.
UITapGestureRecognizer
state
state
.began
UILongPressGestureRecognizer
is a continuous gesture, so checking the state is very useful (determining when the gesture began, changed, ended, etc.). That's why you see it called for the state
of .began
.
UILongPressGestureRecognizer
state
.began
For more information about discrete vs continuous gesture recognizers, please see the Handling UIKit Gestures, which says:
Gesture recognizers come in two types: discrete and continuous. A discrete gesture recognizer calls your action method exactly once after the gesture is recognized. After its initial recognition criteria are met, a continuous gesture recognizer performs calls your action method many times, notifying you whenever the information in the gesture's event changes. For example, a UIPanGestureRecognizer
object calls your action method each time the touch position changes.
UIPanGestureRecognizer
and
The state property of a gesture recognizer communicates the object’s current state of recognition. For continuous gestures, the gesture recognizer updates the value of this property from UIGestureRecognizer.State.began
to UIGestureRecognizer.State.changed
to UIGestureRecognizer.State.ended
, or to UIGestureRecognizer.State.cancelled
.
UIGestureRecognizer.State.began
UIGestureRecognizer.State.changed
UIGestureRecognizer.State.ended
UIGestureRecognizer.State.cancelled
Thanks, I had been reading the UITapGestureRecognizer doc which recommends you do check state, but your link lays out the discrete/continuous distinction more clearly.
– Nick Barr
Nov 5 '14 at 22:51
Thanks for contributing an answer to Stack Overflow!
But avoid …
To learn more, see our tips on writing great answers.
Required, but never shown
Required, but never shown
By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.
I'm guessing UITapGestureRecognizer doesn't have a began state, and I should use touchesBegan if I care, but the docs don't say anything about it: Although taps are discrete gestures, they are discrete for each state of the gesture recognizer; thus the associated action message is sent when the gesture begins and is sent for each intermediate state until (and including) the ending state of the gesture. Code that handles tap gestures should therefore test for the state of the gesture.
– Nick Barr
Nov 5 '14 at 18:04