如何更改导航栏上“后退”按钮的标题


224

当前,左栏按钮的默认值是加载当前视图的视图的标题,换句话说,当按下按钮时将显示的视图(后退按钮)。

我想将按钮上显示的文本更改为其他内容。

我尝试将以下代码行放入视图控制器的viewDidLoad方法中,但似乎不起作用。

self.navigationItem.leftBarButtonItem.title = @"Log Out";

我该怎么办?

谢谢。

Answers:


345

这应该放在调用ViewController的名为“ NewTitle”的方法中。就在push或popViewController语句之前。

UIBarButtonItem *newBackButton = 
        [[UIBarButtonItem alloc] initWithTitle:@"NewTitle" 
                                         style:UIBarButtonItemStyleBordered 
                                        target:nil 
                                        action:nil];
[[self navigationItem] setBackBarButtonItem:newBackButton];
[newBackButton release];

47
在子视图控制器中时,无法从子视图控制器中调用它。您必须在子视图控制器中从父视图控制器调用此函数。
亚历克斯·雷诺兹

2
要更改我的第三级视图控制器的后退按钮(第二次按下),我必须使用以下行代替上面的答案:[[self.parentViewController navigationItem] setBackBarButtonItem:newBackButton]; 难道我做错了什么?
JonB

4
Jordan表示,他“ [添加]了些什么地方,将代码放到了哪里。” 更加清晰:将它放在第一个(又称父)控制器中,紧接在调用第二个(又称子级)控制器的调用之前。
benvolioT 2011年

1
您可以创建自定义BaseViewController并将其放入-viewDidLoad:
ArtFeel 2013年

2
您无需在推入或弹出前立即执行此操作。您可以在viewDidLoad或loadView中执行此操作,也可以在其他任何位置为此视图设置标题和其他属性。维克多·博格丹(Victor Bogdan)在下面的回答更加清楚,恕我直言。
Joe Strout

98

在ChildVC中,这对我有用...

self.navigationController.navigationBar.topItem.title = @"Back";

也可以在Swift中使用!

self.navigationController!.navigationBar.topItem!.title = "Back"

4
在iOS 7上的Xcode 5.0.2中进行了测试和验证。但是,当您返回到前一个屏幕时,它将把前一个屏幕的标题更改为Back。
Alex Zavatone 2014年

最简单的解决方案。在iOS 6和iOS 7上均可使用。放入基本的UIViewController中并完成操作。比IB解决方案或在vc中进行设置要好得多。
Eric Chen

46
它更改了先前视图控制器的标题,这就是此解决方案中的问题
Nikita 2014年

2
@Nikita,您可以在viewWillDisappear瓷砖背面
丹蟠龙

81

这是backBarButtonItem的文档:

“当此导航项目位于堆栈顶部项目的紧下方时,导航控制器将从该导航项目派生导航栏的后退按钮。[...]如果要为后退按钮指定自定义图像或标题,您可以将自定义栏按钮项(带有您的自定义标题或图像)分配给该属性。”

视图控制器A“父”视图控制器):

self.title = @"Really Long Title";
UIBarButtonItem *backButton = [[UIBarButtonItem alloc] initWithTitle:@"Short" style:UIBarButtonItemStyleBordered target:nil action:nil];
self.navigationItem.backBarButtonItem = backButton;

当任何其他视图控制器B在导航堆栈的顶部,并且A在其正下方时,B的后退按钮将具有标题“ Short”


4
棘手的部分是您需要在PARENT视图控制器中设置后退按钮,而不是在子视图中。只是花了一个小时才弄明白了。
Merkurial

56

在使用情节提要的Xcode 4.5中,到目前为止,当不必动态更改“后退”按钮的值时,我发现的最简单的解决方案是使用与“视图控制器”的导航项相关联的““后退按钮””字段希望“返回”按钮说些其他话。

例如,在下面的屏幕截图中,我希望我按下的视图控制器的“后退”按钮具有“后退”作为“后退”按钮的标题。

在此处输入图片说明

当然,如果您每次都需要后退按钮说一些稍有不同的内容,那么这将是行不通的……这里有所有其他解决方案。


最初的问题没有说明使用情节提要,因此,这不是公认的答案,这当然很好,但是针对基于情节提要的开发,请选择正确的解决方案。
villapossu

42

我知道,这个问题很老,但是我找到了一个不错的解决方案。

UIBarButtonItem *barButton = [[UIBarButtonItem alloc] init];
barButton.title = @"Custom Title";
self.navigationController.navigationBar.topItem.backBarButtonItem = barButton;

