因为在Android中,存储系统联系人姓名和电话是存在与不同的ContentProvider中的,具体如何查找,可以从Android的源代码中查看,在android.providers包中列出了所有系统已经封装好的ContentProvider,譬如我们要查看联系人相关的,就去ContactsContract当中去寻找相关信息,要查看短信相关的,就去Telephony中寻找相关信息。

  

查找系统联系人

MainActivity.java

package cn.lixyz.readcontacts;

import java.util.ArrayList;
import java.util.List; import android.app.Activity;
import android.content.ContentResolver;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract;
import android.util.Log;
import android.view.View;
import android.widget.Button; public class MainActivity extends Activity { private Button button;
private static final Uri CONTACTS_URI = ContactsContract.Contacts.CONTENT_URI;
private static final Uri PHONE_URI = ContactsContract.CommonDataKinds.Phone.CONTENT_URI; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); button = (Button) findViewById(R.id.button);
button.setOnClickListener(new MyOnClickListener()); } class MyOnClickListener implements View.OnClickListener { @Override
public void onClick(View v) {
if (v.getId() == R.id.button) {
ContentResolver cr = getContentResolver();
Cursor cursor = cr.query(CONTACTS_URI, new String[] { "_id", "display_name" }, null, null, null);
if (cursor != null) {
List<String> phoneList = new ArrayList<String>();
cursor.moveToFirst();
do {
String name = cursor.getString(cursor.getColumnIndex("display_name"));
String id = cursor.getString(cursor.getColumnIndex("_id")); Cursor c = cr.query(PHONE_URI, new String[] { "data1" }, "name_raw_contact_id=?",
new String[] { id }, null);
c.moveToFirst();
do {
Log.d("TTTT", "姓名:" + name + ",电话=" + c.getString(c.getColumnIndex("data1")));
} while (c.moveToNext());
} while (cursor.moveToNext());
}
cursor.close(); } } }
}

activity_main.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="cn.lixyz.readsmstest.MainActivity" > <Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="点我读取联系人" /> </LinearLayout>

在AndroidManifest.xml文件中添加读取联系人的权限

<uses-permission android:name="android.permission.READ_CONTACTS"/>

  运行结果:

  读取短信息:

MainActivity.java

package cn.lixyz.readsmstest;

import java.text.SimpleDateFormat;
import java.util.Date; import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.ContentResolver;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.Telephony.Sms;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button; @SuppressLint("NewApi")
public class MainActivity extends Activity { private Button button; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
button = (Button) findViewById(R.id.button);
button.setOnClickListener(new OnClickListener() { @Override
public void onClick(View v) {
ContentResolver cr = getContentResolver();
Uri uri = Sms.CONTENT_URI;
Cursor cursor = cr.query(uri, new String[] { "date", "body" }, null, null, null);
if (cursor != null) {
while (cursor.moveToNext()) {
String date = cursor.getString(cursor.getColumnIndex("date"));
String body = cursor.getString(cursor.getColumnIndex("body")); Date d = new Date(Long.valueOf(date));
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String dateStr = dateFormat.format(d); Log.d("TTTT", "时间:" + dateStr + ",内容:" + body); }
}
cursor.close();
}
});
}
}

activity_main.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="cn.lixyz.readsmstest.MainActivity" > <Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="点我读取短信" /> </LinearLayout>

在AndroidManifest.xml文件中添加读取短信的权限

<uses-permission android:name="android.permission.READ_SMS"/>

插入联系人:

MainActivity.java

package cn.lixyz.writecontacts;

