2012-04-11 4 views
10

Каков правильный способ крепления и удаления UIGestureRecognizer на вид?Правильный способ крепления/удаления UIGestureRecognizers

Обычно я создаю и прикрепляю UIGestureReconizers в -viewDidLoad. Должен ли я использовать removeGestureRecognizer в -viewDidUnload? Или они автоматически удаляются?

Например это лучший способ создать свойство UIGestureRecognizer и инициализировать его в методе инициализации в ViewController, а затем прикрепить/удалить это свойство gestureRecognizer в -viewDidAppear/-viewDidDisappear?

(Примечание Я использую ARC)

Спасибо.

+0

Я уже пропустил это, но не нашел ответа на свой вопрос. – mrd3650

+0

@ TheLion: «Извините, эта страница не найдена». – Colas

+0

Извините, что яблоко изменило его так [здесь] (https://developer.apple.com/library/ios/documentation/EventHandling/Conceptual/EventHandlingiPhoneOS/GestureRecognizer_basics/GestureRecognizer_basics.html), это новый URL-адрес для того же ресурса. Спасибо, что указали это @Colas –

ответ

10

По существу вы можете создавать, добавлять и удалять распознаватели жестов, когда это имеет смысл. И «когда это имеет смысл» варьируется в зависимости от нескольких вещей, но обычно только от того, сохраните ли вы их как иваров. С помощью ARC ключ управляет сильными ссылками; С ARC ivars сильные по умолчанию.

Итак, скажем, вы добавляете распознаватель крана. В этом случае вам не нужно снова обращаться к распознавателю. Я бы создал его вот так:

-(void)viewDidLoad{ 
    [super viewDidLoad]; 
    UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(handleTap:)]; 
    [self.view addGestureRecognizer:tap]; 
} 

С помощью этого сценария вам не нужно ничего другого, чтобы управлять этим распознавателем. Система взглядов держит на ней сильную ссылку. Все, что вы делаете, это сидеть сложа руки и ждать, пока он вызовет handleTap:. Когда выгрузите представление, этот распознаватель будет отменен.

Этот сценарий также не будет хорошим дополнением к этому распознавателю в viewWillAppear:, так как нетрудно представить себе ряд событий, которые приведут к созданию нескольких распознавателей.

Так логично, если вы хотите добавить распознаватель в методы внешнего вида, вам нужно будет провести некоторую ссылку на них в ivar. Но опять же это не всегда плохая идея. Как правило, причиной, по которой вы хотите ссылаться на ваши распознаватели, является помощь в логике методов <UIGestureRecognizerDelegate>, если они используются.

Я лично никогда не добавлю распознавателя в метод initWith.. для вложения позже. Единственное преимущество заключается в том, что любой распознаватель, созданный там, будет храниться в течение всего срока действия контроллера вида. Но так как распознаватель довольно явно является частью системы взглядов, этот вид мусора - вверх MVC, что Cocoa большой. Также в режиме низкой памяти состояние контроллеров в стеке навигации очищается, но в этом случае распознаватель может по-прежнему использовать память (а не огромные объекты) по какой-либо причине.

Вы, безусловно, можете добавить распознаватель в метод view(Will/Did)Appear: и удалить его в view(Will/Did)Disappear:. Не мое предпочтение.Я не думаю, что только потому, что представление и удаление modal было обнаружено или удалено или произошло переключение push/pop, я должен удалить и снова добавить мои распознаватели.

Я бы порекомендовал почти всегда использовать viewDidLoad, чтобы создать экземпляр и прикрепить свои распознаватели. Просто помните, чтобы скрыть все сильные ссылки на них в viewDidUnload, чтобы помочь в ситуации с низкой памятью. И снова с ARC не нужно ничего делать с ivars в dealloc.

+0

Спасибо NJones за подробный ответ! Причина присоединения/отсоединения Recognizers в представлении (будет/сделана) Загрузка и выгрузка носит чисто по соображениям памяти (так что, когда вид не отображается на экране, память освобождается и назначается обратно, когда она находится на экране), но из того, что вы говорите , это не делает такой разницы. – mrd3650

0

viewDidUnload вызывается только в условиях низкой памяти и не может быть вызван вообще. Поэтому любые распознаватели жестов, удаленные в viewDidUnload, также должны быть удалены в dealloc. EI другой метод, о котором вы говорите, в порядке.

0

ОК viewWillAppear:Animated и viewWillDisappear:animated будет лучшим выбором для любых действий с помощью жестов, насколько мне известно.

Смежные вопросы