Android: correct usage of PrepareAsync() in media player activity
Asked Answered
C

2

13

I'm following this tutorial, but the usage of prepareAsync is not clear and my code does not output any audio. I'm using prepareAsync() because my mp3 is online and I don't want to lock the activity during media player preparing. Could you explain basic usage of prepareAsync?

package com.example.simplemediaplayer.app;

import android.media.AudioManager;
import android.media.MediaPlayer;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.Toast;

import java.io.IOException;


public class MediaPlayerActivity extends ActionBarActivity implements MediaPlayer.OnPreparedListener {

    private static final String TAG = "tag";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_media_player);

        String url = "http://www.brothershouse.narod.ru/music/pepe_link_-_guitar_vibe_113_club_mix.mp3"; // your URL here
        MediaPlayer myMediaPlayer = new MediaPlayer();
        myMediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
        try {
            myMediaPlayer.setDataSource(url);
            myMediaPlayer.prepareAsync(); // might take long! (for buffering, etc)

        } catch (IOException e) {
            Toast.makeText(this, "mp3 not found", Toast.LENGTH_SHORT).show();
            e.printStackTrace();
        }

    }

    /** Called when MediaPlayer is ready */
    @Override
    public void onPrepared(MediaPlayer player) {
        player.start();
    }


    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.media_player, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();
        if (id == R.id.action_settings) {
            return true;
        }
        return super.onOptionsItemSelected(item);
    }
}
Claudette answered 26/4, 2014 at 10:55 Comment(0)
C
40

The solution is to call the setOnPreparedListener of myMediaPlayer object and wait until prepareAsync() method has finished.

package com.example.simplemediaplayer.app;

import android.media.AudioManager;
import android.media.MediaPlayer;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.Toast;

import java.io.IOException;


public class MediaPlayerActivity extends ActionBarActivity {

    private static final String TAG = "tag";

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_media_player);

        String url = "http://www.brothershouse.narod.ru/music/pepe_link_-_guitar_vibe_113_club_mix.mp3"; // your URL here
        MediaPlayer myMediaPlayer = new MediaPlayer();
        myMediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
        try {
            myMediaPlayer.setDataSource(url);
            myMediaPlayer.prepareAsync(); // prepare async to not block main thread

        } catch (IOException e) {
            Toast.makeText(this, "mp3 not found", Toast.LENGTH_SHORT).show();
            e.printStackTrace();
        }

        //mp3 will be started after completion of preparing...
        myMediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {

            @Override
            public void onPrepared(MediaPlayer player) {
                player.start();
            }

        });

    }


    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.media_player, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();
        if (id == R.id.action_settings) {
            return true;
        }
        return super.onOptionsItemSelected(item);
    }
}
Claudette answered 26/4, 2014 at 12:28 Comment(2)
I have a MainActivity with multiple buttons (each button plays different mp3s from raw folder thorough a MediaPlayerAsynch class that I want to create.) I want to send some parameters from MainActivity to this MediaPlayerAsynch class to play mp3s. This MediaPlayerAsynch class will handle mp3 playback requests from MainActivity asynchronously. And if I request another song before the current playback is not finished, it will stop the playback and start the new song. This is what I use now. #41730894Cyrene
Can you please guide me or show me a little demo. Because the code I use works but it feels wrong.Cyrene
L
0

The mediaPlayer.prepareAsync() method is used to prepare the MediaPlayer instance for playback asynchronously. This method is typically used when playing both local and remote media sources.

When playing a local media source, you can use the mediaPlayer.prepare() method, which prepares the MediaPlayer instance for playback synchronously. However, when playing a remote media source, such as a media file from a server, it's recommended to use the mediaPlayer.prepareAsync() method to avoid blocking the UI thread.

Using prepareAsync() allows the MediaPlayer to prepare the media source in a background thread, without blocking the UI thread. This is important because preparing a remote media source may take some time, and blocking the UI thread can cause the app to become unresponsive and result in a poor user experience.

In short, you can use mediaPlayer.prepareAsync() method for both local and remote media sources, but it is particularly useful when playing remote media sources to avoid blocking the UI thread.

Longford answered 27/3, 2023 at 20:23 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.