从childView作品!经过iOS 7测试。


这似乎只能起到一个作用。对于我的孩子来说,这对孩子不起作用。iOS 8
narco

26

也许我过于简单化了,但是从Apple的文档中,措辞是:

如果两个视图控制器中的任何一个都未指定自定义栏按钮项,则使用默认的后退按钮,其标题设置为上一个视图控制器的title属性的值,即,视图控制器向下一级堆栈。

上面标记为正确的解决方案设置了父控制器的默认按钮项。这是正确的答案,但我通过self.title在将新控制器推入NavigationController堆栈之前更改UIViewController的属性来解决此问题。

这将自动更新下一个控制器上的后退按钮的标题,并且只要您将其设置self.title回原样,viewWillAppear我就不会看到此方法引起太多问题。


19

这对我来说更好。尝试:

 self.navigationController.navigationBar.topItem.backBarButtonItem = [[UIBarButtonItem alloc] 
initWithTitle:@"Back" style:UIBarButtonItemStylePlain target:nil action:nil];

19

在Swift / iOS8中,以下对我有用:

let backButton = UIBarButtonItem(
      title: "Back Button Text",
      style: UIBarButtonItemStyle.Bordered,
      target: nil,
      action: nil
);

self.navigationController.navigationBar.topItem.backBarButtonItem = backButton;

从费利佩的答案移植。


迅捷的1.1语法是self.navigationController?.navigationBar.topItem?.backBarButtonItem
沃伦·伯顿

3
样式应为UIBarButtonItemStyle.Plain
Micro

2
谢谢你 这是一个多么可悲的API。并代表一般的UIKit。在iOS的导航栏和状态栏之间,我们仍然为这个该死的平台开发了一个奇迹。感谢婴儿耶稣堆栈溢出及其贡献者!
Womble

@Wobmle:您应该为Android开发几个月;)
fl034

17

好的,这就是方法。如果您有一个“第一”的视图控制器,并且通过按一个按钮等导航另一个“第二”的视图控制器,则需要做一些工作。首先,您需要在“第二个”视图控制器的ViewDidLoad方法中创建一个BarButtonItem,如下所示:

    UIBarButtonItem *btnBack = [[UIBarButtonItem alloc]
                                   initWithTitle:@"Back" 
                                   style:UIBarButtonItemStyleBordered
                                   target:self
                                   action:@selector(OnClick_btnBack:)];
    self.navigationItem.leftBarButtonItem = btnBack;
    [btnBack release];

完成之后,您需要像这样在同一.m文件中编写“ btnBack”操作的代码;

-(IBAction)OnClick_btnBack:(id)sender  {
      [self.navigationController popViewControllerAnimated:YES];
    //[self.navigationController pushViewController:self.navigationController.parentViewController animated:YES];
}

就这样。


2
一个leftBarButtonItem不具备的外观backBarButtonItem,如果是在应用设计很重要。
亚历克斯·雷诺兹

1
在发布的解决方案中(非常感谢您),这个解决方案似乎可行,尽管正如Alex上面所述,左栏按钮看起来并不像后栏项目。我怎样才能使它看起来像一个后杠物品?
Dale

17

我有一个父视图控制器,标题很长。这导致后退按钮文本渗入子视图控制器的标题中。

在尝试了许多不同的解决方案之后,这就是我最终要做的(扩展@ john.k.doe方法):

使用Xcode 7.2,Swift 2

  1. 在情节提要中,将一个添加Navigation Item视图控制器场景(而不是子VC)

导航项

  1. Attributes Inspectornew的上Navigation ItemspaceBack Button字段中输入一个字符。稍后对此进行更多讨论。

视图层次结构中的导航项目

向后退按钮字段添加空格字符

  1. 视图控制器中,添加以下代码:

片段:

override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    switch segue.destinationViewController {
    case is ChildViewController:
        navigationItem.backBarButtonItem?.title = ""
    default:
        navigationItem.backBarButtonItem?.title = "Full Parent Title"
    }
}

说明:

后退按钮的种类属于父视图控制器。可以Navigation Item为您提供后退按钮的句柄,因此您可以在代码或情节提要中设置标题。

注意:

如果将Navigation Item Back Button文本保留为默认的空字符串,则后退按钮标题将变为“后退”。

其他方法可行,为什么要使用这种方法?:

尽管可以覆盖子视图控制器上的后退按钮标题,但是要获得它的句柄直到它已经在屏幕上短暂闪烁才是一个挑战。

