Introduction To Android Contacts

Learn to work with the Android contacts database. Basic knowledge of accessing SQLite in Android along with using Cursors is expected. See the Android SQLite and Cursor Article for more information. Google changed the contacts database moving from 1.x to 2.0 versions of Android. This tutorial will be broken into 3 sections. First covering accessing contacts in Android 2.0. The second page will deal with accessing the contacts in Android 1.6 and before. Third we'll glue it all together with a class that abstracts specific classes for each version and a set of classes to manage the data from the contact records.

Create a new project called TestContacts in Eclipse setup for Android 2.0.

Android Contact API For 2.0

Granting Access

Before an application can query the contact records access must be granted through the AndroidManifest.xml file stored in the root of the project. Add the following uses-permission belows the uses-sdk statement. 

 

Querying The Android Contact Database

Retrieving Contact Details

Basic contact information stored in Contacts table with detailed information stored in individual tables for normalization. In Android 2.0 to query the base contact records the URI to query is stored in ContactsContract.Contacts.CONTENT_URI. 

package higherpass.TestContacts;import android.app.Activity;import android.content.ContentResolver;import android.database.Cursor;import android.os.Bundle;import android.provider.ContactsContract;public class TestContacts extends Activity {    /** Called when the activity is first created. */    @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);        ContentResolver cr = getContentResolver();        Cursor cur = cr.query(ContactsContract.Contacts.CONTENT_URI,                null, null, null, null);        if (cur.getCount() > 0) {    while (cur.moveToNext()) {        String id = cur.getString(                        cur.getColumnIndex(ContactsContract.Contacts._ID));String name = cur.getString(                        cur.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME)); if (Integer.parseInt(cur.getString(cur.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0) {     //Query phone here.  Covered next         }            } }    }}

This application starts off as any other Android application. First create a ContentResolver isntance in cr. Then use the ContentResolver instance to query the database and return a Cursor with the contacts list. The query is perofrmed against the URI stored in ContactsContract.Contacts.CONTENT_URI. Next check if the cursor contains records and if so loop through them. The record ID field is stored in the id variable. This will be used as a where parameter later. Also the display name field is stored in the string name. For more details about working with cursors see Android Cursors Tutorial.

Phone Numbers

Phone numbers are stored in their own table and need to be queried separately. To query the phone number table use the URI stored in the SDK variable ContactsContract.CommonDataKinds.Phone.CONTENT_URI. Use a WHERE conditional to get the phone numbers for the specified contact. 

            if (Integer.parseInt(cur.getString(                   cur.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0) {                Cursor pCur = cr.query(     ContactsContract.CommonDataKinds.Phone.CONTENT_URI,      null,      ContactsContract.CommonDataKinds.Phone.CONTACT_ID +" = ?",      new String[]{id}, null);         while (pCur.moveToNext()) {     // Do something with phones         }          pCur.close();     }

Perform a second query against the Android contacts SQLite database. The phone numbers are queried against the URI stored in ContactsContract.CommonDataKinds.Phone.CONTENT_URI. The contact ID is stored in the phone table as ContactsContract.CommonDataKinds.Phone.CONTACT_ID and the WHERE clause is used to limit the data returned.

Email Addresses

Querying email addresses is similar to phone numbers. A query must be performed to get email addresses from the database. Query the URI stored in ContactsContract.CommonDataKinds.Email.CONTENT_URI to query the email address table. 

Cursor emailCur = cr.query( ContactsContract.CommonDataKinds.Email.CONTENT_URI, null,ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?", new String[]{id}, null); while (emailCur.moveToNext()) {     // This would allow you get several email addresses            // if the email addresses were stored in an array    String email = emailCur.getString(                      emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));     String emailType = emailCur.getString(                      emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.TYPE));  }  emailCur.close();

As with the phone query the field names for the email table are also stored under ContactsContract.CommonDataKinds. The email query is performed on the URI in ContactsContract.CommonDataKinds.Email.CONTENT_URI and the WHERE clause has to match the ContactsContract.CommonDataKinds.Email.CONTACT_ID field. Since multiple email addresses can be stored loop through the records returned in the Cursor.

Notes

Custom notes can be attached to each contact record. As before these are stored in a separate table and are related based on the contact ID. 

        String noteWhere = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";         String[] noteWhereParams = new String[]{id,  ContactsContract.CommonDataKinds.Note.CONTENT_ITEM_TYPE};                 Cursor noteCur = cr.query(ContactsContract.Data.CONTENT_URI, null, noteWhere, noteWhereParams, null);  if (noteCur.moveToFirst()) {      String note = noteCur.getString(noteCur.getColumnIndex(ContactsContract.CommonDataKinds.Note.NOTE)); }  noteCur.close();

Notes are stored in the Android Contacts generic data table. When accessing specific data the WHERE clause will need 2 conditionals. First the standard contact ID, second a MIMETYPE for the data that is being requested. The Android SDK comes with a series of auto-generated variables that take care of this. Use the ContactsContract.CommonDataKinds.Note.CONTENT_ITEM_TYPE variable to limit the query to note records. The data table URI is stored at ContactsContract.Data.CONTENT_URI. Finally the note field name is stored in ContactsContract.CommonDataKinds.Note.NOTE.

Postal Addresses

Android can store multiple postal addresses per contact. Addresses are also stored in the data table like notes and queried via the URI stored in ContactsContract.Data.CONTENT_URI. Similar to the notes query a MIMETYPE must be added to the WHERE conditional. Also in Android 2.0 the Address record was split into multiple fields containing different parts of the address (PO-Box, stree, city, region, postal code). In earlier versions of the Android SDK this was a free-form string storage. 

String addrWhere = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?"; String[] addrWhereParams = new String[]{id, ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_ITEM_TYPE}; Cursor addrCur = cr.query(ContactsContract.Data.CONTENT_URI,                 null, where, whereParameters, null); while(addrCur.moveToNext()) {String poBox = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.POBOX)); String street = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.STREET)); String city = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.CITY)); String state = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.REGION)); String postalCode = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.POSTCODE)); String country = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.COUNTRY)); String type = addrCur.getString(                     addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.TYPE)); }  addrCur.close();

This code is similar to the previous example. Notice the field names for the address pieces are stored in ContactsContract.CommonDataKinds.StructuredPostal.

Instant Messenger (IM)

The instant messenger query performs just as the notes and address queries. Important field names for IM related data are stored in ContactsContract.CommonDataKinds.Im. 

 String imWhere = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";  String[] imWhereParams = new String[]{id,      ContactsContract.CommonDataKinds.Im.CONTENT_ITEM_TYPE};  Cursor imCur = cr.query(ContactsContract.Data.CONTENT_URI,             null, imWhere, imWhereParams, null);  if (imCur.moveToFirst()) {      String imName = imCur.getString(                 imCur.getColumnIndex(ContactsContract.CommonDataKinds.Im.DATA));     String imType;     imType = imCur.getString(                 imCur.getColumnIndex(ContactsContract.CommonDataKinds.Im.TYPE)); }  imCur.close();

Organizations

The last part of the contact record to be covered is the Organizations data. The Android contact record can contain information about Employment, professional, and social memberships as well as roles and titles. These records are queried from the URI stored in ContactsContract.Data.CONTENT_URI. Important field names for the organization data are stored in ContactsContract.CommonDataKinds.Organization. 

 String orgWhere = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";  String[] orgWhereParams = new String[]{id,  ContactsContract.CommonDataKinds.Organization.CONTENT_ITEM_TYPE};  Cursor orgCur = cr.query(ContactsContract.Data.CONTENT_URI,                 null, orgWhere, orgWhereParams, null); if (orgCur.moveToFirst()) {  String orgName = orgCur.getString(orgCur.getColumnIndex(ContactsContract.CommonDataKinds.Organization.DATA)); String title = orgCur.getString(orgCur.getColumnIndex(ContactsContract.CommonDataKinds.Organization.TITLE)); }  orgCur.close();
   
   

API For 1.6 and Before

If you just read the begining of this article the first bit of this page is going to look familiar. This page is designed to act as a standalone guide to working with the contacts API in Android 1.6 and before.

Granting Access

Before an application can query the contact records access must be granted through the AndroidManifest.xml file stored in the root of the project. Add the following uses-permission belows the uses-sdk statement. 

 

Querying the contact database

Retrieving Contact Details

Basic contact information stored in Contacts table with detailed information stored in individual tables for normalization. In Android 1.x to query the base contact records the URI to query is stored in People.CONTENT_URI. 

package higherpass.TestContacts;import android.app.Activity;import android.content.ContentResolver;import android.database.Cursor;import android.os.Bundle;import android.provider.Contacts;import android.provider.Contacts.People;public class TestContacts extends Activity {    /** Called when the activity is first created. */    @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);        ContentResolver cr = getContentResolver();        Cursor cur = cr.query(People.CONTENT_URI, null, null, null, null);        if (cur.getCount() > 0) {     while (cur.moveToNext()) {         String id = cur.getString(cur.getColumnIndex(People._ID));         String name = cur.getString(cur.getColumnIndex(People.DISPLAY_NAME));     }        }    }}

Start off with the standard view loading. Then we create a ContentResolver instance that will be used to query the SQLite database that stores the contacts. The ContentResolver query returns a Cursor instance that holds the contact records queried from the database. Then take the ID field from the contact record and store it in the string id and take the DISPLAY_NAME field and place it in the string name. For more information about cursors see the Android Cursor Tutorial.

Phone Numbers

Phone numbers are stored in their own table and need to be queried separately. To query the phone number table use the URI stored in the SDK variable Contacts.Phones.CONTENT_URI. Use a WHERE conditional to get the phone numbers for the specified contact. 

if (Integer.parseInt(cur.getString(            cur.getColumnIndex(People.PRIMARY_PHONE_ID))) > 0) {Cursor pCur = cr.query(Contacts.Phones.CONTENT_URI, null, Contacts.Phones.PERSON_ID +" = ?", new String[]{id}, null);int i=0;int pCount = pCur.getCount();String[] phoneNum = new String[pCount];String[] phoneType = new String[pCount];while (pCur.moveToNext()) {phoneNum[i] = pCur.getString(                               pCur.getColumnIndex(Contacts.Phones.NUMBER));phoneType[i] = pCur.getString(                               pCur.getColumnIndex(Contacts.Phones.TYPE));i++;} }

Query the phones table and get a Cursor stored in pCur. Since the Android contacts database can store multiple phone numbers per contact we need to loop through the returned results. In addition to returning the phone number the query also returned the type of number (home, work, mobile, etc).

Email Addresses

Querying email addresses is similar to phone numbers. A special query must be performed to get email addresses from the database. Query the URI stored in Contacts.ContactMethods.CONTENT_EMAIL_URI to query the email addresses. 

Cursor emailCur = cr.query( Contacts.ContactMethods.CONTENT_EMAIL_URI, null,Contacts.ContactMethods.PERSON_ID + " = ?", new String[]{id}, null); while (emailCur.moveToNext()) {     // This would allow you get several email addresses} emailCur.close();

Simple query Contacts.ContactMethods.CONTENT_EMAIL_URI with a conditional limiting the results to numbers that match the ID of the contact record matches the value in the field Contacts.ContactMethods.PERSON_ID. As with phone numbers each contact can contain multiple email addresses so we need to loop through the Cursor records.

Notes

Custom notes can be attached to each contact record. Notes though are stored in the main contact record and are simply accessed through the data stored in People.NOTES. 

 cur.getString(cur.getColumnIndex(People.NOTES));

Postal Addresses

Android can store multiple postal addresses per contact. Addresses are stored in the contact methods table and need to have a second conditional added to retrieve the data. Add a conditional Contacts.ContactMethods.KIND that matches Contacts.ContactMethods.CONTENT_POSTAL_ITEM_TYPE to only query postal addresses from Contacts.ContactMethods.CONTENT_URI.

String addrWhere = Contacts.ContactMethods.PERSON_ID                 + " = ? AND " + Contacts.ContactMethods.KIND + " = ?"; String[] addrWhereParams = new String[]{id, Contacts.ContactMethods.CONTENT_POSTAL_ITEM_TYPE}; Cursor addrCur = cr.query(Contacts.ContactMethods.CONTENT_URI,                 null, addrWhere, addrWhereParams, null); while(addrCur.moveToNext()) {String addr = addrCur.getString(                   addrCur.getColumnIndex(Contacts.ContactMethodsColumns.DATA));String type = addrCur.getString(                   addrCur.getColumnIndex(Contacts.ContactMethodsColumns.TYPE));} addrCur.close();

Query Contacts.ContactMethods.CONTENT_URI with 2 conditionals, one limiting the contact ID and the second Contacts.ContactMethods.KIND matching Contacts.ContactMethods.CONTENT_POSTAL_ITEM_TYPE to only query postall addresses. Android can store multiple postal addresses so loop through the list of returned results. Android also stores a type record for the address. In Android 1.6 and before the address is stored as a free-form string containing the data. In Android 2.0 and later this has changed to being a series of fields containing parts of the address.

Instant Messenger (IM)

The instant messenger query works just like the previous 2. The data is queried from Contacts.ContactMethods.CONTENT_URI and needs conditionals for the contact ID and Contacts.ContactMethods.KIND matching Contacts.ContactMethods.CONTENT_IM_ITEM_TYPE. 

String imWhere = Contacts.ContactMethods.PERSON_ID                + " = ? AND " + Contacts.ContactMethods.KIND + " = ?"; String[] imWhereParams = new String[]{id, Contacts.ContactMethods.CONTENT_IM_ITEM_TYPE}; Cursor imCur = cr.query(Contacts.ContactMethods.CONTENT_URI,                 null, imWhere, imWhereParams, null); if (imCur.moveToFirst()) { String imName = imCur.getString(                    imCur.getColumnIndex(Contacts.ContactMethodsColumns.DATA));String imType = imCur.getString(                    imCur.getColumnIndex(Contacts.ContactMethodsColumns.TYPE));} imCur.close();

Organizations

The last part of the contact record to be covered is the Organizations data. The Android contact record can contain information about Employment, professional, and social memberships as well as roles and titles. These records are queried from the URI stored in Contacts.Organizations.CONTENT_URI. 

String orgWhere = Contacts.ContactMethods.PERSON_ID + " = ?"; String[] orgWhereParams = new String[]{id}; Cursor orgCur = cr.query(Contacts.Organizations.CONTENT_URI,               null, orgWhere, orgWhereParams, null);if (orgCur.moveToFirst()) { String orgName = orgCur.getString(                   orgCur.getColumnIndex(Contacts.Organizations.COMPANY));String title = orgCur.getString(                   orgCur.getColumnIndex(Contacts.Organizations.TITLE));} orgCur.close();

Gluing it together

To put this together into an application there are a few glue pieces that need to be setup along with creating classes to manage accessing the data. First we need to create a set of classes to hold the data. Also we'll create a class to handle 2.0 API calls and a class to handle 1.6 and earlier API calls. There's also a wrapper class that determines and loads the proper class.

Contact Data Classes

The contact classes are a series of classes to hold a list of contacts. The list is stored in the class ContactList that maintains an ArrayList of Contacts. The Contact objects are represented in the Contact class. The contact class stores all the data from the Android contact record. In addition to the ContactList and Contact classes there are specialized classes to represent some of the record data.

We will create classes to represent the address, email, instant messenger, phone number, and organization(s). Most of these classes are mere data storage classes with variables and getter/setters.

ContactList

The ContactList class is a very basic class designed to hold an ArrayList of instances of the Contact class below. We've left this class very plain and ready to be expanded to suit your needs. 

 package com.higherpass.android.ContactAPI.objects;  import java.util.ArrayList;  public class ContactList {  private ArrayList contacts = new ArrayList();  public ArrayList getContacts() { return contacts; }  public void setContacts(ArrayList contacts) { this.contacts = contacts; }  public void addContact(Contact contact) { this.contacts.add(contact); }   public ContactList() {  }  }

Contact

The Contact class is used to store the details about each contact. There are a series of private class variables to hold this data. Singular data such as name and database ID are stored as strings. Complex data is stored either as an instance or ArrayList of data specific classes. This class is mainly getters and setters with a few methods to add to the internal ArrayLists. 

 package com.higherpass.android.ContactAPI.objects;  import java.util.ArrayList;  public class Contact { private String id; private String displayName; private ArrayList phone; private ArrayList email; private ArrayList notes; private ArrayList addresses = new ArrayList(); private ArrayList imAddresses; private Organization organization;    public Organization getOrganization() { return organization; } public void setOrganization(Organization organization) { this.organization = organization; } public ArrayList getImAddresses() { return imAddresses; } public void setImAddresses(ArrayList imAddresses) { this.imAddresses = imAddresses;  } public void addImAddresses(IM imAddr) { this.imAddresses.add(imAddr); } public ArrayList getNotes() { return notes; } public void setNotes(ArrayList notes) { this.notes = notes; } public void addNote(String note) { this.notes.add(note); } public ArrayList getAddresses() { return addresses; } public void setAddresses(ArrayList addresses) { this.addresses = addresses; } public void addAddress(Address address) { this.addresses.add(address); } public ArrayList getEmail() { return email; } public void setEmail(ArrayList email) { this.email = email; } public void addEmail(Email e) { this.email.add(e); } public String getId() { return id; } public void setId(String id) {  this.id = id; } public String getDisplayName() { return displayName; } public void setDisplayName(String dName) { this.displayName = dName; } public ArrayList getPhone() { return phone; } public void setPhone(ArrayList phone) { this.phone = phone; } public void addPhone(Phone phone) { this.phone.add(phone); } }

Address

The Address class is the only class in the ContactList framework that actually does any work. Due to differences in data storage between 1.x and 2.0 versions of Android the Address class has to determine if the input address is free-form from 1.x or was input from the formatted data structure from 2.0. Android 2.0 has individual data columns for PO-Box, street, city, region, postal code, country while 1.x was just a text field with the entire address. This is handled in the toString() method that returns a free-form address from either input type. Unfortunately when using Android 1.x all the individual address getters will return null. 

 package com.higherpass.android.ContactAPI.objects;  public class Address { private String poBox; private String street; private String city; private String state; private String postalCode; private String country; private String type; private String asString = "";  public String getType() { return type; } public void setType(String type) { this.type = type; } public String getPoBox() { return poBox; } public void setPoBox(String poBox) { this.poBox = poBox; } public String getStreet() { return street; } public void setStreet(String street) { this.street = street; } public String getCity() { return city; } public void setCity(String city) { this.city = city; } public String getState() { return state; } public void setState(String state) { this.state = state; } public String getPostalCode() { return postalCode; } public void setPostalCode(String postalCode) { this.postalCode = postalCode; } public String getCountry() { return country; } public void setCountry(String country) { this.country = country; } public String toString() { if (this.asString.length() > 0) { return(this.asString); } else { String addr = ""; if (this.getPoBox() != null) { addr = addr + this.getPoBox() + "n"; } if (this.getStreet() != null) { addr = addr + this.getStreet() + "n"; } if (this.getCity() != null) { addr = addr + this.getCity() + ", "; } if (this.getState() != null) { addr = addr + this.getState() + " "; } if (this.getPostalCode() != null) { addr = addr + this.getPostalCode() + " "; } if (this.getCountry() != null) { addr = addr + this.getCountry(); } return(addr); } }  public Address(String asString, String type) { this.asString = asString; this.type = type; }  public Address(String poBox, String street, String city, String state,  String postal, String country, String type) { this.setPoBox(poBox);  this.setStreet(street); this.setCity(city); this.setState(state); this.setPostalCode(postal); this.setCountry(country); this.setType(type); } }

Email

Another getter/setter and data storage class. The email class stores the email address and address type (work, home, etc). 

 package com.higherpass.android.ContactAPI.objects;  public class Email { private String address; private String type; public String getAddress() { return address; } public void setAddress(String address) { this.address = address; } public String getType() { return type; } public void setType(String t) { this.type = t; }  public Email(String a, String t) { this.address = a; this.type = t; } }

IM

Class to hold instant messenger data. 

 package com.higherpass.android.ContactAPI.objects;  public class IM { private String name; private String type; public String getName() { return name; } public void setName(String name) { this.name = name; } public String getType() { return type; } public void setType(String type) { this.type = type; }  public IM(String name, String type) { this.name = name; this.type = type; } }

Organization

Class to hold the contacts organizational data. 

 package com.higherpass.android.ContactAPI.objects;  public class Organization { private String organization = ""; private String title = ""; public String getOrganization() { return organization; } public void setOrganization(String organization) { this.organization = organization; } public String getTitle() { return title; } public void setTitle(String title) { this.title = title; }  public Organization() {  } public Organization(String org, String title) { this.organization = org; this.title = title; } }

Phone

Class to hold the phone records. 

 package com.higherpass.android.ContactAPI.objects;  public class Phone { private String number; private String type;  public String getNumber() { return number; }  public void setNumber(String number) { this.number = number; }  public String getType() { return type; }  public void setType(String type) { this.type = type; }  public Phone(String n, String t) { this.number = n; this.type = t; }  }

   

Wrapper class

The wrapper class below is what will be invoked by applications. This class will determine the API level running on the device/emulator and load the correct class created on the next pages. To determine the correct Android API running the Build.VERSION.SDK variable is queried. This version code is then compared against the Eclair (2.0) version code stored in Build.VERSION_CODES.ECLAIR. Finally the proper API class is loaded. 

 package com.higherpass.android.ContactAPI;  import android.os.Build; import android.content.ContentResolver; import android.content.Intent; import android.database.Cursor; import android.net.Uri;  import com.highercollaboration.android.ContactAPI.objects.*; public abstract class ContactAPI {  private static ContactAPI api;  private Cursor cur; private ContentResolver cr;  public static ContactAPI getAPI() { if (api == null) { String apiClass; if (Integer.parseInt(Build.VERSION.SDK) >= Build.VERSION_CODES.ECLAIR) { apiClass = "com.highercollaboration.android.ContactAPI.ContactAPISdk5"; } else { apiClass = "com.highercollaboration.android.ContactAPI.ContactAPISdk3"; }  try { Class<? extends ContactAPI> realClass = Class.forName(apiClass).asSubclass(ContactAPI.class); api = realClass.newInstance(); } catch (Exception e) { throw new IllegalStateException(e); }  } return api; }  public abstract Intent getContactIntent();  public abstract ContactList newContactList();  public abstract Cursor getCur(); public abstract void setCur(Cursor cur);  public abstract ContentResolver getCr(); public abstract void setCr(ContentResolver cr);  }

2.0 Data access class

This class takes what was covered on page 1 of the tutorial about the Android 2.0 Contact API and turns it into a class. This class extends and will be invoked by the wrapper class created previously. 

 package com.higherpass.android.ContactAPI;  import java.util.ArrayList;  import com.highercollaboration.android.ContactAPI.objects.*;   import android.content.Intent; import android.database.Cursor; import android.provider.ContactsContract; import android.content.ContentResolver;  public class ContactAPISdk5 extends ContactAPI {  private Cursor cur; private ContentResolver cr;   public Cursor getCur() { return cur; }  public void setCur(Cursor cur) { this.cur = cur; }  public ContentResolver getCr() { return cr; }  public void setCr(ContentResolver cr) { this.cr = cr; }  public Intent getContactIntent() { return(new Intent(Intent.ACTION_PICK, ContactsContract.Contacts.CONTENT_URI)); }  public ContactList newContactList() { ContactList contacts = new ContactList(); String id;  this.cur = this.cr.query(ContactsContract.Contacts.CONTENT_URI,                 null, null, null, null); if (this.cur.getCount() > 0) { while (cur.moveToNext()) { Contact c = new Contact(); id = cur.getString(cur.getColumnIndex(ContactsContract.Contacts._ID)); c.setId(id); c.setDisplayName(cur.getString(cur.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME))); if (Integer.parseInt(cur.getString(cur.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0) { c.setPhone(this.getPhoneNumbers(id)); } c.setEmail(this.getEmailAddresses(id)); c.setNotes(this.getContactNotes(id)); c.setAddresses(this.getContactAddresses(id)); c.setImAddresses(this.getIM(id)); c.setOrganization(this.getContactOrg(id)); contacts.addContact(c); } } return(contacts); }  public ArrayList getPhoneNumbers(String id) { ArrayList phones = new ArrayList();  Cursor pCur = this.cr.query( ContactsContract.CommonDataKinds.Phone.CONTENT_URI,  null,  ContactsContract.CommonDataKinds.Phone.CONTACT_ID +" = ?",  new String[]{id}, null); while (pCur.moveToNext()) { phones.add(new Phone( pCur.getString(pCur.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER)) , pCur.getString(pCur.getColumnIndex(ContactsContract.CommonDataKinds.Phone.TYPE)) ));  }  pCur.close(); return(phones); }  public ArrayList getEmailAddresses(String id) { ArrayList emails = new ArrayList();  Cursor emailCur = this.cr.query(  ContactsContract.CommonDataKinds.Email.CONTENT_URI,  null, ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?",  new String[]{id}, null);  while (emailCur.moveToNext()) {      // This would allow you get several email addresses Email e = new Email(emailCur.getString(emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA)) ,emailCur.getString(emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.TYPE))   ); emails.add(e); }  emailCur.close(); return(emails); }  public ArrayList getContactNotes(String id) { ArrayList notes = new ArrayList(); String where = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";  String[] whereParameters = new String[]{id,  ContactsContract.CommonDataKinds.Note.CONTENT_ITEM_TYPE};  Cursor noteCur = this.cr.query(ContactsContract.Data.CONTENT_URI, null, where, whereParameters, null);  if (noteCur.moveToFirst()) {  String note = noteCur.getString(noteCur.getColumnIndex(ContactsContract.CommonDataKinds.Note.NOTE)); if (note.length() > 0) { notes.add(note); } }  noteCur.close(); return(notes); }  public ArrayList getContactAddresses(String id) { ArrayList addrList = new ArrayList();  String where = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";  String[] whereParameters = new String[]{id,  ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_ITEM_TYPE};   Cursor addrCur = this.cr.query(ContactsContract.Data.CONTENT_URI, null, where, whereParameters, null);  while(addrCur.moveToNext()) { String poBox = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.POBOX)); String street = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.STREET)); String city = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.CITY)); String state = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.REGION)); String postalCode = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.POSTCODE)); String country = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.COUNTRY)); String type = addrCur.getString(addrCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.TYPE)); Address a = new Address(poBox, street, city, state, postalCode, country, type); addrList.add(a); }  addrCur.close(); return(addrList); }  public ArrayList getIM(String id) { ArrayList imList = new ArrayList(); String where = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";  String[] whereParameters = new String[]{id,  ContactsContract.CommonDataKinds.Im.CONTENT_ITEM_TYPE};   Cursor imCur = this.cr.query(ContactsContract.Data.CONTENT_URI, null, where, whereParameters, null);  if (imCur.moveToFirst()) {  String imName = imCur.getString(imCur.getColumnIndex(ContactsContract.CommonDataKinds.Im.DATA)); String imType; imType = imCur.getString(imCur.getColumnIndex(ContactsContract.CommonDataKinds.Im.TYPE)); if (imName.length() > 0) { IM im = new IM(imName, imType); imList.add(im); } }  imCur.close(); return(imList); }  public Organization getContactOrg(String id) { Organization org = new Organization(); String where = ContactsContract.Data.CONTACT_ID + " = ? AND " + ContactsContract.Data.MIMETYPE + " = ?";  String[] whereParameters = new String[]{id,  ContactsContract.CommonDataKinds.Organization.CONTENT_ITEM_TYPE};   Cursor orgCur = this.cr.query(ContactsContract.Data.CONTENT_URI, null, where, whereParameters, null);  if (orgCur.moveToFirst()) {  String orgName = orgCur.getString(orgCur.getColumnIndex(ContactsContract.CommonDataKinds.Organization.DATA)); String title = orgCur.getString(orgCur.getColumnIndex(ContactsContract.CommonDataKinds.Organization.TITLE)); if (orgName.length() > 0) { org.setOrganization(orgName); org.setTitle(title); } }  orgCur.close(); return(org); }  }

   

1.x Data access class

This class is made up of the code explained covering version 1.x of the Android contact API. As with the 2.0 class this class extends the ContactAPI wrapper class and will be invoked by it if the 1.x version of Android is in use. 

 package com.higherpass.android.ContactAPI;  import java.util.ArrayList;   import com.higherpass.android.ContactAPI.objects.Address; import com.higherpass.android.ContactAPI.objects.Contact; import com.higherpass.android.ContactAPI.objects.ContactList; import com.higherpass.android.ContactAPI.objects.Email; import com.higherpass.android.ContactAPI.objects.IM; import com.higherpass.android.ContactAPI.objects.Organization; import com.higherpass.android.ContactAPI.objects.Phone;   import android.content.ContentResolver; import android.content.Intent; import android.database.Cursor; import android.provider.Contacts; import android.provider.Contacts.People;  public class ContactAPISdk3 extends ContactAPI {  private Cursor cur; private ContentResolver cr;  public Cursor getCur() { return cur; }  public void setCur(Cursor cur) { this.cur = cur; }  public ContentResolver getCr() { return cr; }  public void setCr(ContentResolver cr) { this.cr = cr; }  public Intent getContactIntent() { return(new Intent(Intent.ACTION_PICK, People.CONTENT_URI)); }  public ContactList newContactList() { ContactList contacts = new ContactList(); String id;  this.cur = this.cr.query(People.CONTENT_URI,  null, null, null, null); if (this.cur.getCount() > 0) { while (cur.moveToNext()) { Contact c = new Contact(); id = cur.getString(cur.getColumnIndex(People._ID)); c.setId(id); c.setDisplayName(cur.getString(cur.getColumnIndex(People.DISPLAY_NAME))); if (Integer.parseInt(cur.getString(cur.getColumnIndex(People.PRIMARY_PHONE_ID))) > 0) { c.setPhone(this.getPhoneNumbers(id)); } c.setEmail(this.getEmailAddresses(id)); ArrayList notes = new ArrayList(); notes.add(cur.getString(cur.getColumnIndex(People.NOTES))); c.setNotes(notes); c.setAddresses(this.getContactAddresses(id)); c.setImAddresses(this.getIM(id)); c.setOrganization(this.getContactOrg(id)); contacts.addContact(c); } } return(contacts); }  public ArrayList getPhoneNumbers(String id) { ArrayList phones = new ArrayList();  Cursor pCur = this.cr.query( Contacts.Phones.CONTENT_URI,  null,  Contacts.Phones.PERSON_ID +" = ?",  new String[]{id}, null); while (pCur.moveToNext()) { phones.add(new Phone( pCur.getString(pCur.getColumnIndex(Contacts.Phones.NUMBER)) , pCur.getString(pCur.getColumnIndex(Contacts.Phones.TYPE)) ));  }  pCur.close(); return(phones); }  public ArrayList getEmailAddresses(String id) { ArrayList emails = new ArrayList();  Cursor emailCur = this.cr.query(  Contacts.ContactMethods.CONTENT_EMAIL_URI,  null, Contacts.ContactMethods.PERSON_ID + " = ?",  new String[]{id}, null);  while (emailCur.moveToNext()) {      // This would allow you get several email addresses Email e = new Email(emailCur.getString(emailCur.getColumnIndex(Contacts.ContactMethods.DATA)) ,emailCur.getString(emailCur.getColumnIndex(Contacts.ContactMethods.CONTENT_EMAIL_TYPE))   ); emails.add(e); }  emailCur.close(); return(emails); }  public ArrayList getContactAddresses(String id) { ArrayList addrList = new ArrayList();  String where = Contacts.ContactMethods.PERSON_ID + " = ? AND " + Contacts.ContactMethods.KIND + " = ?";  String[] whereParameters = new String[]{id,  Contacts.ContactMethods.CONTENT_POSTAL_ITEM_TYPE};   Cursor addrCur = this.cr.query(Contacts.ContactMethods.CONTENT_URI, null, where, whereParameters, null);  while(addrCur.moveToNext()) { String addr = addrCur.getString(addrCur.getColumnIndex(Contacts.ContactMethodsColumns.DATA)); String type = addrCur.getString(addrCur.getColumnIndex(Contacts.ContactMethodsColumns.TYPE)); Address a = new Address(addr, type); addrList.add(a); }  addrCur.close(); return(addrList); }  public ArrayList getIM(String id) { ArrayList imList = new ArrayList(); String where = Contacts.ContactMethods.PERSON_ID + " = ? AND " + Contacts.ContactMethods.KIND + " = ?";  String[] whereParameters = new String[]{id,  Contacts.ContactMethods.CONTENT_IM_ITEM_TYPE};   Cursor imCur = this.cr.query(Contacts.ContactMethods.CONTENT_URI, null, where, whereParameters, null);  if (imCur.moveToFirst()) {  String imName = imCur.getString(imCur.getColumnIndex(Contacts.ContactMethodsColumns.DATA)); String imType = imCur.getString(imCur.getColumnIndex(Contacts.ContactMethodsColumns.TYPE)); if (imName.length() > 0) { IM im = new IM(imName, imType); imList.add(im); } }  imCur.close(); return(imList); }  public Organization getContactOrg(String id) { Organization org = new Organization(); String where = Contacts.ContactMethods.PERSON_ID + " = ?";  String[] whereParameters = new String[]{id};   Cursor orgCur = this.cr.query(Contacts.Organizations.CONTENT_URI, null, where, whereParameters, null);  if (orgCur.moveToFirst()) {  String orgName = orgCur.getString(orgCur.getColumnIndex(Contacts.Organizations.COMPANY)); String title = orgCur.getString(orgCur.getColumnIndex(Contacts.Organizations.TITLE)); if (orgName.length() > 0) { org.setOrganization(orgName); org.setTitle(title); } }  orgCur.close(); return(org); } }

转自:http://www.higherpass.com/Android/Tutorials/Working-With-Android-Contacts/1/

更多相关文章

  1. 代码中设置drawableleft
  2. android 3.0 隐藏 系统标题栏
  3. Android开发中activity切换动画的实现
  4. Android(安卓)学习 笔记_05. 文件下载
  5. Android中直播视频技术探究之—摄像头Camera视频源数据采集解析
  6. 技术博客汇总
  7. android 2.3 wifi (一)
  8. AndRoid Notification的清空和修改
  9. Android中的Chronometer

随机推荐

  1. Android layout常见的属性大全
  2. 老罗Android开发视频教程 (android常用布
  3. 让Python在Android系统上飞一会儿
  4. Androidの自定义Spinner实现
  5. 【Android Studio使用教程4】Android Stu
  6. 修改android升级系统后启动系统,提示andro
  7. Android TextView 设置行间距字间距
  8. Android 入门前言之 --布局
  9. android selector 背景选择器的使用, butt
  10. Android Studio系列(四)Version Control II