【问题标题】:back button at root controller of uinavigationcontrolleruinavigationcontroller 根控制器的后退按钮
【发布时间】:2011-10-10 01:50:32
【问题描述】:

我有一个带有根视图控制器的 UINavigationController 应用程序,每次我将视图控制器推送到堆栈时。假设堆栈是 A B C D 其中 A 是这里的根视图控制器。问题是当我在视图控制器 D 并执行 popToRootViewController 时,它返回到 A 但 A 上有一个后退按钮。当我点击背面时,背面只是滑入并消失,为什么会发生这种情况?

编辑:我实际上是对我的 UINavigationController 进行子类化,以便我可以按如下方式设置我的 rootViewController:

#import "CustomNavigationController.h"

@implementation CustomNavigationController

@synthesize fakeRootViewController;

//override to remove fake root controller
-(NSArray *)viewControllers {
    NSArray *viewControllers = [super viewControllers];     
if (viewControllers != nil && viewControllers.count > 0) {  
NSMutableArray *array = [NSMutableArray arrayWithArray:viewControllers];        
[array removeObjectAtIndex:0];  
    return array;   } 
    return viewControllers; }

//override so it pops to the perceived root
- (NSArray *)popToRootViewControllerAnimated:(BOOL)animated {
    //we use index 0 because we overrided “viewControllers”
    ((UIViewController *)[self.viewControllers objectAtIndex:0]).navigationItem.hidesBackButton = YES;
    return [self popToViewController:[self.viewControllers objectAtIndex:0] animated:animated]; }

//this is the new method that lets you set the perceived root, the previous one will be popped (released)
-(void)setRootViewController:(UIViewController *)rootViewController {
    rootViewController.navigationItem.hidesBackButton = YES;
    [self popToViewController:fakeRootViewController animated:NO];
    [self pushViewController:rootViewController animated:NO]; }

- (void)dealloc {
    self.fakeRootViewController = nil;
    [super dealloc]; }


-(id)initWithCoder:(NSCoder *)aDecoder{
    self = [super initWithCoder:aDecoder];
    if(self){
        UIViewController *fakeController = [[[UIViewController alloc] init] autorelease];
        self.fakeRootViewController = fakeController;
        NSMutableArray *array = [NSMutableArray arrayWithArray:[super viewControllers]];
        [array insertObject:fakeController atIndex:0];
        self.viewControllers = array;
    }
    return self; }

- (void)didReceiveMemoryWarning {
    // Releases the view if it doesn't have a superview.
    [super didReceiveMemoryWarning];

    // Release any cached data, images, etc that aren't in use. }

#pragma mark - View lifecycle

/* // Implement loadView to create a view hierarchy programmatically, without using a nib.
- (void)loadView { }
*/

/* // Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
- (void)viewDidLoad {
    [super viewDidLoad]; }
*/

- (void)viewDidUnload {
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil; }

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
    // Return YES for supported orientations
    return (interfaceOrientation == UIInterfaceOrientationPortrait); }

@end

更多更新:

所以在我设置我的 rootViewController 然后推送一个 viewController 然后尝试从该视图调用 popToRootViewController 之后,一切正常。但是,如果我在第二个 viewController 之后推送另一个 viewController,然后调用 popToRootViewController,现在我可以在根目录上看到那个奇怪的后退按钮。

【问题讨论】:

  • 是否有可能在将其他视图压入堆栈之前(再次)将 A 压入堆栈?
  • 如果你尝试弹出到根目录,去掉多余的后退按钮,回到堆栈中,然后再次弹出到根目录,后退按钮还在吗?如果不是,则意味着您在初始化时将 A 压入堆栈。
  • 作为健全性检查,您可以枚举 UINavigationController viewControllers 属性并验证哪些控制器已添加到堆栈中。这将解决 A 的附加实例是否已被压入堆栈的问题。后退按钮标题是否提供了关于它是哪个控制器的线索?
  • 对不起..我错过了这个非常重要的部分,我实际上继承了我自己的 UINavigationController 以便我可以像上面一样设置根视图控制器..

标签: iphone objective-c ipad uinavigationcontroller


【解决方案1】:

我也面临同样的问题。所以在你的根控制器中分配 leftBarButtonItem 等于 nil。

self.navigationItem.leftBarButtonItem = nil;

如果您的根控制器在程序中重用。然后你需要检查 ->

BOOL needBackBarButton = (1 < [self.navigationController.viewControllers count]) ? YES : NO ; 
if (! needBackBarButton)
{
    self.navigationItem.leftBarButtonItem = nil;
}

对于其他控制器

if (needBackBarButton)
{
          // Create custom navigationItem here.
}
else 
{
    self.navigationItem.leftBarButtonItem = nil;
}

【讨论】:

  • 但是如何为我需要的人制作后退按钮?
  • 您无需考虑其他控制器。您只需添加 self.navigationItem.leftBarButtonItem = nil;这在你的根视图控制器的 viewDidLoad 方法中。我希望这能解决您的问题。
  • 我确实有,但它并没有改变任何事情
猜你喜欢
  • 1970-01-01
  • 2011-09-08
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-01-15
  • 1970-01-01
  • 1970-01-01
  • 2012-01-01
相关资源
最近更新 更多