How do applications like Soundcloud stop another app's MediaPlayer? For example, when I am playing a song through Google Music and I open SoundCloud, the song from Google Music stops playing as soon as the Soundcloud song starts. I might be missing something obvious but I have always wondered how this is achieved.
Thanks,
Justin
Use Audio Focus. See Request the Audio Focus
AudioManager am = mContext.getSystemService(Context.AUDIO_SERVICE);
...
// Request audio focus for playback
int result = am.requestAudioFocus(afChangeListener,
// Use the music stream.
AudioManager.STREAM_MUSIC,
// Request permanent focus.
AudioManager.AUDIOFOCUS_GAIN);
if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
am.unregisterMediaButtonEventReceiver(RemoteControlReceiver);
// Start playback.
}
Adding on to #TCA's answer:
There is only one AudioManager. So, Audio focus is assigned to each application that requests it one by one. This means that if another application requests audio focus, your application will lose it. You will be notified of the loss of audio focus through the onAudioFocusChange handler of the Audio Focus Change Listener (afChangeListener in TCA's answer) you registered when requesting the audio focus.
private OnAudioFocusChangeListener focusChangeListener =
new OnAudioFocusChangeListener() {
public void onAudioFocusChange(int focusChange) {
AudioManager am =(AudioManager)getSystemService(Context.AUDIO_SERVICE);
switch (focusChange) {
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT) :
//Transient audio loss
break;
case (AudioManager.AUDIOFOCUS_LOSS) :
//Audio focus loss. Stop playback.
break;
case (AudioManager.AUDIOFOCUS_GAIN) :
//Audio focus gain. Start playback.
break;
default: break;
}
}
};
Related
I need to pause a player of a specific application - for example Spotify. But if some other player plays I would like to keep it playing and only pause the Spotify.
Is there any function how I can do it?
I ended up with possibility to pause all apps, but not the specific one.
Or other help would be if I could identify what app is currently playing a Media Player and if it is Spotify then I can pause all apps, but I will know that I stop only Spotify.
Cheers
There is no way to way extensively to stop particular app player audio
If they implement music api which is directly implemented with hardware
then if you play music in your app then its automatically stop
with AudioManager. You can also get callback if other application play audio.
private OnAudioFocusChangeListener focusChangeListener =
new OnAudioFocusChangeListener() {
public void onAudioFocusChange(int focusChange) {
AudioManager am =(AudioManager)getSystemService(Context.AUDIO_SERVICE);
switch (focusChange) {
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK) :
// Lower the volume while ducking.
mediaPlayer.setVolume(0.2f, 0.2f);
break;
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT) :
pause();
break;
case (AudioManager.AUDIOFOCUS_LOSS) :
stop();
ComponentName component =new ComponentName(AudioPlayerActivity.this,MediaControlReceiver.class);
am.unregisterMediaButtonEventReceiver(component);
break;
case (AudioManager.AUDIOFOCUS_GAIN) :
// Return the volume to normal and resume if paused.
mediaPlayer.setVolume(1f, 1f);
mediaPlayer.start();
break;
default: break;
}
}
};
I have created an application to play audio using media player but my player does not stops even if other app like youtube starts playing video.
How to stop audio if other app starts playing an audio.
I have used mediaPlayer.start(); to play an audio.
Any help would be appreciated.
You'll need to listen for Audio focus change.
Refer: https://developer.android.com/reference/android/media/AudioManager.OnAudioFocusChangeListener.html
OnAudioFocusChangeListener callback is called with a flag indicating audio focus status, which can be used to stop media player.
You can set a AudioFocusChangeListener to listen for Audio focus change.
private AudioManager.OnAudioFocusChangeListener mOnAudioFocusChangeListener;
audioFocusChangeListener =new AudioManager.OnAudioFocusChangeListener()
{
#Override
public void onAudioFocusChange ( int focusChange){
switch (focusChange) {
case AudioManager.AUDIOFOCUS_GAIN:
// Set volume level to desired levels
play();
break;
case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT:
// You have audio focus for a short time
play();
break;
case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK:
// Play over existing audio
play();
break;
case AudioManager.AUDIOFOCUS_LOSS:
stop();
break;
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT:
// Temporary loss of audio focus expect to get it back you can keep your resources around
pause();
break;
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK:
// Lower the volume
break;
}
}
}
;
When I play 'Soundcloud' or 'Saavn' music playing app and I start my own app, the music in Saavn or Soundcloud is still playing in background. Need a way to stop it using code. How to do it ?
I tried this -
AudioManager mAudioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
String SERVICECMD = "com.android.music.musicservicecommand";
String CMDNAME = "command";
String CMDSTOP = "stop";
if(mAudioManager.isMusicActive()) {
Intent i = new Intent(SERVICECMD);
i.putExtra(CMDNAME , CMDSTOP );
HomeActivity.this.sendBroadcast(i);
}
but it is only useful in stopping the music if Android's default music player is playing in background and not 3rd party apps like Saavn and Soundcloud.
One possible solution I found on this is using the AudioManager.requestAudioFocus(...) function
AudioManager am = (AudioManager)getSystemService(Context.AUDIO_SERVICE);
Code example:
int result = am.requestAudioFocus(focusChangeListener, //Request audio focus for playback
AudioManager.STREAM_MUSIC, //Use the music stream.
AudioManager.AUDIOFOCUS_GAIN); //Request permanent focus.
if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
// other app had stopped playing song now , so u can do u stuff now .
}
Audio focus is assigned in turn to each application that requests it. This means that if another application requests audio focus, your's will lose it.
The app is notified when there is a change on the AudioFocus, through the onAudioFocusChange event listener. This listener is the first parameter in the requestAudioFocus function.
This listener should look something like:
private OnAudioFocusChangeListener focusChangeListener = new OnAudioFocusChangeListener() {
public void onAudioFocusChange(int focusChange) {
AudioManager am =(AudioManager)getSystemService(Context.AUDIO_SERVICE);
switch (focusChange) {
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK):
//Lower the volume while ducking (not sure what ducking means really)
break;
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT) :
//TODO: pause audio
break;
case (AudioManager.AUDIOFOCUS_LOSS) :
//TODO: pause audio
break;
case (AudioManager.AUDIOFOCUS_GAIN):
//TODO: Return the volume to normal and resume if paused.
break;
default: break; //empty on default
}
}
};
I think it is not possible to stop a service of another app as you may not know the processid, You can stop the service of your app only if you know the Pid of the app using
android.os.Process.killProcess(processIdKillService)
I try to make simple mediaplayer app just for personal/educational purpose (play specific mp3 file) but i have a problem with others apps. I use services to play sound in background. Everything working fine but when i turn another media app i still can play simultaneously different song. How to "tell" to the system that my app is using mediaplayer and no ones can use mediaplayer till my services end. I use AudioManager STREAM_MUSIC and start playing my song when i get AUDIOFOCUS_GAIN checked by AUDIOFOCUS_REQUEST_GRANTED.
to play my music and set the foreground notification i use
AudioManager audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
int result = audioManager.requestAudioFocus(this, AudioManager.STREAM_MUSIC,
AudioManager.AUDIOFOCUS_GAIN);
if (AudioManager.AUDIOFOCUS_REQUEST_GRANTED == result) {
this.startForeground();
player.start();
}
You have to use media players audio focus implementations, detail documentation here:
http://developer.android.com/guide/topics/media/mediaplayer.html#audiofocus
Audio focus is one of the thing which assign to any application who request for that, means if you request for that, any other application using it will stop automatically & you;ll start using audio , same case while you are using it if any other app request for it, your audio will be stopped. You will be notifyed of the loss of audio focus through the onAudioFocusChange handler of the Audio Focus Change Listener you registered when requesting the audio focus
AudioManager am = (AudioManager)getSystemService(Context.AUDIO_SERVICE);
// Request audio focus for playback
int result = am.requestAudioFocus(focusChangeListener,
// Use the music stream.
AudioManager.STREAM_MUSIC,
// Request permanent focus.
AudioManager.AUDIOFOCUS_GAIN);
if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
// other app had stopped playing song now , so u can do u stuff now .
}
private OnAudioFocusChangeListener focusChangeListener =
new OnAudioFocusChangeListener() {
public void onAudioFocusChange(int focusChange) {
AudioManager am =(AudioManager)getSystemService(Context.AUDIO_SERVICE);
switch (focusChange) {
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK) :
// Lower the volume while ducking.
mediaPlayer.setVolume(0.2f, 0.2f);
break;
case (AudioManager.AUDIOFOCUS_LOSS_TRANSIENT) :
pause();
break;
case (AudioManager.AUDIOFOCUS_LOSS) :
stop();
ComponentName component =new ComponentName(AudioPlayerActivity.this,MediaControlReceiver.class);
am.unregisterMediaButtonEventReceiver(component);
break;
case (AudioManager.AUDIOFOCUS_GAIN) :
// Return the volume to normal and resume if paused.
mediaPlayer.setVolume(1f, 1f);
mediaPlayer.start();
break;
default: break;
}
}
};
I am playing an audio using MediaPlayer class. I have a requirement where audio played by my app should automatically stop when some other songs started playing on the device by the user. How to get notified that some other audio has started playing on the device in my app? Please advise.
UPDATED:
I tried this code, it works for the first time. I.e, when I launch my app and play an audio in my app, my app is playing an audio. Then, When I open some music player and play some other audio there, My app detects notification in "AUDIOFOCUS_LOSS". I am stopping my audio here. Then when again play audio in my app, and then coming back to music player and play some other audio there, this time my app doesn't get detected for this notification, so I couldn't do stop again my audio. This is my issue now.
Could someone help me to solve this please?
public class MyActivity extends ActionBarActivity implements OnCompletionListener, OnPreparedListener, OnErrorListener, OnBufferingUpdateListener, AudioManager.OnAudioFocusChangeListener {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_hclsquad_fm);
audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
audioManager.requestAudioFocus(this, AudioManager.STREAM_MUSIC, AudioManager.AUDIOFOCUS_GAIN);
}
#Override
public void onAudioFocusChange(int focusChange) {
switch (focusChange) {
case AudioManager.AUDIOFOCUS_GAIN:
Toast.makeText(MyActivity.this, "Focus GAINED", Toast.LENGTH_LONG).show();
break;
case AudioManager.AUDIOFOCUS_LOSS:
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT:
Toast.makeText(MyActivity.this, "Focus LOSS", Toast.LENGTH_LONG).show();
if(mediaPlayer != null)
killMediaPlayer();
break;
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK:
Toast.makeText(MyActivity.this, "Focus LOSS TRANSIENT", Toast.LENGTH_LONG).show();
break;
default:
}
}
Try this code below. I found this answer here
OnAudioFocusChangeListener listener = 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
}
}
};
AudioManager am = (AudioManager)getSystemService(Context.AUDIO_SERVICE);
int request = am.requestAudioFocus(listener,
AudioManager.STREAM_MUSIC,
AudioManager.AUDIOFOCUS_GAIN);
Responsible apps will always get audio focus before playing audio. I don't think it is possible for you to detect when another app plays audio if it does not request audio focus.
Instead of requesting audio focus in your onCreate, do it before you start to play audio:
private void play(){
requestAudioFocus();
}
You are loosing audio focus. You should call
requestAudioFocus();
to get control back.