我正在用水龙头事件是非常时间敏感的,所以我很好奇,如果有可能使UITapGestureRecognizer激活时,用户只需触地,而不是要求他们去触摸起来呢?
Answer 1:
创建自定义TouchDownGestureRecognizer子类,并在实施的touchesBegan姿态:
TouchDownGestureRecognizer.h
#import <UIKit/UIKit.h>
@interface TouchDownGestureRecognizer : UIGestureRecognizer
@end
TouchDownGestureRecognizer.m
#import "TouchDownGestureRecognizer.h"
#import <UIKit/UIGestureRecognizerSubclass.h>
@implementation TouchDownGestureRecognizer
-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
if (self.state == UIGestureRecognizerStatePossible) {
self.state = UIGestureRecognizerStateRecognized;
}
}
-(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{
self.state = UIGestureRecognizerStateFailed;
}
-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event{
self.state = UIGestureRecognizerStateFailed;
}
@end
执行:
#import "TouchDownGestureRecognizer.h"
TouchDownGestureRecognizer *touchDown = [[TouchDownGestureRecognizer alloc] initWithTarget:self action:@selector(handleTouchDown:)];
[yourView addGestureRecognizer:touchDown];
-(void)handleTouchDown:(TouchDownGestureRecognizer *)touchDown{
NSLog(@"Down");
}
斯威夫特实现:
import UIKit
import UIKit.UIGestureRecognizerSubclass
class TouchDownGestureRecognizer: UIGestureRecognizer
{
override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent)
{
if self.state == .Possible
{
self.state = .Recognized
}
}
override func touchesMoved(touches: Set<UITouch>, withEvent event: UIEvent)
{
self.state = .Failed
}
override func touchesEnded(touches: Set<UITouch>, withEvent event: UIEvent)
{
self.state = .Failed
}
}
下面是斯威夫特语法2017年贴:
import UIKit.UIGestureRecognizerSubclass
class SingleTouchDownGestureRecognizer: UIGestureRecognizer {
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent) {
if self.state == .possible {
self.state = .recognized
}
}
override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent) {
self.state = .failed
}
override func touchesEnded(_ touches: Set<UITouch>, with event: UIEvent) {
self.state = .failed
}
}
请注意,这是一个简易替换为UITap
。 因此,在这样的代码...
func add(tap v:UIView, _ action:Selector) {
let t = UITapGestureRecognizer(target: self, action: action)
v.addGestureRecognizer(t)
}
你可以安全地交换到....
func add(hairtriggerTap v:UIView, _ action:Selector) {
let t = SingleTouchDownGestureRecognizer(target: self, action: action)
v.addGestureRecognizer(t)
}
测试表明,它不会被调用一次以上。 它可以作为一个下拉更换; 你可以在两个电话之间只是交换。
Answer 2:
使用UILongPressGestureRecognizer并设置其minimumPressDuration
0它将期间像向下触摸UIGestureRecognizerStateBegan
状态。
对于斯威夫特4
func setupTap() {
let touchDown = UILongPressGestureRecognizer(target:self, action: #selector(didTouchDown))
touchDown.minimumPressDuration = 0
view.addGestureRecognizer(touchDown)
}
@objc func didTouchDown(gesture: UILongPressGestureRecognizer) {
if gesture.state == .began {
doSomething()
}
}
对于Objective-C的
例:
-(void)setupLongPress
{
self.longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(didLongPress:)];
self.longPress.minimumPressDuration = 0;
[self.view addGestureRecognizer:self.longPress];
}
-(void)didLongPress:(UILongPressGestureRecognizer *)gesture
{
if (gesture.state == UIGestureRecognizerStateBegan){
[self doSomething];
}
}
Answer 3:
斯威夫特(没有子)
这是类似于雨燕版本罗布香菜的Objective-C的答案 。
这个想法是使用长按手势识别与minimumPressDuration
设置为零,而不是使用敲击手势识别。 这是因为长按手势识别报道触摸开始事件,而敲击手势没有。
import UIKit
class ViewController: UIViewController {
@IBOutlet weak var myView: UIView!
override func viewDidLoad() {
super.viewDidLoad()
// Add "long" press gesture recognizer
let tap = UILongPressGestureRecognizer(target: self, action: #selector(tapHandler))
tap.minimumPressDuration = 0
myView.addGestureRecognizer(tap)
}
// called by gesture recognizer
@objc func tapHandler(gesture: UITapGestureRecognizer) {
// handle touch down and touch up events separately
if gesture.state == .began {
// do something...
print("tap down")
} else if gesture.state == .ended { // optional for touch up event catching
// do something else...
print("tap up")
}
}
}
Answer 4:
这是另一种解决方案。 创建UIControl的子类。 你甚至可以在故事板使用它像UIView的,因为UIControl是UIView的子类。
class TouchHandlingView: UIControl {
}
而addTarget吧:
@IBOutlet weak var mainView: TouchHandlingView!
...
mainView.addTarget(self, action: "startAction:", forControlEvents: .TouchDown)
...
然后指定的动作将被称为像的UIButton:
func startAction(sender: AnyObject) {
print("start")
}
文章来源: UITapGestureRecognizer - make it work on touch down, not touch up?