整理一下关于sd卡相关知识点,主要包括sd卡状态监听,sd卡文件搜索,sd卡媒体数据库(系统支持媒体类型)刷新模块:
一:sd卡状态进行监听
有时程序进行外部数据读取和写入时,为防止异常发生需要对sd卡状态进行监听,对于sd卡的状态我们可以采用注册广播来实现
下面是文档中一个经典例子;
[java] view plaincopy在CODE上查看代码片派生到我的代码片
//监听sdcard状态广播
BroadcastReceiver mExternalStorageReceiver;
//sdcard可用状态
boolean mExternalStorageAvailable = false;
//sdcard可写状态
boolean mExternalStorageWriteable = false;
void updateExternalStorageState() {
//获取sdcard卡状态
String state = Environment.getExternalStorageState();
if (Environment.MEDIA_MOUNTED.equals(state)) {
mExternalStorageAvailable = mExternalStorageWriteable = true;
} else if (Environment.MEDIA_MOUNTED_READ_ONLY.equals(state)) {
mExternalStorageAvailable = true;
mExternalStorageWriteable = false;
} else {
mExternalStorageAvailable = mExternalStorageWriteable = false;
}
}
//开始监听
void startWatchingExternalStorage() {
mExternalStorageReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
Log.i("test", "Storage: " + intent.getData());
updateExternalStorageState();
}
};
IntentFilter filter = new IntentFilter();
filter.addAction(Intent.ACTION_MEDIA_MOUNTED);
filter.addAction(Intent.ACTION_MEDIA_REMOVED);
registerReceiver(mExternalStorageReceiver, filter);
updateExternalStorageState();
}
//停止监听
void stopWatchingExternalStorage() {
unregisterReceiver(mExternalStorageReceiver);
}
二:sdcard下搜索某一类型(通常是后缀名相同)文件,或是指定文件名的查找功能
(1)搜索指定文件
[java] view plaincopy在CODE上查看代码片派生到我的代码片
public String searchFile(String filename){
String res="";
File[] files=new File("/sdcard").listFiles();
for(File f:files){
if(f.isDirectory())
searchFile(f.getName());
else
if(f.getName().indexOf(filename)>=0)
res+=f.getPath()+"\n";
}
if(res.equals(""))
res="file can't find!";
return res;
}
(2)指定相同后缀名称文件类型
[java] view plaincopy在CODE上查看代码片派生到我的代码片
private List<String> files = new ArrayList<String>();
class FindFilter implements FilenameFilter {
public boolean accept(File dir, String name) {
return (name.endsWith(".txt"));
}
}
public void updateList() {
File home = new File("/sdcard/");
if (home.listFiles( new FindFilter()).length > 0) {
for (File file : home.listFiles( new FindFilter())) {
files.add(file.getName());
三:媒体数据库的刷新,
当android的系统启动的时候,系统会自动扫描sdcard内的文件,并把获得的媒体文件信息保存在一个系统媒体数据库中,
程序想要访问多媒体文件,就可以直接访问媒体数据库中即可,而用直接去sdcard中取。
但是,如果系统在不重新启动情况下,媒体数据库信息是不会更新的,这里举个例子,当应用程序保存一张图片到本地后(已成功),
但打开系统图片库查看时候,你会发现图片库内并没有你刚刚保存的那张图片,原因就在于系统媒体库没有及时更新,这时就需要手动刷新文件系统了
方式一:发送一广播信息通知系统进行文件刷新
[java] view plaincopy在CODE上查看代码片派生到我的代码片
private void scanSdCard(){
IntentFilter intentfilter = new IntentFilter(Intent.ACTION_MEDIA_SCANNER_STARTED);
intentfilter.addAction(Intent.ACTION_MEDIA_SCANNER_FINISHED);
intentfilter.addDataScheme("file");
registerReceiver(scanSdReceiver, intentfilter);
Intent intent = new Intent();
intent.setAction(Intent.ACTION_MEDIA_MOUNTED);
intent.setData(Uri.parse("file://" + Environment.getExternalStorageDirectory().getAbsolutePath()));
sendBroadcast(intent);
}
private BroadcastReceiver scanSdReceiver = new BroadcastReceiver(){
private AlertDialog.Builder builder;
private AlertDialog ad;
@Override
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
if(Intent.ACTION_MEDIA_SCANNER_STARTED.equals(action)){
builder = new AlertDialog.Builder(context);
builder.setMessage("正在扫描sdcard...");
ad = builder.create();
ad.show();
// adapter.notifyDataSetChanged();
}else if(Intent.ACTION_MEDIA_SCANNER_FINISHED.equals(action)){
ad.cancel();//重新获取文件数据信息
Toast.makeText(context, "扫描完毕", Toast.LENGTH_SHORT).show();
}
}
};
或者
[java] view plaincopy在CODE上查看代码片派生到我的代码片
public void fileScan(File file){
Uri data = Uri.parse("file://"+ Environment.getExternalStorageDirectory())
sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, data));
}
[java] view plaincopy在CODE上查看代码片派生到我的代码片
void insertMeadia(ContentValues values){
Uri uri = getContentResolver().insert( MediaStore.Video.Media.EXTERNAL_CONTENT_URI, values);
sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, uri));
}
刷新所有系统文件,效率可能不高,高效方法是只刷新变化的文件
方式二:指定特定文件操作
[java] view plaincopy在CODE上查看代码片派生到我的代码片
File path = getExternalFilesDir(Environment.DIRECTORY_PICTURES);
File file = new File(path, "DemoPicture.jpg");
try {
InputStream is = getResources().openRawResource(R.drawable.balloons);
OutputStream os = new FileOutputStream(file);
byte[] data = new byte[is.available()];
is.read(data);
os.write(data);
is.close();
os.close();
// Tell the media scanner about the new file so that it is
// immediately available to the user.
MediaScannerConnection.scanFile(this,
new String[] { file.toString() }, null,
new MediaScannerConnection.OnScanCompletedListener() {
public void onScanCompleted(String path, Uri uri) {
Log.i("ExternalStorage", "Scanned " + path + ":");
Log.i("ExternalStorage", "-> uri=" + uri);
}
});
} catch (IOException e) {
// Unable to create file, likely because external storage is
// not currently mounted.
Log.w("ExternalStorage", "Error writing " + file, e);
}