164

Do you know how to hide the 'back' button in a UINavigationController? Also, how to show it back, but I guess that's very similar to hiding it...

Just like the mail application does on the iPhone when you hit 'Edit' while viewing emails.

TheNeil
  • 3,321
  • 2
  • 27
  • 52
Zoran Simic
  • 10,293
  • 6
  • 33
  • 35

14 Answers14

329

I just found out the answer, in a controller use this:

[self.navigationItem setHidesBackButton:YES animated:YES];

And to restore it:

[self.navigationItem setHidesBackButton:NO animated:YES];

--

[UPDATE]

Swift 3.0:

self.navigationItem.setHidesBackButton(true, animated:true)
Irfan Anwar
  • 1,878
  • 17
  • 30
Zoran Simic
  • 10,293
  • 6
  • 33
  • 35
  • 20
    Also learn from my mistake: you have to call `setHidesBackButton:` BEFORE you push the navigationItem into the navigationController. – codingFriend1 Nov 16 '12 at 16:26
  • why before? what about if you want to push a viewController and then hide the back button to prevent user from going back? – user4951 Feb 26 '13 at 14:23
  • 1
    @codingFriend - I find that this also works if you put the setHidesBackButton in the viewDidAppear message handler of the view you don't want to show the backbutton on. – Anon Jul 03 '13 at 18:46
  • 2
    The best events for this are `viewWillAppear:animated` to hide and `viewWillDisappear:animated` to restore it. – Lukas Jun 11 '14 at 07:22
  • Finally something Apple haven't changed in Xcode. More than 5 years later and this answer still works great. – App Dev Guy Dec 08 '14 at 07:01
  • @pechar you even needn't restore it, if go back (pop nav stack) – HotJard Sep 27 '16 at 12:16
27

Add this Code

[self.navigationItem setHidesBackButton:YES];
visakh7
  • 26,380
  • 8
  • 55
  • 69
22

In addition to removing the back button (using the methods already recommended), don't forget the user can still 'pop' to the previous screen with a left-to-right swipe gesture in iOS 7 and later.

To disable that (when appropriate), implement the following (in viewDidLoad for example):

 if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 7.0)
     self.navigationController.interactivePopGestureRecognizer.enabled = NO;
mattv123
  • 979
  • 1
  • 9
  • 13
  • 1
    Matt - +1 for you.Thanks for adding this note. Very useful. For anyone who is wondering how the pop gesture works, simply swipe from left to right on your navigation bar to recreate what Matt is describing here. Adding the above code prevents the user from doing this on the view controller where it is included. – noobzilla Dec 18 '13 at 18:24
20

Just to clarify existing answers: the hidesBackButton property is the right answer, but it isn't clear in many answers what self refers to. Basically you should set self.navigationItem.hidesBackButton = YES in the view controller that is about to get pushed (or just got pushed) onto the UINavigationController.

In other words, say I have a UINavigationController named myNavController. I want to put a new view on it, and when I do I don't want the back button to show anymore. I could do something like:

UIViewController *newVC = [[UIViewController alloc] init];
//presumably would do some stuff here to set up the new view controller
newVC.navigationItem.hidesBackButton = YES;
[myNavController pushViewController:newVC animated:YES];

When the code finishes, the view controlled by newVC should now be showing, and no back button should be visible.

Matt
  • 1,101
  • 11
  • 11
  • Exactly what I needed as I was first doing NavigationController.NavigationItem. Thanks Matt. – Chucky Sep 13 '16 at 16:24
16

For hiding and showing the Back button conditionally you can use following code:

-(void)viewDidAppear:(BOOL)animated
{
    if ([tempAry count]==0)
    {
        [self.navigationItem setHidesBackButton:YES animated:YES];
    }
    else
    {
        [self.navigationItem setHidesBackButton:NO animated:YES];
    }
    [super viewDidAppear:animated];
} 

Note: in some cases, you have to put it in viewDidAppear method instead of viewWillAppear such cases like: when you are updating array of next class into previous class and then checking condition into next class as above.

Alex Zavatone
  • 4,106
  • 36
  • 54
Sandip Patel - SM
  • 3,346
  • 29
  • 27
11

Swift iOS (I have used following)

// hide back button
        self.navigationItem.setHidesBackButton(true, animated: false)

// pgrm mark ----- ------

    // hide the back button for this view controller

    override func setEditing(editing: Bool, animated: Bool) {
        super.setEditing(editing, animated: animated)

        self.navigationItem.setHidesBackButton(editing, animated: animated)

    }// end setEditing