一些方法构造了一个新的后退按钮并覆盖了现有的后退按钮。我确定它可以正常工作,并且在某些用例中可能是必需的。但是我更喜欢在可能的情况下利用现有的API。

title某些情况下,更改父视图控制器的是最快的解决方案。但是,这会更改父标题,因此您必须管理状态。事情也会变得混乱,Tab Bar Controller因为标题更改会给标题带来副作用Tab Bar Item


10

对于那些使用情节提要的用户,只需选择父级(而不是持有目标视图的一个)视图控制器框架(请确保在导航栏上单击鼠标右键,然后打开属性检查器,即可在其中找到三个表单输入。第三个“后退按钮”是我们正在寻找的。


4
如果您不关心本地化,这是最好的解决方案。
MiQUEL

7

迅捷版:

在您的孩子ViewController中:

override func viewWillAppear(animated: Bool) {
    super.viewWillAppear(animated)
    self.navigationController?.navigationBar.backItem?.title = "TEXT"
}

这实际上会将堆栈中先前的视图控制器的标题更改为“ TEXT”,这不理想。
gravitron

6

这是另一种方法。

在父视图控制器中,实现以下方法:

- (void) setBackBarButtonItemTitle:(NSString *)newTitle {
  self.navigationItem.backBarButtonItem.title = newTitle;
}

在您的子视图控制器中,当您想更改标题时,它将起作用:

NSArray *viewControllerArray = [self.navigationController viewControllers];
int parentViewControllerIndex = [viewControllerArray count] - 2;
[[viewControllerArray objectAtIndex:parentViewControllerIndex] setBackBarButtonItemTitle:@"New Title"];

我从未能够使该parentViewController物业正常工作:

[(ParentViewController *)(self.navigationController.parentViewController) setBackBarButtonItemTitle:@"New Title"];

我不知道那是一个错误还是没有正确使用它。但是,抓住viewControllers数组中倒数第二个视图控制器会指向父视图控制器,我可以使用该引用正确调用父方法。


6

好。我个人讨厌所有这些选择。因此,我提出了自己的建议。

根据我所看到的信息。看来上一个视图控制器处于自己的“后退”按钮的控制之下,该按钮将显示在推送的视图控制器上。

我已经在想要更改后退按钮的控制器上为navigationItem创建了一个惰性加载方法。

我的是邀请买家控制器

邀请买方是默认设置的文本。

但后退按钮需要邀请

这是我用来创建后退按钮的代码。

我将此代码放在Controller的Implementation(.m)文件的顶部,它自动覆盖了super的方法。

- (UINavigationItem *)navigationItem{
    UINavigationItem *item = [super navigationItem];
    if (item != nil && item.backBarButtonItem == nil)
    {
        item.backBarButtonItem = [[[UIBarButtonItem alloc] init] autorelease];
        item.backBarButtonItem.title = @"Invite";
    }

    return item;
}

我觉得这是实现这一目标的一种更为优雅的方法。

我将此代码放在一个地方,并在需要时自动填充。

无需在每个推送请求之前调用代码。

希望这可以帮助


5
UIBarButtonItem *btnBack = [[UIBarButtonItem alloc]
                                   initWithTitle:@"Back" 
                                   style:UIBarButtonItemStyleBordered
                                   target:self
                                   action:@selector(OnClick_btnBack:)];
    self.navigationItem.leftBarButtonItem = btnBack;
    [btnBack release];

5

答案是:

viewDidAppear:animated(不在中viewDidLoad)执行以下操作

- (void)viewDidAppear:(BOOL)animated
{
     [self.navigationController.navigationBar.backItem setTitle:@"anything"];

     // then call the super
     [super viewDidAppear:animated];
}

如果您想保持后退按钮的形状。


不错,除了他们可以看到它更改了标题。我在viewWillAppear中尝试过,它不起作用。
特拉维斯·M.

5

这里介绍的解决方案均不适合我。因此,我要做的是通过以下方式从我来自的场景中删除标题:

self.title = @"";

因此,当呈现新场景时,不会出现背面文字。

我绝对同意,这根本不是一个明确的解决方案,但是有效,没有任何解释对我有用。


伙计,我得告诉你,这是2017年,要处理后退按钮仍然很麻烦。您的方法对我有用,尽管我希望使用“取消”一词,但我还是以“ <”符号结尾,但是我会满足于所得到的。:)
AnBisw

5

我发现最好在导航到下一个视图控制器之前,将导航堆栈中当前视图控制器的标题更改为所需的后退按钮文本。

例如

self.navigationItem.title = @"Desired back button text";
[self.navigationController pushViewController:QAVC animated:NO];

