黎活明8天快速掌握android视频教程--21_监听ContentProvider中数据的变化
采用ContentProvider除了可以让其他应用访问当前的app的数据之外,还有可以实现当app的数据发送变化的时候,通知注册了数据变化通知的调用者
其他所有的代码都和第20讲的一样,不同的地方看下面的代码:
package test.weiyuan.sqllite1; import android.content.ContentProvider;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.util.Log; import dB.DbOpenHelper; /**
* Created by wei.yuan on 2015/6/3.
* 一定要在清单文件中对内容提供者进行注册
*/
public class PersonProvider extends ContentProvider { private DbOpenHelper dbOpenHelper;
//该类用于检测的外部应用输入的URL是否正确,如果正确返回码就是codePerson,不正确返回UriMatcher.NO_MATCH
private static final int codePerson = 1;
private static final int codePerson1 = 2;
//该类用于检测的外部应用输入的URL是否正确,如果不正确返回码就是new UriMatcher(UriMatcher.NO_MATCH)构造函数中的参数,这里是UriMatcher.NO_MATCH
private static final UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
static
{
//这个url表示对整个person表进行操作
uriMatcher.addURI("test.weiyuan.sqllite1.PersonProvider","person",codePerson);
//这个url表示对person表中的某个记录进行操作,#表示的是数字,就是对应的person表中的某个记录
uriMatcher.addURI("test.weiyuan.sqllite1.PersonProvider","person/#",codePerson1);
}
//onCreate()之后被调用一次,在调用的时候创建数据库,记得返回值为true
@Override
public boolean onCreate() {
dbOpenHelper = new DbOpenHelper(getContext());
return true;
} //查询数据表的数据
@Override
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
SQLiteDatabase database = dbOpenHelper.getWritableDatabase();
switch (uriMatcher.match(uri))
{
//更新整个表
case codePerson: return database.query("person",projection,selection,selectionArgs,null,null,sortOrder); //更新表中的某条记录
case codePerson1:
long row_id = ContentUris.parseId(uri);
String where = " personid="+row_id;
Log.i("weiyuan",""+row_id);
if (selection!=null&&!"".equals(selection.trim()))
{
where += "and "+selection;
}
return database.query("person",null,where,selectionArgs,null,null,sortOrder); default: //如果传人的url不正确,抛出一个异常提示用户
throw new IllegalArgumentException("this is a unkown url-->"+uri); } } //返回要操作数据的内容类型,如txt文本就是plain/text类型
@Override
public String getType(Uri uri) {
return null;
} //可以让外面的应用向内容提供者插入数据
@Override
public Uri insert(Uri uri, ContentValues values) {
SQLiteDatabase database = dbOpenHelper.getWritableDatabase();
switch (uriMatcher.match(uri))
{
case codePerson:
//这里如果values为空,就必须需要第二个参数有值这里为"name",如果values有值,第二个参数默认为空值
long rowid = database.insert("person",null,values);
// Uri insertUri = Uri.parse("context://test.weiyuan.providers.PersonProvider/person/"+rowid);可以使用下面的方法http://blog.csdn.net/feng88724/article/details/6331396
Uri insertUri = ContentUris.withAppendedId(uri,rowid);
//当数据添加之后,发送通知提供给其他内容提供者
getContext().getContentResolver().notifyChange(uri,null);//发出数据变化的通知
if(database!=null)
{
database.close();
} return insertUri; default:
//如果传人的url不正确,抛出一个异常提示用户
if(database!=null)
{
database.close();
}
throw new IllegalArgumentException("this is a unkown url-->"+uri); } } //返回值int表示你删除了多少条记录
@Override
public int delete(Uri uri, String selection, String[] selectionArgs)
{
SQLiteDatabase database = dbOpenHelper.getWritableDatabase();
switch (uriMatcher.match(uri))
{
//删除整个表
case codePerson: database.delete("preson",selection,selectionArgs);
if(database!=null)
{
database.close();
}
break;
//删除表中的某条记录
case codePerson1:
long row_id = ContentUris.parseId(uri);
String where = " personid="+ row_id;
Log.i("weiyuan",""+row_id);
if (selection!=null&&!"".equals(selection.trim()))
{
where += "and "+selection;
}
database.delete("person",where,selectionArgs);
if(database!=null)
{
database.close();
}
break; default:
//如果传人的url不正确,抛出一个异常提示用户
throw new IllegalArgumentException("this is a unkown url-->"+uri); } return 0;
} @Override
public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) { SQLiteDatabase database = dbOpenHelper.getWritableDatabase();
switch (uriMatcher.match(uri))
{
//更新整个表
case codePerson: database.update("preson",values,selection,selectionArgs);
if(database!=null)
{
database.close();
}
break;
//更新表中的某条记录
case codePerson1:
long row_id = ContentUris.parseId(uri);
String where = " personid="+row_id;
Log.i("weiyuan",""+row_id);
if (selection!=null&&!"".equals(selection.trim()))
{
where += "and "+selection;
}
database.update("person",values,where,selectionArgs);
if(database!=null)
{
database.close();
}
break; default:
if(database!=null)
{
database.close();
}
//如果传人的url不正确,抛出一个异常提示用户
throw new IllegalArgumentException("this is a unkown url-->"+uri); }
return 0;
}
}
当有其他应用通过provider想数据库插入数据的时候就会发出 getContext().getContentResolver().notifyChange(uri,null);这个数据变化的广播
其他第三方应该如果注册了这个广播就会收到这个数据库变化的广播
我们来看下面的代码,第三方监听者的代码:
package com.example.weiyuan.myapplication; import android.app.ActivityManager;
import android.content.ContentResolver;
import android.content.ContentValues;
import android.content.Intent;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.PermissionInfo;
import android.content.pm.ResolveInfo;
import android.database.ContentObserver;
import android.database.Cursor;
import android.net.Uri;
import android.os.Handler;
import android.provider.Contacts;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.ImageView;
import android.widget.TextView; import java.util.List; public class MainActivity extends ActionBarActivity { private ImageView imageView;
private TextView textView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
textView = (TextView)findViewById(R.id.show); //注册内容提供者变化的监听器
Uri uri = Uri.parse("content://test.weiyuan.sqllite1.PersonProvider/person");
/* //第二个参数很关键true表示只要是以"content://test.weiyuan.sqllite1.PersonProvider/person"开头的url都可以监听
比如"content://test.weiyuan.sqllite1.PersonProvider/person/123",是以"content://test.weiyuan.sqllite1.PersonProvider/person"开头的,也可以监听
但是是false的话,如果要监听"content://test.weiyuan.sqllite1.PersonProvider/person/123"就必须写出
"content://test.weiyuan.sqllite1.PersonProvider/person/123"*/
getContentResolver().registerContentObserver(uri,true,new Observer(new Handler())); } //得到数据变化的通知
public class Observer extends ContentObserver
{ /**
* Creates a content observer.
*
* @param handler The handler to run {@link #onChange} on, or null if none.
*/
public Observer(Handler handler) {
super(handler);
} @Override
public void onChange(boolean selfChange) {
//获得最新的插入数据的内容
Uri uri = Uri.parse("content://test.weiyuan.sqllite1.PersonProvider/person");
ContentResolver resolver = getContentResolver();
Cursor cursor = resolver.query(uri, null, null, null, "personid desc ");
if(cursor.moveToFirst())
{
textView.setText(cursor.getString(cursor.getColumnIndex("name"))+"...."+cursor.getString(cursor.getColumnIndex("phone")));
} super.onChange(selfChange);
} @Override
public boolean deliverSelfNotifications() {
return super.deliverSelfNotifications();
}
} @Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.menu_main, menu);
return true;
} @Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId(); //noinspection SimplifiableIfStatement
if (id == R.id.action_settings) {
return true;
} return super.onOptionsItemSelected(item);
}
}
上面的代码或者最新插入到数据库中的最新的一条数据。对应系统的通讯录我们也可以监听系统通讯录发送变化的广播,获得最新的通讯录数据。
黎活明8天快速掌握android视频教程--21_监听ContentProvider中数据的变化的更多相关文章
- 黎活明8天快速掌握android视频教程--22_访问通信录中的联系人和添加联系人
Android系统中联系人的通讯录的contentProvide是一个单独的apk,显示在界面的contact也是一个独立的apk,联系人apk通过contentProvide访问底层的数据库. 现在 ...
- 黎活明8天快速掌握android视频教程--17_创建数据库与完成数据添删改查
1.我们首先来看下整个项目 项目也是采用mvc的框架 package dB; import android.content.Context; import android.database.sqlit ...
- 黎活明8天快速掌握android视频教程--15_采用Pull解析器解析和生成XML内容
1.该项目主要有下面的两个作用 (1)将xml文件解析成对象的List对象,xml文件可以来自手机本地,也可以来自服务器返回的xml数据 (2)强list对象保存成xml文件,xml保存到手机的内存卡 ...
- 黎活明8天快速掌握android视频教程--25_网络通信之资讯客户端
1 该项目的主要功能是:后台通过xml或者json格式返回后台的视频资讯,然后Android客户端界面显示出来 首先后台新建立一个java web后台 采用mvc的框架 所以的servlet都放在se ...
- 黎活明8天快速掌握android视频教程--24_网络通信之网页源码查看器
1 该项目的主要功能就是从将后台的html网页在Android的界面上显示出来 后台就是建立一个java web工程在工程尚建立一个html或者jsp文件就可以了,这里主要看Android客户端的程序 ...
- 黎活明8天快速掌握android视频教程--23_网络通信之网络图片查看器
1.首先新建立一个java web项目的工程.使用的是myeclipe开发软件 图片的下载路径是http://192.168.1.103:8080/lihuoming_23/3.png 当前手机和电脑 ...
- 黎活明8天快速掌握android视频教程--20_采用ContentProvider对外共享数据
1.内容提供者是让当前的app的数据可以让其他应用访问,其他应该可以通过内容提供者访问当前app的数据库 contentProvider的主要目的是提供一个开发的接口,让其他的应该能够访问当前应用的数 ...
- 黎活明8天快速掌握android视频教程--19_采用ListView实现数据列表显示
1.首先整个程序也是采用mvc的框架 DbOpenHelper 类 package dB; import android.content.Context; import android.databas ...
- 黎活明8天快速掌握android视频教程--16_采用SharedPreferences保存用户偏好设置参数
SharedPreferences保存的数据是xml格式,也是存在数据保存的下面四种权限: 我们来看看 我们来看看具体的业务操作类: /** * 文件名:SharedPrecences.java * ...
随机推荐
- [Objective-c] 002_对象 类 变量 方法
接触过Java的对面向对象应该是熟悉不过了, Objective-C也是面向对象的. 类 对象 变量 方法 Objective-c 中如何定义一个类? .h文件 #import <Foundat ...
- (九)显示交易记录 &解决相对路径问题
UserServlet.java package com.aff.bookstore.servlet; import java.io.IOException; import javax.servlet ...
- 设计带构造函数的Dog类 代码参考
#include <iostream> #include <string> using namespace std; class Dog { private: string n ...
- NodeJS——在Sublime中配置NodeJS执行环境
这种方式比在DOS窗中直接执行更加高效!!! nodejs 1.运行Sublime,菜单上找到Tools ---> Build System ---> new Build System 2 ...
- ZooKeeper未授权漏洞
ZooKeeper是一个分布式的,开放源码的分布式应用程序协调服务,是Google的Chubby一个开源的实现,它是集群的管理者,监视着集群中各个节点的状态根据节点提交的反馈进行下一步合理操作.最终, ...
- 50个SQL语句(MySQL版) 问题三
--------------------------表结构-------------------------- student(StuId,StuName,StuAge,StuSex) 学生表 tea ...
- Java面向对象中this关键字详解 意义+实例讲解【hot】
this关键字 >>>便于理解简单的定义 this关键字可以简单的理解为,谁调用this所在的方法,this就是谁. 类的构造函数与getter.setter方法常用到this关键字 ...
- Java实现 LeetCode 349 两个数组的交集
349. 两个数组的交集 给定两个数组,编写一个函数来计算它们的交集. 示例 1: 输入: nums1 = [1,2,2,1], nums2 = [2,2] 输出: [2] 示例 2: 输入: num ...
- java中ReentrantLock类的详细介绍(详解)
博主如果看到请联系小白,小白记不清地址了 简介 ReentrantLock是一个可重入且独占式的锁,它具有与使用synchronized监视器锁相同的基本行为和语义,但与synchronized关键字 ...
- Java实现LeetCode_0014_LongestCommonPrefix
package javaLeetCode.primary; /** * Write a function to find the longest common prefix string amongs ...