如何在Swift中以编程方式调用UIView上的手势轻敲

227

我有一个UIView,并且我已经为它添加了点击手势:

let tap = UITapGestureRecognizer(target: self, action: Selector("handleTap:"))
tap.delegate = self
myView.addGesture(tap)

我正试图在测试文件中以编程方式进行调用。

sendActionForEvent

我正在使用这个函数,但它不起作用:

myView.sendActionForEvent(UIEvents.touchUpDown)

出现了未识别的选择器被发送到实例。

我该如何解决这个问题?


3
在 Swift 2.2 中,你可以使用新的选择器语法:let tap = UITapGestureRecognizer(target: self, action: #selector(self.handleTap(_:)))。 - Wujo
@wujo - 感谢你的回复;奇怪的是,在 UIView 中对我并没有实际作用。或许只能在视图控制器中使用? - Fattie
2
还要记得在使用图像视图时设置 imageView.userInteractionEnabled = true。我曾经因为这个问题卡了很久。 - Josh
@Josh,是的,非常重要的一点。 - NeverHopeless
@George,你找到解决方案了吗?我和你一样有同样的问题。但我的目的是为了单元测试,在那里我想触发视图上的点击。谢谢。 - azun
1
@KhangAzun 最好的选择是直接调用tap函数。 - George
24个回答

331

您需要使用目标和操作来初始化UITapGestureRecognizer,方法如下:

let tap = UITapGestureRecognizer(target: self, action: #selector(self.handleTap(_:)))
myView.addGestureRecognizer(tap)

然后,您应该实现处理程序,每当发生轻触事件时都会调用它:

@objc func handleTap(_ sender: UITapGestureRecognizer? = nil) {
    // handling code
}

现在调用你的触摸手势识别器事件处理程序就像调用一个方法一样容易:

handleTap()

1
不直接调用选择器函数,我想通过以编程方式调用UITapGestureRecognizer事件来调用它。 - George
2
@muhasturk 不要改变已经被点赞的答案的意思。你的编辑使得该答案对于旧版本的Swift无效。如果你想为Swift 2.2发布更新,请发表自己的答案。谢谢。 - Eric Aya
23
既然您已经设置了Target和Action,那么t ap.delegate = self就不是必需的了。 - Daniel
4
在Swift3中会抛出错误,你的“handle tap”函数应该是:func handleTap(_ sender: UITapGestureRecognizer)。 - Travis M.
调用函数应该是 handleTap(_ sender: UITapGestureRecognizer? = nil),你漏掉了“_”,所以你的调用函数没有起作用。 - Prasad Patil

123

对于正在寻找 Swift 3 解决方案的任何人

let tap = UITapGestureRecognizer(target: self, action: #selector(self.handleTap(_:)))

view.addGestureRecognizer(tap)

view.isUserInteractionEnabled = true

self.view.addSubview(view)

// function which is triggered when handleTap is called
@objc func handleTap(_ sender: UITapGestureRecognizer) {
     print("Hello World")
  }

1
isUserInteractionEnabled 真的必要吗?默认值是 false 吗? - jose920405
10
еҰӮжһңжӮЁзҡ„и§ҶеӣҫжҳҜImageViewжҲ–UIVIewзҡ„д»»дҪ•еӯҗзұ»иҖҢдёҚжҳҜUIControlпјҢеҲҷview.isUserInteractionEnabled = trueжҳҜе…ій”®гҖӮ - Pankaj Kulkarni

67

对于 Swift 4

let tap = UITapGestureRecognizer(target: self, action: #selector(self.handleTap(_:)))

view.addGestureRecognizer(tap)

view.isUserInteractionEnabled = true

self.view.addSubview(view)

// function which is triggered when handleTap is called
@objc func handleTap(_ sender: UITapGestureRecognizer) {
    print("Hello World")
}
在Swift 4中,您需要明确指示触发的函数可从Objective-C调用,因此您需要将@objc添加到handleTap函数中。
请参见@Ali Beadle在此处的答案:Swift 4 add gesture: override vs @objc

当您的视图是ImageView或UIVIew的任何子类而不是UIControl时,“view.isUserInteractionEnabled = true”是关键。 - Pankaj Kulkarni

52

提醒一下 - 不要忘记在视图上启用交互功能:

let tap = UITapGestureRecognizer(target: self, action: #selector(handleTap))

view.addGestureRecognizer(tap)

// view.userInteractionEnabled = true

self.view.addSubview(view)

1
这个注释很重要! - Itai Spector

28

实现轻击手势

let tap: UITapGestureRecognizer = UITapGestureRecognizer(target: self, action: "touchHappen") 
view.userInteractionEnabled = true
view.addGestureRecognizer(tap)

识别到触摸操作后调用此函数。

func touchHappen() {
    //Causes the view (or one of its embedded text fields) to resign the first responder status.
    self.view.endEditing(true)
}

Swift 3+ 版本更新

let tap = UITapGestureRecognizer(target: self, action: #selector(self.touchHappen(_:)))
yourView.addGestureRecognizer(tap)
yourView.userInteractionEnabled = true

func touchHappen(_ sender: UITapGestureRecognizer) {
    print("Hello Dear you are here")
}

23

步骤:1

@IBOutlet var viewTap: UIView!

步骤:2

var tapGesture = UITapGestureRecognizer()

步骤:3

override func viewDidLoad() {
    super.viewDidLoad()
    // TAP Gesture
    tapGesture = UITapGestureRecognizer(target: self, action: #selector(ViewController.myviewTapped(_:)))
    tapGesture.numberOfTapsRequired = 1
    tapGesture.numberOfTouchesRequired = 1
    viewTap.addGestureRecognizer(tapGesture)
    viewTap.isUserInteractionEnabled = true
}

步骤:4

func myviewTapped(_ sender: UITapGestureRecognizer) {

    if self.viewTap.backgroundColor == UIColor.yellow {
        self.viewTap.backgroundColor = UIColor.green
    }else{
        self.viewTap.backgroundColor = UIColor.yellow
    }
}

输出

在此输入图片描述


19

Swift 5.1三个视图的示例

步骤1 -> 添加故事板视图并添加outlet视图控制器UIView

@IBOutlet var firstView: UIView!
@IBOutlet var secondView: UIView!
@IBOutlet var thirdView: UIView!

步骤:2 -> 添加storyBoard视图标签

firstView secondView thirdView

步骤:3 -> 添加手势

override func viewDidLoad() {
        super.viewDidLoad()

        firstView.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(self.tap(_:))))
        firstView.isUserInteractionEnabled = true
        secondView.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(self.tap(_:))))
        secondView.isUserInteractionEnabled = true
        thirdView.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(self.tap(_:))))
        thirdView.isUserInteractionEnabled = true
    }

步骤四 -> 选择视图

@objc func tap(_ gestureRecognizer: UITapGestureRecognizer) {
        let tag = gestureRecognizer.view?.tag
        switch tag! {
        case 1 :
            print("select first view")
        case 2 :
            print("select second view")
        case 3 :
            print("select third view")
        default:
            print("default")
        }
    }

1
你可以删除“isUserInteractionEnabled = true”这一行,并直接在属性检查器中的“标记”下方,有一个带有复选框的“用户交互启用”选项,可以设置其值。 - Xav Mac

13

Swift 4

let tap = UITapGestureRecognizer(target: self, action: #selector(self.touchTapped(_:)))
    self.view.addGestureRecognizer(tap)

@objc func touchTapped(_ sender: UITapGestureRecognizer) {
}

9

请尝试下列扩展:

extension UIView {
    
    func  addTapGesture(action : @escaping ()->Void ){
        let tap = MyTapGestureRecognizer(target: self , action: #selector(self.handleTap(_:)))
        tap.action = action
        tap.numberOfTapsRequired = 1
        
        self.addGestureRecognizer(tap)
        self.isUserInteractionEnabled = true
        
    }

    @objc func handleTap(_ sender: MyTapGestureRecognizer) {
        sender.action!()
    }
}

class MyTapGestureRecognizer: UITapGestureRecognizer {
    var action : (()->Void)? = nil
}

然后使用它:

submitBtn.addTapGesture {
     //your code
}

你甚至可以在手机上使用它。
cell.addTapGesture {
     //your code
}

3
虽然仅提供代码的答案确实是一个答案,但稍微解释一下(为什么原始问题的代码不起作用,你的代码背后的一般思想,重要点,警告等)可以使它成为一个更好的答案。 - lfurini
这绝对是对这个问题最好的答案。 - undefined

8
这是Swift 3中的工作方式:
@IBOutlet var myView: UIView!
override func viewDidLoad() {
    super.viewDidLoad()

    let tap = UITapGestureRecognizer(target: self, action:#selector(handleTap))

    myView.addGestureRecognizer(tap)
}

func handleTap() {
    print("tapped")
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接