2012-06-30 6 views
5

Der Titel macht diesen Sound viel einfacher als es ist .. Ich versuche, eine Absicht zu übertragen, die die meisten Musik-Player pausieren wird.Zuverlässige Pause Medienwiedergabe systemweit in Android

Ich weiß, ich kann eine KeyEvent schaffen, dass KEYCODE_MEDIA_PLAY_PAUSE mit diesem ausgestrahlt wird:

long eventTime = SystemClock.uptimeMillis(); 
    Intent downIntent = new Intent(Intent.ACTION_MEDIA_BUTTON, null); 
    KeyEvent downEvent = new KeyEvent(eventTime, eventTime, KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MEDIA_PLAY_PAUSE, 0); 
    downIntent.putExtra(Intent.EXTRA_KEY_EVENT, downEvent); 
    ctx.sendOrderedBroadcast(downIntent, null); 

Und das funktioniert. Es wird den Stock Media Player anhalten, wie ich es will, zusammen mit den meisten anderen Musik-Playern, die Kopfhörer Play/Pause-Tasten unterstützen. Aber aus irgendeinem Grund funktioniert es nur einmal mit dem Stock Music Player. Ich kann den Knopf drücken, um dies anzurufen, und es wird Musik pausieren. Wenn ich es erneut spiele und meine Pause-Taste erneut drücke, funktioniert es nicht. Sobald ich das Gerät neu starte, funktioniert es wieder. Aber mit Pandora funktioniert es immer so, wie es sollte.

Ich dachte, dass ich in der Lage sein könnte, das zu umgehen und einfach ohne ein KeyEvent zu pausieren. Ich versuchte dies mit AudioManager und eine andere Absicht:

Und das funktioniert auch, und es funktioniert konsequent. Aber es ist von Natur aus fragil, denn wenn man die Absicht direkt an den Android-Musikplayer sendet, ist das der einzige Player, mit dem es funktioniert. Keine Kontrolle über Pandora, Last.FM usw. und ich brauche es, um mit den meisten Musik-Playern zu arbeiten.

Ich bin nur nicht sicher, wohin ich als nächstes gehen soll. Ich bin nicht wählerisch, was für eine Lösung ich bekomme, solange es funktioniert. Wenn Sie mir helfen können, das KeyEvent zu funktionieren, fantastisch, wenn Sie eine völlig andere Lösung haben, fantastisch. Ich will nur, dass es funktioniert! Vielen Dank!

+0

Alles, was Sie hier tun, ist "inhärent fragil". Darüber hinaus wird es viele Medienspieler geben, die dieses Ereignis komplett ignorieren werden. Und es ist durchaus möglich, dass das Betriebssystem eines Tages damit beginnt, gefälschte "ACTION_MEDIA_BUTTON" -Ereignisse so zu blockieren, wie sie andere ähnliche gefälschte Ereignisse blockieren. Wenn Sie einen eigenen Media Player schreiben, verwenden Sie die Audiofokus-Funktionen in 'AudioManager', um den Audiofokus zu erhalten. – CommonsWare

+0

Ich schreibe eigentlich nicht meinen eigenen Media Player. Ich weiß, dass es im Play Store viele voll funktionsfähige Apps gibt, die nach einer bestimmten Zeit die Musik stoppen, aber ich bin nicht besonders glücklich mit ihnen. Ich versuche nur meine eigene Einstellung zu schreiben, und ich muss in der Lage sein, die meisten Musik-Apps anzuhalten. – Geniusdog254

Antwort

2

Um systemweites Audio anzuhalten, starten Sie keine Absicht, sondern fordern den Audiofokus vom System an.

Also, wenn Sie wollen die folgende (in onCreate vorgeschlagen) pausieren alles:

//The Variables we'll need to create 
AudioManager am; 
OnAudioFocusChangeListener af; 

//I do nothing with this listener, but it's required for the next step. 
af = new OnAudioFocusChangeListener() { 

     public void onAudioFocusChange(int focusChange) { 
      if (focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK) { 
       // Lower the volume 
      } else if (focusChange == AudioManager.AUDIOFOCUS_GAIN) { 
       // Raise it back to normal 
      }  
     } 

}; 

//Do the actual pause 
am = (AudioManager)getSystemService(Context.AUDIO_SERVICE); 
int request = am.requestAudioFocus(af, 
    AudioManager.STREAM_MUSIC, 
    AudioManager.AUDIOFOCUS_GAIN); 

Aber vergessen Sie nicht, sich von Fokus lassen mit:

am.abandonAudioFocus(af); 
+0

Diese if/else im Listener werden nur aus der Android-Dokumentation kopiert und tun nichts, Sie können sie entfernen. –

4

ich über diese lief auch. Dank Ihrer Beschreibung glaube ich zu verstehen, was vor sich geht. Sie senden das Keydown-Ereignis, aber niemals die Tastenbelegung, so dass das System der Ansicht ist, dass die Play/Pause-Taste kontinuierlich gedrückt wird. Ich habe diesen Code erfolgreich verwendet.

Intent mediaEvent = new Intent(Intent.ACTION_MEDIA_BUTTON); 
KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MEDIA_PLAY); 
mediaEvent.putExtra(Intent.EXTRA_KEY_EVENT, event); 
context.sendBroadcast(mediaEvent); 

new Timer().schedule(new TimerTask() { 
    @Override 
    public void run() { 
     Intent mediaEvent = new Intent(Intent.ACTION_MEDIA_BUTTON); 
     KeyEvent event = new KeyEvent(KeyEvent.ACTION_UP,KeyEvent.KEYCODE_MEDIA_PLAY); 
     mediaEvent.putExtra(Intent.EXTRA_KEY_EVENT, event); 
     context.sendBroadcast(mediaEvent); 
    } 
}, 100);