通告机制
1.NSNotificationCenter 类似于这个应用的智能公告栏,对象可以在这个公告栏中发布通知,其他对象可以将自己注册成观察器。
2.当相应的对象发布通告时,NSNotificationCenter实例会将该通告转发给已注册的观察器。
3.通告即NSNotification实例,每个NSNotification都有自己的名称和一个指向发布该通告的对象的指针。将(其他)对象注册为观察器时,需要指定通告名称,发布通告的对象,和接收到通告后要调用的方法。该方法会带一个NSNotification的参数。
4.NSNotification对象可以附带一个名为userInfo的NSDictionary对象,通告这个对象可以传递额外的信息。
NSDictionary *extraInfo = ...;
NSNotification *note = [NSNotification notificationWithName:@"LostDog" object:self userInfo:extraInfo];
//发布通告
[[NSNotificationCenter defaultCenter] postNotification:note];
5.注意,通告中心不会保留观察器,所以在通告中心注册过的对象必须在释放前取消注册。否则,当相应的通告再次出现时,通告中心会向改观察器发送消息,这时应用就会导致崩溃。
- (void)dealloc
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
[super dealloc];
}
6.UIDivice对象会不间断地发送通告。
UIDevice *device = [UIDevice currentDevice];
//当设备改变方向时开始产生通知
[device beginGeneratingDeviceOrientationNotifications];
//获取应用的通知对象
NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
//将self注册为观察器
[notificationCenter addObserver:self selector:@selector(orientationChanged:) name:UIDeviceOrientationDidChangeNotification object:device];
自动转屏
1.当用户转动设备时,很多应用会转动界面,并调整所有视图大小。要实现自动转屏要(1)覆盖UIViewController的- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation方法。(2)每个子视图设置相应的自动缩放标志(autoresize mask),使之能够在其父视图发生变化时作出相应的调整。- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation
{
return (toInterfaceOrientation == UIInterfaceOrientationPortrait) || UIInterfaceOrientationIsLandscape(toInterfaceOrientation);
}
2.除了在xib文件中设置还可以向视图发送setAutoresisingMask:消息来设置自动缩放标志。比如:
[view setAutoresizingMask:UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleHeight];
上面一段代码为什么用到按位或运算?因为UIViewAutoresizing常量是2的N次幂(只有一位为1,其他为0的二进制序列)下面是这些常量表示。
enum {
UIViewAutoresizingNone = 0,
UIViewAutoresizingFlexibleLeftMargin = 1 << 0,
UIViewAutoresizingFlexibleWidth = 1 << 1,
UIViewAutoresizingFlexibleRightMargin = 1 << 2,
UIViewAutoresizingFlexibleTopMargin = 1 << 3,
UIViewAutoresizingFlexibleHeight = 1 << 4,
UIViewAutoresizingFlexibleBottomMargin = 1 << 5
};
typedef NSUInteger UIViewAutoresizing;
在setAutoresizingMask:的实现中应该是对参数做一个判断,比如上面一段代码的按位或,得到的参数是00010001,表示同时包含UIViewAutoresizingFlexibleHeight与UIViewAutoresizingFlexibleLeftMargin当switch(假设为switch)到这个参数时,就会执行响应的调整。
3.有时需要在自动转屏时做一些额外的处理或改变外观,可以覆盖UIViewController子类的willAnimateRotationToInterfaceOrientation:duration:方法。
- (void)willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)x
duration:(NSTimeInterval)duration{ }