这几天视觉稿还没有出来,于是开始做一些通用的公共组件。自定义了几个控件类,发现出现自定义控件无法响应事件,就在网上查了下资料,遂记下。
程序里创建了一个带xib的MyViewController。然后在xib里拖进去一个UIView进去,然后把这个UIView的custom class 改写成MyCustomControl(自定义的一个控件继承自UIView,可以响应点击事件)。然后运行,发现点击这个自定义控件时无法响应点击事件。。。
MyViewController的实例是通过[ [MyViewController alloc] init] 方式创建和初始化的。打开MyViewController.m文件发现只有
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
初始化方法(创建MyViewController时Xcode自动创建的),但并没有init方法,而且这个方法被调用了。当然我们知道所有继承自NSObject类的对象都会从父类继承到init方法。而我的MyViewController实例通过[ [MyViewController alloc] init] 创建和初始化的。因此可以猜测下,对于带xib的类通过init方法初始化的时候,虽然我们没有重写init方法,但是Xcode一定在某个地方为我们的MyCustomControl重写了init方法,并且改方法体里会主动调用initWithNibName:bundle:方法。问题就来了,如果我们通过initWithNibName:bundle:或者loadNibNamed等通过加载xib方式来初始化视图的时候,是不会调用xib里各控件对象的- (id)initWithFrame:(CGRect)frame方法的(如果代码生成的视图则会调用来完成视图的初始化)。而是通过给xib里的各个对象发送awakeFromNib消息,来完成各个控件对象的初始化(MyCustomControl里重写init方法,发现该方法也没有被调用)。因此我之前在MyCustomControl写的各个响应事件的根本就没有作用,因为根本就没有执行过,++。
只要在MyCustomControl里重写awakeFromNib方法即可,done。