2013-03-07 10 views
5

Mam przycisk, który uruchamia animację, a po zakończeniu animacji zmienia tekst etykiety. Chciałbym napisać test, który sprawdza, czy naciśnięcie przycisku powoduje, że tekst etykiety zmienia się prawidłowo.iOS TDD: Testowanie metody wykorzystującej UIVIew animateWithDuration: animacje: zakończenie:

Wykonanie naciśnięcia przycisku IBAction spowoduje użycie [UIView animateWithDuration:animations:completion:]. Oczywiście nie chcę, aby mój test jednostkowy rzeczywiście czekał 0,5 sekundy na ukończenie animacji.

Myślałem o kpieniu z UIView, ale wydaje się dziwne wstrzykiwać UIView jako zależność od kontrolera widoku. Ponadto, szydercze ramy, których używam (OCMockito) nie wydaje się działać dobrze z szydercze metody klasy.

Myślałem także o metodzie swizzling lub pisania kategorię badań dla UIView i używając implementację, że nic nie robi, ale wywołać blok animations: następnie przez blok completion:. Wydaje mi się to nieco załamane; Obawiam się, że nadpisywanie implementacji metody klasy na UIView może mieć niezamierzone konsekwencje w dół.

Będąc nowicjuszem w TDD, nie jestem pewien, jaka jest najlepsza praktyka. Czy jest to jeden z tych fragmentów kodu, który powinien być uważany za "UI twiddling", a zatem dopuszczalne jest pozostawienie niesprawdzonego? Czy istnieje jakiś bardziej oczywisty sposób na przetestowanie tego, czego mi brakuje?

Odpowiedz

4

Po prostu utworzę właściwość, która określa długość animacji i domyślnie 0,5 sekundy.

W ten sposób test może ustawić czas trwania animacji na 0 i zaobserwować, że tekst etykiety jest aktualizowany bez czekania.

To jest dependency injection i jest szalenie użyteczny, jeśli zaczynasz od TDD. Ma również miły efekt uboczny, aby twój kod był bardziej modułowy i mniej sprzężony.

+0

ciekawy: czy istnieje gwarancja, że ​​animacja zostanie uruchomiona przed zakończeniem testu? czy ta animacja może zostać z jakiegoś powodu opóźniona? – Ying

+1

To naprawdę dobry punkt. Animacja zostanie umieszczona w kolejce na runloopie, co normalnie oznacza, że ​​animacja nastąpi po powrocie testu. Jednak animacja trwająca <= 0 jest przypadkiem specjalnym, który powoduje natychmiastową zmianę. –

+1

@Benoit Ustawienie czasu animacji na 0 lub mniej nie powoduje natychmiastowego wywołania bloku zakończenia. Nawet przy czasie 0 może wywoływać blok w pętli następnego uruchomienia. To, co zrobiłem, to wywołanie asercji w bloku opóźnienia GCD. Zrobiłem oddzielną odpowiedź, aby wyjaśnić moje rozwiązanie. –

Powiązane problemy