How to release Android MediaPlayer? - android

Momentarily I have in LogCat "Mediaplayer error (-19,0)" after repeated plays. So the first time(s) I play my app everything is ok, but after a time the Sound doesn't work anymore.
public TextView tw;
MediaPlayer mpButtonKlick;
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.app);
tw = (TextView)findViewById(R.id.Text);
tw.setOnClickListener(this);
mpButtonKlick = MediaPlayer.create(this, R.raw.sound);
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
mpButtonKlick.start();

you release like this:
mpButtonKlick.release();
mpButtonKlick = null;
It's good practice to also release the MediaPlayer object when you start playing new media to ensure that there is just one instance running.
private void stopMedia(){
mpButtonKlick.release();
mpButtonKlick = null;
}
and when you call start() make sure to first call stopMedia();
stopMedia();
mpButtonKlick.start();

Try this one.
protected void onStop()
{
mediaPlayer.release();
mediaPlayer = null;
}

Related

Changing audio button from play to pause when clicked and vice versa

I want a play button in my app that when clicked plays the audio and changes to pause, and when the pause button is clicked the audio stops and the button changes to play again and so on. But the button is not working as expected. Please help. I'm adding my java code below.
public class surah extends AppCompatActivity {
MediaPlayer mp = new MediaPlayer();
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_surah);
mp=MediaPlayer.create(surah.this, R.raw.surahkahf);
final ImageView audio = (ImageView)findViewById(R.id.btn);
audio.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if(mp.isPlaying()){
mp.stop();
audio.setBackgroundResource(R.drawable.play);
try {
mp.prepare();
}catch (IllegalStateException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
else {
mp.start();
audio.setImageResource(R.drawable.pause);
}
}
});
}
}
Use audio.setImageResource(R.drawable.play) instead of audio.setBackgroundResource(R.drawable.play). Use mp.pause() instead of mp.stop();
First, as aborocz mentions in comments, you probably intend to pause playback instead of stop it, so the method you want to use is pause(). In that case you would not need to prepare the MediaPlayer again, and it will start from the same place it was paused when playback is resumed.
Second, the isPlaying() method is not particularly appropriate for this purpose. There are race conditions that prevent the desired behavior. From the Android MediaPlayer documentation:
Note that the transition from the Started state to the Paused state
and vice versa happens asynchronously in the player engine. It may
take some time before the state is updated in calls to isPlaying(),
and it can be a number of seconds in the case of streamed content.
Instead, store your own boolean value.
public class surah extends AppCompatActivity {
private MediaPlayer mp;
private boolean isMediaPlaying = false;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_surah);
mp = MediaPlayer.create(surah.this, R.raw.surahkahf);
final ImageView audio = (ImageView)findViewById(R.id.btn);
audio.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (isMediaPlaying) {
mp.pause();
audio.setBackgroundResource(R.drawable.play);
isMediaPlaying = false;
} else {
mp.start();
audio.setImageResource(R.drawable.pause);
isMediaPlaying = true;
}
}
});
}
}

Media Player start stop start