然后在viewDidAppear中将标题设置回原始VC所需的标题。瞧!


5

对于Swift:

    // Rename back button
    let backButton = UIBarButtonItem(
        title: "Back",
        style: UIBarButtonItemStyle.Plain, // Note: .Bordered is deprecated
        target: nil,
        action: nil
    )
    self.navigationController!.navigationBar.topItem!.backBarButtonItem = backButton

4

我发现,更改后退按钮名称的最简单方法是将视图控制器标题设置为后退按钮的标题,然后将视图控制器导航项中的titleView替换为真实的自定义标签名称。

像这样:

CustomViewController.m

@implementation CustomViewController

- (NSString*)title {
    return @"Back Button Title";
}

- (void)viewDidLoad {
    [super viewDidLoad];
    UILabel* customTitleView = [[UILabel alloc] initWithFrame:CGRectZero];
    customTitleView.text = @"Navigation Bar Title";
    customTitleView.font = [UIFont boldSystemFontOfSize:20];
    customTitleView.backgroundColor = [UIColor clearColor];
    customTitleView.textColor = [UIColor whiteColor];
    customTitleView.shadowColor = [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:0.5];
    customTitleView.shadowOffset = CGSizeMake(0, -1);

    [customTitleView sizeToFit];

    self.navigationItem.titleView = [customTitleView autorelease];
}

@end

这将使您在UINavigationBar中的标题看起来像是本机的。使视图控制器具有分隔标题和后退按钮标题的功能。

对于视图控制器A和B,当显示B时,A负责告诉它后退按钮的外观。

编辑:这也保持了后退按钮的本机外观(左箭头的条形按钮项目)。


4

此代码也适用。将其放在导航控制器的根控制器上:

self.navigationItem.backBarButtonItem = [[UIBarButtonItem alloc] initWithTitle:@"" style:UIBarButtonItemStylePlain target:nil action:nil];

4

我在iOS中是新手,但我将提供覆盖导航控制器类的非常简单的答案。我可以简单地覆盖push和pop方法,并保存以前的视图控制器的标题。很抱歉粘贴到js块中。很少混淆如何将其粘贴到常规代码块中。

#import "MyCustomNavController.h"


@implementation MyCustomNavController {

    NSString *_savedTitle;
}

- (void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated withBackBtnTitle:(NSString *)title {
    _savedTitle = self.topViewController.title;

    self.topViewController.title = title;
    [super pushViewController:viewController animated:animated];
}

- (UIViewController *)popViewControllerAnimated:(BOOL)animated {

    [self.viewControllers objectAtIndex:self.viewControllers.count - 2].title = _savedTitle;
    return [super popViewControllerAnimated:animated];
}

@end


4

self.navigationController.navigationBar.backItem.title = @"TEXT";

在Swift中:

self.navigationController?.navigationBar.backItem?.title = "TEXT"

3
self.navigationItem.backBarButtonItem = [[[UIBarButtonItem alloc] 
                                              initWithTitle:@"Log out" 
                                              style:UIBarButtonItemStyleDone 
                                              target:nil 
                                              action:nil] autorelease];

您可以在parrent控制器中的代码中随意放置它,从而可以为不同的子视图使用不同的后退按钮。


3

大多数解决方案都破坏了BackButton的原始样式(左箭头的条形按钮),同时添加了具有所需标题的常规按钮。
因此,要保留原始样式,有2种方法:
第一种:使用我不想做的未记录的按钮样式(110或类似的样式)。但是,如果您愿意,可以在stackoverflow上找到如何执行此操作。
第二:使用特伦斯科的想法。我喜欢它,使用时有所变化。
而不是覆盖-(NSString *)标题,我决定以以下方式保留原始标题(这使我可以在推送状态btw上使用nib的标题以及给定的标题)。

- (void)viewDidLoad {
    [super viewDidLoad];
    static NSString * backButtonTitle=@"Back"; //or whatever u want

    if (![self.title isEqualToString:backButtonTitle]){

        UILabel* customTitleView = [[UILabel alloc] initWithFrame:CGRectZero];
        customTitleView.text = self.title; // original title
        customTitleView.font = [UIFont boldSystemFontOfSize:20];
        customTitleView.backgroundColor = [UIColor clearColor];
        customTitleView.textColor = [UIColor whiteColor];
        customTitleView.shadowColor = [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:0.5];
        customTitleView.shadowOffset = CGSizeMake(0, -1);

        [customTitleView sizeToFit];

        self.navigationItem.titleView = [customTitleView autorelease];
        self.title = backButtonTitle; 
    }
}

该解决方案效果很好,看起来很自然。另外,如果在viewDidLoad方法中使用它,则会阻止执行超过1次。
我也尝试了Jessedc的解决方案,但是看起来很糟糕。这会导致用户标题栏的可见变化(从原始变化到BackButton的变化)。


2

这对我来说是以前发布的答案的“简化”版本。

UIBarButtonItem *backButton = [[UIBarButtonItem alloc] init];

backButton.title = @"Go Back";

self.navigationItem.backBarButtonItem = backButton;

切记将代码放入父视图控制器(例如,具有表视图或UITableViewController的视图)中,而不是子视图或详细信息视图(例如,UIViewController)中。

您可以像这样轻松地定位后退按钮字符串:

backButton.title = NSLocalizedString(@"Back Title", nil);

2

我们有两个VC A和B。

如果要在B中更改标题,请在A中编写此代码

- (IBAction)goToBViewController:(UIButton *)sender {

    BViewController *vc = [self.storyboard instantiateViewControllerWithIdentifier:@"VC"];
    UIBarButtonItem *newBackButton = [[UIBarButtonItem alloc] initWithTitle:@"Your title here"
                                                                  style:UIBarButtonItemStylePlain
                                                                 target:nil
                                                                 action:nil];
    [[self navigationItem] setBackBarButtonItem:newBackButton];
    [self.navigationController pushViewController:vc animated:NO];

}

斯威夫特4.1 Xcode 9.4

let secondViewController = self.storyboard?.instantiateViewController(withIdentifier: "VC"])
let newBackButton = UIBarButtonItem.init(title: "Your title here", style: UIBarButtonItemStyle.plain, target: nil, action: nil)
navigationController?.navigationBar.topItem?.backBarButtonItem = newBackButton
navigationController?.pushViewController(secondViewController!, animated: true)

