Меня заинтересовало использование подкласса UIGestureRecognizer (UILongPressGestureRecognizer) в подклассе ViewController, который у меня был. Мой ViewController имеет UIToolBar, и программно я могу создать экземпляр UILongPressGestureRecognizer, присоединенный к UIToolBar, и все будет работать. Мой ViewController принимает протокол UIGestureRecognizerDelegate. В ViewController у меня есть:
//My ViewController.h
@interface MyViewController: UIViewController<UIGestureRecognizerDelegate>
/* ... */
@property (nonatomic, retain) IBOutlet UIToolbar *toolbar;
@property (nonatomic, retain) IBOutlet UILongPressGestureRecognizer *longPressGesureRecognizer;
/* ... */
- (IBAction)handleGesture;
@end
Затем работает следующий код:
- (void)viewDidLoad
{
[super viewDidLoad];
//configure UILongPressGestureRecognizer
if(self.longPressGesureRecognizer == nil){
UILongPressGestureRecognizer *longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleGesture)];
longPress.minimumPressDuration = 1.5;
longPress.numberOfTouchesRequired = 1;
longPress.delegate = self;
self.longPressGesureRecognizer = longPress;
[self.toolbar addGestureRecognizer:self.longPressGesureRecognizer];
[longPress release];
}
}
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch
{
return YES;
}
- (IBAction)handleGesture{
NSLog(@"Got a gesture!");
}
Я не думал, что мне действительно нужен UILongPressGestureRecognizer в моем View Controller. Когда я попытался создать его полностью в файле MyViewController.xib, я сделал следующее, используя XCode 4.2
- Перетянул UILongPressRecognizer на мой UIToolBar в XIB (прикреплен к панели инструментов в MyViewController).
- Установить свойство делегата UILongPressRecognizer владельцем файла
- Установите свойство селектора для сообщения handleGesture MyViewController.
Когда я запускаю приложение в симуляторе, происходит сбой, который приводит к следующей ошибке GDB в консоли:
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[UILongPressGestureRecognizer initWithCoder:]: unrecognized selector sent to instance
Очевидно, что UILongPressGestureRecognizer initWithCoder: не реализован, но мне интересно, как правильно настроить UIGestureRecognizer в xib-файле. У XCode есть жесты, и я связал это с представлением. Я не вижу, что я иду не так. Все ссылки, которые я видел на UIGestureRecognizer, включая ссылку на класс Apple *1021* UIGestureRecognizer *1021*, всегда используют UIGestureRecognizer из кода. Я не видел пример использования только xib-файла для его настройки.
Я не слишком обеспокоен этой проблемой, потому что я могу обработать ее с помощью кода в ViewController, но я запутался, почему XCode позволяет добавлять распознаватели жестов в кончик, если UILongPressGestureRecognizer и / или UIGestureRecognizer не соответствуют протокол NSCoding и initWithCoder будут вызваны. Моя интуиция говорит, что проблема моя, а не Apple, но я бы хотел понять, что происходит не так.
Спасибо!
Обновление
Кажется, я вижу это поведение только при тестировании, когда использую UISplitViewController. Если я создаю проект на основе ViewController, UIGestureRecognizer работает как положено. Если я добавляю Gesture Recognizer в DetailView приложения UISplitViewController, я получаю сбой, подобный этому:
2011-11-03 10:17:55.873 GestureSplitViewTest[1143:b603] -[UILongPressGestureRecognizer initWithCoder:]: unrecognized selector sent to instance 0x59696b0
2011-11-03 10:17:55.877 GestureSplitViewTest[1143:b603] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[UILongPressGestureRecognizer initWithCoder:]: unrecognized selector sent to instance 0x59696b0'
*** Call stack at first throw:
(
0 CoreFoundation 0x011b15a9 __exceptionPreprocess + 185
1 libobjc.A.dylib 0x01305313 objc_exception_throw + 44
2 CoreFoundation 0x011b30bb -[NSObject(NSObject) doesNotRecognizeSelector:] + 187
3 CoreFoundation 0x01122966 ___forwarding___ + 966
4 CoreFoundation 0x01122522 _CF_forwarding_prep_0 + 50
5 UIKit 0x002fe9fd UINibDecoderDecodeObjectForValue + 2592
6 UIKit 0x002fe2f5 UINibDecoderDecodeObjectForValue + 792
7 UIKit 0x002ff6ac -[UINibDecoder decodeObjectForKey:] + 398
8 UIKit 0x00214979 -[UIRuntimeConnection initWithCoder:] + 212
9 UIKit 0x003d34a8 -[UIRuntimeOutletCollectionConnection initWithCoder:] + 64
10 UIKit 0x002fe9fd UINibDecoderDecodeObjectForValue + 2592
11 UIKit 0x002fe2f5 UINibDecoderDecodeObjectForValue + 792
12 UIKit 0x002ff6ac -[UINibDecoder decodeObjectForKey:] + 398
13 UIKit 0x00213c36 -[UINib instantiateWithOwner:options:] + 804
14 UIKit 0x00215ab7 -[NSBundle(UINSBundleAdditions) loadNibNamed:owner:options:] + 168
15 UIKit 0x000cb628 -[UIViewController _loadViewFromNibNamed:bundle:] + 70
16 UIKit 0x000c9134 -[UIViewController loadView] + 120
17 UIKit 0x000c900e -[UIViewController view] + 56
18 UIKit 0x000c7482 -[UIViewController contentScrollView] + 42
19 UIKit 0x000d7f25 -[UINavigationController _computeAndApplyScrollContentInsetDeltaForViewController:] + 48
20 UIKit 0x000d6555 -[UINavigationController _layoutViewController:] + 43
21 UIKit 0x000d7870 -[UINavigationController _startTransition:fromViewController:toViewController:] + 524
22 UIKit 0x000d232a -[UINavigationController _startDeferredTransitionIfNeeded] + 266
23 UIKit 0x001ed2e9 -[UILayoutContainerView layoutSubviews] + 226
24 QuartzCore 0x01888a5a -[CALayer layoutSublayers] + 181
25 QuartzCore 0x0188addc CALayerLayoutIfNeeded + 220
26 QuartzCore 0x018300b4 _ZN2CA7Context18commit_transactionEPNS_11TransactionE + 310
27 QuartzCore 0x01831294 _ZN2CA11Transaction6commitEv + 292
28 UIKit 0x0001b9c9 -[UIApplication _reportAppLaunchFinished] + 39
29 UIKit 0x0001be83 -[UIApplication _runWithURL:payload:launchOrientation:statusBarStyle:statusBarHidden:] + 690
30 UIKit 0x00026617 -[UIApplication handleEvent:withNewEvent:] + 1533
31 UIKit 0x0001eabf -[UIApplication sendEvent:] + 71
32 UIKit 0x00023f2e _UIApplicationHandleEvent + 7576
33 GraphicsServices 0x00eb2992 PurpleEventCallback + 1550
34 CoreFoundation 0x01192944 __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE1_PERFORM_FUNCTION__ + 52
35 CoreFoundation 0x010f2cf7 __CFRunLoopDoSource1 + 215
36 CoreFoundation 0x010eff83 __CFRunLoopRun + 979
37 CoreFoundation 0x010ef840 CFRunLoopRunSpecific + 208
38 CoreFoundation 0x010ef761 CFRunLoopRunInMode + 97
39 UIKit 0x0001b7d2 -[UIApplication _run] + 623
40 UIKit 0x00027c93 UIApplicationMain + 1160
41 GestureSplitViewTest 0x0000234a main + 170
42 GestureSplitViewTest 0x00002295 start + 53
)
terminate called throwing an exceptionsharedlibrary apply-load-rules all
Current language: auto; currently objective-c
(gdb)