简体   繁体   English

UIButton.addTarget 工作不正常。 似乎是一个时间问题?

[英]UIButton.addTarget not working correctly. Seems to be a timing thing?

I am creating a ViewController with 2 child views.我正在创建一个带有 2 个子视图的 ViewController。 One is for navigation buttons that is on the top of my main view, and a browser window below (WKWebView)一个用于位于主视图顶部的导航按钮,以及下方的浏览器窗口 (WKWebView)

In the main view controller's viewDidLoad function I create and add these views as subviews.在主视图控制器的 viewDidLoad 函数中,我创建并添加这些视图作为子视图。 I then create and add buttons to the navigationView.然后我创建按钮并将其添加到导航视图。 I programatically set the constraints of all the buttons to position them and size them manually.我以编程方式设置所有按钮的约束以手动定位它们并调整它们的大小。

-- Edit -- - 编辑 -

I noticed that when inspecting the button in the hierarchy, the target is set but the action is null.我注意到在检查层次结构中的按钮时,目标已设置,但操作为空。

Here is an image showing this这是一张图片,显示了这一点

However, when I check the actions on a breakpoint immediately after adding the target, it does appear to be there.但是,当我在添加目标后立即检查断点上的操作时,它似乎确实存在。

This was done on a breakpoint immediately after adding the target这是在添加目标后立即在断点上完成的


I am adding the target as follows我正在添加目标如下

