Я использую категорию на UIViewController для swizzle viewWillAppear: метод для нескольких ViewControllers.Метод UIViewController swizzling не работает
@implementation UIViewController (Tracking)
+(void)load
{
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
Class class = [self class];
SEL originalSelector = @selector(viewWillAppear:);
SEL swizzledSelector = @selector(xx_viewWillAppear:);
Method originalMethod = class_getInstanceMethod(class, originalSelector);
Method swizzledMethod = class_getInstanceMethod(class, swizzledSelector);
BOOL didAddMethod = class_addMethod(class, originalSelector, method_getImplementation(swizzledMethod), method_getTypeEncoding(swizzledMethod));
if (didAddMethod)
{
class_replaceMethod(class, swizzledSelector, method_getImplementation(originalMethod), method_getTypeEncoding(originalMethod));
}else{
method_exchangeImplementations(originalMethod, swizzledMethod);
}
});
}
-(void)xx_viewWillAppear:(BOOL)animated
{
[self xx_viewWillAppear:animated];
NSLog(@"VC loaded");
}
@end
Когда я загружаю исходный VC из раскадровки, метод swizzled никогда не вызывается. Он вызывается только в том случае, если метод viewWillAppear в VC закомментирован. Однако, когда я удаляю категорию и перемещаю код в отдельный VC, вызываются оба метода.
#import "ViewController.h"
#import "UIViewController+Tracking.h"
@interface ViewController()
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
}
-(void)viewWillAppear:(BOOL)animated
{
NSLog(@"Inside Controller1");
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
@end
Это нормально реализовать viewWillAppear в ВК, если он будет swizzled? Если нет, как мне это сделать, если мне нужно написать какой-то код в viewVillAppear VC?
Попробуйте только 'method_exchangeImplementations', без добавления, как метод уже существует часть вашего расширения. – Cristik
Кроме того, вы изучаете метод из базового класса, переопределяя его в своем пользовательском классе, поэтому вам нужно вызвать 'super', чтобы выполнить swizzled-метод. – Cristik
@Cristik Я использую категорию, и я не подклассифицирую VC , – KrishnaKumar