一.前言
1.1 Android的電話本是sdk通過contentProvider封裝好的。我們只要通過sdk提供的Uri和字段來對其進行增、刪、改、查。
1.2 權限
- <uses-permission android:name="android.permission.WRITE_CONTACTS"></uses-permission>
- <uses-permission android:name="android.permission.READ_CONTACTS"></uses-permission>
1.3 ContentProvider其實自己管理一個Sqlist數據庫文件( .db)。這個文件的路徑為/data/data/com.android.providers.contacts/databases/contacts2.db。如圖:
1.4 在模擬器中的電話本裡創建幾個聯系人,打開1.2中的.db文件,可以用數據庫查看工具SQLite Expert Professional打開看下,如圖:
從上圖,可以看出左邊是.db文件的表,點開各表後可以看出主要的表有raw_contacts,contacts,data
二. api
2.1 從api中可以看到android.provider.ContactsContract是sdk2.0的類庫,從api和上面的圖都可以看出關於電話本主要信息都存在
ContactsContract.Data,
ContactsContract.RawContacts,
ContactsContract.Contacts
三張表裡
2.1.1 ContactsContract.Data, ContactsContract.RawContacts, ContactsContract.Contacts 三張表的關聯,
ContactsContract.RawContacts表裡包含ContactsContract.Contacts的contact_id;ContactsContract.Data表裡有ContactsContract.RawContacts的raw_contact_id,和ContactsContract.Contacts的contact_id
2.2 各數據對應的類庫
2.2.1 Email 對應ContactsContract.CommonDataKinds.Email
Type Alias Data column StringADDRESS
DATA1
Email address itself. intTYPE
DATA2
Allowed values are:String
TYPE_CUSTOM
. Put the actual type inLABEL
.TYPE_HOME
TYPE_WORK
TYPE_OTHER
TYPE_MOBILE
LABEL
DATA3
Email數據有三個字段存儲:ADDRESS為Email值;TYPE為類型,當為自定義(TYPE_CUSTOM)時,LABEL字段要寫入用戶自定義的類型;2.2.2 IM 對應 ContactsContract.CommonDataKinds.Im
Type Alias Data column StringDATA
DATA1
intTYPE
DATA2
Allowed values are:String
TYPE_CUSTOM
. Put the actual type inLABEL
.TYPE_HOME
TYPE_WORK
TYPE_OTHER
LABEL
DATA3
StringPROTOCOL
DATA5
Allowed values:
String
PROTOCOL_CUSTOM
. Also provide the actual protocol name asCUSTOM_PROTOCOL
.PROTOCOL_AIM
PROTOCOL_MSN
PROTOCOL_YAHOO
PROTOCOL_SKYPE
PROTOCOL_QQ
PROTOCOL_GOOGLE_TALK
PROTOCOL_ICQ
PROTOCOL_JABBER
PROTOCOL_NETMEETING
CUSTOM_PROTOCOL
DATA6
Im有5個字段2.2.3 Phone 對應 ContactsContract.CommonDataKinds.Phone
Type Alias Data column StringNUMBER
DATA1
intTYPE
DATA2
Allowed values are:String
TYPE_CUSTOM
. Put the actual type inLABEL
.TYPE_HOME
TYPE_MOBILE
TYPE_WORK
TYPE_FAX_WORK
TYPE_FAX_HOME
TYPE_PAGER
TYPE_OTHER
TYPE_CALLBACK
TYPE_CAR
TYPE_COMPANY_MAIN
TYPE_ISDN
TYPE_MAIN
TYPE_OTHER_FAX
TYPE_RADIO
TYPE_TELEX
TYPE_TTY_TDD
TYPE_WORK_MOBILE
TYPE_WORK_PAGER
TYPE_ASSISTANT
TYPE_MMS
LABEL
DATA3
2.2.4 Postal address 通訊地址 對應 ContactsContract.CommonDataKinds.StructuredPostal
Type Alias Data column StringFORMATTED_ADDRESS
DATA1
intTYPE
DATA2
Allowed values are:String
TYPE_CUSTOM
. Put the actual type inLABEL
.TYPE_HOME
TYPE_WORK
TYPE_OTHER
LABEL
DATA3
StringSTREET
DATA4
StringPOBOX
DATA5
Post Office Box number StringNEIGHBORHOOD
DATA6
StringCITY
DATA7
StringREGION
DATA8
StringPOSTCODE
DATA9
StringCOUNTRY
DATA10
最長用的有 TYPE:類型;STREET:街道;CITY:市;REGION:省;POSTCODE:郵政編碼;
三.代碼
3.1在api裡 ContactsContract.Data 和ContactsContract.RawContacts文檔裡有關於insert ,update, delete,query的代碼,顯示出操作各自的表的代碼。可以根據這些來完成我們自己的邏輯。
3.2 查詢 (查出全部聯系人,在只顯示姓名)需要如圖:
需求分析:由於列表中只需要姓名,所以在查詢表時就只查詢出姓名信息就好。當點擊某個聯系人再查出Email,phone等詳細信息。
3.2.1 查詢聯系人總表代碼:
說明:由於姓名可以直接在ContactsContract.Contacts表裡查到,所以如下
3.2.2 根據contactId查詢聯系人詳細
- public static final String[] PROJECTION_CONTACTS = { Contacts._ID,
- Contacts.PHOTO_ID, Contacts.IN_VISIBLE_GROUP,
- Contacts.HAS_PHONE_NUMBER, Contacts.DISPLAY_NAME,
- Contacts.CUSTOM_RINGTONE };
- /**
- * wu0wu
- *
- * 功能:查詢所有聯系人PROJECTION_CONTACTS信息
- *
- * */
- public static void _getContacts(ContentResolver cr) {
- Cursor cursorContact = null;
- try {
- cursorContact = cr.query(ContactsContract.Contacts.CONTENT_URI,
- PROJECTION_CONTACTS, Contacts.IN_VISIBLE_GROUP + "=1",
- null, null);
- Log.e("wu0wu", "聯系人個數=" + cursorContact.getCount());
- int[] indexs = getColumnIndexs(PROJECTION_CONTACTS, cursorContact);
- while (cursorContact.moveToNext()) {
- Log.e("wu0wu", "------------------------------------");
- for (int i = 0; i < PROJECTION_CONTACTS.length; i++) {
- String value = cursorContact.getString(indexs[i]);
- Log.e("wu0wu", PROJECTION_CONTACTS[i] + "=" + value);
- }
- }
- } catch (Exception e) {
- Log.e("wu0wu", e.toString());
- } finally {
- if (cursorContact != null) {
- cursorContact.close();
- }
- }
- }
- private static int[] getColumnIndexs(String[] projections, Cursor c) {
- int[] ret = new int[projections.length];
- for (int i = 0; i < projections.length; i++) {
- ret[i] = c.getColumnIndex(projections[i]);
- }
- return ret;
- }