UIGestureRecognizerDelegate за управление на жестове мога ли да разреша докосване?

Работя върху приложение, при което повечето от жестовете с докосване ще бъдат жестове за панорамиране (но не използвам разпознавател на жестове за панорамиране). Използвам UIGestureRecognizerDelegate и използвам touchesBegan, touchesMoved, touchesEnded и touchesCancelled. Има обаче няколко точки на екрана, където, ако там започне панорама, искам вместо това да го разпозная като събитие с докосване. Мога да направя това, като просто разпозная местоположението в touchesBegan. Въпросът ми е, мога ли да разпределя докосването в този момент, за да предотвратя продължаването на панорамата? Ако тиган започва от това място на екрана, гарантирано е, че няма да бъде наистина замислен като тиган от потребителя. Надявам се, че това има смисъл.

РЕДАКТИРАНЕ: Разбрах, че допълнителните разходи за управление на кран дори за точка, която трябва да се игнорира, са незначителни, така че мисля, че просто ще направя това. Ще запазя въпроса тук обаче, в случай че има начин да спрете проследяването на жеста.

Имам нужда и от предложение как да се справя със следната ситуация.

Да предположим, че потребителят стартира панорама (не в току-що описаната зона, а другаде, където наистина е предвидено да бъде панорама), и докато панорамата продължава, друга панорама се стартира другаде на екрана. Как да разпозная тази ситуация?

РЕДАКТИРАНЕ: Сега тествам дали този код ще реши този проблем:

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer {
   return YES;
}

Редактиране: ARC забранява изричния dealloc, така че сега преразглеждам въпроса си към по-общ за това какво, ако изобщо мога да направя, за да потисна по-нататъшни действия. Или просто трябва да се справя с това?


person Victor Engel    schedule 18.12.2012    source източник
comment
Можете да потиснете по-нататъшно действие. Моля, вижте въпроса: stackoverflow.com/questions/11667329/   -  person bibo bode    schedule 18.12.2012
comment
@Fawaz Не мисля, че това се отнася за моята ситуация. Имам основен изглед, който съдържа неизвестен брой подизгледи, които по същество са спрайтове, движещи се наоколо. Разпознавателят на жестове, с който работя, е прикрепен към главния изглед, а не към подизгледите. Разпознавателят никога не трябва да се премахва, освен ако не пропускам нещо.   -  person Victor Engel    schedule 18.12.2012


Отговори (4)


Искате метода UIGestureRecognizerDelegate gestureRecognizer:shouldReceiveTouch:. Що се отнася до разпознаването, когато започва второ панорамиране, докато такова вече е в ход, можете да опитате променлива на състоянието, която задавате, когато разпознавателят на жестове започне да разпознава докосвания.

person Brendon    schedule 18.12.2012
comment
Току-що направих проследяване на местоположения и случаи на докосване и съм изненадан от резултатите. По принцип това, което направих, беше да добавя NSLog, отпечатващ номера на екземпляра на докосване, който увеличавам, докато преминава през цикъла на докосване, и да отпечатам местоположението на докосване. Винаги има само един случай. Когато добавя нов пан, докато предишният е в ход, местоположенията просто се актуализират за всяко едно, сякаш движението преминава от едно към друго. Мислех, че ще има отделни случаи на докосване за всяко докосване. - person Victor Engel; 18.12.2012
comment
Забравете предишния коментар. Има отделни обекти. Сигурно имам грешка някъде, която пречи на второто да бъде разпознато. Ще работя върху тази грешка, преди да се върна към този въпрос. - person Victor Engel; 18.12.2012
comment
Ето какво изглежда се случва: UI потокът върви: 1) Потребителят започва докосване1, 2) потребителят премества докосване1, 3) потребителят започва докосване2, 4) потребителят премества докосване2, 5) потребителят завършва докосване 2, 6) потребителят приключва докосване1 (вероятно беше движейки се през цялото време). Резултатът е, че touchesEnded се извиква за touch1, но не и за touch2. Това е неочакван резултат и не съм сигурен как да се справя. Има обект на докосване с начало, преместен, но без край или отменен. Така че моята логика за обработка на докосването никога не се извиква. - person Victor Engel; 18.12.2012
comment
Опитахте ли да зададете maximumNumberOfTouches на разпознавателите на 1? Това може да елиминира проблема ви с втория жест. - person Brendon; 19.12.2012
comment
Ами ако искам повече от едно докосване да е възможно? Ако това беше проблемът, бих очаквал един обект с брой докосвания да е различен от едно. Това не е така. - person Victor Engel; 19.12.2012
comment
Ако се нуждаете само от две или три докосвания, за да са възможни наведнъж, можете да опитате да използвате толкова много разпознаватели на жестове. Не бих го нарекъл страхотно решение, но трябва да е лесно за изпълнение. - person Brendon; 21.12.2012
comment
Играта, върху която работя, може да има до четирима играчи, като всеки може да използва повече от едно едновременно докосване. Не е много вероятно, но е възможно горната граница от 11 действително да се използва. Във всеки случай проблемът ми беше, че подизгледът имаше активирано взаимодействие с потребителя. Това в комбинация с проследяване на докосвания по обект вместо по координати разреши проблема ми. - person Victor Engel; 22.12.2012