Vinod Joshi
  • 7,696
  • 1
  • 50
  • 51
10

sethidesbackbutton did not work for me for some reason

I used this way ->

self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:[[UIView alloc]initWithFrame:CGRectMake(0, 0, 20, 30)]] ;
M.Othman
  • 5,132
  • 3
  • 35
  • 39
  • thanks ..I had same issue where setHidesBackButton:YES didnt worked . but this solution worked for iOS 7. – mohsinj Feb 20 '14 at 17:37
7

Always use Apple Documentation for simple issues they are more straightforward and lightweight :)

Here is the syntax for Swift 3.0:

self.navigationItem.setHidesBackButton(true, animated:true)

Reference

https://developer.apple.com/reference/uikit/uinavigationitem#//apple_ref/occ/instm/UINavigationItem/setHidesBackButton:animated:

Leena
  • 2,678
  • 1
  • 30
  • 43
Irfan Anwar
  • 1,878
  • 17
  • 30
6

In my case I had few issues with current answers:

  • inside viewDidLoad/viewWillAppear only back icon was hidden and the string "Back" was inactive but still visible
  • inside viewDidAppear the back button disappeared...but I did not want the user to see it at all

So the solution that finally have worked for me is:

- (id)initWithCoder:(NSCoder *)aDecoder {
    self = [super initWithCoder:aDecoder];

    if (self) {
        [self.navigationItem setHidesBackButton:YES animated:NO];
    }

    return self;
}
micromanc3r
  • 569
  • 1
  • 8
  • 16
3

The solution suggest by Zoran Simic didn't work for me for some reason.

This code did work however:

MyController* controller   =   [[MyController alloc]  init];
NSArray* array             =   [[[NSArray alloc] initWithObjects:controller, nil] autorelease];

[self.navigationController setViewControllers:array animated:NO];

[controller release];

Obviously you'd have to manipulate an NSArray to your taste to make it work for you. Hope that helps somebody :)

PowerAktar
  • 2,341
  • 1
  • 21
  • 17
  • Thanks for this! I was fighting a weird bug and this did the trick. Not for everyone, but useful in the right cases. – Brandon Jan 07 '14 at 20:00
1

In my UIViewController subclass I have this method:

-(void)setEditing:(BOOL)editing animated:(BOOL)animated {
    [super setEditing:editing animated: animated];

    // hide back button in edit mode
    [self.navigationItem setHidesBackButton:editing animated:YES];
}
neoneye
  • 50,398
  • 25
  • 166
  • 151
0

This hides the back button and replaces it with an add button in Swift:

override func setEditing(_ editing: Bool, animated: Bool) {
    super.setEditing(editing, animated: animated)

    // This hides the back button while in editing mode, which makes room for an add item button
    self.navigationItem.setHidesBackButton(editing, animated: animated)

    if editing {
        // This adds the add item button
        let addButton = UIBarButtonItem(barButtonSystemItem: .add, target: self, action: #selector(addTapped))
        // Use the animated setter for the left button so that add button fades in while the back button fades out
        self.navigationItem.setLeftBarButton(addButton, animated: animated)
        self.enableBackGesture(enabled: false)
    } else {
        // This removes the add item button
        self.navigationItem.setLeftBarButton(nil, animated: animated)
        self.enableBackGesture(enabled: true)
    }
}

func enableBackGesture(enabled: Bool) {
    // In addition to removing the back button and adding the add item button while in edit mode, the user can still exit to the previous screen with a left-to-right swipe gesture in iOS 7 and later. This code disables this action while in edit mode.
    if let navigationController = self.navigationController {
        if let interactivePopGestureRecognizer = navigationController.interactivePopGestureRecognizer {
            interactivePopGestureRecognizer.isEnabled = enabled
        }
    }
}
David Weiss
  • 1,842
  • 3
  • 17
  • 25
0

Swift 3.

Generally, you should use Apple's per-ViewController API as described many times already on this page, but sometimes you need immediate control of the Back button.

The following code hides the Back button and ensures that tap collision detection doesn't occur in the hidden button region.

let emptyView = UIView(frame: .zero)
self.navigationItem.leftBarButtonItem = UIBarButtonItem(customView: emptyView)
Womble
  • 4,607
  • 2
  • 31
  • 45
0

This hides the back button

let backBtn = UIBarButtonItem(title: "", style: UIBarButtonItemStyle.plain, target: navigationController, action: nil)


navigationItem.leftBarButtonItem = backBtn
Vega
  • 27,856
  • 27
  • 95
  • 103
Zeeshan
  • 51
  • 5