0

I know this maybe a silly question but I'm new to Android development and after a hours of search, I can't find how to do it. I'm trying to develop a music app, which I get help from below tutorial.

https://www.sitepoint.com/a-step-by-step-guide-to-building-an-android-audio-player-app/

In this tutorial, mp3 files readed via Uri uri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI; from the device. However, I only want to read the songs in my project. As I searched, best place to put mp3 files in a project is inside asset folder.

Right place for putting mp3 files in an android project

The code in the tutorial get mp3 data with cursor

    private void loadAudio() {
    ContentResolver contentResolver = getContentResolver();

    Uri uri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
    String selection = MediaStore.Audio.Media.IS_MUSIC + "!= 0";
    String sortOrder = MediaStore.Audio.Media.TITLE + " ASC";
    Cursor cursor = contentResolver.query(uri, null, selection, null, sortOrder);

    if (cursor != null && cursor.getCount() > 0) {
        audioList = new ArrayList<>();
        while (cursor.moveToNext()) {
            String data = cursor.getString(cursor.getColumnIndex(MediaStore.Audio.Media.DATA));
            String title = cursor.getString(cursor.getColumnIndex(MediaStore.Audio.Media.TITLE));
            String album = cursor.getString(cursor.getColumnIndex(MediaStore.Audio.Media.ALBUM));
            String artist = cursor.getString(cursor.getColumnIndex(MediaStore.Audio.Media.ARTIST));

            // Save to audioList
            audioList.add(new Audio(data, title, album, artist));
        }
    }
    cursor.close();
}

I try to modify it to get it from asset folder but I can't figure out. I tried to change the uri to file:///android_asset/RELATIVEPATH however, cursor returns null in that situation. I can get the files inside Asset with below code but in that situation I can't get the audio data;

    private void listFiles() {

        Resources res = getResources(); //if you are in an activity
        AssetManager am = res.getAssets();
    String fileList[] = new String[0];
    try {
        fileList = am.list("Content");
    } catch (IOException e) {
        e.printStackTrace();
    }

    if (fileList != null)
            {
 }
                audioList = new ArrayList<>();
                for ( int i = 0;i<fileList.length;i++)
                {
                     File file = new File(fileList[i]);
                     if ((file.getName()).endsWith(".mp3")) {
                         String data = file.getName();
                         Audio audio = new Audio(file.getName(),data,data,data);
                         audioList.add(audio);
                         Log.d("Hata",file.getPath());
                      Log.i("Hata", "getEpubFilesFromFileManager: " + ".." + file.getName() +"Path"+ file.getPath());
                     }
                }
            }

As I debug MediaStore.Audio.Media.DATA returns the filepath. I also tried to use file.getPath() in second function, but didn't work. So my question is that, How Can I use cursor while iterating from asset folder?

EDIT: I'm getting AssetFileDescriptor of a file and then in mediaplayer, I play it with AssetFileDescriptor not the url. This works but I have two question;

  • Does this writes songs as cache in ram because I have like 100 songs in the app?

  • I can't get duration or title information with this approach.

     File file = new File(fileList[i]);
                 if ((file.getName()).endsWith(".mp3")) {
                     String data = file.getName();
                     try {
                         AssetFileDescriptor descriptor =     am.openFd("Contents/"+data);
    
                         Audio audio = new      Audio(descriptor,data,data,data,data);
                     audioList.add(audio);
                     } catch (IOException e) {
                         e.printStackTrace();
                     }
    
                     Log.d("Hata",file.getPath());
                  //Log.i("Hata", "getEpubFilesFromFileManager: " + ".." + file.getName() +"Path"+ file.getPath());
                 }
    
Emre Önder
  • 2,408
  • 2
  • 23
  • 73

1 Answers1

0

I try to modify it to get it from asset folder but I can't figure out

You can't. MediaStore knows nothing about the contents of your app's assets/ directory.

I can get the files inside Asset with below code but in that situation I can't get the audio data

Correct. I am not aware of any way for MediaStore to get that data for you. You can try MediaMetadataRetriever, using a FileDescriptor that you get from AssetManager.

However, it would be more efficient for you to get that data on your development machine and include it in your app, rather than having to try to get it from the media files at runtime. There are countless media players that can tell you the title, album, and artist for your media file. Collect that information and put it in your app:

  • As string resources
  • As an XML resource containing all the data
  • As a JSON file in assets/ containing all the data
  • As Java/Kotlin code (e.g., Java static field)
  • Etc.
CommonsWare
  • 986,068
  • 189
  • 2,389
  • 2,491
  • Sorry I don't understand the part of "get data on your development machine and include it in your app". – Emre Önder Oct 28 '18 at 06:54
  • @EmreÖnder: You say that these MP3 files are assets in your app. Therefore, they are files on your development machine, inside of an `assets/` directory in your project. You can use media players to look at those files and see what the title, album, and artist are. You can then type that information into your app, using some of the techniques that I outlined in the bullets. There is no need to look that information up at runtime. – CommonsWare Oct 28 '18 at 11:16
  • Aaa I got it. I'll look into that however, I don't think it is a good approach – Emre Önder Oct 28 '18 at 11:17
  • @EmreÖnderL Doing it that way would be more efficient for the user, in terms of processing time and battery consumption. After all, the data will not change for the lifetime of the installed copy of the app. – CommonsWare Oct 28 '18 at 11:18