ios 如何捕获返回按钮事件

dnph8jn4  于 2023-10-21  发布在  iOS
关注(0)|答案(8)|浏览(132)

我有一个启动UIViewController的可执行ViewController,每当在子控制器中按下返回按钮时,我想捕获,这是从'UIViewController'派生的类。我可以改变返回按钮的标题,但设置backBarButtonItem时设置目标和动作值似乎被忽略了。有什么方法可以接收到后退按钮被点击的通知?

- (void)showDetailView 
{
    // How I'm creating & showing the detail controller
    MyViewController *controller = [[MyViewController alloc] initWithNibName:@"MyDetailView" bundle:nil];   

    UIBarButtonItem *backButton = [[UIBarButtonItem alloc] initWithTitle:@"Pages"
                            style:UIBarButtonItemStyleBordered 
                            target:self                                     
                            action:@selector(handleBack:)];

    self.navigationItem.backBarButtonItem = backButton;
    [backButton release];

    [self.navigationController pushViewController:controller animated:animated];
    [controller release];

}   

- (void)handleBack:(id)sender
{
    // not reaching here
    NSLog(@"handleBack event reached");
}
h7appiyu

h7appiyu1#

您可以实现UIViewController的viewWillDisappear方法。当你的控制器即将离开时,这个函数会被调用(或者是因为另一个控制器被推到了导航控制器堆栈上,或者是因为“后退”按钮被按下了)。
要确定视图是否因为按下后退按钮而消失,可以使用自定义标志,在将新控制器推到导航控制器上的任何位置设置该标志,如下所示

- (void)viewWillDisappear:(BOOL)animated {
    [super viewWillDisappear:animated];
    if (viewPushed) {
        viewPushed = NO;   // Flag indicates that view disappeared because we pushed another controller onto the navigation controller, we acknowledge it here
    } else {
        // Here, you know that back button was pressed
    }   
}

无论你在哪里推一个新的视图控制器,你都必须记住设置那个标志。

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    ...
    viewPushed = YES;
    [self.navigationController pushViewController:myNewController animated:YES];
    ...
}
trnvg8h3

trnvg8h32#

自从有人问这个问题以来已经有一段时间了,但我只是试着自己做。我使用了一个类似于Zoran的解决方案,但是我没有使用旗帜,而是这样做:

- (void)viewWillDisappear: (BOOL)animated
{
    [super viewWillDisappear: animated];
    if (![[self.navigationController viewControllers] containsObject: self])
    {
        // the view has been removed from the navigation stack, back is probably the cause
        // this will be slow with a large stack however.
    }
}

我认为它绕过了旗帜的问题,IMO更干净,但效率不高(如果导航控制器上有很多物品的话)。

w6mmgewl

w6mmgewl3#

在我看来,最好的解决方案。

- (void)didMoveToParentViewController:(UIViewController *)parent
{
    if (![parent isEqual:self.parentViewController]) {
         NSLog(@"Back pressed");
    }
}

但它只适用于iOS5+

krcsximq

krcsximq4#

我使用这个代码:

- (void) viewWillDisappear:(BOOL)animated {

   if ([self.navigationController.viewControllers indexOfObject:self] == NSNotFound)
   {
      // your view controller already out of the stack, it meens user pressed Back button
   }
}

但这是不实际的,当用户按下标签栏按钮,并弹出到根视图控制器在一个步骤。对于这种情况,请使用以下命令:

[[NSNotificationCenter defaultCenter] addObserver:self
                                            selector:@selector(viewControllerChange:)
                                                name:@"UINavigationControllerWillShowViewControllerNotification"
                                              object:self.navigationController];

- (void) viewControllerChange:(NSNotification*)notification {

   NSDictionary* userInfo = [notification userInfo];

   if ([[userInfo objectForKey:@"UINavigationControllerNextVisibleViewController"] isKindOfClass:[<YourRootControllerClass> class]])
   { 
      // do your staff here
   }
}

别忘了:

[[NSNotificationCenter defaultCenter] removeObserver:self
                                                   name:@"UINavigationControllerWillShowViewControllerNotification"
                                                 object:self.navigationController];
jfewjypa

jfewjypa5#

您可以制作自己的按钮并将其放置为leftBarButtonItem。然后让它调用你可以做任何事情的方法,并自己调用[self.navigationController popViewController...

iyfjxgzm

iyfjxgzm6#

{
    UIBarButtonItem *backButton = [[UIBarButtonItem alloc] initWithTitle:@"back"
                                                                   style:UIBarButtonItemStyleBordered 
                                                                  target:self                                                                             
                                                                  action:@selector(handleBack:)];
    self.navigationItem.leftBarButtonItem = backButton;
    [backButton release];
    [self filldata];
    [super viewDidLoad];
}

只需将backBarButtonItem替换为leftBarButtonItem

kulphzqa

kulphzqa7#

backAction的帮助下,从iOS16+开始,这似乎是可能的
以下是文档中的内容:
如果“后退”按钮已出现在导航栏中,则设置此属性将替换其操作,而不修改其外观。
因此,在您的viewDidLoad或其他适当的地方,您可以添加以下代码:

navigationItem.backAction = UIAction { [weak self] _ in
    // Handle your other logic here for back button tap
    self?.navigationController?.popViewController(animated: true)
    
}
cnh2zyt3

cnh2zyt38#

使用viewDidDisappear代替。它将在任何情况下被完美地调用。
我们将您的生命周期管理基于viewDidAppear和viewDidDisappear。如果你了解Android:这两种方法都与onResume和onResume方法相当。但在iOS上,锁定屏幕或按下主页按钮是有区别的。

相关问题