首先我们的引入安卓的四大组件之一的Contentprovider,内容提供者,负责数据的搬运。跨程序的通信,主要有提供者和获取者。
例如首先介绍提供方:首先创了contentprider提供方可以把数据库的数据提供出来:首先继承ContentProvider,
有五个方法重写:
public class Myprider extends ContentProvider {
@Override
public boolean onCreate() {
return false;
}
@Nullable
@Override
public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) {
return null;
}
@Nullable
@Override
public String getType(@NonNull Uri uri) {
return null;
}
@Nullable
@Override
public Uri insert(@NonNull Uri uri, @Nullable ContentValues values) {
return null;
}
@Override
public int delete(@NonNull Uri uri, @Nullable String selection, @Nullable String[] selectionArgs) {
return 0;
}
@Override
public int update(@NonNull Uri uri, @Nullable ContentValues values, @Nullable String selection, @Nullable String[] selectionArgs) {
return 0;
}
}
2.第二步在清单里对contentprovider进行注册:
自定义权限,注意这里的第一个参数的意思是
authorities:是一个唯一标示,通过这个东西可以找到contentprider,名字自己取
name:是自己的包名+类名;
第三个参数设置为true:可以保证外部程序访问成功;
permission:这是自己定义的权限。
<provider
android:authorities="com.wj.class"
android:name=".db.Myprider"
android:exported="true"
android:permission="android.permission.READ_WJ_DB"
/>
注意这里提供者添加了权限,则需要在清单里注册权限:
<permission
android:description="@string/wj_db" android:icon="@mipmap/ic_launcher_round" android:label="@string/app_name" android:name="READ_WJ_DB" android:protectionLevel="normal" />//第一个参数description是权限的描述,如果你失败了这会谈出这句话。注意这里需要@string
<string name="wj_db">wj close the door</string>
//第二个是直接填app名字即可,第三个是权限的名字:包名+刚才的权限名字
READ_WJ_DB,第四个是权限的等级:normol最低默认。这里就注册了权限,你自定义的权限就生效了
3.介绍一下uri
uri代表了要操作的数据,是一个路径。由两部分组成,第一部分是说你代表一个什么样的contentprovider,第二个是说对contentprovider什么样的数据进行操作(音乐,通讯录等等),
下面就是Uri和它的介绍
这里的person代表数据库的意思。
首先我们来看一个提供者如何拿到数据库,对数据库插入一条数据:
刚才重写了ContentProvider这个类,里面的
public Uri insert(@NonNull Uri uri, @Nullable ContentValues values) {
首先我们需要在这里进行格式判断,比如用户只需要进行找到student数据库,只插入name值,或者只是id,又或者两个都要添加
//只name的格式
// 首先要判断一个uri 格式//content:// com.wj.class/student/name
//既有name又有id的格式
// 格式//content:// com.wj.class/student/id/name
if(uri.equals("//content:// com.wj.class/student/id/name)"))
{
//接着我们要对进行赋值调用Contentvalues的方法
int id= values.getAsInteger("id");
String st=values.getAsString("name");
String sql="insert into student values("+id+","+st+")";
db.execSQL(sql); }
return null; }
注意这里必须的对数据库初始化:datebse哪里来的呢
SQLiteDatabase db;
//这里直接把数据库的获取放在Oncreate里边
@Override
public boolean onCreate() {
db = new Mydbhelper(getContext()).getWritableDatabase();
return false;
}
这是重写的第二个方法,用来取数据,在这里默认给我一个uri我给你取所有数据。
@Override
public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) {
//首先你需要传一个uri进行判断是否符合我的要求,如果不是则返回null
if(uri.equals("content:// com.wj.class/student"))
{
String sq = "select * from student";
Cursor cursor = db.rawQuery(sq, null);
return cursor;
}else
{
return null;
}}
写到这里一个Contentprovider提供者就写好了
下面要开始写一个获取者,获取数据,获取方。看下面代码:
public class LocalActivity extends AppCompatActivity {
ArrayList<String> pathName = new ArrayList<String>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_local);
// File file= Environment.getDataDirectory();
// String str=Environment.DIRECTORY_MUSIC;
// File str1=Environment.getExternalStorageDirectory();
// Log.e("msg",""+file);
// Log.e("msg",""+str);
// Log.e("msg",""+str1);
// String sql = "insert into student values(1,'zzz')";
// db.execSQL(sql);
//首先是通过当前activty获取ContentResover来获取当前的获取的对象。
ContentResolver contentResolver=this.getContentResolver();
//然后填写你要拿的uri
Uri uri=Uri.parse("content://com.wj.class/student");//出入数据的地址
//查询方法生成一个游标对象,下面就是对游标进行判断索引。
Cursor cursor=contentResolver.query(uri,null,null,null,null);
if (cursor.moveToNext()) {
//代表第几列拿
int id=cursor.getInt(0);
//通过列名拿
int id1=cursor.getInt(cursor.getColumnIndex("id"));
String name=cursor.getString(1);
Log.e("msg","id"+id+"id1"+id1+"name"+name);
}else
{
Log.e("msg","游标失败");
}
}
}
后面出现报错说明需要添加权限这个,就是刚才自定义的
<uses-permission android:name="android.permission.READ_WJ_DB"/>
同时要特别注意填写的uri,用getpath()获取到的是后面的数据库和资源并非全名称所以应该直接uri.equals()就可以,好了
4.刚才我们拿到是自己的数据库,现在我们要拿手机上的系统音乐数据库:
首先要找到系统的uri是什么:
MediaStore.Audio.Media.EXTERNAL_CONTENT_URI
这个就是系统的uri音乐地址:然后通过Uri类进行生成对象
Uri uri1=MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;下一步调用获取方法,获取方法是这个 ContentResolver contentResolver=this.getContentResolver();//调用这个query()方法,同时要添加提供者要的参数后面的四个null; Cursor cursor=contentResolver.query(uri,null,null,null,null);//改成下面这个信息,具体信息,包括歌曲的各种信息,这是在提供方里面已经定义好了的Cursor cursor=contentResolver.query(uri1,
new String[]{MediaStore.Audio.Media._ID, //写入我想要获得的信息(列)
MediaStore.Audio.Media.TITLE,
MediaStore.Audio.Media.ALBUM,
MediaStore.Audio.Media.DISPLAY_NAME,
MediaStore.Audio.Media.ARTIST,
MediaStore.Audio.Media.DURATION,
MediaStore.Audio.Media.SIZE,
MediaStore.Audio.Media.DATA},null,null,null);//下面通过游标把提供方的东西取出来看下
if(cursor!=null)
{
while(cursor.moveToNext())
{
long id = cursor.getLong(0);
String title = cursor.getString(1);
String album = cursor.getString(2);
String displayName = cursor.getString(3);
String artist = cursor.getString(4);
long duration = cursor.getLong(5);
long size = cursor.getLong(6);
String url = cursor.getString(7); //转存数据
Log.e("msg",""+id+""+title+""+ album+""+displayName+""+artist+""+duration
+""+size+""+url);
}
}
这个就是拿到的歌曲信息包括
下面把拿到的歌曲放到自己的集合中在这里需要:
这样首先创了一个类:用集合对象
MusicInfo
public class MusicInfo
{
private long id;
private String title;
private String album;
private String displayName;
private String artist;
private long duration;
private long size;
private String url;
public MusicInfo() {
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getAlbum() {
return album;
}
public void setAlbum(String album) {
this.album = album;
}
public String getDisplayName() {
return displayName;
}
public void setDisplayName(String displayName) {
this.displayName = displayName;
}
public String getArtist() {
return artist;
}
public void setArtist(String artist) {
this.artist = artist;
}
public long getDuration() {
return duration;
}
public void setDuration(long duration) {
this.duration = duration;
}
public long getSize() {
return size;
}
public void setSize(long size) {
this.size = size;
}
}
MusicInfo musicInfo = new MusicInfo();
ArrayList<MusicInfo> mMusicInfos = new ArrayList< MusicInfo>();
musicInfo.setTitle(title);
musicInfo.setId(id);
musicInfo.setAlbum(album);
musicInfo.setArtist(artist);
musicInfo.setSize(size);
musicInfo.setDisplayName(displayName);
musicInfo.setDuration(duration);
musicInfo.setUrl(url); //存到数据单元
mMusicInfos.add(musicInfo); //添加到List
//下面我们把它迭代出来:看到的结果
for(MusicInfo musicInf : mMusicInfos) {
Log.e("msg",""+musicInf.getDisplayName());
}