ContentProvider开发步骤:
第一步需要继承ContentProvider并重写下面方法:
public classPersonContentProvider extends ContentProvider{
public boolean onCreate() ://一般做初始化操作在实例创建出来后执行这个方法
public Uri insert(Uri uri, ContentValues values) : //插入时会返回一个rowid如果主键是自增长的话 这个rowid就是主键值
public int delete(Uri uri, String selection, String[] selectionArgs)
public int update(Uri uri, ContentValues values, String selection,String[] selectionArgs)
public Cursor query(Uri uri, String[] projection, String selection,String[] selectionArgs, String sortOrder)
public String getType(Uri uri) :返回的数据内容类型:如,txt:plain/text html:html/text
} :// 该方法用于返回当前Url所代表数据的MIME类型。如果操作的数据属于集合类型,那么MIME类型字符串应该以vnd.android.cursor.dir/开头,例如:要得到所有person记录的Uri为content://cn.itcast.provider.personprovider/person,那么返回的MIME类型字符串应该为:“vnd.android.cursor.dir/person”。如果要操作的数据属于非集合类型数据,那么MIME类型字符串应该以vnd.android.cursor.item/开头,例如:得到id为10的person记录,Uri为content://cn.itcast.provider.personprovider/person/10,那么返回的MIME类型字符串应该为:“vnd.android.cursor.item/person”。
//uri是外面传过来的uri路径:所以在操作时一定得判断这个uri是不是符合要求的。但是怎样判断呢?android提供了一个类,叫做UriMatcher。
UriMatcher的构造函数有一个参数为Int型 :表示不匹配返回的匹配码是多少。
UriMatcher uriMatcher = new UriMatcher(intcode) ;如果code==UriMatcher.NO_MATCH;表示如果不匹配返回的是-1.
定义一个UriMatcher后,下一步就是要在这个应用程序中增加要操作的路径。
一般使用静态方法static{
uriMatcher.addUri(“主机名”,”路径名”,”匹配码”);
}
如果我们要对某条进行操作时。那么该如何编写带数据的uri呢?
在android中一般用#代表的是数字
如:uriMatcher.addUri(“cn.otcyan.adprovier”,”ad/#”,2) ;这个#号就匹配所有的数字
在另一个应用程序编写的uri这样是符合的:
Uri uri = Content:// cn.otcyan.adprovier/ad/2;
在进行删除时,我们又如何获取2这个数字呢,android又提供了一个工具类:
ContentUris.parseid(uri) ;//具体ContentUris看API
Uri介绍:
Uri代表了要操作的数据,Uri主要包含了两部分信息:1》需要操作的ContentProvider,2》对ContentProvider中的什么数据进行操作,一个Uri由以下几部分组成:
在项目开发时,,一般的增,删,改,查时 都要对uri进行判断 这个判断一般都是通过urimatcher来进行的。
监听ContentProvider数据的变化:
为什么要监听:
如果二个应用一个在ContentProvider中插入了一个数据,那个ContentProvider需要发出通知 ,另一个应用就会收到相应的通知。
如何在ContentProvider中发送数据变化通知呢?
方法:
This.getContent.getContentResolver.notifyChange(Uri uri,ContentObserver observer);
如果observer为null值表示没有必须得到该通知。否则必须得到该通知。
在另外一个应用程序中。需要通过ContentResolver进行注册。
This.getContet.GetContentResolver.
registerContentObserver(Uri uri, boolean notifyForDescendents, ContentObserver observer) |
Uri:这个是你发出通知的Uri
notifyForDescendents:是否依赖一般为true ;
observer:抽象类监听后的处理。
注意事项:
在实现contentprovider时,一定不能在provider里面不能自己new构造函数,初始化放在oncreate()否则会报错。还有contentProvider不能new我第一次做demo时就是new的。。嘿嘿。。。有什么错误 望大家指出。下面是一个例子
package com.example.db.activity;
import com.example.db.service.AdService;
import com.example.db.service.MySQLiteHelper;
import android.content.ContentProvider;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.Context;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
public class AdProvider extends ContentProvider {
//private AdService adService ;
private MySQLiteHelper sqLiteHelper ;
private SQLiteDatabase database ;
//定义一个urimatcher这个对象去操作匹配uri
static UriMatcher matcher = new UriMatcher(UriMatcher.NO_MATCH) ; //表示 不进行匹配操作
final static int MULADS = 1 ;
final static int SINGLEADS = 2 ;
//在静态块里定义几个uri
static{
//其实cn.otcyan.providers.adprovider 和ads 这些都 可以定义到外面 去 定义一个静态类
matcher.addURI("cn.otcyan.providers.adprovider", "ads", AdProvider.MULADS) ; //当操作多个时 就返回1
matcher.addURI("cn.otcyan.providers.adprovider", "ad/#", AdProvider.SINGLEADS) ;//当操作单个时就返回2
}
@Override
public int delete(Uri arg0, String arg1, String[] arg2) {
//可以删除多个也可以删除 一个
//匹配uri
database = sqLiteHelper.getWritableDatabase() ;
switch (matcher.match(arg0)) {
case AdProvider.MULADS:
//删除带条件的
return database.delete("ad", arg1, arg2) ;
case AdProvider.SINGLEADS:
//删除指定的id
String whereClause = "aid="+ContentUris.parseId(arg0) ;
if(arg1!=null){
whereClause = whereClause+arg1 ;
}
return database.delete("ad", whereClause, arg2) ;
default:
//uri不正确
throw new IllegalArgumentException("程序无法匹配uri: "+arg0) ;
}
}
@Override
public String getType(Uri arg0) {
return null;
}
@Override
public Uri insert(Uri arg0, ContentValues arg1) {
database = sqLiteHelper.getWritableDatabase() ;
switch (matcher.match(arg0)) {
case AdProvider.MULADS:
Long rowId = database.insert("ad", "aTitle", arg1) ;
Uri uri = ContentUris.withAppendedId(Uri.parse("cn.otcyan.providers.adprovider/ad"), rowId) ;
return uri ;
default:
//uri不正确
throw new IllegalArgumentException("程序无法匹配uri: "+arg0) ;
}
}
@Override
public boolean onCreate() {
//adService = new AdService(this.getContext(), "ad.db", 1) ;
sqLiteHelper = new MySQLiteHelper(this.getContext(), "ad.db", 1) ;
return true;
}
@Override
public Cursor query(Uri arg0, String[] arg1, String arg2, String[] arg3,
String arg4) {
database = sqLiteHelper.getWritableDatabase() ;
switch (matcher.match(arg0)) {
case AdProvider.MULADS:
//查出所有
return database.query("ad", arg1, arg2, arg3, null, null, arg4) ;
case AdProvider.SINGLEADS:
String where = "aid="+ContentUris.parseId(arg0) ;
if(arg2!=null){
where = where + arg2 ;
}
return database.query("ad", arg1, arg2, arg3, null, null, arg4) ;
default:
//uri不正确
throw new IllegalArgumentException("程序无法匹配uri: "+arg0) ;
}
}
@Override
public int update(Uri uri, ContentValues values, String selection,
String[] selectionArgs) {
database = sqLiteHelper.getWritableDatabase() ;
switch (matcher.match(uri)) {
case AdProvider.MULADS:
//更新所有
return database.update("ad", values, selection, selectionArgs) ;
case AdProvider.SINGLEADS:
String where = "aid="+ContentUris.parseId(uri) ;
if(selection!=null){
where = where + selection ;
}
return database.update("ad", values, where, selectionArgs) ;
default:
//uri不正确
throw new IllegalArgumentException("程序无法匹配uri: "+uri) ;
}
}
}