I am making a new android sound application. I made a clickable button to play sound when I click on it. But I also want it to stop playing sound when I click for the second time. That part works fine now here is the problem, when I click again on button to play sound again, it doesn't play it, Media player is completely stopped. I was looking on forums but I can't seem to find an answer that could help me.
Here is my Activity:
MediaPlayer mpButtonClick1;
MediaPlayer mpButtonClick2;
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.prvi);
final MediaPlayer mpButtonClick1 = MediaPlayer.create(this, R.raw.spalshm);
final MediaPlayer mpButtonClick2 = MediaPlayer.create(this, R.raw.splashs);
Button dugme = (Button) findViewById(R.id.dugme);
dugme.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (mpButtonClick1.isPlaying()) {
mpButtonClick1.stop();
mpButtonClick1.reset();
}
else {
mpButtonClick1.start();
}
}
});
When I try to write mpButtonClick1.prepare(); I get error Unhandled Exception Type IOE exception
Try to use pause instead of stop.
Reason: if you pause the MediaPlayer, then you can resume it later. However, if you use stop, almost any other method won't work and you will have to prepare the MediaPlayer again (or create a new one).
More info: here and here
PS: don't forget to release the memory when you finish using the resources.
Try this:
You should use only one mediaplayer object
public class PlayaudioActivity extends Activity {
private MediaPlayer mp;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
Button b = (Button) findViewById(R.id.button1);
Button b2 = (Button) findViewById(R.id.button2);
final TextView t = (TextView) findViewById(R.id.textView1);
b.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
stopPlaying();
mp = MediaPlayer.create(PlayaudioActivity.this, R.raw.far);
mp.start();
}
});
b2.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
stopPlaying();
mp = MediaPlayer.create(PlayaudioActivity.this, R.raw.beet);
mp.start();
}
});
}
private void stopPlaying() {
if (mp != null) {
mp.stop();
mp.release();
mp = null;
}
}
}
Change your class with below code:
remove reset();.
init well all components:
MediaPlayer mpButtonClick1;
MediaPlayer mpButtonClick2;
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.prvi);
mpButtonClick1 = MediaPlayer.create(this, R.raw.spalshm);
mpButtonClick2 = MediaPlayer.create(this, R.raw.splashs);
Button dugme = (Button) findViewById(R.id.dugme);
dugme.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (mpButtonClick1.isPlaying()) {
mpButtonClick1.stop();
}
else {
mpButtonClick1.start();
}
}
});
You're calling mpButtonClick1.reset() after mpButtonClick1.stop() - don't do that:
if (mpButtonClick1.isPlaying()) {
mpButtonClick1.stop();
mpButtonClick1.reset(); //<--------- calling reset(), remove this line
}
The docs for reset() say:
Resets the MediaPlayer to its uninitialized state. After calling this method, you will have to initialize it again by setting the data source and calling prepare().
Remove mpButtonClick1.reset() and it should work.
Keep in mind that MediaPlayer works as a state machine, which means that if you call methods in the wrong order, you'll get problems. Please read about MediaPlayer here and here.
Hey please use following
for stop -> media player
mp.seekTo(0);
mp.pause();
again for start just call
mp.start();
In my experience when I need to play multiple times and I may need to stop one play to start another play, (like in the case of multiple buttons), I just create another player, making sure that I release the resources for the previous one. To stop just use
mediaPlayer.stop();
But for play use something like this (adapt the logging to your specific needs) to create/recreate your player:
private boolean createMediaPlayer()
{
if (mediaPlayer!=null)
{
if(mediaPlayer.isPlaying())
{
mediaPlayer.stop();
mediaPlayer.reset();
mediaPlayer.release();
mediaPlayer=null;
}
}
mediaPlayer = new MediaPlayer();
mediaPlayer.setVolume(1f, 1f);
try
{
mediaPlayer.setAudioStreamType(Interop.PRIMARY_STREAM);
mediaPlayer.setDataSource(m_soundFile);
mediaPlayer.prepare();
return true;
// Interop.logDebug(TAG + "-loadAudio: SUCCESS" + m_soundFile);
} catch (Exception e)
{
Interop.logError(TAG + "-LoadAudio for Clic Sound: audioPlayer prepare failed for current file: " + m_soundFile);
Interop.logError(TAG + "-Exception: " , e);
return false;
}
}
and than use
if (createMediaPlayer())
mediaPlayer.start();
this will ensure proper release of the resources used by the media player.
A simple solution is to Use pause instead of stop and the seek to the beginning of the song.
I know that this question is quite old but recently while learning Android, I also got stuck at this point and found a very simple solution which I'd like to share with everyone.
Instead of trying to stop or reset the media, you can just seek back to the starting position.
mediaPlayer.seekTo(0);
For reference, I am also posting my code below:
public class MainActivity extends AppCompatActivity {
MediaPlayer mp;
public void play(View view) {
mp.start();
}
public void pause(View view) {
mp.pause();
}
public void stop(View view) {
// this seeks to the beginning of the file
mp.seekTo(0);
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mp = MediaPlayer.create(this, R.raw.sample_audio);
}
}

Android MedialPlayer, where to release and create?

