【问题标题】:iOS 5 Back Button SizeiOS 5 后退按钮大小
【发布时间】:2012-05-06 14:32:00
【问题描述】:

我正在使用 iOS 5 UIAppearance protocol 来使用自定义导航栏后退按钮,如 here 所示。与我发现的其他方法不同,这是最好的方法,因为它保留了默认的后退按钮动画和行为。

唯一的问题是我不能改变它的大小或将它设置为not clip subviews。以下是正在发生的事情:

A 是预期行为,B 是默认样式,C 是剪辑结果。

不幸的是,这并不像将 UIBarButtonItem 设置为 clipsToBounds=NO 那样简单。

有谁知道如何解决这个问题?谢谢!

【问题讨论】:

  • 你试过 UIBarButtonItem.superview.clipsToBounds = NO 吗? (或 superview.superview ...)因为导航栏不打算比它已经大。因此,您将尝试的任何事情都将是“黑客”。如果它是一个黑客,那么这就是“标准”的方式:-)
  • 您所推荐的内容是不可能的,因为UIBarButtonItem 不继承自UIView。但是,我尝试设置self.navigationController.navigationItem.backBarButtonItem.customView.clipsToBounds = NO;self.navigationItem.backBarButtonItem.customView.clipsToBounds = NO;。我假设您的意思是 UIBarButtonItem 不打算更大,因为我没有触摸导航栏本身。
  • 是的,你是对的!我通常的意思是遍历视图层次结构并找出哪个剪辑。此外,您可能需要以不同方式处理 iOS =5。我实际上的意思是导航栏并不意味着更大,因为栏项目不受限制,导航栏是限制它们的原因。它有硬编码的填充,剩下的就是按钮的空间。

标签: ios ios5 uinavigationitem uiappearance


【解决方案1】:

正如您所发现的,UIAppearance 代理不允许您调整按钮本身的尺寸:UIBarButtonItem 支持的外观方法列表在文档中给出,同时它包括标题的指标给自己贴上标签,按钮是禁止使用的。

对于它的价值,按钮本身的可触摸区域实际上是 44 pts(88 像素,如果你在视网膜中)高,只是按钮 graphic 比那个小。

如果您对 3 pt 的高度差异感到困惑,那么最好的选择可能是创建自己的自定义按钮并使用 UINavigationItem setLeftBarButtonItem 方法。正如您所指出的,您将需要实现一个附加到该按钮的简短方法,该方法实现 popNavigationController 以确保保持正确的行为。

更新:我刚刚发现,如果您将后退按钮保持在周围,实际上可以对其进行动画处理,使其以与标准后退按钮类似的方式滑动。在下面的代码中,self.backButton 是您在 initWithCustomView UIBarButtonItem 方法中使用的 UIButton

- (void)viewWillDisappear:(BOOL)animated {
    [UIView animateWithDuration:0.3 
                     animations:^{
                         self.backButton.frame = CGRectMake(self.backButton.frame.origin.x+100, 
                                                            self.backButton.frame.origin.y, 
                                                            self.backButton.frame.size.width, 
                                                            self.backButton.frame.size.height);
                     }];
}

...这将在视图控制器消失时触发(即,当弹出 推送时),但您可以挂钩到 UINavigationController 委托以仅在弹出导航控制器时触发它反而。虽然我只在模拟器上测试过,但按下控制器时,它似乎肯定会移动按钮。

【讨论】:

  • 感谢您确认我对UIAppearance、@lxt 的怀疑。不幸的是,通过设置自定义leftBarButtonItem,我失去了backBarButtonItem 动画(水平滑动),并且由于UIBarButtonItem 没有从UIView 继承,我无法自己制作动画。
  • 试试我刚刚发布的代码,可能会对你的动画有所帮助。似乎对我有用。
【解决方案2】:

我最终为我在导航控制器中使用的每个 VC 使用了一个自定义视图控制器类。

OEViewController.h

#import <UIKit/UIKit.h>
#import "OEBarButtonItem.h"

@interface OEViewController : UIViewController

@property (nonatomic, retain) UIButton *backButton;
@property (atomic) BOOL pushed;

- (void)pushViewController:(UIViewController*)vc;

@end

OEViewController.m

#import "OEViewController.h"

#define ANIMATION_DURATION 0.33

@implementation OEViewController
@synthesize backButton, pushed;

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    return self;
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view.
    pushed=YES;
    self.navigationItem.hidesBackButton = YES;

    backButton = [OEBarButtonItem backButtonWithTitle:[(UIViewController*)[self.navigationController.viewControllers objectAtIndex:[self.navigationController.viewControllers count]-2] title]];

    [backButton addTarget:self action:@selector(backButtonPressed:) forControlEvents:UIControlEventTouchUpInside];

    self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:backButton];
}

- (void)viewDidUnload
{
    [super viewDidUnload];
    // Release any retained subviews of the main view.
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation == UIInterfaceOrientationPortrait);
}

- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
    if (pushed) {
        self.backButton.frame = CGRectMake(self.backButton.frame.origin.x+100, 
                                           self.backButton.frame.origin.y+6, 
                                           self.backButton.frame.size.width, 
                                           self.backButton.frame.size.height);
        [UIView animateWithDuration:ANIMATION_DURATION 
                         animations:^{
                             self.backButton.frame = CGRectMake(self.backButton.frame.origin.x-100, 
                                                                self.backButton.frame.origin.y, 
                                                                self.backButton.frame.size.width, 
                                                                self.backButton.frame.size.height);
                         }];
        pushed=NO;
    } else {
        self.backButton.frame = CGRectMake(self.backButton.frame.origin.x-100, 
                                           self.backButton.frame.origin.y, 
                                           self.backButton.frame.size.width, 
                                           self.backButton.frame.size.height);
        [UIView animateWithDuration:ANIMATION_DURATION 
                         animations:^{
                             self.backButton.frame = CGRectMake(self.backButton.frame.origin.x+100, 
                                                                self.backButton.frame.origin.y, 
                                                                self.backButton.frame.size.width, 
                                                                self.backButton.frame.size.height);
                         }];
    }
}

- (void)backButtonPressed:(id)sender {
    [self.navigationController popViewControllerAnimated:YES];
    [UIView animateWithDuration:ANIMATION_DURATION 
                     animations:^{
                         self.backButton.frame = CGRectMake(self.backButton.frame.origin.x+100, 
                                                            self.backButton.frame.origin.y, 
                                                            self.backButton.frame.size.width, 
                                                            self.backButton.frame.size.height);
                     }];
}

- (void)pushViewController:(UIViewController*)vc {
    [self.navigationController pushViewController:vc animated:YES];
    [UIView animateWithDuration:ANIMATION_DURATION 
                     animations:^{
                         self.backButton.frame = CGRectMake(self.backButton.frame.origin.x-100, 
                                                            self.backButton.frame.origin.y, 
                                                            self.backButton.frame.size.width, 
                                                            self.backButton.frame.size.height);
                     }];
}

@end

与使用 UIAppearance 相比,这具有使用 iOS 4.0+ 的额外好处。

感谢@lxt 的帮助!

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-10-01
    • 2023-04-05
    • 2011-10-03
    • 1970-01-01
    相关资源
    最近更新 更多