1.packages\providers\MediaProvider :含以下 java 文件 MediaProvider.java
MediaScannerReceiver.java
MediaScannerService.java
MediaThumbRequest.java
2.查看該目錄下AndroidMainfest.xml,從MediaScannerService.java 入手。
if (action.equals(Intent.ACTION_BOOT_COMPLETED)) {
//收到” 啟動(dòng)完畢“廣播后,掃描內部存儲 /system/media目錄,掃描手機內存中的媒體文件
scan(context, MediaProvider.INTERNAL_VOLUME);
}
if (action.equals(Intent.ACTION_MEDIA_MOUNTED) &&externalStoragePath.equals(path)) {
// 收到MOUNT 信息后,掃描外部存儲,/mnt/sdcard,sdcard掛載完畢后掃描擴展卡的媒體文件
scan(context, MediaProvider.EXTERNAL_VOLUME);
}
if (action.equals(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE) && path != null && path.startsWith(externalStoragePath + "/")) {
// 收到請求啟動(dòng)單個(gè)文件的掃描工作,注意這個(gè)文件必須位于SD卡上。
scanFile(context, path);
}
通過(guò)scan(...),scanFile(...)函數啟動(dòng)MediaScannerService.
context.startService(new Intent(context,MediaScannerService.class).putExtras(args));
3.MediaScannerService.java
onCreate(...)函數開(kāi)啟新的線(xiàn)程。
onStartCommand(...)函數,每次調用startService時(shí),執行此函數。mServiceHandler發(fā)送Message。
跟中ServiceHandler類(lèi),handleMessage(...)根據volume類(lèi)型,執行scan(directories, volume);函數。
在scan(String[] directories, String volumeName)函數中, 創(chuàng )建MediaScanner,進(jìn)行掃描
MediaScanner scanner = createMediaScanner();
scanner.scanDirectories(directories, volumeName);
4.媒體掃描工作流程總結:
* MSR 接收外部發(fā)來(lái)的掃描請求,并通過(guò)startService方式啟動(dòng)MSS處理。
* MSS 的主線(xiàn)程接收MSR所收到的請求,然后投遞給工作線(xiàn)程去處理。
* 工作線(xiàn)程做一些前期處理工作后(例如向系統廣播掃描開(kāi)始的消息),就創(chuàng )建媒體掃描器mediaScanner來(lái)處理掃描目標。
* MS掃描完成后,工作線(xiàn)程再做一些后期處理,然后向系統發(fā)送掃描完畢的廣播。
二MediaScanner分析。
1.創(chuàng )建MediaScanner
System.loadLibrary("media_jni");//加載libmedia_jni.so
native_init();//android_media_MediaScanner.cpp
native_setup();//調用JNI層的函數做一些初始化工作。
2.void scanDirectiories(String[] directories,String volumeName)
initialize(volumeName); //初始化。
prescan(null);//掃描前的預處理。
processDirectory(directories[i],MediaFile.sFileExtensions,mClient);//native函數,對目標文件夾進(jìn)行掃描
postscan(directories);//掃描后處理
3.MediaFile.java
MediaFile.sFileExtensions是一個(gè)字符串,包含了當前多媒體系統所支持的媒體文件的后綴名,例如.MP3,.MP4等。
addFileType("MP3",FILE_TYPE_MP3,"audio/mpeg");
addFileType("AMR",FILE_TYPE_AMR,"audio/amr");
4.數據庫表
cd /data/data/com.android.providers.media/database
external.db表名:album_art/albums/app_package/artists/audio_genres/audio_genres_map/audio_meta/audio_playlists/
audio_playlists_map/audio_ringtone/images/music_audio_playlists/music_audio_playlists_map/
music_quick_list/thumbnails/video/videocall_images/videothumbnails
5.MediaProvider.java
創(chuàng )建數據庫表:
[java]
view plaincopyprivate static final String[] EXTERNAL_DATABASE_TABLES = new String[] {
"images",
"thumbnails",
"audio_meta",
"artists",
"albums",
"audio_genres",
"audio_genres_map",
"audio_playlists",
"audio_playlists_map",
"video",
};
(未完待續...)