import android.app.Activity;
import android.content.ContentUris;
import android.content.ContentValues;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract;
import android.provider.ContactsContract.CommonDataKinds.Phone;
import android.provider.ContactsContract.CommonDataKinds.StructuredName;
import android.provider.ContactsContract.Data;
import android.provider.ContactsContract.RawContacts;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button; public class MainActivity extends Activity { private Button button;
public static final Uri CONTACTS_URI = ContactsContract.Contacts.CONTENT_URI;
public static final Uri Phone_URI = ContactsContract.CommonDataKinds.Phone.CONTENT_URI; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); button = (Button) findViewById(R.id.button); button.setOnClickListener(new OnClickListener() { @Override
public void onClick(View v) { ContentValues values = new ContentValues();
// 首先向RawContacts.CONTENT_URI执行一个空值插入(raw_contacts 表),
// 为了获取生成的联系人 ID
Uri rawContactUri = getContentResolver().insert(RawContacts.CONTENT_URI, values);
// 然后获取系统返回的rawContactId , 就是新加入的这个联系人的 ID
long rawContactId = ContentUris.parseId(rawContactUri);
/*
* Andorid 中,将联系人的姓名、电话、分别存放在 data 表的同一个字段的两条记录当中 因此要 Insert 两次
*/
// 往data表入姓名数据
values.clear();
// raw_contacts_id 字段,是 raw_contacts表id 的外键,用于说明此记录属于哪一个联系人
values.put(Data.RAW_CONTACT_ID, rawContactId);
// mimitype_id 字段,用于描述此数据的类型,电话号码?Email?....
values.put(Data.MIMETYPE, StructuredName.CONTENT_ITEM_TYPE); // 注意查看第二个参数的常量值
values.put(StructuredName.GIVEN_NAME, "肆肆肆"); // 这个名字真好听
getContentResolver().insert(android.provider.ContactsContract.Data.CONTENT_URI, values);
// 往data表入电话数据
values.clear();
values.put(Data.RAW_CONTACT_ID, rawContactId); values.put(Data.MIMETYPE, Phone.CONTENT_ITEM_TYPE);
values.put(Phone.NUMBER, "444444444");
values.put(Phone.TYPE, Phone.TYPE_MOBILE);
getContentResolver().insert(android.provider.ContactsContract.Data.CONTENT_URI, values);
}
});
}
}

activity_main.xml

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="cn.lixyz.writecontacts.MainActivity" > <Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" /> </RelativeLayout>

在AndroidManifest.xml中添加写入联系人的权限

<uses-permission android:name="android.permission.WRITE_CONTACTS"/>