I am trying to play a sound when button is pressed. To do so, I tried few methods :
1 : Created a MediaPlayer under and played it when button is pressed like this :
MediaPlayer mp;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mp = MediaPlayer.create(MainActivity.this, R.raw.bell);
mp.setLooping(false);
Button b = (Button) findViewById(R.id.button1);
b.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View arg0) {
// TODO Auto-generated method stub
mp.seekTo(0);
mp.start();
}
});
}
This method worked like charm. But then I wanted to conserve memory and wanted to release MediaPlayer when activity is in background. So I added this
#Override
protected void onPause() {
// TODO Auto-generated method stub
mp.release();
super.onPause();
}
But now, when activity comes back in foreground it throws an error ( because MediaPlayer is created under OnCreate).
So, I thought to create it under onResume since it is always called.
#Override
protected void onResume() {
// TODO Auto-generated method stub
mp = MediaPlayer.create(MainActivity.this, R.raw.bell);
mp.setLooping(false);
super.onResume();
}
It worked.
Full code is like this :
package com.example.learn;
import android.app.Activity;
import android.media.MediaPlayer;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
public class MainActivity extends Activity implements OnClickListener {
MediaPlayer mp;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button b = (Button) findViewById(R.id.button1);
b.setOnClickListener(this);
}
#Override
protected void onPause() {
// TODO Auto-generated method stub
mp.release();
super.onPause();
}
#Override
protected void onResume() {
// TODO Auto-generated method stub
mp = MediaPlayer.create(MainActivity.this, R.raw.bell);
mp.setLooping(false);
super.onResume();
}
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
switch (v.getId()) {
case R.id.button1: {
mp.seekTo(0);
mp.start();
}
}
}
}
just thinking have I done it right? Are there better and easier ways?
By looking on your code I think you have done it in a right way. You can Create that in onResume as it is always called. On Create is Called for the first time only.
And Yes ALWAYS call
mediaPlayer.relaese();
instead of
mediaPlayer.stop();
Everything in your code is looking right. For more accuracy you can have a glance on this
LINK

How to duck and unduck Mediaplayer output in Android

I am implementing a new application that plays two songs with Media player. What I need to do is, I need to duck the first player output when the second player output is come in to the picture. And need to unduck the first player when second player was completed. Is this possible?
My code is as follows:
public class SampleMediaPlayerActivity extends Activity implements OnClickListener, OnPreparedListener {
/** Called when the activity is first created. */
Button playSong;
MediaPlayer player1;
MediaPlayer player2;
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
playSong = (Button) findViewById(R.id.playSongButton);
playSong.setOnClickListener(this);
player1 = MediaPlayer.create(SampleMediaPlayerActivity.this, R.raw.song);
player1.setVolume(100.0f, 100.0f);
player1.setOnPreparedListener(this);
}
#Override
public void onClick(View v)
{
// TODO Auto-generated method stub
System.out.println("Play song");
//player1.setVolume(0.5, rightVolume)
player2 = MediaPlayer.create(SampleMediaPlayerActivity.this, R.raw.song);
player2.setVolume(100.0f, 100.0f);
//player.
player2.start();
}
#Override
public void onPrepared(MediaPlayer mp)
{
// TODO Auto-generated method stub
player1.start();
}
}

How to stop Audio?

Here is my problem, when I start the Activity the Music start like I want it to, but when I leave the Activity (by pressing the back button) the Application crashes and "stopped unexpectedly" :( All I want to do is have the audio STOP and go to another activity without the unexpected stop. How can I do this?
public class Run extends Activity {
/** The OpenGL View */
private GLSurfaceView glSurface;
private MediaPlayer mPlayer;
/**
* Initiate the OpenGL View and set our own
*/
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//Create an Instance with this Activity
glSurface = new GLSurfaceView(this);
//Set our own Renderer and hand the renderer this Activity Context
glSurface.setRenderer(new Lesson06(this));
//Set the GLSurface as View to this Activity
setContentView(glSurface);
new Thread(new Runnable() {
public void run() {
try{
MediaPlayer mPlayer = MediaPlayer.create(Run.this, R.drawable.theygonelovemeformyambition);
mPlayer.setLooping(true);
mPlayer.start();
while(mPlayer.isPlaying()){
android.os.SystemClock.sleep(100);
}
}catch(Exception e){
String TAG = null;
Log.d(TAG,"ERROR PLAYING");
e.printStackTrace();
}
}}).start();
}
#Override
protected void onDestroy() {
// TODO Auto-generated method stub
super.onDestroy();
mPlayer.release();
}
}
hi before you have to release media player resources. You should stop media player like below.
#Override
protected void onDestroy() {
// TODO Auto-generated method stub
if(mPlayer.isPlaying())
mPlayer.stop();
mPlayer.release();
super.onDestroy();
}
You dont have innitialized the mPlayer
In the public void run() you are just creating a new MediaPlayer
and so when you are trying mPlayer.release(); you are reffering to the null mPlayer and so you get a nullPointerExceptionerror (i guess)

Categories

Resources