46

I have a game in which a sound plays when a level is completed. Everything works fine to start with but after repeating a level 10 or 20 times the logcat suddenly reports: "MediaPlayer error (-19,0)" and/or "MediaPlayer start called in state 0" and the sounds are no longer made.

I originally had the all sounds in mp3 format but, after reading that ogg may be more reliable, I converted them all to ogg, but the errors appeared just the same.

Any idea how I can fix this problem?

Mick
  • 8,284
  • 22
  • 81
  • 173

6 Answers6

72

I was getting the same problem, I solved it by adding the following code to release the player:

mp1 = MediaPlayer.create(sound.this, R.raw.pan1);
mp1.start();
mp1.setOnCompletionListener(new OnCompletionListener() {
    public void onCompletion(MediaPlayer mp) {
        mp.release();

    };
});
Gabriel Kaffka
  • 1,039
  • 8
  • 9
61

I think you are not releasing the mediaplayers you are using to play the sound.. You need to release() the media players otherwise the resources are not released , and you soon get out of memory (since you allocate them again next time). so,I think you can play twice or even thrice... but not many times without releasing the resources

5hssba
  • 8,079
  • 2
  • 33
  • 35
16

MediaPlayer is not a good option when you are playing small sound effects as the user can click on multiple buttons very soon and you will have to create a MP object for all of them which doesnt happen synchronously. That is why you are not hearing sounds for every click. Go for the SoundPool Class which allows you to keep smaller sounds loaded in memory and you can play them any time you want without any lag which you would feel in a mediaplayer. http://developer.android.com/reference/android/media/SoundPool.html Here is a nice tutorial : http://www.anddev.org/using_soundpool_instead_of_mediaplayer-t3115.html

Akhil
  • 13,888
  • 7
  • 35
  • 39
2

I solved both the errors (-19,0) and (-38,0) , by creating a new object of MediaPlayer every time before playing and releasing it after that.

Before :

void play(int resourceID) {
    if (getActivity() != null) {

         //Using the same object - Problem persists
        player = MediaPlayer.create(getActivity(), resourceID);
        player.setAudioStreamType(AudioManager.STREAM_MUSIC);

        player.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
            @Override
            public void onCompletion(MediaPlayer mp) {
                player.release();
            }
        });

        player.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
            @Override
            public void onPrepared(MediaPlayer mp) {
                mp.start();
            }
        });

    }
}

After:

 void play(int resourceID) {

    if (getActivity() != null) {

        //Problem Solved
        //Creating new MediaPlayer object every time and releasing it after completion
        final MediaPlayer player = MediaPlayer.create(getActivity(), resourceID);
        player.setAudioStreamType(AudioManager.STREAM_MUSIC);

        player.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
            @Override
            public void onCompletion(MediaPlayer mp) {
                player.release();
            }
        });

        player.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
            @Override
            public void onPrepared(MediaPlayer mp) {
                mp.start();
            }
        });

    }
}
Saurabh Padwekar
  • 3,888
  • 1
  • 31
  • 37
1

This is a very old question, But this came up first in my search results So other people with the same issue will probably come upon this page eventually.

Unlike what some others have said, you can in fact use MediaPlayer for small sounds without using a lot of memory. I'll put in a little modified snippit from my soundboard app to show you what I'm getting at.

private MediaPlayer mp;

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.your_layout);

    mp = new MediaPlayer();

}

private void playSound(int soundID){
     mp.reset();
     AssetFileDescriptor sound = getResources().openRawResourceFd(soundID);
     try {
         mp.setDataSource(sound.getFileDescriptor(),sound.getStartOffset(),sound.getLength());
         mp.prepare();
     } catch (IOException e) {
         e.printStackTrace();
     }
     mp.start();


}

with the way I set it up, you create on MediaPlayer object that you reuse everytime you play a sound so that you don't use up too much space.

You call .reset() instead of .release() because .release() is only used if you are disposing of an object, however you want to keep your MediaPlayer Object.

You use an assetfiledescriptor to set a new soundfile for your mediaplayer to play instead of setting a new object to your mediaplayer address because that way you are creating new objects within the method that aren't being handled properly and you will eventually run into the same error as you described.

This is only one of many ways to use MediaPlayer but I personally think it is the most efficient if you are only using it for small sound applications. The only issue with it is that it is relatively restrictive in what you can accomplish, but that shouldn't be much of an issue if you are indeed using it for small sound applications.

CarbonZonda
  • 167
  • 2
  • 11
0

i try delete emulator and new create emulator for remove error of (-19,0) media player.

AnilPatel
  • 2,356
  • 1
  • 24
  • 40