1

斯坦的答案是最好的。但这也有一个问题,当您将控制器与标签栏一起使用并更改控制器的标题时,您也可以更改标签栏的标题,因此最佳答案是仅更改view_controller.navigationItem.title并使用view_controller.navigationItem函数中的.title。答案在这里:(使用ARC并将它们添加到视图的viewDidLoad中)

  static NSString * back_button_title=@"Back"; //or whatever u want
  if (![view_controller.navigationItem.title isEqualToString:back_button_title]){
    UILabel* custom_title_view = [[UILabel alloc] initWithFrame:CGRectZero];
    custom_title_view.text = view_controller.navigationItem.title; // original title
    custom_title_view.font = [UIFont boldSystemFontOfSize:20];
    custom_title_view.backgroundColor = [UIColor clearColor];
    custom_title_view.textColor = [UIColor whiteColor];
    custom_title_view.shadowColor = [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:0.5];
    custom_title_view.shadowOffset = CGSizeMake(0, -1);

    [custom_title_view sizeToFit];

    view_controller.navigationItem.titleView = custom_title_view;
    view_controller.navigationItem.title = back_button_title;
  }

在我自己的使用中,我使它成为这样的功能,只是在viewDidLoad中具有仅包含一行代码的功能。

+ (void)makeSubViewHaveBackButton:(UIViewController*) view_controller{
  static NSString * back_button_title=@"Back"; //or whatever u want
  if (![view_controller.navigationItem.title isEqualToString:back_button_title]){
    UILabel* custom_title_view = [[UILabel alloc] initWithFrame:CGRectZero];
    custom_title_view.text = view_controller.navigationItem.title; // original title
    custom_title_view.font = [UIFont boldSystemFontOfSize:20];
    custom_title_view.backgroundColor = [UIColor clearColor];
    custom_title_view.textColor = [UIColor whiteColor];
    custom_title_view.shadowColor = [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:0.5];
    custom_title_view.shadowOffset = CGSizeMake(0, -1);

    [custom_title_view sizeToFit];

    view_controller.navigationItem.titleView = custom_title_view;
    view_controller.navigationItem.title = back_button_title;
  }
}

1

如果您不仅希望将“后退”按钮的文本更改为相同的文本并保持原始的左箭头形状,而且还希望在用户单击“后退”按钮时执行某些操作,则建议您浏览一下“ CustomNavigationController ” 。


1

问题:导航栏中的“后退”文本无法替换。

原因:推送视图后,在导航栏中设置了“后退”标签,因为父视图控制器中的.title属性设置为nil(或未初始化)。

一种解决方案:如果设置self.title =“ Whatever ...”,则在按下新的视图控制器后,您会看到显示的是“ Whatever ...”而不是“ Back”。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.