I want to load contacts from android device, I have used different methods but contacts load so slow,
I am using CommanDataKinds,
I am getting index of column out of the loop(only one, then use
that variable in loop).
also I want to use fast scrolling technique like viber.
What exactly I need is viber contact list, It is fast, use sections, fast scrolling etc..
try with this dude :) best of luck
public class ReadContacts extends AsyncTask<Void, Void, Void>{
private ListView contactsList;
private Context cntx;
private Constant constants;
static final String[] CONTACTS_SUMMARY_PROJECTION = new String[] {
Contacts._ID, // 0
Contacts.DISPLAY_NAME, // 1
Contacts.STARRED, // 2
Contacts.TIMES_CONTACTED, // 3
Contacts.CONTACT_PRESENCE, // 4
Contacts.PHOTO_ID, // 5
Contacts.LOOKUP_KEY, // 6
Contacts.HAS_PHONE_NUMBER, // 7
};
private long contactId;
private String display_name;
private String phoneNumber;
private ArrayList<ContactsWrapper>contactWrap = new ArrayList<ContactsWrapper>();
private HashMap<Long, ArrayList<ContactsWrapper>>map = new HashMap<Long, ArrayList<ContactsWrapper>>();
private ContactsAdapter adapter;
private DataController controller;
public ReadContacts(Context cntx, ListView contactList) {
// TODO Auto-generated constructor stub
this.cntx = cntx;
constants = new Constant();
this.contactsList = contactList;
controller = DataController.getInstance();
}
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
super.onPreExecute();
if(!(controller.contactWrapper.size()>0))
constants.displayProgressDialog(cntx, "Loading Contacts...", "Please Wait");
}
#Override
protected Void doInBackground(Void... params) {
// TODO Auto-generated method stub
if(!(controller.contactWrapper.size()>0))
{
try {
String select = "((" + Contacts.DISPLAY_NAME + " NOTNULL) AND ("
+ Contacts.HAS_PHONE_NUMBER + "=1) AND ("
+ Contacts.DISPLAY_NAME + " != '' ))";
Cursor c = cntx.getContentResolver().query(Contacts.CONTENT_URI, CONTACTS_SUMMARY_PROJECTION, select,
null, Contacts.DISPLAY_NAME + " COLLATE LOCALIZED ASC");
int colorcounter = 0;
String[] colorcounter_array = { "#91A46B", "#8BB6B5", "#CAA973", "#8DA6C8","#D19B8D"};
int color_string;
for(int i=0;i<c.getCount();i++)
{
// contactWrap.clear();
try {
contactId = 0;
String hasPhone = "";
display_name = "";
phoneNumber = "";
c.moveToPosition(i);
contactId = c.getLong(0);
display_name = c.getString(1);
hasPhone = c.getString(7);
if (hasPhone.equalsIgnoreCase("1"))
hasPhone = "true";
else
hasPhone = "false" ;
if (Boolean.parseBoolean(hasPhone))
{
Cursor phones = cntx.getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,ContactsContract.CommonDataKinds.Phone.CONTACT_ID +" = "+ contactId,null, null);
while (phones.moveToNext())
{
int indexPhoneType = phones.getColumnIndexOrThrow(Phone.TYPE);
String phoneType = phones.getString(indexPhoneType);
phoneNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
String lookupKey = phones.getString(phones.getColumnIndex(ContactsContract.Contacts.LOOKUP_KEY));
if (colorcounter < 5)
{
color_string =Color.parseColor(colorcounter_array[colorcounter]);
colorcounter++;
} else {
colorcounter = 0;
color_string =Color.parseColor(colorcounter_array[colorcounter]);
colorcounter++;
}
contactWrap.add(new ContactsWrapper(contactId, display_name, phoneNumber,lookupKey,false,color_string));
}
// map.put(contactId, new ArrayList<ContactsWrapper>(contactWrap));
phones.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
controller.contactWrapper = contactWrap;
}
catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
return null;
}
#Override
protected void onPostExecute(Void result) {
// TODO Auto-generated method stub
super.onPostExecute(result);
constants.dismissDialog();
adapter = new ContactsAdapter(cntx);
contactsList.setAdapter(adapter);
}
}
and this is my contact wrapper class
public class ContactsWrapper {
private long contactId;
private String displayName,displayNumber,lookUp;
public boolean checked = true;
int color_string;
public ContactsWrapper(long contactId, String displayName, String displayNumber, String lookUp, boolean checked,int color_string) {
// TODO Auto-generated constructor stub
this.contactId = contactId;
this.displayName = displayName;
this.displayNumber = displayNumber;
this.lookUp = lookUp;
this.checked = checked;
this.color_string =color_string;
}
public String getLookUp() {
return lookUp;
}
public int getColor_string() {
return color_string;
}
public boolean isChecked() {
return checked;
}
public long getContactId() {
return contactId;
}
public String getDisplayName() {
return displayName;
}
public String getDisplayNumber() {
return displayNumber;
}
public void setChecked(boolean checked) {
this.checked = checked;
}
}
checkout this sample to retriev contacts and display in listview like fastscroll.
Related
Here i am fetching the name,email,phone number from the mobile and trying to upload to server..Here if the contacts contains name,email and phone number the values will be inserted successfully..but if any of the field is empty it is throwing NULL pointer exception.How to avoid this one..i mean if the contact does not contain email it should atleast send name and phone number.
here is my code.
public class DisplayContact1 extends Activity {
private static String TAG = WorkDetails1.class.getSimpleName();
Button select;
private String vault;
List<AddressBookContact> list;
public static final String kvault = "vault_no";
public static final String kname = "name";
public static final String kphone = "phone";
public static final String kemail = "email";
public static final String kcontacts = "contacts";
public static final String SHARED_PREF_NAME = "myloginapp";
public static final String UPLOAD_URL = "http://oursite.com/contacts_1.php";
private static final int MY_PERMISSIONS_REQUEST_READ_CONTACTS = 1;
Cursor cursor;
LongSparseArray<AddressBookContact> array;
long start;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//getActionBar().setDisplayShowTitleEnabled(false);
setContentView(R.layout.display);
SharedPreferences sharedPreferences = getSharedPreferences(ProfileLogin.SHARED_PREF_NAME, MODE_PRIVATE);
vault = sharedPreferences.getString(ProfileLogin.EMAIL_SHARED_PREF,"Not Available");
getAllContacts(this.getContentResolver());
}
public void getAllContacts(ContentResolver cr) {
int result = ContextCompat.checkSelfPermission(DisplayContact1.this, Manifest.permission.READ_CONTACTS);
if (result == PackageManager.PERMISSION_GRANTED){
//fetches contacts from the phone contact list and displays in ascending order
list = new LinkedList<AddressBookContact>();
array = new LongSparseArray<AddressBookContact>();
start = System.currentTimeMillis();
String[] projection = {
ContactsContract.Data.MIMETYPE,
ContactsContract.Data.CONTACT_ID,
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.CommonDataKinds.Contactables.DATA,
ContactsContract.CommonDataKinds.Contactables.TYPE,
};
String selection = ContactsContract.Data.MIMETYPE + " in (?, ?)";
String[] selectionArgs = {
ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE,
ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE,
};
String sortOrder = ContactsContract.Contacts.SORT_KEY_ALTERNATIVE;
Uri uri = ContactsContract.Data.CONTENT_URI;
// we could also use Uri uri = ContactsContract.Data.CONTENT_URI;
cursor = getContentResolver().query(uri, projection, selection, selectionArgs, sortOrder);
contactsdisplay();
} else {
requestForLocationPermission();
}
}
private void requestForLocationPermission()
{
if (ActivityCompat.shouldShowRequestPermissionRationale(DisplayContact1.this, Manifest.permission.READ_CONTACTS))
{
}
else {
ActivityCompat.requestPermissions(DisplayContact1.this, new String[]{Manifest.permission.READ_CONTACTS}, MY_PERMISSIONS_REQUEST_READ_CONTACTS);
}
}
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults)
{
switch (requestCode) {
case MY_PERMISSIONS_REQUEST_READ_CONTACTS:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED)
{
getAllContacts(DisplayContact1.this.getContentResolver());
contactsdisplay();
}
break;
}
}
public void contactsdisplay() {
//Cursor phones = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,null,null, null);
final int mimeTypeIdx = cursor.getColumnIndex(ContactsContract.Data.MIMETYPE);
final int idIdx = cursor.getColumnIndex(ContactsContract.Data.CONTACT_ID);
final int nameIdx = cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME);
final int dataIdx = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Contactables.DATA);
final int typeIdx = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Contactables.TYPE);
while (cursor.moveToNext()) {
long id = cursor.getLong(idIdx);
AddressBookContact addressBookContact = array.get(id);
if (addressBookContact == null) {
addressBookContact = new AddressBookContact(id, cursor.getString(nameIdx), getResources());
array.put(id, addressBookContact);
list.add(addressBookContact);
}
int type = cursor.getInt(typeIdx);
String data = cursor.getString(dataIdx);
String mimeType = cursor.getString(mimeTypeIdx);
if (mimeType.equals(ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE)) {
// mimeType == ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE
addressBookContact.addEmail(type, data);
} else {
// mimeType == ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE
addressBookContact.addPhone(type, data);
}
}
long ms = System.currentTimeMillis() - start;
cursor.close();
// done!!! show the results...
int i = 1;
for (AddressBookContact addressBookContact : list) {
Log.d(TAG, "AddressBookContact #" + i++ + ": " + addressBookContact.toString(true));
}
final String cOn = "<b><font color='#ff9900'>";
final String cOff = "</font></b>";
Spanned l1 = Html.fromHtml("got " + cOn + array.size() + cOff + " contacts<br/>");
Spanned l2 = Html.fromHtml("query took " + cOn + ms / 1000f + cOff + " s (" + cOn + ms + cOff + " ms)");
Log.d(TAG, "\n\n╔══════ query execution stats ═══════" );
Log.d(TAG, "║ " + l1);
Log.d(TAG, "║ " + l2);
Log.d(TAG, "╚════════════════════════════════════" );
SpannableStringBuilder msg = new SpannableStringBuilder().append(l1).append(l2);
ListView lv= (ListView) findViewById(R.id.lv);
lv.setAdapter(new ArrayAdapter<AddressBookContact>(this, android.R.layout.simple_list_item_1, list));
lv.setItemsCanFocus(false);
lv.setTextFilterEnabled(true);
select = (Button) findViewById(R.id.button1);
select.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick(View v){
uploadImage();
}
});
}
public void uploadImage(){
SharedPreferences sharedPreferences = getSharedPreferences(DisplayContact.SHARED_PREF_NAME, MODE_PRIVATE);
final String vault_no = vault;
class UploadImage extends AsyncTask<Void,Void,String> {
ProgressDialog loading;
#Override
protected void onPreExecute() {
super.onPreExecute();
loading = ProgressDialog.show(DisplayContact1.this,"Please wait...","uploading",false,false);
}
#Override
protected void onPostExecute(String s) {
super.onPostExecute(s);
loading.dismiss();
if(s.equalsIgnoreCase("Successfully Saved")){
//Intent intent = new Intent(CollegeDetails.this,Work.class);
Toast.makeText(DisplayContact1.this, s, Toast.LENGTH_SHORT).show();
// startActivity(intent);
}else{
Toast.makeText(DisplayContact1.this,s,Toast.LENGTH_SHORT).show();
}
}
#Override
protected String doInBackground(Void... params) {
RequestHandler rh = new RequestHandler();
//RegisterUserClass rh = new RegisterUserClass();
HashMap<String,String> param = new HashMap<String,String>();
JSONArray contacts = new JSONArray();
int i = 1;
for (AddressBookContact addressBookContact : list) {
try {
Log.d(TAG, "AddressBookContact #" + i++ + ": " + addressBookContact.toString(true));
JSONObject contact = new JSONObject();
contact.put(kname, addressBookContact.name.toString());
contact.put(kvault, vault_no);
contact.put(kphone, addressBookContact.phone.toString());
if(addressBookContact.email.toString()!=null)
contact.put(kemail, addressBookContact.email.toString());
contacts.put(contact);
}
catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
param.put(kcontacts, contacts.toString());
System.out.println("param value.." + i++ +":"+ contacts.toString());
}
return rh.sendPostRequest(UPLOAD_URL, param);
}
}
UploadImage u = new UploadImage();
u.execute();
}
}
here is the AddressBookContact.class
public class AddressBookContact {
private long id;
private Resources res;
String name;
LongSparseArray<String> email;
LongSparseArray<String> phone;
AddressBookContact(long id, String name, Resources res) {
this.id = id;
this.name = name;
this.res = res;
}
#Override
public String toString() {
return toString(false);
}
public String toString(boolean rich) {
SpannableStringBuilder builder = new SpannableStringBuilder();
if (rich) {
builder.append("id: ").append(Long.toString(id))
.append(", name: ").append(name);
} else {
builder.append("name: ").append(name);
}
if (phone != null) {
builder.append("\nphone: ");
for (int i = 0; i < phone.size(); i++) {
int type = (int) phone.keyAt(i);
builder.append(phone.valueAt(i));
if (i + 1 < phone.size()) {
builder.append(", ");
}
}
}
if (email != null) {
builder.append("\nemail: ");
for (int i = 0; i < email.size(); i++) {
int type = (int) email.keyAt(i);
builder.append(email.valueAt(i));
if (i + 1 < email.size()) {
builder.append(", ");
}
}
}
return builder.toString();
}
public void addEmail(int type, String address) {
if (email == null) {
email = new LongSparseArray<String>();
}
email.put(type, address);
}
public void addPhone(int type, String number) {
if (phone == null) {
phone = new LongSparseArray<String>();
}
phone.put(type, number);
}
}
if email field is empty, i am getting null pointer exception at this line..
contact.put(kemail, addressBookContact.email.toString());..so i have added if loop to check the null condition..but then also i am getting exception.
Here
if (addressBookContact.email.toString() != null)
you try to get String from 'email' variable that is null.
Correct comparing is:
if (addressBookContact.email != null)
Add two conditions as below your string might not be null but can be
empty ""
if(addressBookContact.email.toString() != null && !addressBookContact.email.toString().equalsIgnoreCase(""))
contact.put(kemail, addressBookContact.email.toString());
Use TextUtils.
if(!TextUtils.isEmpty(addressBookContact.email.toString())){
contact.put(kemail, addressBookContact.email.toString());
}
And if kemail is compulsory field then in else condition just pass "" empty value.
In my android code
I want to fetch contact's name,email and phone number as as json and then want to display.
Here is my code:
public class MainActivity extends Activity {
public TextView outputText;
String[] phoneNumber;
String[] email;
String name;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
outputText = (TextView) findViewById(R.id.textView1);
try {
//fetchContacts();
outputText.setText(fetchContacts());
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public String fetchContacts() throws JSONException {
Uri CONTENT_URI = ContactsContract.Contacts.CONTENT_URI;
String _ID = ContactsContract.Contacts._ID;
String DISPLAY_NAME = ContactsContract.Contacts.DISPLAY_NAME;
String HAS_PHONE_NUMBER = ContactsContract.Contacts.HAS_PHONE_NUMBER;
Uri PhoneCONTENT_URI = ContactsContract.CommonDataKinds.Phone.CONTENT_URI;
String Phone_CONTACT_ID = ContactsContract.CommonDataKinds.Phone.CONTACT_ID;
String NUMBER = ContactsContract.CommonDataKinds.Phone.NUMBER;
Uri EmailCONTENT_URI = ContactsContract.CommonDataKinds.Email.CONTENT_URI;
String EmailCONTACT_ID = ContactsContract.CommonDataKinds.Email.CONTACT_ID;
String DATA = ContactsContract.CommonDataKinds.Email.DATA;
ContentResolver contentResolver = getContentResolver();
Cursor cursor = contentResolver.query(CONTENT_URI, null, null, null,
null);
List<Contact> contacts = new ArrayList<Contact>();
Gson gson = new Gson();
// Loop for every contact in the phone
if (cursor.getCount() > 0) {
while (cursor.moveToNext()) {
String contact_id = cursor
.getString(cursor.getColumnIndex(_ID));
name = cursor.getString(cursor.getColumnIndex(DISPLAY_NAME));
int hasPhoneNumber = Integer.parseInt(cursor.getString(cursor
.getColumnIndex(HAS_PHONE_NUMBER)));
if (hasPhoneNumber > 0) {
int p = 0;
// Query and loop for every phone number of the contact
Cursor phoneCursor = contentResolver.query(
PhoneCONTENT_URI, null, Phone_CONTACT_ID + " = ?",
new String[] { contact_id }, null);
while (phoneCursor.moveToNext()) {
phoneNumber[p] = phoneCursor.getString(phoneCursor
.getColumnIndex(NUMBER));
p++;
}
phoneCursor.close();
int q = 0;
// Query and loop for every email of the contact
Cursor emailCursor = contentResolver.query(
EmailCONTENT_URI, null, EmailCONTACT_ID + " = ?",
new String[] { contact_id }, null);
while (emailCursor.moveToNext()) {
email[q] = emailCursor.getString(emailCursor
.getColumnIndex(DATA));
q++;
}
emailCursor.close();
contacts.add(new Contact(name, phoneNumber, email));
}
}
}
return gson.toJson(contacts);
}
}
But I am getting nullpointer exception error :
java.lang.RuntimeException: Unable to start activity
ComponentInfo{com.example.contactdemo/com.example.contactdemo.MainActivity}: java.lang.NullPointerException
error found in below line of code:
phoneNumber[p] = phoneCursor.getString(phoneCursor.getColumnIndex(NUMBER));
Here I am storing phonenumber and email as array.Is there array initialization problem ?? any idea guys?
You can use these approach to finds the contact from contact list
class FetchDeviceContact extends AsyncTask<Void, Integer, String>
{
protected void onPreExecute (){
Constant.showProgressDialog(AddDeviceContactScreeen.this);
}
protected String doInBackground(Void...arg0) {
arrayList.clear();
ContentResolver cr = AddDeviceContactScreeen.this.getContentResolver();
Cursor cur = AddDeviceContactScreeen.this.getContentResolver().query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);
while (cur.moveToNext()) {
String id = cur.getString(cur.getColumnIndex(ContactsContract.Data._ID));
String name = cur.getString(cur.getColumnIndex(ContactsContract.Data.DISPLAY_NAME));
String photoUri = cur.getString(cur.getColumnIndex(ContactsContract.Data.PHOTO_THUMBNAIL_URI));
Bitmap my_btmp = BitmapFactory.decodeResource(getResources(), R.drawable.ic_arrow_up_blue);
String email = null;
String phoneNo = null;
Cursor phonecur = AddDeviceContactScreeen.this.getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?",
new String[]{id}, null);
if (photoUri != null) {
Uri my_contact_Uri = Uri.parse(photoUri);
try {
my_btmp = MediaStore.Images.Media.getBitmap(AddDeviceContactScreeen.this.getContentResolver(), my_contact_Uri);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
if (phonecur.getCount() > 0) {
while (phonecur.moveToNext()) {
phoneNo = phonecur.getString(phonecur.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
}
}
Cursor emailCur = cr.query(
ContactsContract.CommonDataKinds.Email.CONTENT_URI, null,
ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?",
new String[]{id}, null);
while (emailCur.moveToNext()) {
// to get the contact names
// = cur1.getString(cur1.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA)
email = emailCur.getString(emailCur.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));
if (email != null) {
System.out.println("Email============== :" + email);
}
}
emailCur.close();
ContactBean bean = new ContactBean();
bean.setName(name);
bean.setEmail(email);
bean.setImage(my_btmp);
bean.setPhone_number(phoneNo);
if (phoneNo == null || email == null) {
} else {
arrayList.add(bean);
}
}
return "";
}
protected void onProgressUpdate(Integer...a){
}
protected void onPostExecute(String result) {
Constant.cancelDialog();
}
}
new FetchDeviceContact().execute();
Create the getter and setter class for it:-
public class ContactBean {
String name;
String email;
Bitmap image;
String phone_number;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public Bitmap getImage() {
return image;
}
public void setImage(Bitmap image) {
this.image = image;
}
public String getPhone_number() {
return phone_number;
}
public void setPhone_number(String phone_number) {
this.phone_number = phone_number;
}
}
I think you should fix :
if (phoneCursor.movetoFirst()){
while (!phoneCursor.isAfterLast()) {
phoneNumber[p] = phoneCursor.getString(phoneCursor.getColumnIndex(NUMBER));
p++;
phoneCursor.movetoNext();
}
}
Here:
phoneNumber[p] = phoneCursor.getString(phoneCursor.getColumnIndex(NUMBER));
NullPointerException caused because phoneNumber is null and not initialized.
Use Cursor. getCount() to initialize it as:
phoneNumber = new String[phoneCursor.getCount()];
phoneCursor.moveToFirst();
while (phoneCursor.moveToNext()) {
//..your code here..
}
I want the code to use my phone book contacts in any of my application means I want to get the code to my phone book contact data so that i can select any contact from it and use its number and other details that are stored in that contact
try with this dude :) best of luck
and this is code of class
public class ReadContacts extends AsyncTask<Void, Void, Void>{
private ListView contactsList;
private Context cntx;
private Constant constants;
static final String[] CONTACTS_SUMMARY_PROJECTION = new String[] {
Contacts._ID, // 0
Contacts.DISPLAY_NAME, // 1
Contacts.STARRED, // 2
Contacts.TIMES_CONTACTED, // 3
Contacts.CONTACT_PRESENCE, // 4
Contacts.PHOTO_ID, // 5
Contacts.LOOKUP_KEY, // 6
Contacts.HAS_PHONE_NUMBER, // 7
};
private long contactId;
private String display_name;
private String phoneNumber;
private ArrayList<ContactsWrapper>contactWrap = new ArrayList<ContactsWrapper>();
private HashMap<Long, ArrayList<ContactsWrapper>>map = new HashMap<Long, ArrayList<ContactsWrapper>>();
private ContactsAdapter adapter;
private DataController controller;
public ReadContacts(Context cntx, ListView contactList) {
// TODO Auto-generated constructor stub
this.cntx = cntx;
constants = new Constant();
this.contactsList = contactList;
controller = DataController.getInstance();
}
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
super.onPreExecute();
if(!(controller.contactWrapper.size()>0))
constants.displayProgressDialog(cntx, "Loading Contacts...", "Please Wait");
}
#Override
protected Void doInBackground(Void... params) {
// TODO Auto-generated method stub
if(!(controller.contactWrapper.size()>0))
{
try {
String select = "((" + Contacts.DISPLAY_NAME + " NOTNULL) AND ("
+ Contacts.HAS_PHONE_NUMBER + "=1) AND ("
+ Contacts.DISPLAY_NAME + " != '' ))";
Cursor c = cntx.getContentResolver().query(Contacts.CONTENT_URI, CONTACTS_SUMMARY_PROJECTION, select,
null, Contacts.DISPLAY_NAME + " COLLATE LOCALIZED ASC");
int colorcounter = 0;
String[] colorcounter_array = { "#91A46B", "#8BB6B5", "#CAA973", "#8DA6C8","#D19B8D"};
int color_string;
for(int i=0;i<c.getCount();i++)
{
// contactWrap.clear();
try {
contactId = 0;
String hasPhone = "";
display_name = "";
phoneNumber = "";
c.moveToPosition(i);
contactId = c.getLong(0);
display_name = c.getString(1);
hasPhone = c.getString(7);
if (hasPhone.equalsIgnoreCase("1"))
hasPhone = "true";
else
hasPhone = "false" ;
if (Boolean.parseBoolean(hasPhone))
{
Cursor phones = cntx.getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,ContactsContract.CommonDataKinds.Phone.CONTACT_ID +" = "+ contactId,null, null);
while (phones.moveToNext())
{
int indexPhoneType = phones.getColumnIndexOrThrow(Phone.TYPE);
String phoneType = phones.getString(indexPhoneType);
phoneNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
String lookupKey = phones.getString(phones.getColumnIndex(ContactsContract.Contacts.LOOKUP_KEY));
if (colorcounter < 5)
{
color_string =Color.parseColor(colorcounter_array[colorcounter]);
colorcounter++;
} else {
colorcounter = 0;
color_string =Color.parseColor(colorcounter_array[colorcounter]);
colorcounter++;
}
contactWrap.add(new ContactsWrapper(contactId, display_name, phoneNumber,lookupKey,false,color_string));
}
// map.put(contactId, new ArrayList<ContactsWrapper>(contactWrap));
phones.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
controller.contactWrapper = contactWrap;
}
catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
return null;
}
#Override
protected void onPostExecute(Void result) {
// TODO Auto-generated method stub
super.onPostExecute(result);
constants.dismissDialog();
adapter = new ContactsAdapter(cntx);
contactsList.setAdapter(adapter);
}
}
and this is my contact wrapper class
public class ContactsWrapper {
private long contactId;
private String displayName,displayNumber,lookUp;
public boolean checked = true;
int color_string;
public ContactsWrapper(long contactId, String displayName, String displayNumber, String lookUp, boolean checked,int color_string) {
// TODO Auto-generated constructor stub
this.contactId = contactId;
this.displayName = displayName;
this.displayNumber = displayNumber;
this.lookUp = lookUp;
this.checked = checked;
this.color_string =color_string;
}
public String getLookUp() {
return lookUp;
}
public int getColor_string() {
return color_string;
}
public boolean isChecked() {
return checked;
}
public long getContactId() {
return contactId;
}
public String getDisplayName() {
return displayName;
}
public String getDisplayNumber() {
return displayNumber;
}
public void setChecked(boolean checked) {
this.checked = checked;
}
}
You can use content provider of COntacts app in your application.
go through this tutorial
I am trying to query the Contacts database for contacts information, I have designed the program in a way that only contacts with Birth Day details are fetched:
projection = new String[] {
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.CommonDataKinds.Phone.NUMBER,
ContactsContract.CommonDataKinds.Event.CONTACT_ID,
ContactsContract.CommonDataKinds.Event.START_DATE,
ContactsContract.CommonDataKinds.Email.DATA,
};
where = ContactsContract.Data.MIMETYPE + "= ? AND " +
ContactsContract.CommonDataKinds.Event.TYPE + "=" + ContactsContract.CommonDataKinds.Event.TYPE_BIRTHDAY;
selectionArgs = new String[] { ContactsContract.CommonDataKinds.Event.CONTENT_ITEM_TYPE };
The Call:
getLoaderManager().initLoader(0, null, this);
And Finally I try to fetch the result:
public Loader<Cursor> onCreateLoader(int arg0, Bundle arg1) {
CursorLoader loader = new CursorLoader(this, uri, projection, where,
selectionArgs, null);
return loader;
}
#SuppressWarnings("unchecked")
#Override
public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
Map<Date,String> BD = new HashMap<Date,String>();
while (cursor.moveToNext()) {
String id = cursor.getString(cursor
.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
Toast.makeText(getApplicationContext(), ""+id, 10000).show();
String displayBirthday = cursor
.getString(cursor
.getColumnIndex(ContactsContract.CommonDataKinds.Event.START_DATE));
String name = cursor.getString(cursor
.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
String DateStr=displayBirthday;
Date d = null;
try {
d = new SimpleDateFormat("yyyy-MM-dd", current).parse(DateStr);
} catch (ParseException e) {
e.printStackTrace();
}
java.sql.Date d1 = new java.sql.Date(d.getTime());
BD.put(d1, name);
}
TreeMap Sorted = new TreeMap<Date,String>(BD);
//new MagicCall().execute(Sorted);
}
However I do not get the phone number, it gives me the birth day field result in the toast message instead of the phone number, if I change it to email it still gives me the birthday detail. Please neglect the suppress warnings as this is a test project in which I have isolate the problem code.
try with this dude :) best of luck
<uses-permission android:name="android.permission.READ_CONTACTS" />
and this is code of class
public class ReadContacts extends AsyncTask<Void, Void, Void>{
private ListView contactsList;
private Context cntx;
private Constant constants;
static final String[] CONTACTS_SUMMARY_PROJECTION = new String[] {
Contacts._ID, // 0
Contacts.DISPLAY_NAME, // 1
Contacts.STARRED, // 2
Contacts.TIMES_CONTACTED, // 3
Contacts.CONTACT_PRESENCE, // 4
Contacts.PHOTO_ID, // 5
Contacts.LOOKUP_KEY, // 6
Contacts.HAS_PHONE_NUMBER, // 7
};
private long contactId;
private String display_name;
private String phoneNumber;
private ArrayList<ContactsWrapper>contactWrap = new ArrayList<ContactsWrapper>();
private HashMap<Long, ArrayList<ContactsWrapper>>map = new HashMap<Long, ArrayList<ContactsWrapper>>();
private ContactsAdapter adapter;
private DataController controller;
public ReadContacts(Context cntx, ListView contactList) {
// TODO Auto-generated constructor stub
this.cntx = cntx;
constants = new Constant();
this.contactsList = contactList;
controller = DataController.getInstance();
}
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
super.onPreExecute();
if(!(controller.contactWrapper.size()>0))
constants.displayProgressDialog(cntx, "Loading Contacts...", "Please Wait");
}
#Override
protected Void doInBackground(Void... params) {
// TODO Auto-generated method stub
if(!(controller.contactWrapper.size()>0))
{
try {
String select = "((" + Contacts.DISPLAY_NAME + " NOTNULL) AND ("
+ Contacts.HAS_PHONE_NUMBER + "=1) AND ("
+ Contacts.DISPLAY_NAME + " != '' ))";
Cursor c = cntx.getContentResolver().query(Contacts.CONTENT_URI, CONTACTS_SUMMARY_PROJECTION, select,
null, Contacts.DISPLAY_NAME + " COLLATE LOCALIZED ASC");
int colorcounter = 0;
String[] colorcounter_array = { "#91A46B", "#8BB6B5", "#CAA973", "#8DA6C8","#D19B8D"};
int color_string;
for(int i=0;i<c.getCount();i++)
{
// contactWrap.clear();
try {
contactId = 0;
String hasPhone = "";
display_name = "";
phoneNumber = "";
c.moveToPosition(i);
contactId = c.getLong(0);
display_name = c.getString(1);
hasPhone = c.getString(7);
if (hasPhone.equalsIgnoreCase("1"))
hasPhone = "true";
else
hasPhone = "false" ;
if (Boolean.parseBoolean(hasPhone))
{
Cursor phones = cntx.getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,ContactsContract.CommonDataKinds.Phone.CONTACT_ID +" = "+ contactId,null, null);
while (phones.moveToNext())
{
int indexPhoneType = phones.getColumnIndexOrThrow(Phone.TYPE);
String phoneType = phones.getString(indexPhoneType);
phoneNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
String lookupKey = phones.getString(phones.getColumnIndex(ContactsContract.Contacts.LOOKUP_KEY));
if (colorcounter < 5)
{
color_string =Color.parseColor(colorcounter_array[colorcounter]);
colorcounter++;
} else {
colorcounter = 0;
color_string =Color.parseColor(colorcounter_array[colorcounter]);
colorcounter++;
}
contactWrap.add(new ContactsWrapper(contactId, display_name, phoneNumber,lookupKey,false,color_string));
}
// map.put(contactId, new ArrayList<ContactsWrapper>(contactWrap));
phones.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
controller.contactWrapper = contactWrap;
}
catch (Exception e) {
// TODO: handle exception
e.printStackTrace();
}
}
return null;
}
#Override
protected void onPostExecute(Void result) {
// TODO Auto-generated method stub
super.onPostExecute(result);
constants.dismissDialog();
adapter = new ContactsAdapter(cntx);
contactsList.setAdapter(adapter);
}
}
and this is my contact wrapper class
public class ContactsWrapper {
private long contactId;
private String displayName,displayNumber,lookUp;
public boolean checked = true;
int color_string;
public ContactsWrapper(long contactId, String displayName, String displayNumber, String lookUp, boolean checked,int color_string) {
// TODO Auto-generated constructor stub
this.contactId = contactId;
this.displayName = displayName;
this.displayNumber = displayNumber;
this.lookUp = lookUp;
this.checked = checked;
this.color_string =color_string;
}
public String getLookUp() {
return lookUp;
}
public int getColor_string() {
return color_string;
}
public boolean isChecked() {
return checked;
}
public long getContactId() {
return contactId;
}
public String getDisplayName() {
return displayName;
}
public String getDisplayNumber() {
return displayNumber;
}
public void setChecked(boolean checked) {
this.checked = checked;
}
}
dont panic dude just match list with thar birthdate and take one temp arraylist and when any name match then add in that temp arraylist and then show that list view according to that temp arraylist :) here i give u code and hint i think it will help u to achieve whatever u want...:)
ArrayList<String> matchname = new ArrayList<String>();
for(int l =0;l<contactarraylist.size();l++)
{
String keyname = contactarraylist[k];
if((keyname.trim().equals("birthdate_string")))
{
matchname.add(keyname);
}
}
}
How can I get all the names of the contacts in my Android and put them into array of strings?
Try this too,
private void getContactList() {
ContentResolver cr = getContentResolver();
Cursor cur = cr.query(ContactsContract.Contacts.CONTENT_URI,
null, null, null, null);
if ((cur != null ? cur.getCount() : 0) > 0) {
while (cur != null && cur.moveToNext()) {
String id = cur.getString(
cur.getColumnIndex(ContactsContract.Contacts._ID));
String name = cur.getString(cur.getColumnIndex(
ContactsContract.Contacts.DISPLAY_NAME));
if (cur.getInt(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()) {
String phoneNo = pCur.getString(pCur.getColumnIndex(
ContactsContract.CommonDataKinds.Phone.NUMBER));
Log.i(TAG, "Name: " + name);
Log.i(TAG, "Phone Number: " + phoneNo);
}
pCur.close();
}
}
}
if(cur!=null){
cur.close();
}
}
If you need more reference means refer this link Read ContactList
Get contacts info , photo contacts , photo uri and convert to Class model
1). Sample for Class model :
public class ContactModel {
public String id;
public String name;
public String mobileNumber;
public Bitmap photo;
public Uri photoURI;
}
2). get Contacts and convert to Model
public List<ContactModel> getContacts(Context ctx) {
List<ContactModel> list = new ArrayList<>();
ContentResolver contentResolver = ctx.getContentResolver();
Cursor cursor = contentResolver.query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);
if (cursor.getCount() > 0) {
while (cursor.moveToNext()) {
String id = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts._ID));
if (cursor.getInt(cursor.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER)) > 0) {
Cursor cursorInfo = contentResolver.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?", new String[]{id}, null);
InputStream inputStream = ContactsContract.Contacts.openContactPhotoInputStream(ctx.getContentResolver(),
ContentUris.withAppendedId(ContactsContract.Contacts.CONTENT_URI, new Long(id)));
Uri person = ContentUris.withAppendedId(ContactsContract.Contacts.CONTENT_URI, new Long(id));
Uri pURI = Uri.withAppendedPath(person, ContactsContract.Contacts.Photo.CONTENT_DIRECTORY);
Bitmap photo = null;
if (inputStream != null) {
photo = BitmapFactory.decodeStream(inputStream);
}
while (cursorInfo.moveToNext()) {
ContactModel info = new ContactModel();
info.id = id;
info.name = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
info.mobileNumber = cursorInfo.getString(cursorInfo.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
info.photo = photo;
info.photoURI= pURI;
list.add(info);
}
cursorInfo.close();
}
}
cursor.close();
}
return list;
}
public class MyActivity extends Activity
implements LoaderManager.LoaderCallbacks<Cursor> {
private static final int CONTACTS_LOADER_ID = 1;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// Prepare the loader. Either re-connect with an existing one,
// or start a new one.
getLoaderManager().initLoader(CONTACTS_LOADER_ID,
null,
this);
}
#Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) {
// This is called when a new Loader needs to be created.
if (id == CONTACTS_LOADER_ID) {
return contactsLoader();
}
return null;
}
#Override
public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
//The framework will take care of closing the
// old cursor once we return.
List<String> contacts = contactsFromCursor(cursor);
}
#Override
public void onLoaderReset(Loader<Cursor> loader) {
// This is called when the last Cursor provided to onLoadFinished()
// above is about to be closed. We need to make sure we are no
// longer using it.
}
private Loader<Cursor> contactsLoader() {
Uri contactsUri = ContactsContract.Contacts.CONTENT_URI; // The content URI of the phone contacts
String[] projection = { // The columns to return for each row
ContactsContract.Contacts.DISPLAY_NAME
} ;
String selection = null; //Selection criteria
String[] selectionArgs = {}; //Selection criteria
String sortOrder = null; //The sort order for the returned rows
return new CursorLoader(
getApplicationContext(),
contactsUri,
projection,
selection,
selectionArgs,
sortOrder);
}
private List<String> contactsFromCursor(Cursor cursor) {
List<String> contacts = new ArrayList<String>();
if (cursor.getCount() > 0) {
cursor.moveToFirst();
do {
String name = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
contacts.add(name);
} while (cursor.moveToNext());
}
return contacts;
}
}
and do not forget
<uses-permission android:name="android.permission.READ_CONTACTS" />
Get all contacts in less than a second and without any load in your activity.
Follow my steps works like a charm.
ArrayList<Contact> contactList = new ArrayList<>();
private static final String[] PROJECTION = new String[]{
ContactsContract.CommonDataKinds.Phone.CONTACT_ID,
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.CommonDataKinds.Phone.NUMBER
};
private void getContactList() {
ContentResolver cr = getContentResolver();
Cursor cursor = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, PROJECTION, null, null, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME + " ASC");
if (cursor != null) {
HashSet<String> mobileNoSet = new HashSet<String>();
try {
final int nameIndex = cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME);
final int numberIndex = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER);
String name, number;
while (cursor.moveToNext()) {
name = cursor.getString(nameIndex);
number = cursor.getString(numberIndex);
number = number.replace(" ", "");
if (!mobileNoSet.contains(number)) {
contactList.add(new Contact(name, number));
mobileNoSet.add(number);
Log.d("hvy", "onCreaterrView Phone Number: name = " + name
+ " No = " + number);
}
}
} finally {
cursor.close();
}
}
}
Contacts
public class Contact {
public String name;
public String phoneNumber;
public Contact() {
}
public Contact(String name, String phoneNumber ) {
this.name = name;
this.phoneNumber = phoneNumber;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPhoneNumber() {
return phoneNumber;
}
public void setPhoneNumber(String phoneNumber) {
this.phoneNumber = phoneNumber;
}
}
Benefits
less than a second
without load
ascending order
without duplicate contacts
Improving on the answer of #Adiii - It Will Cleanup The Phone Number and Remove All Duplicates
Declare a Global Variable
// Hash Maps
Map<String, String> namePhoneMap = new HashMap<String, String>();
Then Use The Function Below
private void getPhoneNumbers() {
Cursor phones = getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null, null, null, null);
// Loop Through All The Numbers
while (phones.moveToNext()) {
String name = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
String phoneNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
// Cleanup the phone number
phoneNumber = phoneNumber.replaceAll("[()\\s-]+", "");
// Enter Into Hash Map
namePhoneMap.put(phoneNumber, name);
}
// Get The Contents of Hash Map in Log
for (Map.Entry<String, String> entry : namePhoneMap.entrySet()) {
String key = entry.getKey();
Log.d(TAG, "Phone :" + key);
String value = entry.getValue();
Log.d(TAG, "Name :" + value);
}
phones.close();
}
Remember in the above example the key is phone number and value is a name so read your contents like 998xxxxx282->Mahatma Gandhi instead of Mahatma Gandhi->998xxxxx282
Cursor contacts = getContentResolver().query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);
String aNameFromContacts[] = new String[contacts.getCount()];
String aNumberFromContacts[] = new String[contacts.getCount()];
int i = 0;
int nameFieldColumnIndex = contacts.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME);
int numberFieldColumnIndex = contacts.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER);
while(contacts.moveToNext()) {
String contactName = contacts.getString(nameFieldColumnIndex);
aNameFromContacts[i] = contactName ;
String number = contacts.getString(numberFieldColumnIndex);
aNumberFromContacts[i] = number ;
i++;
}
contacts.close();
The result will be aNameFromContacts array full of contacts. Also ensure that you have added
<uses-permission android:name="android.permission.READ_CONTACTS" />
in main.xml
This is the Method to get contact list Name and Number
private void getAllContacts() {
ContentResolver contentResolver = getContentResolver();
Cursor cursor = contentResolver.query(ContactsContract.Contacts.CONTENT_URI, null, null, null, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME + " ASC");
if (cursor.getCount() > 0) {
while (cursor.moveToNext()) {
int hasPhoneNumber = Integer.parseInt(cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER)));
if (hasPhoneNumber > 0) {
String id = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts._ID));
String name = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
Cursor phoneCursor = contentResolver.query(
ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?", new String[]{id},
null);
if (phoneCursor != null) {
if (phoneCursor.moveToNext()) {
String phoneNumber = phoneCursor.getString(phoneCursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
//At here You can add phoneNUmber and Name to you listView ,ModelClass,Recyclerview
phoneCursor.close();
}
}
}
}
}
}
//GET CONTACTLIST WITH ALL FIELD...
public ArrayList < ContactItem > getReadContacts() {
ArrayList < ContactItem > contactList = new ArrayList < > ();
ContentResolver cr = getContentResolver();
Cursor mainCursor = cr.query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);
if (mainCursor != null) {
while (mainCursor.moveToNext()) {
ContactItem contactItem = new ContactItem();
String id = mainCursor.getString(mainCursor.getColumnIndex(ContactsContract.Contacts._ID));
String displayName = mainCursor.getString(mainCursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
Uri contactUri = ContentUris.withAppendedId(ContactsContract.Contacts.CONTENT_URI, Long.parseLong(id));
Uri displayPhotoUri = Uri.withAppendedPath(contactUri, ContactsContract.Contacts.Photo.DISPLAY_PHOTO);
//ADD NAME AND CONTACT PHOTO DATA...
contactItem.setDisplayName(displayName);
contactItem.setPhotoUrl(displayPhotoUri.toString());
if (Integer.parseInt(mainCursor.getString(mainCursor.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0) {
//ADD PHONE DATA...
ArrayList < PhoneContact > arrayListPhone = new ArrayList < > ();
Cursor phoneCursor = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null, ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?", new String[] {
id
}, null);
if (phoneCursor != null) {
while (phoneCursor.moveToNext()) {
PhoneContact phoneContact = new PhoneContact();
String phone = phoneCursor.getString(phoneCursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
phoneContact.setPhone(phone);
arrayListPhone.add(phoneContact);
}
}
if (phoneCursor != null) {
phoneCursor.close();
}
contactItem.setArrayListPhone(arrayListPhone);
//ADD E-MAIL DATA...
ArrayList < EmailContact > arrayListEmail = new ArrayList < > ();
Cursor emailCursor = cr.query(ContactsContract.CommonDataKinds.Email.CONTENT_URI, null, ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?", new String[] {
id
}, null);
if (emailCursor != null) {
while (emailCursor.moveToNext()) {
EmailContact emailContact = new EmailContact();
String email = emailCursor.getString(emailCursor.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));
emailContact.setEmail(email);
arrayListEmail.add(emailContact);
}
}
if (emailCursor != null) {
emailCursor.close();
}
contactItem.setArrayListEmail(arrayListEmail);
//ADD ADDRESS DATA...
ArrayList < PostalAddress > arrayListAddress = new ArrayList < > ();
Cursor addrCursor = getContentResolver().query(ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_URI, null, ContactsContract.CommonDataKinds.StructuredPostal.CONTACT_ID + " = ?", new String[] {
id
}, null);
if (addrCursor != null) {
while (addrCursor.moveToNext()) {
PostalAddress postalAddress = new PostalAddress();
String city = addrCursor.getString(addrCursor.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.CITY));
String state = addrCursor.getString(addrCursor.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.REGION));
String country = addrCursor.getString(addrCursor.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.COUNTRY));
postalAddress.setCity(city);
postalAddress.setState(state);
postalAddress.setCountry(country);
arrayListAddress.add(postalAddress);
}
}
if (addrCursor != null) {
addrCursor.close();
}
contactItem.setArrayListAddress(arrayListAddress);
}
contactList.add(contactItem);
}
}
if (mainCursor != null) {
mainCursor.close();
}
return contactList;
}
//MODEL...
public class ContactItem {
private String displayName;
private String photoUrl;
private ArrayList<PhoneContact> arrayListPhone = new ArrayList<>();
private ArrayList<EmailContact> arrayListEmail = new ArrayList<>();
private ArrayList<PostalAddress> arrayListAddress = new ArrayList<>();
public String getDisplayName() {
return displayName;
}
public void setDisplayName(String displayName) {
this.displayName = displayName;
}
public String getPhotoUrl() {
return photoUrl;
}
public void setPhotoUrl(String photoUrl) {
this.photoUrl = photoUrl;
}
public ArrayList<PhoneContact> getArrayListPhone() {
return arrayListPhone;
}
public void setArrayListPhone(ArrayList<PhoneContact> arrayListPhone) {
this.arrayListPhone = arrayListPhone;
}
public ArrayList<EmailContact> getArrayListEmail() {
return arrayListEmail;
}
public void setArrayListEmail(ArrayList<EmailContact> arrayListEmail) {
this.arrayListEmail = arrayListEmail;
}
public ArrayList<PostalAddress> getArrayListAddress() {
return arrayListAddress;
}
public void setArrayListAddress(ArrayList<PostalAddress> arrayListAddress) {
this.arrayListAddress = arrayListAddress;
}
}
public class EmailContact
{
private String email = "";
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}
public class PhoneContact
{
private String phone="";
public String getPhone()
{
return phone;
}
public void setPhone(String phone) {
this.phone = phone;
}
}
public class PostalAddress
{
private String city="";
private String state="";
private String country="";
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 getCountry() {
return country;
}
public void setCountry(String country) {
this.country = country;
}
}
//In Kotlin
private fun showContacts() {
// Check the SDK version and whether the permission is already granted or not.
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && checkSelfPermission(
requireContext(),
Manifest.permission.READ_CONTACTS
) != PackageManager.PERMISSION_GRANTED
) {
requestPermissions(
arrayOf(Manifest.permission.READ_CONTACTS),
1001
)
//After this point you wait for callback in onRequestPermissionsResult(int, String[], int[]) overriden method
} else {
// Android version is lesser than 6.0 or the permission is already granted.
getContactList()
}
}
private fun getContactList() {
val cr: ContentResolver = requireActivity().contentResolver
val cur: Cursor? = cr.query(
ContactsContract.Contacts.CONTENT_URI,
null, null, null, null
)
if ((if (cur != null) cur.getCount() else 0) > 0) {
while (cur != null && cur.moveToNext()) {
val id: String = cur.getString(
cur.getColumnIndex(ContactsContract.Contacts._ID)
)
val name: String = cur.getString(
cur.getColumnIndex(
ContactsContract.Contacts.DISPLAY_NAME
)
)
if (cur.getInt(cur.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER)) > 0) {
val pCur: Cursor? = cr.query(
ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?",
arrayOf(id),
null
)
pCur?.let {
while (pCur.moveToNext()) {
val phoneNo: String = pCur.getString(
pCur.getColumnIndex(
ContactsContract.CommonDataKinds.Phone.NUMBER
)
)
Timber.i("Name: $name")
Timber.i("Phone Number: $phoneNo")
}
pCur.close()
}
}
}
}
if (cur != null) {
cur.close()
}
}
I am using this method, and it is working perfectly.
It gets fav, picture, name, number etc. (All the details of the contact). And also it is not repetitive.
List
private static List<FavContact> contactList = new ArrayList<>();
Method to get contacts
#SuppressLint("Range")
public static void readContacts(Context context) {
if (context == null)
return;
ContentResolver contentResolver = context.getContentResolver();
if (contentResolver == null)
return;
String[] fieldListProjection = {
ContactsContract.CommonDataKinds.Phone.CONTACT_ID,
ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME_PRIMARY,
ContactsContract.CommonDataKinds.Phone.NUMBER,
ContactsContract.CommonDataKinds.Phone.NORMALIZED_NUMBER,
ContactsContract.Contacts.HAS_PHONE_NUMBER,
ContactsContract.Contacts.PHOTO_URI
,ContactsContract.Contacts.STARRED
};
String sort = ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME_PRIMARY + " ASC";
Cursor phones = contentResolver
.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI
, fieldListProjection, null, null, sort);
HashSet<String> normalizedNumbersAlreadyFound = new HashSet<>();
if (phones != null && phones.getCount() > 0) {
while (phones.moveToNext()) {
String normalizedNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
if (Integer.parseInt(phones.getString(phones.getColumnIndex(
ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0) {
if (normalizedNumbersAlreadyFound.add(normalizedNumber)) {
int id = phones.getInt(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.CONTACT_ID));
String name = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
String phoneNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
int fav = phones.getInt(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.STARRED));
boolean isFav;
isFav= fav == 1;
String uri = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.PHOTO_URI));
if(uri!=null){
contactList.add(new FavContact(id,isFav,uri,name,phoneNumber));
}
else{
contactList.add(new FavContact(id,isFav,name,phoneNumber));
}
}
}
}
phones.close();
}
}
Model Class
public class FavContact{
private int id;
private boolean isFavorite;
private String image;
private String name;
private String number;
public FavContact(int id,boolean isFavorite, String image, String name, String number){
this.id=id;
this.isFavorite = isFavorite;
this.image = image;
this.name = name;
this.number = number;
}
public FavContact(int id,boolean isFavorite, String name, String number){
this.id=id;
this.isFavorite = isFavorite;
this.name = name;
this.number = number;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public boolean isFavorite() {
return isFavorite;
}
public void setFavorite(boolean favorite) {
isFavorite = favorite;
}
public String getImage() {
return image;
}
public void setImage(String image) {
this.image = image;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
}
Adapter
public class ContactAdapter extends RecyclerView.Adapter<ContactAdapter.MyViewHolder> implements Filterable {
private final Context context;
private final List<FavContact> contactList;
private final List<FavContact> filterList;
private final OnMyOwnClickListener onMyOwnClickListener;
private final FavContactRepo favContactRepo;
public ContactAdapter(Application application,Context context, List<FavContact> contactList, OnMyOwnClickListener onMyOwnClickListener) {
this.context = context;
this.contactList = contactList;
this.onMyOwnClickListener = onMyOwnClickListener;
filterList = new ArrayList<>(contactList);
favContactRepo = new FavContactRepo(application);
}
#NonNull
#Override
public MyViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
final LayoutInflater inflater = LayoutInflater.from(context);
#SuppressLint("InflateParams") final View view = inflater.inflate(R.layout.design_fav_contact, null, false);
return new MyViewHolder(view,onMyOwnClickListener);
}
#Override
public void onBindViewHolder(#NonNull MyViewHolder holder, int position) {
final FavContact obj = contactList.get(position);
holder.tv_contact_name.setText(obj.getName());
holder.tv_contact_number.setText(obj.getNumber());
if(obj.getImage()==null){
Picasso.get().load(R.drawable.ic_circle_fav_no_dp).fit().into(holder.img_contact);
}
else{
Bitmap bp;
try {
bp = MediaStore.Images.Media
.getBitmap(context.getContentResolver(),
Uri.parse(obj.getImage()));
Glide.with(context).load(bp).centerInside().into(holder.img_contact);
} catch (IOException e) {
e.printStackTrace();
Picasso.get().load(R.drawable.ic_circle_fav_no_dp).fit().into(holder.img_contact);
}
}
obj.setFavorite(favContactRepo.checkIfFavourite(obj.getId()));
if(obj.isFavorite()){
Picasso.get().load(R.drawable.ic_menu_favorite_true).into(holder.img_fav_true_or_not);
}
else{
Picasso.get().load(R.drawable.ic_menu_favorite_false).into(holder.img_fav_true_or_not);
}
}
#Override
public int getItemCount() {
return contactList.size();
}
#Override
public long getItemId(int position) {
return position;
}
#Override
public int getItemViewType(int position) {
return position;
}
static class MyViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
CircleImageView img_contact;
TextView tv_contact_name,tv_contact_number;
ImageView img_fav_true_or_not;
ImageView img_call;
RecyclerView fav_contact_rv;
OnMyOwnClickListener onMyOwnClickListener;
public MyViewHolder(#NonNull View itemView, OnMyOwnClickListener onMyOwnClickListener) {
super(itemView);
img_contact = itemView.findViewById(R.id.img_contact);
tv_contact_name = itemView.findViewById(R.id.tv_contact_name);
img_fav_true_or_not = itemView.findViewById(R.id.img_fav_true_or_not);
tv_contact_number = itemView.findViewById(R.id.tv_contact_number);
img_call = itemView.findViewById(R.id.img_call);
fav_contact_rv = itemView.findViewById(R.id.fav_contact_rv);
this.onMyOwnClickListener = onMyOwnClickListener;
img_call.setOnClickListener(this);
img_fav_true_or_not.setOnClickListener(this);
img_contact.setOnClickListener(this);
itemView.setOnClickListener(this);
}
#Override
public void onClick(View view) {
onMyOwnClickListener.onMyOwnClick(getAbsoluteAdapterPosition(),view);
}
}
public interface OnMyOwnClickListener{
void onMyOwnClick(int position,View view);
}
#Override
public Filter getFilter() {
return filteredList;
}
public Filter filteredList = new Filter() {
#Override
protected FilterResults performFiltering(CharSequence constraint) {
List<FavContact> filteredList = new ArrayList<>();
if (constraint == null || constraint.length() == 0) {
filteredList=filterList;
} else {
String filterText = constraint.toString().toLowerCase().trim();
for (FavContact item : filterList) {
if (item.getName().toLowerCase().contains(filterText)
||item.getNumber().toLowerCase().contains(filterText)) {
filteredList.add(item);
}
}
}
FilterResults results = new FilterResults();
results.values = filteredList;
return results;
}
#SuppressLint("NotifyDataSetChanged")
#Override
protected void publishResults(CharSequence constraint, FilterResults results) {
contactList.clear();
contactList.addAll((ArrayList)results.values);
notifyDataSetChanged();
}
};