SWIFT-UIBarButtonItem未调用操作



我的NavAction有问题,项目按钮在触摸后没有调用定义的操作。我在viewDidload函数之外定义了UIBarButtonItem:

let uploadButton = UIBarButtonItem(title: "UPLOAD", style: .plain, target: self, action: #selector(uploadHandler)) 

然后我将其添加到NavBar中(在viewDidLoad((中(:

self.navigationItem.setRightBarButton(uploadButton, animated: true)
self.navigationItem.rightBarButtonItem!.setTitleTextAttributes([.font : UIFont.systemFont(ofSize: 14, weight: .heavy), .foregroundColor : UIColor.label], for: .normal)

如果我点击按钮,什么都没有发生,就不会调用操作,但如果我点击textView或textField并开始键入,之后如果我点击该按钮,就会调用操作。我曾试图让FirstResponder辞职,认为这是问题所在,但无济于事。有什么想法吗?提前Thanx。

问题是uploadButton初始化太早,即在视图控制器ifself初始化期间。此时,self还没有准备好使用。

有几种方法可以解决这个问题。

  1. 初始化viewDidLoad中的按钮:
class MyViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
let uploadButton = UIBarButtonItem(title: "UPLOAD", style: .plain, target: self, action: #selector(uploadHandler)) 
self.navigationItem.setRightBarButton(uploadButton, animated: false)
}
...
}
  1. 如果类中的某些其他方法需要访问它,请通过创建一个隐式展开的存储属性并在viewDidLoad中设置它来稍微修改上面的代码:
class MyViewController: UIViewController {
private var uploadButton: UIBarButtonItem!
override func viewDidLoad() {
super.viewDidLoad()
uploadButton = UIBarButtonItem(title: "UPLOAD", style: .plain, target: self, action: #selector(uploadHandler)) 
self.navigationItem.setRightBarButton(uploadButton, animated: false)
}
...
}
  1. 将按钮的初始化设为惰性,这样在第一次访问时就会对其进行初始化,即在viewDidLoad中:
class MyViewController: UIViewController {
private lazy var uploadButton = UIBarButtonItem(title: "UPLOAD", style: .plain, target: self, action: #selector(uploadHandler)) 
override func viewDidLoad() {
super.viewDidLoad()
self.navigationItem.setRightBarButton(uploadButton, animated: false)
}
...
}
  1. 初始化不带操作和选择器的按钮,稍后将它们添加到viewDidLoad中:
class MyViewController: UIViewController {
private let uploadButton = UIBarButtonItem(title: "UPLOAD", style: .plain, target: nil, action: nil) 
override func viewDidLoad() {
super.viewDidLoad()
uploadButton.target = self
uploadButton.action = #selector(uploadHandler)
self.navigationItem.setRightBarButton(uploadButton, animated: false)
}
...
}

所有这些选项之间几乎没有区别,所以无论你选择哪一个都应该没问题。

几个旁注:

  • 在我的示例中,我将uploadButton声明为私有,以表明它不是视图控制器的公共API的一部分。如果您需要在视图控制器之外访问此按钮,只需移除private修改器即可
  • viewDidLoad中没有执行动画,因为您的视图还没有在屏幕上,所以调用setRightBarButton(uploadButton, animated: true)不会触发动画,因此我用false替换了true。如果希望用户看到动画,请在viewDidAppear中调用它

最新更新