Рекурсивное воспаление приводит к аварии
Я использую DAKeyboardControll
в моем приложении. у него есть метод с именем: swizzled_addSubview
и реализовать как это:
- (void)swizzled_addSubview:(UIView *)subview
{
if (!subview.inputAccessoryView)
{
if ([subview isKindOfClass:[UITextField class]])
{
UITextField *textField = (UITextField *)subview;
if ([textField respondsToSelector:@selector(setInputAccessoryView:)])
{
UIView *nullView = [[UIView alloc] initWithFrame:CGRectZero];
nullView.backgroundColor = [UIColor clearColor];
textField.inputAccessoryView = nullView;
}
}
else if ([subview isKindOfClass:[UITextView class]]) {
UITextView *textView = (UITextView *)subview;
if ([textView respondsToSelector:@selector(setInputAccessoryView:)] && [textView respondsToSelector:@selector(isEditable)] && textView.isEditable)
{
UIView *nullView = [[UIView alloc] initWithFrame:CGRectZero];
nullView.backgroundColor = [UIColor clearColor];
textView.inputAccessoryView = nullView;
}
}
}
[self swizzled_addSubview:subview];
}
проблема
Недавно в моей новой версии, совместимой с AutoLayout, я получил некоторые сбои в этом методе и причины их:-[UIView(DAKeyboardControl) swizzled_addSubview:]
,EXC_BAD_ACCESS KERN_PROTECTION_FAILURE at 0x0090dffc
Я знаю, что эта проблема произошла для многих, но почему она не может работать правильно?
этот сбой произошел только для 8 пользователей 54 раза, у 50 % из них устройство для джейлбрейка, а у другого - устройство без джейлбрейка!
2 ответа
Метод Swizzling вызывает проблемы во время выполнения. Я также получил такое же исключение, чтобы избавиться от этого, я использовал BABFrameObservingInputAccessoryView, который отлично работает для меня. https://github.com/brynbodayle/BABFrameObservingInputAccessoryView
Скорее всего, ваш метод на самом деле не работает, поэтому вы получите рекурсивный вызов, который, очевидно, завершится сбоем. Это хитрая вещь в Swizzling: он обменивается двумя методами, поэтому каждый вызов addSubview будет вызывать swizzled_addSubview, а вызов swizzled_addSubview фактически вызывает addSubview.