代码之家  ›  专栏  ›  技术社区  ›  pgb

UINavigationController中的自定义后退按钮

  •  18
  • pgb  · 技术社区  · 16 年前

    对于我正在开发的应用程序,我需要在导航栏中显示一个自定义的后退按钮。我将按钮资产作为PNG图像,我正在编写以下代码:

    - (void)viewWillAppear:(BOOL)animated {
        [super viewWillAppear:animated];
        UIButton *backButton = [UIButton buttonWithType:UIButtonTypeCustom];
        backButton.frame = CGRectMake(0, 0, 79, 29.0);
        [backButton setImage:[UIImage imageNamed:@"button_back.png"] forState:UIControlStateNormal];
        self.navigationItem.backBarButtonItem = [[[UIBarButtonItem alloc] initWithCustomView:backButton] autorelease];
    

    }

    我已经尝试过的事情:

    1. backButton 通过将其添加到视图层次结构来正确创建。正确显示。
    2. 用同样的方法,改变了 title 财产 navigationItem 并确认它改变了我后退按钮的内容。

    UINavigationController ?

    10 回复  |  直到 16 年前
        1
  •  18
  •   pgb    13 年前

    从iOS 5开始,这很简单:

    [[UIBarButtonItem appearance]
                setBackButtonBackgroundImage:[UIImage imageNamed:@"back_button.png"]
                forState:UIControlStateNormal barMetrics:UIBarMetricsDefault];
    

    你可以把它放在你的应用程序代理中,它会将背景图像设置为应用程序中的所有后退按钮(当然,对于那个控件状态和条度量)。

        2
  •  13
  •   Community Mohan Dere    9 年前

    我正在重新发布我的解决方案 https://stackoverflow.com/a/16831482/171933 :

    UIViewController :

    UIViewController+ImageBackButton.h

    #import <UIKit/UIKit.h>
    
    @interface UIViewController (ImageBackButton)
    
    - (void)setUpImageBackButton;
    
    @end
    

    UIViewController+ImageBackButton.m

    #import "UIViewController+ImageBackButton.h"
    
    @implementation UIViewController (ImageBackButton)
    
    - (void)setUpImageBackButton
    {
        UIButton *backButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, 34, 26)];
        [backButton setBackgroundImage:[UIImage imageNamed:@"back_arrow.png"] forState:UIControlStateNormal];
        UIBarButtonItem *barBackButtonItem = [[UIBarButtonItem alloc] initWithCustomView:backButton];
        [backButton addTarget:self action:@selector(popCurrentViewController) forControlEvents:UIControlEventTouchUpInside];
        self.navigationItem.leftBarButtonItem = barBackButtonItem;
        self.navigationItem.hidesBackButton = YES;
    }
    
    - (void)popCurrentViewController
    {
        [self.navigationController popViewControllerAnimated:YES];
    }
    
    @end
    

    现在你要做的就是 #import UIViewController+ImageBackButton.h 在所有视图控制器中,或者在其他视图控制器继承并实现的自定义基本视图控制器类中 viewWillAppear:

    - (void)viewWillAppear:(BOOL)animated
    {
        [self setUpImageBackButton];
    }
    

    这就是全部。现在你到处都有一个图像返回按钮。没有边界。好好享受!

        3
  •  5
  •   explodes    14 年前

    这个 backBarButtonItem

    您可以自定义文本,但不能替换图像。

    一个解决方法,正如安德鲁·普利奥特所建议的,是使用 leftBarButtonItem 但我还是坚持按标准按钮。

        4
  •  4
  •   vladCovaliov    12 年前

    最简单的解决方案不就是从你的故事板上设计出你想要的任何图像或颜色,然后把一个新动作拖到你的控制器上吗?

    @IBAction func backButton(sender: AnyObject) {
        self.navigationController?.popViewControllerAnimated(true)
    }
    
        5
  •  3
  •   Andrew Pouliot    16 年前

    令人困惑地 backBarButtonItem 不是你要找的。

    它只控制下一个视图控制器的“后退”按钮上的标题。你要做的是设置 leftBarButtonItem

        6
  •  2
  •   duan    10 年前

    johannesfahrenkrug的答案是可行的,但是后面的图像会出现在一个非常有线的位置。

    在这里,我找到了一个更好的方法来将图像定位到正确的位置:

    确保你有一个尺寸为24x24(@1x)的背面图像,我称之为 backImage

    在应用程序启动时执行以下代码

    UINavigationBar.appearance().barTintColor = nil
    UINavigationBar.appearance().backIndicatorImage = backImage
    UINavigationBar.appearance().backIndicatorTransitionMaskImage = backImage
    UIBarButtonItem.appearance().setBackButtonTitlePositionAdjustment(UIOffsetMake(0, -60), forBarMetrics: .Default)
    
        7
  •  1
  •   Community Mohan Dere    9 年前
        8
  •  1
  •   Rich Tolley    10 年前

    根据OOP,这是插入视图控制器的containerViewController的责任,例如UINavigationController。

    将NavigationController子类化并在其超类方法中重载,如下所示:

    @implementation STONavigationController
    
    - (void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated
    {
        [super pushViewController:viewController animated:animated];
        if ([self.viewControllers indexOfObject:viewController] != NSNotFound &&
            [self.viewControllers indexOfObject:viewController] > 0){
            UIImage *img = [UIImage imageNamed:@"back-1"];
            UIButton *backButton = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, img.size.width * 2, img.size.height * 2)];
            [backButton setBackgroundImage:img forState:UIControlStateNormal];
            UIBarButtonItem *barBackButtonItem = [[UIBarButtonItem alloc] initWithCustomView:backButton];
            [backButton addTarget:self action:@selector(popCurrentViewController) forControlEvents:UIControlEventTouchUpInside];
            viewController.navigationItem.leftBarButtonItem = barBackButtonItem;
            viewController.navigationItem.hidesBackButton   = YES;
        }
    }
    
    - (void)popCurrentViewController
    {
        [self popViewControllerAnimated:YES];
    }
    
    @end 
    
        9
  •  0
  •   Venk    13 年前

    UIBarButtonItem UIButton 在里面 栏按钮项 . 很好用!

    UIBarButtonItem *backButton = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"button_back.png"] style:UIBarButtonItemStyleBordered target:nil action:nil];
    
    self.navigationItem.backBarButtonItem = backButton; 
    
        10
  •  0
  •   Ammar Mujeeb    9 年前

    正如@pgb所建议的,您可以使用leftBarButtonItem而不是back button项。要删除默认的back按钮项,请将其设置为nil,如下所示;

    navigationController?.navigationBar.backIndicatorImage = nil
    navigationController?.navigationBar.backIndicatorTransitionMaskImage = nil
    
    let button = UIButton.init(type: .custom)
    button.imageView?.contentMode = UIViewContentMode.scaleAspectFit
    button.setImage(UIImage.init(named: "top_back"), for: UIControlState.normal)
    button.frame = CGRect.init(x: 0, y: 0, width: 75, height: 50) 
    button.addTarget(self, action: #selector(handleBackButton), for: .touchUpInside)
    
    let barButton = UIBarButtonItem.init(customView: button)
    self.navigationItem.leftBarButtonItem = barButton