複数のプロトコルを実装する必要があるビュー コントローラー クラスがあります。整理整頓しすぎないように、各プロトコルのメソッドをビュー コントローラー クラスのカテゴリに入れる習慣があります。
今回は、クラスがいずれかのプロトコルを実装していないという警告をリンカから受け取りました。メソッドは実行時に機能しますが、リンカーはカテゴリ内の実装を認識できないようです。
別のプロジェクトでクラスを単純化したところ、同じ場所で同じエラーが発生しました。
クラスヘッダー:
#import <UIKit/UIKit.h>
#import <AddressBook/AddressBook.h>
#import <AddressBookUI/AddressBookUI.h>
@interface TopVC : UIViewController
<
UINavigationControllerDelegate,
ABPeoplePickerNavigationControllerDelegate
>
{}
@end
TopVC.m (表示されていません) は、変更なしで自動的に生成されたものです。UINavigationControllerDelegate
プロトコル メソッドは、このカテゴリで実装されます。
#import <Foundation/Foundation.h>
#import "TopVC.h"
@interface TopVC (UINavigationControllerDelegate)
- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated;
- (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated;
@end
#import "TopVC+UINavigationControllerDelegate.h"
@implementation TopVC (UINavigationControllerDelegate)
- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated{
NSLog(@"navigationController:willShowViewController:animated:");
}
- (void)navigationController:(UINavigationController *)navigationController didShowViewController:(UIViewController *)viewController animated:(BOOL)animated{
NSLog(@"navigationController:didShowViewController:animated:");
}
@end
リンカーは、このカテゴリのこのメソッドについて文句を言いません。ただし、カテゴリをABPeoplePickerNavigationControllerDelegate
同じ方法でプロトコルを実装しようとすると、次のように不平を言います。
#import "TopVC.h"
@interface TopVC (ABPeoplePickerNavigationControllerDelegate)
- (void)peoplePickerNavigationControllerDidCancel:(ABPeoplePickerNavigationController *)peoplePicker;
- (BOOL)peoplePickerNavigationController:(ABPeoplePickerNavigationController *)peoplePicker shouldContinueAfterSelectingPerson:(ABRecordRef)person;
- (BOOL)peoplePickerNavigationController:(ABPeoplePickerNavigationController *)peoplePicker shouldContinueAfterSelectingPerson:(ABRecordRef)person property:(ABPropertyID)property identifier:(ABMultiValueIdentifier)identifier;
@end
#import "TopVC+ABPeoplePickerNavigationControllerDelegate.h"
@implementation TopVC (ABPeoplePickerNavigationControllerDelegate)
- (void)peoplePickerNavigationControllerDidCancel:(ABPeoplePickerNavigationController *)peoplePicker{
}
- (BOOL)peoplePickerNavigationController:(ABPeoplePickerNavigationController *)peoplePicker shouldContinueAfterSelectingPerson:(ABRecordRef)person{
return YES;
}
- (BOOL)peoplePickerNavigationController:(ABPeoplePickerNavigationController *)peoplePicker shouldContinueAfterSelectingPerson:(ABRecordRef)person property:(ABPropertyID)property identifier:(ABMultiValueIdentifier)identifier{
return YES;
}
@end
リンカーは不平を言います:
warning: incomplete implementation of class 'TopVC'
warning: method definition for '-peoplePickerNavigationController:shouldContinueAfterSelectingPerson:property:identifier:' not found
warning: method definition for '-peoplePickerNavigationController:shouldContinueAfterSelectingPerson:' not found
warning: method definition for '-peoplePickerNavigationControllerDidCancel:' not found
warning: class 'TopVC' does not fully implement the 'ABPeoplePickerNavigationControllerDelegate' protocol
私が見ることができる唯一の違いは、UINavigationControllerDelegate
プロトコルメソッドがすべてオプションであるのに対し、ABPeoplePickerNavigationControllerDelegate
すべて必須であることです。
それでも、リンカーが文句を言ったとしても、メソッドは実行時に呼び出されます。警告のあるビルドを拒否するだけです。どうやら何かを見逃したか、どこかで些細な間違いを犯したようですが、それを見つけることはできません。