前言
本篇属个人阶段总结,纯代码,无xib,无sb,老少皆不宜。
关于作者: 周辉
All rights reserved.
本篇内容:
-
UINavigationController
的使用 -
UITabBarController
的使用 -
UINavigationController
和UITabBarController
的综合使用 -
UITabBar
,UINavigationBar
介绍 -
UINavigationItem
,UIBarItem
,UIBarButtonItem
,UITabBarItem
介绍 - 导航栏标题,背景,颜色,返回按钮等的自定义
继承关系
// controller类
UIViewController : UIResponder
UINavigationController : UIViewController
UITabBarController : UIViewController
// bar类
UINavigationBar : UIView
UITabBar : UIView
// item类
UINavigationItem : NSObject
UIBarItem : NSObject
UITabBarItem : UIBarItem
UIBarButtonItem : UIBarItem
常用属性结构
UINavigationController 的使用
参见这篇文章
UITabBarController 的使用
参见这篇文章
综合使用
大多数的App都是对Cocoa中的UINavigationController
和UITabBarController
结合使用的。下面就来看看两种结合方式:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
UIViewController *firstViewController = [[UIViewController alloc] init];
UIViewController *secondViewController = [[UIViewController alloc] init];
UIViewController *thirdViewController = [[UIViewController alloc] init];
UITabBarController *tabBarController = [[UITabBarController alloc] init];
tabBarController.viewControllers = @[firstViewController, secondViewController, thirdViewController];
UINavigationController *navigationController = [[UINavigationControlle alloc] initWithRootViewController:tabBarController];
self.window.rootViewController = tabBarController;
[self.window makeKeyAndVisible];
[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
return YES;
} // 1
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
UIViewController *firstViewController = [[UIViewController alloc] init];
UIViewController *secondViewController = [[UIViewController alloc] init];
UIViewController *thirdViewController = [[UIViewController alloc] init];
UINavigationController *firstNavigationController = [[UINavigationController alloc]
initWithRootViewController:rootViewController];
UINavigationController *secondNavigationController = [[UINavigationController alloc]
initWithRootViewController:rootViewController];
UINavigationController *thirdNavigationController = [[UINavigationController alloc]
initWithRootViewController:rootViewController];
NSArray* controllers = [NSArray arrayWithObjects:firstNavigationController, secondNavigationController, thirdNavigationController, nil];
UITabBarController *tabBarController = [[UITabBarController alloc] init];
tabBarController.viewControllers = controllers;
self.window.rootViewController = tabBarController;
[self.window makeKeyAndVisible];
[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
return YES;
} // 2
方法1显然比方法2简单许多,我们必须需要初始化5个navigation controllers来服务5个view controllers吗?
是的,为什么呢?
- 有些情况下在
navigationController
里用self
点语法时候,会得到null
, 因为5个viewController都被pushed on the stack 。 - 当你修改了
navigationBar
,切换到其他页面,你会发现其他页面的navigationBar
也被修改了,因为只有一个navigationController
,一个navigationBar
。 - 当你从
tabBarController
的某一个viewController
里push进另一个viewController
,tab bar 会消失,因为tabBarController
不是rootViewController
, 它仅仅是在 stack 中。
关于 bar 和 item
参见我的一个小Demo
导航栏标题,背景,颜色,返回按钮等的自定义
- 原点坐标
UINavigationController *nvc = [[UINavigationController alloc] initWithRootViewController:[ViewController new]];
nvc.navigationBar.translucent = NO;
UINavigationController *nvc = [[UINavigationController alloc] initWithRootViewController:[ViewController new]];
nvc.navigationBar.translucent = YES;
- 如果想把画面B返回按钮的文字去掉在,需要在画面A的
pushViewController
之前调用
UIBarButtonItem *barButtonItem = [[UIBarButtonItem alloc] initWithTitle:@""
style:UIBarButtonItemStyleDone
target:nil
action:nil];
self.navigationItem.backBarButtonItem = barButtonItem;
注意一定要在 pushViewController
之前,在viewDidLoad
中会crash,至于为什么我也不知道。
-
更改导航栏背景和文字颜色
- 方法1
//set NavigationBar 背景颜色&title 颜色
[self.navigationController.navigationBar setBarTintColor:[UIColor colorWithRed:20/255.0 green:155/255.0 blue:213/255.0 alpha:1.0]];
[self.navigationController.navigationBar setTitleTextAttributes:[NSDictionary dictionaryWithObjectsAndKeys:[UIColor whiteColor],UITextAttributeTextColor,nil]];
蓝色背景,白色title。NavigationBar
极其push过去的子页面也会是修改后的背景颜色。
- 方法2
// 设置NavigationBar背景颜色
[[UINavigationBar appearance] setBarTintColor:[UIColor redColor]];
// @{}代表Dictionary
[[UINavigationBar appearance] setTitleTextAttributes:@{NSForegroundColorAttributeName:[UIColor whiteColor]}];
- 导航栏使用背景图片
如果应用程序使用了自定义图像作为栏的背景,需要提供一个“更大”的图片,使其延伸了状态栏的后面。导航栏的高度现在是从44点(88像素)更改为64点(128像素)。仍然可以使用了setBackgroundImage:
方法来指定自定义图像的导航栏:
[[UINavigationBar appearance] setBackgroundImage:[UIImage imageNamed:@"nav_bg.png"] forBarMetrics:UIBarMetricsDefault];
- 改变导航栏标题的字体
我们可以通过使用导航栏的“titleTextAttributes”属性来自定义的文本样式。可以指定字体,文字颜色,文字阴影颜色,文字阴影在文本标题偏移属性字典,使用下面的文本属性键:
UITextAttributeFont
- 字体
UITextAttributeTextColor
- 文字颜色
UITextAttributeTextShadowColor
- 文字阴影颜色
UITextAttributeTextShadowOffset
- 偏移用于文本阴影
NSShadow *shadow = [[NSShadow alloc] init];
shadow.shadowColor = [UIColor colorWithRed:0.0 green:0.0 blue:0.0 alpha:0.8];
shadow.shadowOffset = CGSizeMake(0, 1);
[[UINavigationBar appearance] setTitleTextAttributes: [NSDictionary dictionaryWithObjectsAndKeys:
[UIColor colorWithRed:245.0/255.0 green:245.0/255.0 blue:245.0/255.0 alpha:1.0], NSForegroundColorAttributeName,
shadow, NSShadowAttributeName,
[UIFont fontWithName:@"HelveticaNeue-CondensedBlack" size:21.0], NSFontAttributeName, nil nil]];
- 使用图片作为导航栏标题
self.navigationItem.titleView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"appcoda-logo.png"]];
- 添加多个栏按钮项目
UIBarButtonItem *shareItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemAction target:self action: nil nil];
UIBarButtonItem *cameraItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemCamera target:self action: nil nil];
NSArray *itemsArr = @[shareItem,cameraItem];
self.navigationItem.rightBarButtonItems = itemsArr;
- 自定义后退按钮的文字和颜色
通常情况下,我们使用UINavigationController
时,push到的子页面,左上角会是系统自动取值上一层父页面的title名称,默认情况是这样。我们有多种方法改变之。 - 方法
通过设置navigationItem的backBarButtonItem可以直接更换文字,【注意,要在父视图的Controller中设置】如下:
UIBarButtonItem *item = [[UIBarButtonItem alloc] initWithTitle:@"返回" style:UIBarButtonItemStylePlain target:nil action:nil];
self.navigationItem.backBarButtonItem = item;
所有的子界面返回时都变成了我们定义的文字,如果不想显示文字,直接"",就会单独显示一个系统的返回箭头图标,也是很清晰的感觉。
- 自定义其颜色
在iOS7,可以改变tintColor属性,它提供了一个快速和简单的方式,下面是一个示例代码片段:
[[UINavigationBar appearance] setTintColor:[UIColor whiteColor]];
- 另外一种实现自定义导航控制器返回按钮:
[self.navigationController.navigationBar setTitleTextAttributes:@{NSForegroundColorAttributeName: [UIColor redColor],NSFontAttributeName:[UIFont systemFontOfSize:19.0]}];
self.title=[NSString stringWithFormat:@"第%lu页",(unsigned long)self.navigationController.viewControllers.count];
//自定义返回按钮
UIImage *backButtonImage = [[UIImage imageNamed:@"fanhui.png"] resizableImageWithCapInsets:UIEdgeInsetsMake(0, 30, 0, 0)];
[[UIBarButtonItem appearance] setBackButtonBackgroundImage:backButtonImage forState:UIControlStateNormal barMetrics:UIBarMetricsDefault];
//将返回按钮的文字position设置不在屏幕上显示
[[UIBarButtonItem appearance] setBackButtonTitlePositionAdjustment:UIOffsetMake(NSIntegerMin, NSIntegerMin) forBarMetrics:UIBarMetricsDefault];
注意 title
只要设置 self.title
,那么self.navigationItem.title
和self.tabBarItem.title
值不管设置与否都和self.title
一致。
self.title
要在- (id)init:
里写,否则在tabBar里不加载的几个bar不显示title。