您好,登錄后才能下訂單哦!
MediaStore播放器制作的示例分析,很多新手對此不是很清楚,為了幫助大家解決這個難題,下面小編將為大家詳細講解,有這方面需求的人可以來學習下,希望你能有所收獲。
在最初的構思中,我使用的是File類遞歸遍歷SD卡中的所有文件,然后篩選出以".mp3"格式結尾的文件,放入一個map.然后將map放入List,讓media加載.
但是,發現這樣的方法耗時比較長,容易出現"卡住"的現象,然后就想將List永久化存到本地,但是發現如果有幾百首歌的話,文件太大了,非常占內存控件.在查閱了一些資料后,發現android手機自身就有一個媒體庫,可以直接查詢.在多次嘗試后,終于成功讀取文件.這里做一個筆記.
一,獲取ContextResolver實例;
方法:ContexrResolver cr=context.getContextResolver();
解釋:context 表示Activity.this的這種context,就是要進行操作的Activity中的Context.
當使用getContextResolver();方法得到ContextResolver對象后,就可以直接查詢了.
二,使用Cursor對象;
方法:
1,Cursor c=cr.getContentResolver().query(uri, projection, selection, selectionArgs, sortOrder)
這里的cr就是前面得到的ContextResolver對象;這種方式必須先實例化ContextResolver對象.
那么,能不能直接實例出來呢?可以啊的喲~
2,Cursor c=context.getContentResolver().query(uri, projection, selection, selectionArgs, sortOrder)
只要將context.getContextResolver()直接使用就可以了.兩種方式不會出錯,根據實際情況使用不同的方式吧.
參數的意義:
Uri:指明要查詢的數據庫名稱加上表的名稱,從MediaStore中可以找到相應信息的參數,具體請參考開發文檔。
Projection: 指定查詢數據庫表中的哪幾列,返回的游標中將包括相應的信息。Null則返回所有信息。
selection: 指定查詢條件
selectionArgs:參數selection里有 ?這個符號是,這里可以以實際值代替這個問號。如果selection這個沒有?的話,那么這個String數組可以為null。
SortOrder:指定查詢結果的排列順序
三,MediaStore數據庫
主語句:
MediaStore.Audio :存放音頻信息 MediaStore.Image :存放圖片信息 MediaStoue.Video :存放視頻信息
這三個是基本的三大文件信息,每個類后面還有許多方法和參數.目前我用到的是音頻信息,其他的還沒用到,想來方法應該差不多.
1,MediaStore.Audio查詢參數:
首先我們要查詢的是媒體文件,就是Media類,所以在主語句后面加上:Media
變成了:MediaStore.Audio.Media;
好,現在我們要查詢的是媒體的一些信息,這里我搜集了一些常用的屬性大家可以參考一下:
MediaStore.Audio.Media._ID; //內部ID
MediaStore.Audio.Media.DISPLAY_NAME;//音樂名稱
MediaStore.Audio.Media.TITLE; //音樂標題
MediaStore.Audio.Media.ARTIST; //演唱者
MediaStore.Audio.Media.ALBUM; //所屬專輯
MediaStore.Audio.Media.DURATION; //音樂時長
MediaStore.Audio.Media.DATA; //音樂路徑
以上是一些查詢文件時常用的屬性.那么我們如何使用這些屬性呢?
我搜到查詢兩種方式:
第一種:
這里我使用的就是直接將ContextResolver對象放在語句里面.
在獲取音樂時長的時候要注意一點,這里的時長是沒有轉換的,我也不知道是按秒還是毫秒,反正打印出來老長一串.那么,我們就需要轉化一下:
public class tools { /** * 轉換時間 * * @param time * @return */ public static String formatTime(long time) { String min = time / (1000 * 60) + ""; String sec = time % (1000 * 60) + ""; if (min.length() < 2) { min = "0" + time / (1000 * 60) + ""; } else { min = time / (1000 * 60) + ""; } if (sec.length() == 4) { sec = "0" + (time % (1000 * 60)) + ""; } else if (sec.length() == 3) { sec = "00" + (time % (1000 * 60)) + ""; } else if (sec.length() == 2) { sec = "000" + (time % (1000 * 60)) + ""; } else if (sec.length() == 1) { sec = "0000" + (time % (1000 * 60)) + ""; } return min + ":" + sec.trim().substring(0, 2); } }
啊~不是我寫的,網上抄來的.哈哈哈.可以看到在獲取時長的那一段之前我就用了.
第一種方法,個人感覺比較清晰一點.
public static List<Map<String, String>> findMusicFileUseCuesor( Context context) { Cursor cursor = context.getContentResolver().query( MediaStore.Audio.Media.EXTERNAL_CONTENT_URI, null, null, null, MediaStore.Audio.Media.DEFAULT_SORT_ORDER); List<Map<String, String>> list = new ArrayList<Map<String, String>>(); if (cursor.moveToFirst()) { do { Map<String, String> map = new HashMap<String, String>(); // 獲得音樂ID map.put("_id", cursor.getString( cursor.getColumnIndexOrThrow(MediaStore.Audio.Media._ID)) .toString()); // 獲得音樂名稱 map.put("name", cursor.getString(cursor .getColumnIndexOrThrow(MediaStore.Audio.Media.DISPLAY_NAME))); // 獲得音樂標題 map.put("tittle", cursor.getString(cursor .getColumnIndexOrThrow(MediaStore.Audio.Media.TITLE))); // 獲得音樂歌手 map.put("artist", cursor.getString(cursor .getColumnIndexOrThrow(MediaStore.Audio.Media.ARTIST))); // 獲得音樂專輯 map.put("album", cursor.getString(cursor .getColumnIndexOrThrow(MediaStore.Audio.Media.ALBUM))); // 獲得音樂時長 map.put("duration", tools.formatTime(cursor.getLong(cursor .getColumnIndexOrThrow(MediaStore.Audio.Media.DURATION)))); // 獲得音樂路徑 map.put("path", cursor.getString(cursor .getColumnIndexOrThrow(MediaStore.Audio.Media.DATA))); list.add(map); } while (cursor.moveToNext()); } if (list.size() > 0) { for (int i = 0; i < list.size(); i++) { System.out.println("list :---->" + list.get(i).toString()); } return list; } return null; }
第二種方法:
public static List<Map<String, String>> findMusicFileFromPhone( Context context) { Cursor cursor = context.getContentResolver().query(Parameter.MEDIA_URI, Parameter.MEDIA_PROJECTION, Parameter.MEDIA_SELECTION, Parameter.MEDIA_SELECTIONARGS, null); List<Map<String, String>> musicDate = new ArrayList<Map<String, String>>(); while (cursor.moveToNext()) { Map<String, String> map = new HashMap<String, String>(); map.put("tittle", cursor.getString(0)); map.put("artist", cursor.getString(1)); map.put("durtion", tools.formatTime(cursor.getLong(2))); map.put("path", cursor.getString(3)); musicDate.add(map); } if (musicDate.size() > 0) { return musicDate; } else { System.out.println("musicDate :" + musicDate.size()); return null; } }
第二個方法的參數:
public static final Uri MEDIA_URI = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI; public static final String[] MEDIA_PROJECTION = { MediaStore.Audio.Media.TITLE, MediaStore.Audio.Media.ARTIST, MediaStore.Audio.Media.DURATION, MediaStore.Audio.Media.DATA }; public static final String[] MEDIA_SELECTIONARGS = { "audio/mpeg","audio/x-ms-wma" }; public static final String MEDIA_SELECTION = MediaStore.Audio.Media.MIME_TYPE+ "=? or " + MediaStore.Audio.Media.MIME_TYPE + "=?";
這里在后兩句話是什么意思我大概猜得到,但還是希望大牛能給解釋一下...
特別是最后一句,應該是篩選類型,網上看說"?"的地方可以自己定義,可以我一改這代碼就報錯了.不知道為啥....我試過.MP3和MP3小寫的也試過...=.=求科普..
這種方式呢,我覺得一是看起來比較亂..(好吧,其實是我寫的不好).二呢,總覺得在寫的時候寫死數據不太好,比如:
map.put("tittle", cursor.getString(0));
如果參數順序改了的話,那就逗逼了...
但是這種方式在更新,增加,刪除,操作的時候比較方便。
看完上述內容是否對您有幫助呢?如果還想對相關知識有進一步的了解或閱讀更多相關文章,請關注億速云行業資訊頻道,感謝您對億速云的支持。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。