Не съм сигурен, че разбирам напълно въпроса ви, но може би това ще помогне:

Първо: С ARC не трябва да се опитвате да освободите нищо, но можете да деактивирате жеста. Например, ако сте нарекли жеста panGesture, можете да направите следното:

panGesture.enabled = NO;

Вместо да се опитвате да разпределяте и освобождавате, просто активирайте и деактивирайте.

Второ: Можете да проследявате движенията на панорамен жест. Във вашия метод IBAction можете да заснемете координатите на първото докосване, след което да решите дали искате това движение да се брои като панорама или докосване въз основа на това къде започва жестът.

За повече информация относно Pan Gestures ви предлагам да погледнете тук:

Урок за UIGestureRecognizer в iOS 5: щипки, панорами и още!

и разбира се тук:

Ръководство за обработка на събития за iOS: Разпознаватели на жестове

person Axeva    schedule 18.12.2012
comment
Не си спомням защо не използвах разпознаването на панорамни жестове, но имаше ограничения, които бяха твърде ограничаващи. Предполагам, че пропуснах да отбележа, че използвам UIGestureRecognizerDelegate и улавям събитията начало, преместване, край и отмяна. - person Victor Engel; 18.12.2012

не, не можете да го освободите и това така или иначе няма да работи


тъй като използвате GestureRecognizer, можете да отмените това

@interface UIGestureRecognizer (Cancel)
- (void)cancel;
@end

@implementation UIGestureRecognizer (Cancel)
- (void)cancel
{
    self.enabled = NO;
    self.enabled = YES;
}
@end

OR

трябва да отмените докосванията ... но досега има само частен api за това. най-добрият ви залог е да зададете bool за вашия клас като _isCanceled

нулирайте го на NO в touchesBegan и го задайте на YES, когато искате да прекратите обработката на докосване

OR

можете да запазите докосванията, които искате да отмените, в NSSET, който съхранявате във вашия клас, и да игнорирате тези докосвания

person Daij-Djan    schedule 18.12.2012
comment
Предполагате ли, че съществува метод за отмяна, който трябва да използвам (не виждам такъв в документацията) или че създам свой собствен в моя подклас? - person Victor Engel; 18.12.2012

Ето решенията, които използвах.

За да разпозная докосване, аз просто сравнявам координатите за докосване на обект от touchesBegan до touchesEnded и го считам за докосване, ако координатите са еднакви или преместени незначително. Пренебрегвам touchesMoved, тъй като докосване, което започва и завършва приблизително на едно и също място, но се движи между тях, е много малко вероятно да се случи в приложението ми.

За да разпозная второ панорамиране, след като първото панорамиране е започнало, проследявам докоснати обекти. В този сценарий първата и втората панорама получават два различни обекта за докосване. Първоначално проследявах координатите и следвах последователната верига, съответстваща на currentLocation с previousLocation, но това не проработи, защото второто докосване се държи различно от първото по някаква причина. Както и да е, проследяването на допирните обекти е лесно. Що се отнася до кода, той не "знае" дали вторият обект на докосване се появява едновременно с първия или не.

person Victor Engel    schedule 22.12.2012