btnClose!.addTarget(self, action: #selector(onCloseClicked), for:UIControlEvents.touchUpInside)

The click event does not fire.点击事件不会触发。 However if I put a breakpoint after that line, and in the console I look at the actions for the button via但是,如果我在该行之后放置一个断点,并且在控制台中,我会通过以下方式查看按钮的操作

po btnClose!.allTargets

Then it shows me the target, and then when continuing execution the button works fine.然后它向我显示目标,然后在继续执行时按钮工作正常。 I assume there's some sort of timing issue as a result but I'm not sure what the problem is.我认为结果存在某种时间问题,但我不确定问题是什么。

I'm using Swift 4.1.我正在使用 Swift 4.1。

-- Edit -- - 编辑 -

Here is all the code involved in that button: (I removed all the webview code that isn't relevant)这是该按钮中涉及的所有代码:(我删除了所有不相关的 webview 代码)

public func initialize(){ // called by viewDidLoad
    navigationView = UIView(frame:navigationRect)
    navigationView!.isOpaque = true
    navigationView!.isUserInteractionEnabled = true
    navigationView!.backgroundColor = UIColor(red: 58.0/255.0, green: 60.0/255.0, blue: 67.0/255.0, alpha: 1)
    view.addSubview(navigationView!)
    addNavigationButtons()
}
private func addNavigationButtons(){
    btnClose = UIButton()
    btnClose!.addTarget(self, action: #selector(onCloseClicked), for:UIControlEvents.touchUpInside)

    btnClose!.frame = btnRect // x:0, y:0, width:50, height:50

    btnClose?.translatesAutoresizingMaskIntoConstraints = false
    btnClose!.setImage(UIImage(named: "navigationClose", in: Bundle(identifier:"myframework"), compatibleWith:nil), for:UIControlState.normal)

    navigationView!.addSubview(btnClose!)

    addButtonConstraints()
}

private func addButtonConstraints(){
    // close
    navigationView!.addConstraint(NSLayoutConstraint(item:navigationView!, attribute: .right, relatedBy: .equal, toItem: btnClose!, attribute: .right, multiplier:1.0, constant:0))
    navigationView!.addConstraint(NSLayoutConstraint(item:navigationView!, attribute: .centerY, relatedBy: .equal, toItem: btnClose!, attribute: .centerY, multiplier:1.0, constant:0))
    btnClose!.addConstraint(NSLayoutConstraint(item:btnClose!, attribute: .width, relatedBy:.equal, toItem: nil, attribute: .notAnAttribute, multiplier: 1.0, constant:MRAIDBrowserWindow.btnWidth)) //btnWidth = 50
    btnClose!.addConstraint(NSLayoutConstraint(item:btnClose!, attribute: .height, relatedBy:.equal, toItem: nil, attribute: .notAnAttribute, multiplier: 1.0, constant:MRAIDBrowserWindow.btnHeight)) //btnHeight = 50
}

@objc public func onCloseClicked(){ // tried this without @objc
    print("this doesn't work, unless I have a breakpoint stoppage")
}

First of all I should have tell you that I am not so good at setting constraints programatically, so I cannot suggest you a reasonable suggestion to that.首先,我应该告诉您,我不太擅长以编程方式设置约束,因此我无法向您提出合理的建议。

Here is what I have done and I am sharing the working code of your own, with a few only changes...这是我所做的,我正在分享您自己的工作代码,仅进行了一些更改...

  1. I have added my own Image name, and backgroundColor to button to see some components might effecting the button我已将自己的图像名称和背景颜色添加到按钮以查看某些组件可能会影响按钮
  2. I have removed the frame which was setting up on btnClose!, because I have noticed that you do not need to tell a frame when you are telling the container for its all sides constraints.我已经删除了在 btnClose! 上设置的框架,因为我注意到当你告诉容器的所有边约束时你不需要告诉框架。

further more you should have a look on to it, down here is he code I have compiled to check -> your actions method calls fine此外,您应该查看它,下面是我编译以检查的代码->您的操作方法调用正常

import UIKit导入 UIKit

class MyTestActionViewController: UIViewController {类 MyTestActionViewController: UIViewController {

var navigationView : UIView?
var btnClose : UIButton?

override func viewDidLoad() {
    super.viewDidLoad()
    
    self.initialize()
}

public func initialize(){ // called by viewDidLoad
    navigationView = UIView(frame:CGRect(x:5, y:55, width:200, height:200))
    navigationView!.isOpaque = true
    navigationView!.isUserInteractionEnabled = true
    navigationView!.backgroundColor = UIColor(red: 58.0/255.0, green: 60.0/255.0, blue: 67.0/255.0, alpha: 1)
    view.addSubview(navigationView!)
    addNavigationButtons()
}
private func addNavigationButtons(){
    btnClose = UIButton()
    btnClose!.addTarget(self, action: #selector(onCloseClicked), for:UIControlEvents.touchUpInside)
    
    btnClose?.backgroundColor = UIColor.red
    btnClose?.translatesAutoresizingMaskIntoConstraints = false
    btnClose?.setImage(UIImage(named: "myButtonImage"), for:UIControlState.normal)
    navigationView?.addSubview(btnClose!)
    
    addButtonConstraints()
}

private func addButtonConstraints(){
    // close
    navigationView!.addConstraint(NSLayoutConstraint(item:navigationView!, attribute: .right, relatedBy: .equal, toItem: btnClose!, attribute: .right, multiplier:1.0, constant:0))
    navigationView!.addConstraint(NSLayoutConstraint(item:navigationView!, attribute: .centerY, relatedBy: .equal, toItem: btnClose!, attribute: .centerY, multiplier:1.0, constant:0))
    btnClose!.addConstraint(NSLayoutConstraint(item:btnClose!, attribute: .width, relatedBy:.equal, toItem: nil, attribute: .notAnAttribute, multiplier: 1.0, constant:50)) //btnWidth = 50
    btnClose!.addConstraint(NSLayoutConstraint(item:btnClose!, attribute: .height, relatedBy:.equal, toItem: nil, attribute: .notAnAttribute, multiplier: 1.0, constant:50)) //btnHeight = 50
}

@objc public func onCloseClicked(){ // tried this without @objc
    print("this doesn't work, unless I have a breakpoint stoppage")
}

} }

An image showing -> your button action acting properly显示图像 -> 您的按钮操作正常

在此处输入图片说明

Within method addNavigationButtons , put the following the line在方法addNavigationButtons ,添加以下行

btnClose!.addTarget(self, action: #selector(onCloseClicked), for:UIControlEvents.touchUpInside)

after

navigationView!.addSubview(btnClose!)

I think there is a restriction with the new version of swift, if a button is not in a ui view hierarchy, and you try to add a targe-action onto it, it won't actually work.我认为新版本的 swift 有一个限制,如果按钮不在 ui 视图层次结构中,并且您尝试向其添加目标操作,它实际上将不起作用。 So make sure that the button is added into a ui view hierarchy first.因此,请确保首先将按钮添加到 ui 视图层次结构中。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM