Android开发之ContentProvider结合LoaderManager加载数据

来源:互联网 发布:五子棋c语言代码 编辑:程序博客网 时间:2024/06/08 11:15

ContentProvider作为Android的四大存储方式之一,有着广泛的应用性,它暴露了数据地址,可以让其他应用访问数据,可以用于存储图片、通讯录等信息,这篇博文将详细介绍ContentProvider、URIMatcher,LoaderManager,cursorAdapter的方法使用与介绍。使用ContentProvider的时候一定要注意在manifest清单文件中像Acticity文件一样,声明其属性。如图所示

\

此外因为我们是用loadermanager来加载数据,MainAcitivity类要实现LoaderCallback接口。按照惯例我们还是看下谷歌官方文档对contentprovider的解释,ContentProvider管理一个结构化的数据集。它封装了数据,并提供定义数据安全机制。ContentProvider的标准接口实现多线程机制来连接数据,一般是用loaderManager异步加载数据。当你想要访问数据在一个ContentProvider,我们使用ContentResolver对象在应用程序的上下文中作为沟通方法。ContentResolver用来解析请求码返还数据。

我们先看看一下本次介绍的工程的目录结构

\

MainActivity的代码

view sourceprint?
01.package com.example.f14_contentprovider;
02. 
03.import java.util.ArrayList;
04.import java.util.HashMap;
05.import java.util.List;
06. 
07.import android.net.Uri;
08.import android.os.Bundle;
09.import android.app.Activity;
10.import android.app.LoaderManager;
11.import android.app.LoaderManager.LoaderCallbacks;
12.import android.content.ContentResolver;
13.import android.content.ContentValues;
14.import android.content.CursorLoader;
15.import android.content.Loader;
16.import android.database.Cursor;
17.import android.view.Menu;
18.import android.view.View;
19.import android.widget.Button;
20.import android.widget.ListView;
21.import android.widget.SimpleCursorAdapter;
22. 
23.public class MainActivity extends Activity implements LoaderCallbacks<Cursor> {
24.private Button button;
25.private ListView listView;
26.private LoaderManager loaderManager;
27.private SimpleCursorAdapter adapter;
28. 
29.@Override
30.protected void onCreate(Bundle savedInstanceState) {
31.super.onCreate(savedInstanceState);
32.setContentView(R.layout.activity_main);
33.button = (Button) this.findViewById(R.id.button1);
34.listView = (ListView) this.findViewById(R.id.listView1);
35.button.setOnClickListener(new View.OnClickListener() {
36. 
37.@Override
38.public void onClick(View v) {
39.// TODO Auto-generated method stub
40.ContentResolver resolver = getContentResolver();
41.Uri uri = Uri
42..parse("content://com.example.f14_contentprovider.PersonContentProvider/person");
43.ContentValues values = new ContentValues();
44.values.put("name""jack");
45.values.put("address""hangzhou");
46.resolver.insert(uri, values);
47.loaderManager.restartLoader(1001null, MainActivity.this);
48.}
49.});
50.loaderManager = getLoaderManager();
51.loaderManager.initLoader(1001nullthis);
52.}
53. 
54. 
55. 
56.@Override
57.public Loader<Cursor> onCreateLoader(int id, Bundle args) {
58.// TODO Auto-generated method stub
59./**
60.* CursorLoader该类用于加载程序,查询ContentResolver并返回一个指针。这个类实现了装载机协议查询游标的标准方法,
61.* 基于AsyncTaskLoader执行游标查询在一个后台线程,以便它不会阻止应用程序的UI。
62.*/
63.CursorLoader loader = new CursorLoader(this);
64.Uri uri = Uri
65..parse("content://com.example.f14_contentprovider.PersonContentProvider/person");
66.loader.setUri(uri);
67.loader.setProjection(new String[] { "name""address" });
68.return loader;
69.}
70. 
71.@SuppressWarnings("deprecation")
72.@Override
73.public void onLoadFinished(Loader<Cursor> arg0, Cursor arg1) {
74.// TODO Auto-generated method stub
75.List<HashMap<String, String>> list = new ArrayList<HashMap<String, String>>();
76.// 加载数据
77.while (arg1.moveToNext()) {
78.HashMap<String, String> map = new HashMap<String, String>();
79.map.put("name", arg1.getString(arg1.getColumnIndex("name")));
80.map.put("address", arg1.getString(arg1.getColumnIndex("address")));
81.list.add(map);
82.}
83.adapter = new SimpleCursorAdapter(this, R.layout.item, arg1,
84.new String[] { "name""address" }, new int[] { R.id.textView1,
85.R.id.textView2 });
86.listView.setAdapter(adapter);
87.adapter.notifyDataSetChanged();// 若内容发生变化 触发该方法
88.}
89. 
90.@Override
91.public void onLoaderReset(Loader<Cursor> arg0) {
92.// TODO Auto-generated method stub
93. 
94.}
95. 
96.}
如上所示,在MainAcitivity主方法中,大家可以看到第40-47行代码中,通过内容提供者contentProvider插入数据的时候,是通过contentResolver进行连接,通过其insert方法提供插入指定的数据表和数据完成操作。操作完成后还需要调用loadermanager的restart方法更新一次UI。
PersonContentProvider继承了ContentProvider的方法

