在日常开发中,我们经常会使用MediaStore来获取手机的音频、图片、视频等相关信息。下面3个是常见的内部类:
MediaStore.Audio 获取音频信息的类
MediaStore.Images 获取图片信息
MediaStore.Video 获取视频信息
1、MediaStore.Audio
在这个类中我们可以获取音频的专辑、艺术家、流派等等,通过 MediaStore.Audio.AlbumColumns 可以查阅专辑表的字段信息,我们也可以通过Uri来查询手机上的
专辑表的字段信息。主要是用 MediaStore.Audio.Albums.EXTERNAL_CONTENT_URI 的Uri来查询。其中EXTERNAL_CONTENT_URI 为查询外置内存卡的,内置内存卡
为 INTERNAL_CONTENT_URI。
private Uri albumUri = MediaStore.Audio.Albums.EXTERNAL_CONTENT_URI;
// 配置
private void getUriColumns(Uri uri){
Cursor cursor = getContentResolver().query(uri, null, null, null, null);
cursor.moveToFirst();
String[] columns = cursor.getColumnNames();
for (String string : columns) {
System.out.println(cursor.getColumnIndex(string)+" = "+string);
}
}
结果为:
06-24 01:05:44.979: I/System.out(1529): 0 = _id
06-24 01:05:44.983: I/System.out(1529): 1 = album
06-24 01:05:44.987: I/System.out(1529): 2 = album_key
06-24 01:05:44.987: I/System.out(1529): 3 = minyear
06-24 01:05:44.987: I/System.out(1529): 4 = maxyear
06-24 01:05:44.987: I/System.out(1529): 5 = artist
06-24 01:05:44.987: I/System.out(1529): 6 = artist_id
06-24 01:05:44.987: I/System.out(1529): 7 = artist_key
06-24 01:05:44.987: I/System.out(1529): 8 = numsongs
06-24 01:05:44.987: I/System.out(1529): 9 = album_art
可以看到相应的字段和下标是什么。
// 艺术家
private Uri artUri = MediaStore.Audio.Artists.EXTERNAL_CONTENT_URI;
// 流派
private Uri genresUri = MediaStore.Audio.Genres.EXTERNAL_CONTENT_URI;
也可以通过上面的Uri来查询音频的艺术家和流派相应的信息。
音频信息比较全的是这个类 MediaStore.Audio.Media 可以通过Uri来看下字段有什么:
private Uri mediaUri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
字段为:
06-24 01:25:51.656: I/System.out(5292): 0 = _id
06-24 01:25:51.656: I/System.out(5292): 1 = _data 音频路径
06-24 01:25:51.656: I/System.out(5292): 2 = _display_name 音频名称包括后缀名
06-24 01:25:51.656: I/System.out(5292): 3 = _size 音频大小
06-24 01:25:51.656: I/System.out(5292): 4 = mime_type 音频类型
06-24 01:25:51.656: I/System.out(5292): 5 = date_added
06-24 01:25:51.656: I/System.out(5292): 6 = is_drm
06-24 01:25:51.656: I/System.out(5292): 7 = date_modified
06-24 01:25:51.656: I/System.out(5292): 8 = title 音频名称不包括后缀名
06-24 01:25:51.656: I/System.out(5292): 9 = title_key
06-24 01:25:51.664: I/System.out(5292): 10 = duration 音频时长
06-24 01:25:51.664: I/System.out(5292): 11 = artist_id
06-24 01:25:51.664: I/System.out(5292): 12 = composer
06-24 01:25:51.664: I/System.out(5292): 13 = album_id
06-24 01:25:51.672: I/System.out(5292): 14 = track
06-24 01:25:51.672: I/System.out(5292): 15 = year
06-24 01:25:51.672: I/System.out(5292): 16 = is_ringtone
06-24 01:25:51.672: I/System.out(5292): 17 = is_music
06-24 01:25:51.672: I/System.out(5292): 18 = is_alarm
06-24 01:25:51.672: I/System.out(5292): 19 = is_notification
06-24 01:25:51.672: I/System.out(5292): 20 = is_podcast
06-24 01:25:51.672: I/System.out(5292): 21 = bookmark
06-24 01:25:51.700: I/System.out(5292): 22 = album_artist
06-24 01:25:51.700: I/System.out(5292): 23 = artist_id:1
06-24 01:25:51.700: I/System.out(5292): 24 = artist_key
06-24 01:25:51.700: I/System.out(5292): 25 = artist
06-24 01:25:51.700: I/System.out(5292): 26 = album_id:1
06-24 01:25:51.700: I/System.out(5292): 27 = album_key
06-24 01:25:51.700: I/System.out(5292): 28 = album
字段很多,就对比较常用的注释了下,有字段是和其他表关联的如 artist_id、album_id等等,其中比较常用的是 _data、 _display_name、 _size、mime_type、 title、duration等字段
可以通过常用的字段来查询手机下相应的音频文件:
private Uri mediaUri = MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
private void getUriData(Uri uri){
String[] projection = {"_data","_display_name","_size","mime_type","title","duration"};
Cursor cursor = getContentResolver().query(uri, projection, null, null, null);
cursor.moveToFirst();
do {
System.out.println("_data = "+cursor.getString(cursor.getColumnIndex("_data")));
System.out.println("_display_name = "+cursor.getString(cursor.getColumnIndex("_display_name")));
System.out.println("_size = "+cursor.getString(cursor.getColumnIndex("_size")));
System.out.println("mime_type = "+cursor.getString(cursor.getColumnIndex("mime_type")));
System.out.println("title = "+cursor.getString(cursor.getColumnIndex("title")));
System.out.println("duration = "+cursor.getString(cursor.getColumnIndex("duration")));
} while (cursor.moveToNext());
}
结果如下:
06-24 13:40:12.445: I/System.out(4610): _data = /mnt/sdcard/kgmusic/download/孙楠、神话、韩红 - 美丽的神话.mp3
06-24 13:40:12.445: I/System.out(4610): _display_name = 孙楠、神话、韩红 - 美丽的神话.mp3
06-24 13:40:12.445: I/System.out(4610): _size = 4635648
06-24 13:40:12.445: I/System.out(4610): mime_type = audio/mpeg
06-24 13:40:12.445: I/System.out(4610): title = 美丽的神话
06-24 13:40:12.445: I/System.out(4610): duration = 289712
06-24 13:40:12.445: I/System.out(4610): _data = /mnt/sdcard/kgmusic/download/那英、孙楠 - 只要有你.mp3
06-24 13:40:12.445: I/System.out(4610): _display_name = 那英、孙楠 - 只要有你.mp3
06-24 13:40:12.445: I/System.out(4610): _size = 4012536
06-24 13:40:12.445: I/System.out(4610): mime_type = audio/mpeg
06-24 13:40:12.445: I/System.out(4610): title = 只要有你( 少年包青天 片尾曲)
06-24 13:40:12.446: I/System.out(4610): duration = 250784
由于音频过多就列举了两个,可以看到通过字段的查询获取到音频的详细信息。
2、MediaStore.Images
在该类中有一个借口和两个class ,分别为:
MediaStore.Images.ImageColumns 可以查看图片的字段信息
MediaStore.Images.Media 可以获取图片的相关信息
MediaStore.Images.Thumbnails 可以获取图片的缩略图
关于MediaStore.Images.ImageColumns 可以查看api ,下面通过MediaStore.Images.Media 查询手机上的图片。
private Uri imageUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
通过上面查看字段的代码,可以看到如下图片的字段信息:
06-24 13:52:34.018: I/System.out(4755): 0 = _id
06-24 13:52:34.018: I/System.out(4755): 1 = _data
06-24 13:52:34.018: I/System.out(4755): 2 = _size
06-24 13:52:34.018: I/System.out(4755): 3 = _display_name
06-24 13:52:34.018: I/System.out(4755): 4 = mime_type
06-24 13:52:34.018: I/System.out(4755): 5 = title
06-24 13:52:34.018: I/System.out(4755): 6 = date_added
06-24 13:52:34.018: I/System.out(4755): 7 = date_modified
06-24 13:52:34.018: I/System.out(4755): 8 = description
06-24 13:52:34.018: I/System.out(4755): 9 = picasa_id
06-24 13:52:34.018: I/System.out(4755): 10 = isprivate
06-24 13:52:34.018: I/System.out(4755): 11 = latitude
06-24 13:52:34.018: I/System.out(4755): 12 = longitude
06-24 13:52:34.018: I/System.out(4755): 13 = datetaken
06-24 13:52:34.018: I/System.out(4755): 14 = orientation
06-24 13:52:34.018: I/System.out(4755): 15 = mini_thumb_magic
06-24 13:52:34.018: I/System.out(4755): 16 = bucket_id
06-24 13:52:34.018: I/System.out(4755): 17 = bucket_display_name
06-24 13:52:34.018: I/System.out(4755): 18 = is_drm
06-24 13:52:34.018: I/System.out(4755): 19 = drm_content_uri
06-24 13:52:34.018: I/System.out(4755): 20 = drm_offset
06-24 13:52:34.018: I/System.out(4755): 21 = drm_dataLen
06-24 13:52:34.018: I/System.out(4755): 22 = drm_rights_issuer
06-24 13:52:34.018: I/System.out(4755): 23 = drm_content_name
06-24 13:52:34.018: I/System.out(4755): 24 = drm_content_description
06-24 13:52:34.018: I/System.out(4755): 25 = drm_content_vendor
06-24 13:52:34.019: I/System.out(4755): 26 = drm_icon_uri
06-24 13:52:34.019: I/System.out(4755): 27 = drm_method
可以查看和音频的字段是有些不同的。获取图片的基本信息:
private void getUriData(Uri uri){
String[] projection = {"_data","_display_name","_size","mime_type","title","orientation"};
Cursor cursor = getContentResolver().query(uri, projection, null, null, null);
cursor.moveToFirst();
do {
System.out.println("_data = "+cursor.getString(cursor.getColumnIndex("_data")));
System.out.println("_display_name = "+cursor.getString(cursor.getColumnIndex("_display_name")));
System.out.println("_size = "+cursor.getString(cursor.getColumnIndex("_size")));
System.out.println("mime_type = "+cursor.getString(cursor.getColumnIndex("mime_type")));
System.out.println("title = "+cursor.getString(cursor.getColumnIndex("title")));
System.out.println("orientation = "+cursor.getString(cursor.getColumnIndex("orientation")));
} while (cursor.moveToNext());
}
orientation 为图片的对其方式, 输出信息为:
06-24 13:57:59.653: I/System.out(4851): _data = /mnt/sdcard/sdcard2/Photo/IMG_20100101_081333.jpg
06-24 13:57:59.653: I/System.out(4851): _display_name = IMG_20100101_081333.jpg
06-24 13:57:59.653: I/System.out(4851): _size = 795457
06-24 13:57:59.653: I/System.out(4851): mime_type = image/jpeg
06-24 13:57:59.653: I/System.out(4851): title = IMG_20100101_081333
06-24 13:57:59.654: I/System.out(4851): orientation = 90
06-24 13:57:59.654: I/System.out(4851): _data = /mnt/sdcard/sdcard2/Photo/IMG_20100101_081344.jpg
06-24 13:57:59.654: I/System.out(4851): _display_name = IMG_20100101_081344.jpg
06-24 13:57:59.654: I/System.out(4851): _size = 673729
06-24 13:57:59.654: I/System.out(4851): mime_type = image/jpeg
06-24 13:57:59.654: I/System.out(4851): title = IMG_20100101_081344
06-24 13:57:59.654: I/System.out(4851): orientation = 90
06-24 13:57:59.654: I/System.out(4851): _data = /mnt/sdcard/QQ_Screenshot/1425453607656.png
06-24 13:57:59.654: I/System.out(4851): _display_name = 1425453607656.png
06-24 13:57:59.654: I/System.out(4851): _size = 65742
06-24 13:57:59.654: I/System.out(4851): mime_type = image/png
06-24 13:57:59.654: I/System.out(4851): title = 1425453607656
06-24 13:57:59.654: I/System.out(4851): orientation = null
MediaStore.Images.Thumbnails 获取缩略图这个类和下面获取手机视频信息一起讲。
2、MediaStore.Video
该类有两个class比较常用:MediaStore.Video.Media MediaStore.Video.Thumbnails 一个是获取视频的相关信息,一个是获取视频的缩略图
MediaStore.Video.Media 用法和上面介绍的一样,不清楚它有什么字段的,可以先查询出来,再来获取视频的相关信息,和路径、名称、类型等等,这里就不介绍了。下面是获取视频的缩略图的相关操作。
MediaStore.Video.Thumbnails 主要用到这个两个方法:
static Bitmap getThumbnail(ContentResolver cr, long origId, long groupId, int kind, BitmapFactory.Options options)
static Bitmap getThumbnail(ContentResolver cr, long origId, int kind, BitmapFactory.Options options)
这里第一个参数可以通过 getContentResolver() 来获取 、第二个参数 origId 为视频的ID ,第三个参数 groupId 我也不太清楚,大家知道的可以告诉我一下O(∩_∩)O, 第四个参数kind 有两种类型分别为:
MICRO_KIND(微型分辨率小)MINI_KIND (迷你型)、第五个参数 为BitmapFactory.Option对象
<1> 第一种是使用上面介绍的方法:
public class ThumbnailActivity extends Activity {
private ListView listView;
private Uri videoUri = MediaStore.Video.Media.EXTERNAL_CONTENT_URI;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.video_listview);
listView = (ListView) findViewById(R.id.mylistview1);
new MyThumbnailAsyncTask().execute(videoUri);
}
/**
* 异步加载
*
*/
private class MyThumbnailAsyncTask extends AsyncTask
@Override
protected List
// TODO Auto-generated method stub
List
return data;
}
@Override
protected void onPostExecute(List
listView.setAdapter(new MyThumbnailAdapter(result));
super.onPostExecute(result);
}
}
/**
* 获取手机上视频的缩略图
* @param uri 视频的Uri
* @return
*/
private List
List
ContentResolver cr = getContentResolver();
Cursor cursor = cr.query(uri, new String[]{Media._ID}, null, null, null);
cursor.moveToFirst();
do {
long id = cursor.getLong(0); // 取得视频的ID,因为我上行只有一个参数所以下标为0
BitmapFactory.Options options = new Options();
Bitmap bitmap = MediaStore.Video.Thumbnails.getThumbnail(cr, id, MediaStore.Video.Thumbnails.MINI_KIND, options);
if (bitmap == null) {
Log.e("TAG", "bitmap == null");
}
list.add(bitmap);
} while (cursor.moveToNext());
return list;
}
private class MyThumbnailAdapter extends BaseAdapter{
private List
public MyThumbnailAdapter(List
this.mlist = list;
}
@Override
public int getCount() {
// TODO Auto-generated method stub
return mlist.size();
}
@Override
public Object getItem(int position) {
// TODO Auto-generated method stub
return mlist.get(position);
}
@Override
public long getItemId(int position) {
// TODO Auto-generated method stub
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder = null;
if (convertView == null) {
holder = new ViewHolder();
convertView = LayoutInflater.from(getApplicationContext()).inflate(R.layout.video_img, null);
holder.imageView = (ImageView) convertView.findViewById(R.id.my_img);
convertView.setTag(holder);
}else{
holder = (ViewHolder) convertView.getTag();
}
holder.imageView.setImageBitmap(mlist.get(position));
return convertView;
}
private class ViewHolder{
private ImageView imageView;
}
}
}
很简单XML就不贴了,就一个ListView。通过上面的方法图片缩略图的获取也是一样。
<2> 第二种通过 MediaMetadataRetriever 来获取:
public class MediaMetadataActivity extends Activity{
private ProgressDialog dialog = null;
private Uri videoUri = MediaStore.Video.Media.EXTERNAL_CONTENT_URI;
private ListView listView;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.list_view);
listView = (ListView) findViewById(R.id.mylistview);
dialog = new ProgressDialog(this);
dialog.setMessage("加载数据中...");
dialog.show();
new myAsyncTask().execute(videoUri);
}
private class myAsyncTask extends AsyncTask
@Override
protected List
// TODO Auto-generated method stub
List
List
return items;
}
@Override
protected void onPostExecute(List
// TODO Auto-generated method stub
if (dialog!=null) {
dialog.dismiss();
}
listView.setAdapter(new MyAdapter(result));
super.onPostExecute(result);
}
}
private List
List
for (int i = 0; i < items.size(); i++) {
ListItem item = new ListItem();
item.setBitmap(getThumbnail(items.get(i).getPath()));
item.setTitle(items.get(i).getTitle());
listItems.add(item);
}
return listItems;
}
/**
* 主要是这个方法通过为MediaMetadataRetriever 设置视频的路径来取得缩略图
* @param path 视频的路径
* @return
*/
private Bitmap getThumbnail(String path){
MediaMetadataRetriever retriever = new MediaMetadataRetriever();
retriever.setDataSource(path);
Bitmap bitmap = retriever.getFrameAtTime();
retriever.release();
return bitmap;
}
private List
List
String projection[] = {Media.DATA,Media.TITLE,Media.DURATION};
Cursor cursor = getContentResolver().query(uri, projection, null, null, null);
cursor.moveToFirst();
int count = cursor.getCount();
for (int i = 0; i < count; i++) {
VideoItem item = new VideoItem();
item.setPath(cursor.getString(0));
item.setTitle(cursor.getString(1));
mylist.add(item);
cursor.moveToNext();
}
return mylist;
}
private class MyAdapter extends BaseAdapter{
List
public MyAdapter(List
super();
this.mlist = list;
}
@Override
public int getCount() {
// TODO Auto-generated method stub
return mlist.size();
}
@Override
public Object getItem(int position) {
// TODO Auto-generated method stub
return mlist.get(position);
}
@Override
public long getItemId(int position) {
// TODO Auto-generated method stub
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder = null;
if (convertView == null) {
holder = new ViewHolder();
convertView = LayoutInflater.from(getApplicationContext()).inflate(R.layout.item, null);
holder.imageView = (ImageView) convertView.findViewById(R.id.img);
holder.textView = (TextView) convertView.findViewById(R.id.tv);
convertView.setTag(holder);
}else{
holder = (ViewHolder) convertView.getTag();
}
holder.imageView.setImageBitmap(mlist.get(position).getBitmap());
holder.textView.setText(mlist.get(position).getTitle());
return convertView;
}
private class ViewHolder{
private ImageView imageView;
private TextView textView;
}
}
}
MediaMetadataRetriever 除了通过 getFrameAtTime() 方法获取外,还可以用getFrameAtTime(long timeUs)和getFrameAtTime(long timeUs, int option)方法通过时长来获取,这就是获取视频缩略图的两种方式。
以上如果有错的地方,欢迎指出!!O(∩_∩)O~