Android笔记(五十五) Android四大组件之一——ContentProvider,使用系统提供的ContentProvider的更多相关文章

  1. Android笔记(十五) Android中的基本组件——单选框和复选框

    单选框和多选框通常用来在设置用户个人资料时候,选择性别.爱好等,不需要用户直接输入,直接在备选选项中选择,简单方便. 直接看代码: <?xml version="1.0" e ...

  2. Android笔记(七十五) Android中的图片压缩

    这几天在做图记的时候遇第一次遇到了OOM,好激动~~ 追究原因,是因为在ListView中加载的图片太大造成的,因为我使用的都是手机相机直接拍摄的照片,图片都比较大,所以在加载的时候会出现内存溢出,那 ...

  3. Android笔记(六十五) android中的动画——属性动画(propertyanimation)

    补间动画只能定义起始和结束两个帧在“透明度”.“旋转”.“倾斜”.“位移”4个方面的变化,逐帧动画也只能是播放多个图片,无法满足我们日常复杂的动画需求,所以谷歌在3.0开始,推出了属性动画(prope ...

  4. Android笔记二十四.Android基于回调的事件处理机制

        假设说事件监听机制是一种托付式的事件处理,那么回调机制则与之相反,对于基于回调的事件处理模型来说,事件源和事件监听器是统一的,或者说事件监听器全然消失了,当用户在GUI控件上激发某个事件时,控 ...

  5. Android笔记(六十六) android中的动画——XML文件定义属性动画

    除了直接在java代码中定义动画之外,还可以使用xml文件定义动画,以便重用. 如果想要使用XML来编写动画,首先要在res目录下面新建一个animator文件夹,所有属性动画的XML文件都应该存放在 ...

  6. Android笔记(十) Android中的布局——表格布局

    TableLayout运行我们使用表格的方式来排列控件,它的本质依然是线性布局.表格布局采用行.列的形式来管理控件,TableLayout并不需要明确的声明包含多少行多少列,而是通过添加TableRo ...

  7. Android笔记(六十四) android中的动画——补间动画(tweened animation)

    补间动画就是只需要定义动画开始和结束的位置,动画中间的变化由系统去补齐. 补间动画由一下四种方式: 1.AplhaAnimation——透明度动画效果 2.ScaleAnimation ——缩放动画效 ...

  8. Nodejs学习笔记(十五)--- Node.js + Koa2 构建网站简单示例

    目录 前言 搭建项目及其它准备工作 创建数据库 创建Koa2项目 安装项目其它需要包 清除冗余文件并重新规划项目目录 配置文件 规划示例路由,并新建相关文件 实现数据访问和业务逻辑相关方法 编写mys ...

  9. [转]Nodejs学习笔记(十五)--- Node.js + Koa2 构建网站简单示例

    本文转自:https://www.cnblogs.com/zhongweiv/p/nodejs_koa2_webapp.html 目录 前言 搭建项目及其它准备工作 创建数据库 创建Koa2项目 安装 ...

  10. Nodejs学习笔记(十五)—Node.js + Koa2 构建网站简单示例

    前言 前面一有写到一篇Node.js+Express构建网站简单示例:http://www.cnblogs.com/zhongweiv/p/nodejs_express_webapp.html 这篇还 ...

随机推荐

  1. 有无关键字new的区别

    function Person(firstName, lastName) { this.firstName = firstName; this.lastName = lastName; } const ...

  2. [c++] Sequence Containers

    写在前面 C++ Standard Library For efficiency reasons, STL is not object-oriented: Makes little use of in ...

  3. MongoDB学习笔记二:使用Docker安装MongoDB

    目录 Docker安装MongoDB Docker给MongoDB设置用户密码 NoSQL Manager for MongoDB连接 为admin赋权限 上一个笔记介绍了Windows下安装Mong ...

  4. [LeetCode] 314. Binary Tree Vertical Order Traversal 二叉树的垂直遍历

    Given a binary tree, return the vertical order traversal of its nodes' values. (ie, from top to bott ...

  5. Office Online Server2016搭建与部署(在线编辑)

    至少需要两台服务器,一台域控制器,一台部署Office Online Server https://docs.microsoft.com/zh-cn/officeonlineserver/office ...

  6. 【Python学习之四】集合类型

    环境 虚拟机:VMware 10 Linux版本:CentOS-6.5-x86_64 客户端:Xshell4 FTP:Xftp4 python3.6 一.字符串:字符串实际上就是字符的数组1.切片是指 ...

  7. 【视频开发】【Live555】摄像头采集,264编码,live555直播(0)

    参看 有关live555 1.首先需要修改live555,定义从 内存中直接获取source而不是从文件读取source的类. 自己实现的类命名为 H264FramedLiveSource   /* ...

  8. elasticsearch的数据写入流程及优化

    Elasticsearch 写入流程及优化 一. 集群分片设置:ES一旦创建好索引后,就无法调整分片的设置,而在ES中,一个分片实际上对应一个lucene 索引,而lucene索引的读写会占用很多的系 ...

  9. [gRPC] 在 .NET Core 中创建 gRPC 服务端和客户端

    gRPC 官网:https://grpc.io/ 1. 创建服务端 1.1 基于 ASP.NET Core Web 应用程序模板创建 gRPC Server 项目. 1.2 编译并运行 2. 创建客户 ...

  10. Hbase面试题

    hbase的特点 )hbase适合存储海量数据,是一个分布式的,基于列式存储的数据库,基于hadoop的hdfs存储,zookeeper进行管理. )hbase 适合存储半结构化或非结构化的数据,对于 ...