2013-03-11 31 views
6

Próbuję programowo podnieść głośność do maksymalnej wartości strumienia STREAM_MUSIC, ale mam, gdy robię "Wysyłanie komunikatu do obsługi po nieważnym wątku". Wydaje się również, że nie zwiększa to objętości w 100% czasu, chociaż kiedy dostanę ten błąd, podniesie go NAJCZĘŚCIEJ z biegiem czasu.Menedżer zarządzania dźwiękiem wysyłający wiadomość do programu obsługi w martwym wątku?

Kod jest:

System.out.println("Maximum volume for this stream is: "+maxstreamvol+" and it used to be set to: "+currentvol);  
final AudioManager am = (AudioManager)this.getSystemService(Context.AUDIO_SERVICE); 
am.setStreamVolume(AudioManager.STREAM_MUSIC, maxstreamvol, AudioManager.FLAG_SHOW_UI); 
am.setStreamSolo(AudioManager.STREAM_MUSIC, true); 
System.out.println("Volume Raised!"); 

Po googling wokół, wydaje się, że błąd ten ma do czynienia z wielowątkowych sytuacji ... Kod w tym momencie powinien być uruchomiony na wątków UI.

W rzeczywistości, nawet otoczył go:

runOnUiThread(new Runnable() { 

    public void run() { 
     // code_goes_here 
    } 
}); 

, a które produkowały ten sam błąd. Błąd, który widzę jest następujący:

I/System.out(24949): Maximum volume for this stream is: 15 and it used to be set to: 0 
W/MessageQueue( 490): Handler (android.media.AudioManager$FocusEventHandlerDelegate$1) {42b52f28} sending message to a Handler on a dead thread 
W/MessageQueue( 490): java.lang.RuntimeException: Handler (android.media.AudioManager$FocusEventHandlerDelegate$1) {42b52f28} sending message to a Handler on a dead thread 
W/MessageQueue( 490): at android.os.MessageQueue.enqueueMessage(MessageQueue.java:294) 
W/MessageQueue( 490): at android.os.Handler.enqueueMessage(Handler.java:618) 
W/MessageQueue( 490): at android.os.Handler.sendMessageAtTime(Handler.java:587) 
W/MessageQueue( 490): at android.os.Handler.sendMessageDelayed(Handler.java:558) 
W/MessageQueue( 490): at android.os.Handler.sendMessage(Handler.java:495) 
W/MessageQueue( 490): at android.media.AudioManager$1.dispatchAudioFocusChange(AudioManager.java:1894) 
W/MessageQueue( 490): at android.media.IAudioFocusDispatcher$Stub.onTransact(IAudioFocusDispatcher.java:57) 
W/MessageQueue( 490): at android.os.Binder.execTransact(Binder.java:351) 
W/MessageQueue( 490): at dalvik.system.NativeStart.run(Native Method) 
I/System.out(24949): Volume Raised! 

Czy ktoś wie, co się tutaj dzieje?

+1

Czy żądasz * Audio Focus * w swoim kodzie? Spróbuj także użyć 'applicationContext' np. '(AudioManager) getApplicationContext(). GetSystemService (Context.AUDIO_SERVICE);' – iTech

+0

Próbowałem tego i przetestowałem. To sprawiło, że upadek Handler'a zniknął, ale nadal nie pozwala mi niezawodnie podnosić dźwięku ... – Dwebtron

+0

Edycja: Okazało się, że audio nie było moją winą, ponieważ spowodowałem wyścig! Ups! (Zapomniałem edytować to jakiś czas temu) – Dwebtron

Odpowiedz

3

Twój problem może być związany z przedstawionego w tym wątku - onPostExecute not being called in AsyncTask (Handler runtime exception)

się ekran audio zmiany ostrości jest wyzwalanie zdarzenia UI, że Android nie jest w stanie wypełnić. Nie jest od razu jasne, dlaczego tak się dzieje. Być może menedżer audio został uzyskany z jednym kontekstem, a toast w celu pokazania, że ​​głośność jest wykonywana w innym kontekście? Szybką i brudną zmianą jest zamienić flagę na FLAG_VIBRATE i sprawdzić, czy to robi różnicę. To ograniczyłoby problem do aktualizacji interfejsu użytkownika, nad którą możesz następnie pracować.

+0

Właściwie dodałem właśnie AudioManager.FLAG_SHOW_UI, aby upewnić się, że dźwięk został poprawnie podniesiony. Poprzednio wywoływałem funkcję setStreamVolume z flagą "0". Naprawdę, strzelam, żeby to wszystko działo się za kulisami, więc nie mam nic przeciwko, jeśli będę musiał wrócić do flagi '0' .... ale to też nie działa w 100% sposób, flagi na 0 lub AudioManager.FLAG_SHOW_UI wydają się dawać taki sam wynik, oczywiście jeden ze wskaźnikiem interfejsu użytkownika i bez niego. – Dwebtron

+1

Czy aplikacja AudioManager jest wymagana w innym miejscu aplikacji? Zakładam, że początkowo wysłany fragment kodu pochodzi z działania.Wkopałem się w kod Impl i okazało się, że menedżer audio używa wewnętrznego looper'a i handler'a, aby ostrzec framework o zmianach fokusu. Zastanawiam się, czy wewnętrzny program obsługi, który jest buforowany z niewłaściwym kontekstem, może spowodować ten problem. –

+0

Nie jestem pewien ... ale to może być możliwe. Jak mam to sprawdzić i/lub naprawić, jeśli tak było? Ilekroć wywołuję setStreamVolume, poprzednia linia jest zawsze: final AudioManager am = (AudioManager) getApplicationContext(). GetSystemService (Context.AUDIO_SERVICE); – Dwebtron

0

Audiomanager wykorzystuje wątek, który został stworzony, aby powołać swoją zwrotnego czy manipulowanie UI (wyświetlacz Tom tosty itp)
(przez Looper.myLooper lub getMainLooper patrz this).

Powinieneś więc upewnić się, że twoje pierwsze połączenie do Context.getSystemService(AUDIO_MANAGER) dzieje się w wątku interfejsu użytkownika.
(nie jestem pewien, że połączenia podsekwencji będzie ponownie użyć tego wystąpienia, ale nawet gdybym ponownie odzyskać Audiomanager wyjątek nadal występują)

Natknąłem ten problem i rozwiązać go dzisiaj, dodając, że wezwanie do mojej aplikacji. onCreate(). (Nieco podobna do odpowiedzi this?)