如何在自定义的UIView(XIB)中以编程方式添加手势识别器?

4

简介

我正在尝试将一个点击手势识别器添加到我自定义的UIViewCardView的实例中。因此,我创建了一个自定义视图xib并通过File's Owner链接我的Swift类文件CardView.swift。然后,我连接每个输出口到相应的UI元素。

我想在代码中将我的自定义视图CardView添加到我的ViewController,并将一个tap手势附加到新创建的视图上。

CardView类:

class CardView: UIView {

    // Delcare outlets
    @IBOutlet var view: UIView!
    @IBOutlet weak var title: UILabel!
    @IBOutlet weak var icon: UIImageView!


    //MARK: Initialization
    override init(frame: CGRect) {
        super.init(frame: frame)

        Bundle.main.loadNibNamed("CardView", owner: self, options: nil)
        addSubview(view)
    }

    required init(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)!
    }

}

视图控制器类

在 ViewController.swift 文件的 viewDidLoad() 函数中,我创建了一个 CardView() 的实例:

override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.

        let cardView = CardView()
        self.view.addSubview(cardView)

        // Style cardView instance
        cardView.view.backgroundColor = UIColor.yellow
        cardView.view.center.x = self.view.center.x
        cardView.view.center.y = self.view.center.y

        let tapGesture = UITapGestureRecognizer(target: self, action: #selector(handleTap(gestureRecognizer:)))
        cardView.addGestureRecognizer(tapGesture)

    }

然后我像平常一样使用Swift将tapGesture添加到我的cardView中:

let tapGesture = UIPanGestureRecognizer(target: self, action: #selector(handleTap(gestureRecognizer:)))    cardView.addGestureRecognizer(panGesture)

并添加相应的函数进行调用:

func handleTap(gestureRecognizer: UIGestureRecognizer) {
        let alert = UIAlertController(title: "Alert", message: "Message", preferredStyle: UIAlertControllerStyle.alert)
        alert.addAction(UIAlertAction(title: "Click", style: UIAlertActionStyle.default, handler: nil))
        self.present(alert, animated: true, completion: nil)
    }

主要问题/难题

我在为新创建的 CardView 添加 Tap 手势识别器时遇到了一个问题 - 即无法调用 handleTap() 函数。

我已经尝试了多种方法,例如将 cardView.isUserInteractionEnabled = true 添加到两个文件(ViewController.swiftCardView.swift 类)中。也尝试只在其中一个文件中添加而不是两个都添加。

在声明手势类型后,我还尝试将它添加到我的超级视图中,即与 ViewController.swift 文件相关联的视图。当我点击屏幕时,函数将被触发,但不会在我自己创建的自定义 UIView 上触发。

除此之外,我还尝试将 UIGestureRecognizerDelegate 添加到我的 VC 类中,但没有结果。

class ViewController: UIViewController, UIGestureRecognizerDelegate {}

在我的 viewDidLoad() 函数中,在将手势连接到我的 cardView 之前,我添加了这一行额外的代码:tapGesture.delegate = self

let tapGesture = UITapGestureRecognizer(target: self, action: #selector(handleTap(gestureRecognizer:)))
tapGesture.delegate = self
architectView.addGestureRecognizer(tapGesture)

尝试将卡片视图置于最前面。 - badhanganesh
我已经简化了我的代码。拖动后仍然没有消息。请查看我上面更新的问题。 - Caspert
你正在为第一张卡片添加手势,而在它上面可能还有许多其他的卡片。那么第一张卡片如何检测手势呢?因此,将其移动到前面或在循环内为每个卡片添加手势并使用gesture.view检测每个卡片。 - Deepak Kumar
@DeepakKumar 我修改了代码,所以现在只有一张卡片。但是 panGesture 还是没有起作用.. - Caspert
你终于成功了吗? - Sylphos
你解决了吗? - Alganadi Mhd Hasan
2个回答

0

我遇到了与自定义UIView相关的问题。

我创建了Xibswift文件并将其连接起来。 然后为UIView添加手势,但它不起作用。 我将UIView更改为UIButton以解决问题,但仍然无效。

解决我的问题是

自动布局问题

当我运行应用程序并通过Debug view hierarchy进行调试时,我的customUIView存在歧义问题。

通过打印UIView的描述,我可以发现它具有frame(0,0),而子视图则具有自己的frame。

因此,我删除并重新创建,每次运行测试并解决问题。 当单击自定义UIView时,手势函数也会起作用。

我希望这对你有用。我看了你的代码,似乎没有问题,所以请检查xib文件和自动布局那些标签和图像。


-1

UIPanGestureRecognizer(target: self, action: #selector(dragged)) 更正为:

UIPanGestureRecognizer(target: self, action: #selector(dragged(sender:)))

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