view sourceprint?
001.package com.example.f14_contentprovider;
002. 
003.import android.content.ContentProvider;
004.import android.content.ContentResolver;
005.import android.content.ContentUris;
006.import android.content.ContentValues;
007.import android.content.UriMatcher;
008.import android.database.Cursor;
009.import android.database.sqlite.SQLiteDatabase;
010.import android.net.Uri;
011. 
012.//要在manifest文件中注册provider
013.public class PersonContentProvider extends ContentProvider {
014.private MyOpenHelper helper;
015.private static final UriMatcher matcher = new UriMatcher(
016.UriMatcher.NO_MATCH);// 专门用来匹配URI的类
017.private static final int PERSONS = 1;
018.private static final int PERSON = 2;
019.private ContentResolver resolver;
020.static {
021.matcher.addURI("com.example.f14_contentprovider.PersonContentProvider",
022."person", PERSONS);
023.matcher.addURI("com.example.f14_contentprovider.PersonContentProvider",
024."person/#", PERSON);
025.}
026. 
027.@Override
028.public int delete(Uri uri, String selection, String[] selectionArgs) {
029.// TODO Auto-generated method stub
030.return 0;
031.}
032. 
033.// 当您需要匹配一个URI,调用匹配(URI),用来来建立一个查询,返回类型,插入或删除一行。
034.@Override
035.public String getType(Uri arg0) {
036.// TODO Auto-generated method stub
037.int match = matcher.match(arg0);
038.switch (match) {
039.case PERSONS:
040.return "vnd.android.cursor.dir/person";
041.case PERSON:
042.return "vnd.android.cursor.item/person";
043.default:
044.return null;
045.}
046. 
047.}
048. 
049.@Override
050.public Uri insert(Uri uri, ContentValues values) {
051.// TODO Auto-generated method stub
052.SQLiteDatabase database = helper.getWritableDatabase();
053.long id = database.insert("person"null, values);
054.Uri rUri = ContentUris.withAppendedId(uri, id);
055.resolver.notifyChange(rUri, null);
056.return rUri;
057.}
058. 
059.@Override
060.public boolean onCreate() {
061.// TODO Auto-generated method stub
062.helper = new MyOpenHelper(getContext());
063.resolver = getContext().getContentResolver();
064.return true;
065.}
066. 
067.@Override
068.public Cursor query(Uri uri, String[] projection, String selection,
069.String[] selectionArgs, String sortOrder) {
070.// TODO Auto-generated method stub
071.Cursor cursor = null;
072.int flag = matcher.match(uri);
073.SQLiteDatabase database = helper.getReadableDatabase();
074.switch (flag) {
075.case PERSONS:
076.cursor=database.query("person"nullnullnull,nullnullnull);
077.break;
078.case PERSON:
079.long _id = ContentUris.parseId(uri);
080.String where_value = " _id  = " + _id;
081.if (selection != null && !selection.equals("")) {
082.where_value += selection;
083.}
084.cursor = database.query("person", projection, where_value,
085.selectionArgs, nullnull, sortOrder);
086.break;
087. 
088.default:
089.break;
090.}
091.cursor.setNotificationUri(resolver, uri);
092.return cursor;
093.}
094. 
095.@Override
096.public int update(Uri arg0, ContentValues arg1, String arg2, String[] arg3) {
097.// TODO Auto-generated method stub
098.return 0;
099.}
100. 
101.}

数据库创建类MyopenHelper

view sourceprint?
01.package com.example.f14_contentprovider;
02. 
03.import android.content.Context;
04.import android.database.sqlite.SQLiteDatabase;
05. 
06.import android.database.sqlite.SQLiteOpenHelper;
07. 
08.public class MyOpenHelper extends SQLiteOpenHelper {
09.private static final int DATABASE_VERSION = 1;
10.private static final String PERSON_TABLE_NAME = "person";
11. 
12.public MyOpenHelper(Context context) {
13.super(context, PERSON_TABLE_NAME, null, DATABASE_VERSION);
14.// TODO Auto-generated constructor stub
15.}
16. 
17.@Override
18.public void onCreate(SQLiteDatabase db) {
19.// TODO Auto-generated method stub
20.db.execSQL("create table "
21.+ PERSON_TABLE_NAME
22."(_id integer primary key autoincrement,name varchar(64),address varchar(64))");
23. 
24.}
25. 
26.@Override
27.public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
28.// TODO Auto-generated method stub
29. 
30.}
31. 
32.}
0 0
原创粉丝点击