下面是ArticlesAdapter类的实现,它实现在src/shy/luo/ArticlesAdapter.java文件中:
- package shy.luo.article;
-
- import java.util.LinkedList;
-
- import shy.luo.providers.articles.Articles;
- import android.content.ContentResolver;
- import android.content.ContentUris;
- import android.content.ContentValues;
- import android.content.Context;
- import android.content.IContentProvider;
- import android.database.Cursor;
- import android.net.Uri;
- import android.os.Bundle;
- import android.os.RemoteException;
- import android.util.Log;
-
-
- public class ArticlesAdapter {
- private static final String LOG_TAG = "shy.luo.article.ArticlesAdapter";
-
- private ContentResolver resolver = null;
-
- public ArticlesAdapter(Context context) {
- resolver = context.getContentResolver();
- }
-
- public long insertArticle(Article article) {
- ContentValues values = new ContentValues();
- values.put(Articles.TITLE, article.getTitle());
- values.put(Articles.ABSTRACT, article.getAbstract());
- values.put(Articles.URL, article.getUrl());
-
- Uri uri = resolver.insert(Articles.CONTENT_URI, values);
- String itemId = uri.getPathSegments().get(1);
-
- return Integer.valueOf(itemId).longValue();
- }
-
- public boolean updateArticle(Article article) {
- Uri uri = ContentUris.withAppendedId(Articles.CONTENT_URI, article.getId());
-
- ContentValues values = new ContentValues();
- values.put(Articles.TITLE, article.getTitle());
- values.put(Articles.ABSTRACT, article.getAbstract());
- values.put(Articles.URL, article.getUrl());
-
- int count = resolver.update(uri, values, null, null);
-
- return count > 0;
- }
-
- public boolean removeArticle(int id) {
- Uri uri = ContentUris.withAppendedId(Articles.CONTENT_URI, id);
-
- int count = resolver.delete(uri, null, null);
-
- return count > 0;
- }
-
- public LinkedList<Article> getAllArticles() {
- LinkedList<Article> articles = new LinkedList<Article>();
-
- String[] projection = new String[] {
- Articles.ID,
- Articles.TITLE,
- Articles.ABSTRACT,
- Articles.URL
- };
-
- Cursor cursor = resolver.query(Articles.CONTENT_URI, projection, null, null, Articles.DEFAULT_SORT_ORDER);
- if (cursor.moveToFirst()) {
- do {
- int id = cursor.getInt(0);
- String title = cursor.getString(1);
- String abs = cursor.getString(2);
- String url = cursor.getString(3);
-
- Article article = new Article(id, title, abs, url);
- articles.add(article);
- } while(cursor.moveToNext());
- }
-
- return articles;
- }
-
- public int getArticleCount() {
- int count = 0;
-
- try {
- IContentProvider provider = resolver.acquireProvider(Articles.CONTENT_URI);
- Bundle bundle = provider.call(Articles.METHOD_GET_ITEM_COUNT, null, null);
- count = bundle.getInt(Articles.KEY_ITEM_COUNT, 0);
- } catch(RemoteException e) {
- e.printStackTrace();
- }
-
- return count;
- }
-
- public Article getArticleById(int id) {
- Uri uri = ContentUris.withAppendedId(Articles.CONTENT_URI, id);
-
- String[] projection = new String[] {
- Articles.ID,
- Articles.TITLE,
- Articles.ABSTRACT,
- Articles.URL
- };
-
- Cursor cursor = resolver.query(uri, projection, null, null, Articles.DEFAULT_SORT_ORDER);
-
- Log.i(LOG_TAG, "cursor.moveToFirst");
-
- if (!cursor.moveToFirst()) {
- return null;
- }
-
- String title = cursor.getString(1);
- String abs = cursor.getString(2);
- String url = cursor.getString(3);
-
- return new Article(id, title, abs, url);
- }
-
- public Article getArticleByPos(int pos) {
- Uri uri = ContentUris.withAppendedId(Articles.CONTENT_POS_URI, pos);
-
- String[] projection = new String[] {
- Articles.ID,
- Articles.TITLE,
- Articles.ABSTRACT,
- Articles.URL
- };
-
- Cursor cursor = resolver.query(uri, projection, null, null, Articles.DEFAULT_SORT_ORDER);
- if (!cursor.moveToFirst()) {
- return null;
- }
-
- int id = cursor.getInt(0);
- String title = cursor.getString(1);
- String abs = cursor.getString(2);
- String url = cursor.getString(3);
-
- return new Article(id, title, abs, url);
- }
- }
这个类首先在构造函数里面获得应用程序上下文的ContentResolver接口,然后通过就可以通过这个接口来访问ArticlesProvider中的文章信息了。成员函数insertArticle、updateArticle和removeArticle分别用来新增、更新和删除一个文章信息条目;成员函数getAllArticlese用来获取所有的文章信息;成员函数getArticleById和getArticleByPos分别根据文章的ID和位置来获得具体文章信息条目;成员函数getArticleCount直接使用ContentProvider的未公开接口call来获得文章信息条目的数量,注意,这个函数要源代码环境下编译才能通过。
下面是程序主界面MainActivity类的实现,它实现在src/shy/luo/article/MainActivity.java文件中:
- package shy.luo.article;
-
- import shy.luo.providers.articles.Articles;
- import android.app.Activity;
- import android.content.Context;
- import android.content.Intent;
- import android.database.ContentObserver;
- import android.os.Bundle;
- import android.os.Handler;
- import android.util.Log;
- import android.view.LayoutInflater;
- import android.view.View;
- import android.view.ViewGroup;
- import android.widget.AdapterView;
- import android.widget.BaseAdapter;
- import android.widget.Button;
- import android.widget.ListView;
- import android.widget.TextView;
-
- public class MainActivity extends Activity implements View.OnClickListener, AdapterView.OnItemClickListener {
- private final static String LOG_TAG = "shy.luo.article.MainActivity";
-
- private final static int ADD_ARTICAL_ACTIVITY = 1;
- private final static int EDIT_ARTICAL_ACTIVITY = 2;
-
- private ArticlesAdapter aa = null;
- private ArticleAdapter adapter = null;
- private ArticleObserver observer = null;
-
- private ListView articleList = null;
- private Button addButton = null;
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.main);
-
- aa = new ArticlesAdapter(this);
-
- articleList = (ListView)findViewById(R.id.listview_article);
- adapter = new ArticleAdapter(this);
- articleList.setAdapter(adapter);
- articleList.setOnItemClickListener(this);
-
- observer = new ArticleObserver(new Handler());
- getContentResolver().registerContentObserver(Articles.CONTENT_URI, true, observer);
-
- addButton = (Button)findViewById(R.id.button_add);
- addButton.setOnClickListener(this);
-
- Log.i(LOG_TAG, "MainActivity Created");
- }
-
- @Override
- public void onDestroy() {
- super.onDestroy();
- getContentResolver().unregisterContentObserver(observer);
- }
-
- @Override
- public void onClick(View v) {
- if(v.equals(addButton)) {
- Intent intent = new Intent(this, ArticleActivity.class);
- startActivityForResult(intent, ADD_ARTICAL_ACTIVITY);
- }
- }
-
- @Override
- public void onItemClick(AdapterView<?> parent, View view, int pos, long id) {
- Intent intent = new Intent(this, ArticleActivity.class);
-
- Article article = aa.getArticleByPos(pos);
- intent.putExtra(Articles.ID, article.getId());
- intent.putExtra(Articles.TITLE, article.getTitle());
- intent.putExtra(Articles.ABSTRACT, article.getAbstract());
- intent.putExtra(Articles.URL, article.getUrl());
-
- startActivityForResult(intent, EDIT_ARTICAL_ACTIVITY);
- }
-
- @Override
- public void onActivityResult(int requestCode,int resultCode, Intent data) {
- super.onActivityResult(requestCode, resultCode, data);
-
- switch(requestCode) {
- case ADD_ARTICAL_ACTIVITY: {
- if(resultCode == Activity.RESULT_OK) {
- String title = data.getStringExtra(Articles.TITLE);
- String abs = data.getStringExtra(Articles.ABSTRACT);
- String url = data.getStringExtra(Articles.URL);
-
- Article article = new Article(-1, title, abs, url);
- aa.insertArticle(article);
- }
-
- break;
- }
-
- case EDIT_ARTICAL_ACTIVITY: {
- if(resultCode == Activity.RESULT_OK) {
- int action = data.getIntExtra(ArticleActivity.EDIT_ARTICLE_ACTION, -1);
- if(action == ArticleActivity.MODIFY_ARTICLE) {
- int id = data.getIntExtra(Articles.ID, -1);
- String title = data.getStringExtra(Articles.TITLE);
- String abs = data.getStringExtra(Articles.ABSTRACT);
- String url = data.getStringExtra(Articles.URL);
-
- Article article = new Article(id, title, abs, url);
- aa.updateArticle(article);
- } else if(action == ArticleActivity.DELETE_ARTICLE) {
- int id = data.getIntExtra(Articles.ID, -1);
-
- aa.removeArticle(id);
- }
-
- }
-
- break;
- }
- }
- }
-
- private class ArticleObserver extends ContentObserver {
- public ArticleObserver(Handler handler) {
- super(handler);
- }
-
- @Override
- public void onChange (boolean selfChange) {
- adapter.notifyDataSetChanged();
- }
- }
-
- private class ArticleAdapter extends BaseAdapter {
- private LayoutInflater inflater;
-
- public ArticleAdapter(Context context){
- inflater = LayoutInflater.from(context);
- }
-
- @Override
- public int getCount() {
- return aa.getArticleCount();
- }
-
- @Override
- public Object getItem(int pos) {
- return aa.getArticleByPos(pos);
- }
-
- @Override
- public long getItemId(int pos) {
- return aa.getArticleByPos(pos).getId();
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- Article article = (Article)getItem(position);
-
- if (convertView == null) {
- convertView = inflater.inflate(R.layout.item, null);
- }
-
- TextView titleView = (TextView)convertView.findViewById(R.id.textview_article_title);
- titleView.setText("Title: " + article.getTitle());
-
- TextView abstractView = (TextView)convertView.findViewById(R.id.textview_article_abstract);
- abstractView.setText("Abstract: " + article.getAbstract());
-
- TextView urlView = (TextView)convertView.findViewById(R.id.textview_article_url);
- urlView.setText("URL: " + article.getUrl());
-
- return convertView;
- }
- }
- }
在应用程序的主界面中,我们使用一个ListView来显示文章信息条目,这个ListView的数据源由ArticleAdapter类来提供,而ArticleAdapter类又是通过ArticlesAdapter类来获得ArticlesProvider中的文章信息的。在MainActivity的onCreate函数,我们还通过应用程序上下文的ContentResolver接口来注册了一个ArticleObserver对象来监控ArticlesProvider中的文章信息。一旦ArticlesProvider中的文章信息发生变化,就会通过ArticleAdapter类来实时更新ListView中的文章信息。
下面是ArticleActivity类的实现,它实现在src/shy/luo/article/ArticleActivity.java文件中:
- package shy.luo.article;
-
- import shy.luo.providers.articles.Articles;
- import android.app.Activity;
- import android.content.Intent;
- import android.os.Bundle;
- import android.util.Log;
- import android.view.View;
- import android.widget.Button;
- import android.widget.EditText;
-
- public class ArticleActivity extends Activity implements View.OnClickListener {
- private final static String LOG_TAG = "shy.luo.article.ArticleActivity";
-
- public final static String EDIT_ARTICLE_ACTION = "EDIT_ARTICLE_ACTION";
- public final static int MODIFY_ARTICLE = 1;
- public final static int DELETE_ARTICLE = 2;
-
- private int articleId = -1;
-
- private EditText titleEdit = null;
- private EditText abstractEdit = null;
- private EditText urlEdit = null;
-
- private Button addButton = null;
- private Button modifyButton = null;
- private Button deleteButton = null;
- private Button cancelButton = null;
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.article);
-
- titleEdit = (EditText)findViewById(R.id.edit_article_title);
- abstractEdit = (EditText)findViewById(R.id.edit_article_abstract);
- urlEdit = (EditText)findViewById(R.id.edit_article_url);
-
- addButton = (Button)findViewById(R.id.button_add_article);
- addButton.setOnClickListener(this);
-
- modifyButton = (Button)findViewById(R.id.button_modify);
- modifyButton.setOnClickListener(this);
-
- deleteButton = (Button)findViewById(R.id.button_delete);
- deleteButton.setOnClickListener(this);
-
- cancelButton = (Button)findViewById(R.id.button_cancel);
- cancelButton.setOnClickListener(this);
-
- Intent intent = getIntent();
- articleId = intent.getIntExtra(Articles.ID, -1);
-
- if(articleId != -1) {
- String title = intent.getStringExtra(Articles.TITLE);
- titleEdit.setText(title);
-
- String abs = intent.getStringExtra(Articles.ABSTRACT);
- abstractEdit.setText(abs);
-
- String url = intent.getStringExtra(Articles.URL);
- urlEdit.setText(url);
-
- addButton.setVisibility(View.GONE);
- } else {
-
- modifyButton.setVisibility(View.GONE);
- deleteButton.setVisibility(View.GONE);
- }
-
- Log.i(LOG_TAG, "ArticleActivity Created");
- }
-
- @Override
- public void onClick(View v) {
- if(v.equals(addButton)) {
- String title = titleEdit.getText().toString();
- String abs = abstractEdit.getText().toString();
- String url = urlEdit.getText().toString();
-
- Intent result = new Intent();
- result.putExtra(Articles.TITLE, title);
- result.putExtra(Articles.ABSTRACT, abs);
- result.putExtra(Articles.URL, url);
-
- setResult(Activity.RESULT_OK, result);
- finish();
- } else if(v.equals(modifyButton)){
- String title = titleEdit.getText().toString();
- String abs = abstractEdit.getText().toString();
- String url = urlEdit.getText().toString();
-
- Intent result = new Intent();
- result.putExtra(Articles.ID, articleId);
- result.putExtra(Articles.TITLE, title);
- result.putExtra(Articles.ABSTRACT, abs);
- result.putExtra(Articles.URL, url);
- result.putExtra(EDIT_ARTICLE_ACTION, MODIFY_ARTICLE);
-
- setResult(Activity.RESULT_OK, result);
- finish();
- } else if(v.equals(deleteButton)) {
- Intent result = new Intent();
- result.putExtra(Articles.ID, articleId);
- result.putExtra(EDIT_ARTICLE_ACTION, DELETE_ARTICLE);
-
- setResult(Activity.RESULT_OK, result);
- finish();
- } else if(v.equals(cancelButton)) {
- setResult(Activity.RESULT_CANCELED, null);
- finish();
-
- }
- }
- }
在ArticleActivity窗口中,我们可以执行新增、更新和删除文章信息的操作。如果启动ArticleActivity时,没有把文章ID传进来,就说明要执行操作是新增文章信息;如果启动ArticleActivity时,把文章ID和其它信自都传进来了,就说明要执行的操作是更新或者删除文章,根据用户在界面点击的是更新按钮还是删除按钮来确定。