Android - Playing mp3 from byte[]

I have my mp3 file in byte[] (downloaded from an service) and I would like to play it on my device similar to how you can play files:

MediaPlayer mp = new MediaPlayer();
mp.setDataSource(PATH_TO_FILE);
mp.prepare();
mp.start();

But I can't seem to find a way to do it. I wouldn't mind saving file to phone and then playing it. How can I play the file, or download then play it?


Asked by: Julia462 | Posted: 20-01-2022






Answer 1

OK, thanks to all of you but I needed to play mp3 from byte[] as I get that from .NET webservice (don't wish to store dynamically generated mp3s on server).

In the end - there are number of "gotchas" to play simple mp3... here is code for anyone who needs it:

private MediaPlayer mediaPlayer = new MediaPlayer();
private void playMp3(byte[] mp3SoundByteArray) {
    try {
        // create temp file that will hold byte array
        File tempMp3 = File.createTempFile("kurchina", "mp3", getCacheDir());
        tempMp3.deleteOnExit();
        FileOutputStream fos = new FileOutputStream(tempMp3);
        fos.write(mp3SoundByteArray);
        fos.close();

        // resetting mediaplayer instance to evade problems
        mediaPlayer.reset();

        // In case you run into issues with threading consider new instance like:
        // MediaPlayer mediaPlayer = new MediaPlayer();                     

        // Tried passing path directly, but kept getting 
        // "Prepare failed.: status=0x1"
        // so using file descriptor instead
        FileInputStream fis = new FileInputStream(tempMp3);
        mediaPlayer.setDataSource(fis.getFD());

        mediaPlayer.prepare();
        mediaPlayer.start();
    } catch (IOException ex) {
        String s = ex.toString();
        ex.printStackTrace();
    }
}

EDIT: I've wrote this answer more than 4 years ago - obviously lots of things have changed since then. See Justin's comment on how to reuse MediaPlayer instance. Also, I don't know if .deleteOnExit() will work for you now - feel free to suggest improvement so that temp files do not pile up.

Answered by: Freddie418 | Posted: 21-02-2022



Answer 2

I found an easy solution by encoding my MP3 file as Base64 (I already receive the data encoded from a Restful API service), and then creating a URL object. I tested it in Android 4.1.

public void PlayAudio(String base64EncodedString){
        try
        {
            String url = "data:audio/mp3;base64,"+base64EncodedString; 
            MediaPlayer mediaPlayer = new MediaPlayer();
            mediaPlayer.setDataSource(url);
            mediaPlayer.prepare();
            mediaPlayer.start();
        }
        catch(Exception ex){
            System.out.print(ex.getMessage());
        }
    }

Answered by: Blake753 | Posted: 21-02-2022



Answer 3

Starting Android MarshMellow (Version Code 23), there is new API that will make this possible.

MediaPlayer.setDataSource(android.media.MediaDataSource)

You can provide a custom implementation of MediaDataSource and wrap a byte[]. A basic implementation given below.

import android.annotation.TargetApi;
import android.media.MediaDataSource;
import android.os.Build;
import java.io.IOException;


@TargetApi(Build.VERSION_CODES.M)
public class ByteArrayMediaDataSource extends MediaDataSource {

    private final byte[] data;

    public ByteArrayMediaDataSource(byte []data) {
        assert data != null;
        this.data = data;
    }
    @Override
    public int readAt(long position, byte[] buffer, int offset, int size) throws IOException {
        System.arraycopy(data, (int)position, buffer, offset, size);
        return size;
    }

    @Override
    public long getSize() throws IOException {
        return data.length;
    }

    @Override
    public void close() throws IOException {
        // Nothing to do here
    }
}

Answered by: Audrey385 | Posted: 21-02-2022



Answer 4

Not sure about bytearrays/bytestreams, but if you have a URL from the service, you can try setting the data source to a network URI by calling

setDataSource(Context context, Uri uri)

See the API docs.

Answered by: Nicole271 | Posted: 21-02-2022



Answer 5

If you target API 23 and above, create a class like this

class MyMediaDataSource(val data: ByteArray) : MediaDataSource() {

override fun readAt(position: Long, buffer: ByteArray, offset: Int, size: Int): Int {

    if (position >= data.size) return -1 // -1 indicates EOF 

    val endPosition: Int = (position + size).toInt()
    var size2: Int = size
    if (endPosition > data.size)
        size2 -= endPosition - data.size

    System.arraycopy(data, position.toInt(), buffer, offset, size2)
    return size2
}

override fun getSize(): Long {
    return data.size.toLong()
}

override fun close() {}

}

and use like this

val mediaSource = MyMediaDataSource(byteArray)
MediaPlayer().apply {
    setAudioStreamType(AudioManager.STREAM_MUSIC)
    setDataSource(mediaSource)
    setOnCompletionListener { release() }
    prepareAsync()
    setOnPreparedListener { start() }
}

credits to krishnakumarp's answer above and to this article

Answered by: Chester876 | Posted: 21-02-2022



Answer 6

wrong code:

 MediaPlayer mp = new MediaPlayer();
 mp.setDataSource(PATH_TO_FILE);
 mp.prepare();
 mp.start();

CORRECT CODE:

 MediaPlayer mp = new MediaPlayer();
 mp.setDataSource(PATH_TO_FILE);
 mp.setOnpreparedListener(this);
 mp.prepare();

//Implement OnPreparedListener 
OnPrepared() {
    mp.start();
 }

see API Demos ..

Answered by: Justin256 | Posted: 21-02-2022



Similar questions

android - Facebook Check-in with camera picture bytearray

Is it possible to checkin with a picture on the device? I tried using "picture" bundle, but it only works if I point to a URL, not working if I use a byte array. The picture is just not shown on the wall if I use byte array. Working: bundle.putString("picture", "http://www.somewhere.com/picture.jpg"); Not working: bundle.putByteArray("picture", imageByteArray[]);


java - ByteArray To XML file in Android

I am sending a file in byte[] format from web service to android device. If that file is an XML file i.e. byte[] array then how could i convert it to original XML file. If that file is an image i.e. byte[] array then how could i convert it to original Image. I am using android sdk 2.2 on samsung galaxy tab.


canvas - create Bitmap from byteArray in android

I want to create a bitmap from a bytearray . I tried the following codes Bitmap bmp; bmp = BitmapFactory.decodeByteArray(data, 0, data.length); and ByteArrayInputStream bytes = new ByteArrayInputStream(data); BitmapDrawable bmd = new BitmapDrawable(bytes); bmp = bmd.getBitmap(); But ,When i am tring to initialize the Canvas object with the bitm...


bytearray - Android/Java: Saving a byte array to a file (.jpeg)

I am developing an application for Android, and part of the application has to takes pictures and save them to the SDcard. The onPictureTaken method returned a byte array with the data of the captured image. All I need to do is save the byte array into a .jpeg image file. I have attempted to do this with the help of BitmapFactory.decodeByteArray (to get a Bitmap) and then bImage.compress (to an OutputStream), a pl...


bytearray - How to create a Drawable from byte[] ? (Android)

I have an array of bytes and I need to convert it into a Android Drawable. How can I perform this conversion? Here is what i tried but without success: byte[] b = getByteArray(); ByteArrayInputStream is = new ByteArrayInputStream(b); Drawable drw = Drawable.createFromStream(is, "articleImage"); drw is always null! EDIT: My byte[] was actually corrupted/incomplete, t...


android - How to convert a Mac Address to a Hex and pass it to a bytearray in java

How can i convert a MacAddress to a Hex String and then parse it to a byte in java? and similarly an IP Address as well? Thank you


android - How can I download Image File from an URL to ByteArray?

following is my code: private byte[] downloadImage(String image_url) { byte[] image_blob = null; URL _image_url = null; HttpURLConnection conn = null; InputStream inputStream = null; try { _image_url = new URL(image_url); } catch (MalformedURLException e) { e.printStackTrace(); } t...


http post - Android & CherryPy: Trying to upload a file, string, or bytearray from android app to CherryPy

I'm having trouble setting up the HTTP Post android app code to upload a file, string, or byte array to CherryPy. Can someone point me in the right direction? I get HTTPError: (404, 'Missing parameters: myFile'). CherryPy code: html += """ <h2>Upload a file</h2> <form action="upload" method="post" enctype="multipart/form-data"> filename: <input ...


android - Convert bytearray with image to string

in my program I receive a bytearray. The first part is actually a string and the second a picture converted into a byte array. Like this: <STX>1<US>length of picture<ETX> here are the bytes... At the moment I have this to split the part before and after the ETX string incomingMessage = incomingBytes.toString(); String messagePart = incomingMessage....


web services - How To convert .wav file into bytearray withought any change in quality of .wav in android?

Somehow I'm creating the .wav file from the android device and storing it on my SD-card. Now I want to send that .wav file to a Java webservice.I need to do some processing on that .wav file in some java application. So what I need to do is send the wav file through webservice to my server where the java application is stored. So for that I need to know how to convert wave file to byte array without making any change in th...






Still can't find your answer? Check out these communities...



Android Google Support | Android Community | Android Community (Facebook) | Dev.io Android



top