2012-10-17 8 views
5

Moja aplikacja to OpenGL, mocno wykorzystywana, używana do przetwarzania obrazów, renderowania scen, podglądów itp. Jednak po wdrożeniu wielu zadań jako oficjalnego dokumentu firmy Apple "Podręcznik programowania OpenGL ES dla iOS", dziwne awarie wciąż pojawiały się sporadycznie. Debug Navigator ślad stosu pokazuje coś jak „sgxPatchDeferredFramebufferOffsets”, „presentRenderbuffer EXC_BAD_ACCESS”, „gpus_ReturnNotPermittedKillClient” itpAplikacja OpenGL ES ulega awarii po zablokowaniu ekranu lub wprowadzeniu tła

Więc chciałbym wiedzieć, co dokładnie należy wdrożyć OpenGL ES wielozadaniowych.

============= UPDATE: Problem rozwiązany ============

Dzięki za odpowiedź, CStreel i innych facetów, którzy próbował pomóc.

Po przeczytaniu "Aplikacje w tle mogą nie wykonywać poleceń w sprzęcie graficznym" w "Podręczniku programowania ES dla systemu iOS" po raz drugi, linia po linii, mam nowe zrozumienie tego problemu.

Duży problem z moją aplikacją to: I nie powinien implementować wielozadaniowego OpenGL ES w metodzie powiadamiania. Ponieważ, w przeciwieństwie do metod delegowania, metody powiadomień będą nazywane asynchronicznie, te zatrzymujące akcje animacji i wywołania glFinish() mogą nie zadziałać, gdy aplikacja zostanie już przeniesiona w tło. Może się to zdarzyć częściej, gdy kliknę przycisk blokady ekranu, gdy wykonuję serię akcji związanych z OpenGL ES.

Jeśli znalazłeś inne problemy, skontaktuj się ze mną.

+0

Problem występuje, jeśli wywołasz OpenGL ES z kolejki szeregowej w tle. Nawet po powiedzeniu stoperowi, aby przestał strzelać, blok kończy się i może spowodować awarię. http://stackoverflow.com/questions/19215554/how-to-stop-opengl-drawing-when-calling-opengl-from-background – openfrog

Odpowiedz

4

Gdy aplikacja ma zamiar wprowadzić tła, jeśli nazywa aplikacja dowolny Ogles funkcjonuje system operacyjny zabije swoją aplikację od razu

Przeczytaj App States & Multitasking więcej informacji Przeczytaj Being a Responsible Background App

Oto niektóre wyciągi z tego dokumentu:

(Required) When moving to the background, make sure your app adjusts its behavior appropriately. 

w odniesieniu do Ogles

...the app should stop calling OpenGL ES functions. 
+0

Zaimplementowałem tych delegatów, a także powiadomienia. Gdy aplikacja zrezygnowała z aktywnego stanu, zatrzymałem sesję przechwytywania i animację. Próbowałem wywołać polecenie glfinish() w kolejce wywołania przetwarzania po otrzymaniu aktywnego powiadomienia o rezygnacji, ale to nie pomogło. – cocoatoast

0

Powiadomienia mogą być synchroniczne lub asynchroniczne. Jeśli zarejestrujesz się w powiadomieniach określających NSOperationQueue, wywołanie zwrotne będzie asynchroniczne, w przeciwnym razie uważam, że zawsze będzie ono synchroniczne.

Miałem kilka z tych wypadków i znalazłem kilka błędów w moim kodu:

  1. Wspólna EAGLContext, mimo że „wielowątkowy” nie został zawsze ustawione na wszystkich wątków go używać. Wygląda na to, że musisz ustawić kontekst na głównym wątku za każdym razem, gdy opuszcza RunLoop , aby wprowadzić kod aplikacji i wydać polecenie openGL.
  2. iOS 6 potrzebował dodatkowego "glFlush()" podczas zmiany buforów, prawdopodobnie z powodu błędu w iOS 6. iOS 5 i 7 nie uległy zmianie.
  3. Brak synchronizacji między powiadomieniem "DidEnterBackground" a innym kodem/wątkami, co oznaczało, że główny wątek powiadamiający o zmianie stanu aplikacji powracał wcześniej, gdy inne wątki nadal używały OpenGL.Przytrzymaj wątek powiadomień, aż zakończysz wywoływanie OpenGL. Dopiero po powrocie, iOS uruchamia "watchdog" na openGL.

Używam powiadomień DidEnterBackground/WillEnterForeground (bez wywołań zwrotnych) do zatrzymywania/restartowania operacji OpenGL. Nadal dostaję bardzo rzadką awarię (muszę użyć automatyzacji i zablokować/odblokować/obrócić przez 20-30 minut przed jej otrzymaniem), ale użycie WillResignActive/DidBecomeActive nie ma znaczenia; zdarzają się niezależnie.