0

我有一个函数可以创建一个以选择器函数为目标的按钮。按钮的地址被传递给handleSelectPhoto.

lazy var image1Button = createButton(selector: #selector(handleSelectPhoto))
func createButton(selector: Selector) -> UIButton {
    let button = UIButton(type: .system)
    button.addTarget(self, action: selector, for: .touchUpInside)
    return button
}
@objc func handleSelectPhoto(button: UIButton) {
    // Do something with button, this works
}

现在,我正在尝试将上面的类从 UIButton 更改为 UIImageView ,如下所示,

lazy var image1Button = createButton(selector: #selector(handleSelectPhoto))
func createButton(selector: Selector) -> UIImageView {
    let view = UIImageView()
    view.addGestureRecognizer(UITapGestureRecognizer(target: self, action: selector))
    view.isUserInteractionEnabled = true
    return view
}
@objc func handleSelectPhoto(button: UIImageView) {
    // HERE, button does not get passed
}

通过上述更改,在handleSelectPhoto, 按钮实例中不正确。我无法将其读取为 UIImageView 类型。

如果我使用 添加选择器函数,就选择器函数如何使用参数执行而言,addGestureRecognizer它的行为是否与使用 添加选择器函数不同?addTarget也许我不明白这个选择器功能是如何工作的......

4

2 回答 2

2

将目标添加到类似UIGestureRecognizerUIButton仅将一个参数传递给所选函数。此参数取决于您要添加目标的类型。

在您的情况下,第一个代码片段有效,因为您正在将目标添加到UIButton,因此您选择的函数会传递给这个 UIButton 实例。

在您的第二个场景中,您将目标添加到UITapGestureRecognizer,因此传递的实例将正是这个手势识别器,它不能是 type UIImageView

所以从目标参数的角度来看,和之间UIGestureRecognizerUIButton区别是没有区别的。它们都将它们的实例传递给选定的函数。

UIView子类的角度来看,区别UIGestureRecognizer不是 的子类UIView,而是的子类UIButton。这就是为什么你可以UIButton在你的第一个片段中使用传递的实例。在第二个片段中,您需要UIGestureRecognizer使用.

guard let imageView = gestureRecognizer.view as? UIImageView else { return }

#selector除了您的实际问题之外,澄清如何正确编写 s似乎很重要。你已经做对了。无需更改。有人可能会说您需要像这样添加(_:)或添加:到您的选择器中:#selector(handleSelectPhoto(_:))但事实并非如此。通常,您只需要在选择具有参数数量不同但基本名称相同的重载方法的方法时添加这些特殊字符。

于 2019-02-26T09:47:29.767 回答
1

您应该在设置选择时告诉您,您的函数将通过:在方法名称的末尾添加来接受参数。

lazy var image1Button = createButton(selector: #selector(handleSelectPhoto:))

UIKit将自动理解选择器方法参数的类型为UITapGestureRecognizer. 现在像这样重写下面的方法,你会很高兴的。

@objc func handleSelectPhoto(gesture: UITapGestureRecognizer) {
        if let buttonImageView = gesture.view as? UIImageView {
            //Here you can make changes in imageview what ever you want.
        }
}
于 2019-02-26T09:57:35.597 回答