60

Here is what I used previously,

var barButtonItem = UIBarButtonItem(image: backImgs, style: UIBarButtonItemStyle.plain, target: self, action: Selector("menuButtonTapped:"))

But there is some syntax changes for Swift 3.

Zorayr
  • 23,770
  • 8
  • 136
  • 129
Bhanupriya
  • 1,202
  • 1
  • 9
  • 20

12 Answers12

119

ex:-

navigationItem.rightBarButtonItem = UIBarButtonItem(title: "Add", style: .plain, target: self, action: #selector(addTapped))
Tony Vincent
  • 13,354
  • 7
  • 49
  • 68
62

Summarize the mostly used method in Swift 3 for adding action to a barButton.

  1. Barbutton with text

    navigationItem.rightBarButtonItem = UIBarButtonItem(title: "Add", style: .plain, target: self, action: #selector(addTapped))
    
  2. BarButton with your own image

    navigationItem.rightBarButtonItem = UIBarButtonItem(image: UIImage(named:"add"), style: .plain, target: self, action: #selector(addTapped))
    
  3. BarButton with system image

    navigationItem.rightBarButtonItem = UIBarButtonItem(barButtonSystemItem: .add, target: self, action: #selector(addTapped))
    
flame3
  • 2,812
  • 1
  • 24
  • 32
38

If anyone is using customView:

barButtonItem.customView?.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(onBarButtonItemClicked)))
Onuray Sahin
  • 4,093
  • 4
  • 33
  • 34
  • 1
    This is what will work if you need to add the gesture recognizer to a bar button item when using the `customView` initializer. As far as I've found only this method signature will work (adding the gesture to the view itself/to the bar button/anything else didn't work for me). – Scott O'Toole Jan 27 '19 at 06:46
14

You just need to change your selector syntax as of from Swift 3 you need to specify the first parameter name of method in your function call so change your selector like this.

#selector(menuButtonTapped(sender:))

And your method should be like this.

func menuButtonTapped(sender: UIBarButtonItem) {

}
Nirav D
  • 71,513
  • 12
  • 161
  • 183
  • From swift 3, I have to specify first parameter, but I don't need to do this.. anyway, thanks – Bhanupriya Sep 29 '16 at 11:28
  • 2
    @Bhanupriya Yes you can but for that you need to use `_` with selector `#selector(menuButtonTapped(_:))` and also need to add `_` as first parameter to your method like `func menuButtonTapped(_ sender: UIBarButtonItem) {` either one of the option you have to use other wise it will not work. – Nirav D Sep 29 '16 at 11:37
  • @Bhanupriya Are you getting what i have tell you about selector in above comment? – Nirav D Sep 29 '16 at 11:56
  • No, I don't need to. what I need is as follows: var barButtonItem = UIBarButtonItem(image: backImgs, style: .plain, target: self, action: #selector(menuButtonTapped)) – Bhanupriya Sep 29 '16 at 12:35
  • @Bhanupriya then why you are previously try `Selector("menuButtonTapped:")` here `:` means method contain one parameter that is the reason i have given answer this way. – Nirav D Sep 29 '16 at 12:41
12

One line of code on Swift 3 for iOS 10.1:

navigationController?.navigationBar.topItem?.rightBarButtonItem = UIBarButtonItem(title: "Add", style: .plain, target: self, action: nil)
Arpit Dongre
  • 1,683
  • 19
  • 30
8
let barButtonItem = UIBarButtonItem(image: UIImage(named: "backImgs"),
                                            style: .plain,
                                            target: self,
                                            action: #selector(menuButtonTapped))

// Adding button to navigation bar (rightBarButtonItem or leftBarButtonItem)
self.navigationItem.rightBarButtonItem = barButtonItem

 // Private action
@objc fileprivate func menuButtonTapped() { // body method here }
Mihail Salari
  • 1,471
  • 16
  • 17
8

If someone is looking for a way to set the action on an existing button (Swift 5):

if let leftBarButtonItem = navigationItem.leftBarButtonItem {
    leftBarButtonItem.target = self
    leftBarButtonItem.action = #selector(onBack(_:))
}


@IBAction func onBack(_ sender: AnyObject) {
    _ = navigationController?.popViewController(animated: true)
}
ergunkocak
  • 3,334
  • 1
  • 32
  • 31
6

create an extension for barbutton item.

 extension UINavigationItem {
    func addSettingButtonOnRight(){
       let button = UIButton(type: .Custom)
       button.setTitle("setting", forState: .Normal)
       button.titleLabel?.font = UIFont.systemFontOfSize(15.0)
       button.layer.cornerRadius = 5
       button.backgroundColor = UIColor.grayColor()
       button.frame = CGRect(x: 0, y: 0, width: 100, height: 25)
       button.addTarget(self, action: #selector(gotSettingPage), forControlEvents: UIControlEvents.TouchUpInside)
       let barButton = UIBarButtonItem(customView: button)

       self.rightBarButtonItem = barButton
   }

   func gotSettingPage(){

   }
 }

And call it from viewDidLoad()

 self.navigationItem.addSettingButtonOnRight()
Tanvir Nayem
  • 702
  • 10
  • 25
6

In Swift 3, you can add UIBarButtonItem like that,

let addButton = UIBarButtonItem(image:UIImage(named:"your_icon_name"), style:.plain, target:self, action:#selector(YourControllerName.buttonAction(_:)))
addButton.tintColor = UIColor.white
self.navigationItem.rightBarButtonItem = addButton

And handle button action like that,

func buttonAction(_ sender: UIBarButtonItem) {

}

Hope it helps.

Riajur Rahman
  • 1,976
  • 19
  • 28
6

for Swift 4 add in viewDidLoad:

navigationItem.rightBarButtonItem = UIBarButtonItem(
    barButtonSystemItem: UIBarButtonSystemItem.add, 
    target: self, 
    action: #selector(addTransaction)
)
Tim Diekmann
  • 7,755
  • 11
  • 41
  • 69
pankaj nigam
  • 381
  • 1
  • 6
  • 9
4

In Swift 5

//For righter button item
let rightBtn = UIBarButtonItem(image: UIImage(named: "rightmenu"), style: .plain, target: self, action: #selector(onClickMethod))//Change your function name and image name here
self.navigationItem.rightBarButtonItem = rightBtn
//self.navigationItem.rightBarButtonItem = [rightBtn, anotherBtn] //If you want to add more buttons add like this

//For left bar button item
let leftBtn = UIBarButtonItem(image: UIImage(named: "rightmenu"), style: .plain, target: self, action: #selector(onClickMethod)) //Change your function name and image name here
self.navigationItem.leftItemsSupplementBackButton = true
self.navigationItem.leftBarButtonItem = leftBtn
//self.navigationItem.leftBarButtonItems = [leftBtn, anotherBtn] //If you want to add more buttons add like this

//This is your function name
@objc func onClickMethod() {
    print("Left bar button item")
}
Naresh
  • 16,698
  • 6
  • 112
  • 113
1

Make a UIBarButtonItem:

let rightButton: UIBarButtonItem = UIBarButtonItem(title: "Done", style: UIBarButtonItemStyle.done, target: self, action: #selector(LocationViewController.doneButtonClicked(_:)))

Add to NavigationItem:

self.navigationItem.rightBarButtonItem = rightButton

Associated function:

func doneButtonClicked(_ button:UIBarButtonItem!){    
    print("Done clicked")    
}
Alvin George
  • 14,148
  • 92
  • 64