Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
74 views
in Technique[技术] by (71.8m points)

How can I refresh MediaStore on Android?

This started out as a general user question on Android forums. However it's become, by necessity, a programming question. Here's my problem.

Android has a service - MediaScanner - which runs in the background any time (I believe) the SD card is un-mounted and re-mounted. This service collects data on all the media files on the card, and provides a SQLite DB which can be queried by music applications. Most music applications use this service as it saves on battery-drain associated with scanning the SD card.

Since I started using android, I've consistently had a problem whereby M3U playlists synchronised to the device remain in this SQLite DB even after being deleted from the SD Card. It's gotten to the point where I now have a collection of about 40 playlists showing up in any music app I use, despite there only being around 10 m3u files on the card. The remaining playlists do not play, and are empty. I can remove them manually by deleting them from the music app, but I'm sick of doing this. There has to be a better way to remove these ghost playlists.

There are two apps on the Android Market - SDRescan and Music Scanner, which supposedly do exactly this but neither of them work.

I set about writing my own app to refresh or delete the MediaStore database and start from scratch, but I'm not getting very far. I've got an android app which runs the following code :

sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, 
        Uri.parse("file://" + Environment.getExternalStorageDirectory()))); 

I've found a few examples of this code online as a way to scan the SD Card but I'm not having any luck with it whatsoever. Any tips?

FULL CODE:

package com.roryok.MediaRescan;

import android.app.Activity;
import android.content.Intent;
import android.content.IntentFilter;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;

public class MediaRescan extends Activity {
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, 
                Uri.parse("file://" + Environment.getExternalStorageDirectory()))); 
        setContentView(R.layout.main);
    }

    //Rescan the sdcard after copy the file
    private void rescanSdcard() throws Exception{     
      Intent scanIntent = new Intent(Intent.ACTION_MEDIA_MOUNTED, 
                Uri.parse("file://" + Environment.getExternalStorageDirectory()));   
      IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MEDIA_SCANNER_STARTED);
      intentFilter.addDataScheme("file");     
      sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED, 
                Uri.parse("file://" + Environment.getExternalStorageDirectory())));    
    }
}
Question&Answers:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Here is an easy to use 'single file based' solution:

Adding a file:

Whenever you add a file, inform MediaStore's Content Provider using:

sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.fromFile(newMediaFile)));

Deleting a file:

Similarly, when you delete a file, inform MediaStore's Content Provider using:

getContentResolver().delete(uri, null, null)  // (Credit goes to [DDSports][1])

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...