I have a code that retrieve the history of the default browser in android, lately I added the chrome browser history. But I have a problem- I get only the chrome history. E.g. if there is no chrome, I get the default browser, if there is chrome, both methods get the chrome only history.
I use this code-
String[] mProjection = {
Browser.BookmarkColumns.BOOKMARK,
BookmarkColumns.CREATED, BookmarkColumns.DATE,
BookmarkColumns.TITLE, BookmarkColumns.URL,
BookmarkColumns.VISITS,
BookmarkColumns._ID };
String mSelectionClause = "DATE > ? ";
String[] selectionArgs = {getEpochDate("DefaultBrowser")}; //"1332115200-000"
String mSortOrder = "DATE";
Cursor cr = getContentResolver().query(Browser.BOOKMARKS_URI, mProjection, mSelectionClause, selectionArgs, mSortOrder);
cr.moveToFirst();
if (cr.moveToFirst() && cr.getCount() > 0) {
while (cr.isLast() == false) {
try {
if (cr.getString(cr.getColumnIndex("BOOKMARK")).equals("0")) {
Log.d("getHistory", cr.getString(cr.getColumnIndex("TITLE")));
mc.writeDataToDB("URL", mc.ConvertFromEpoch(cr.getString(cr.getColumnIndex("DATE"))), cr.getString(cr.getColumnIndex("URL")), cr.getString(cr.getColumnIndex("TITLE")),"");
}
} catch (Exception e) {
e.printStackTrace();
}
cr.moveToNext();
}
mc.insertPref("HistoryDate", cr.getString(cr.getColumnIndex("DATE")));
}
// get google chrome history
String[] selectionArgsChrome = {getEpochDate("ChromeBrowser")};
Uri uriCustom = Uri.parse("content://com.android.chrome.browser/bookmarks");
if (getContentResolver().query(uriCustom, mProjection, mSelectionClause, selectionArgsChrome, mSortOrder) !=null){
Cursor mCur = getContentResolver().query(uriCustom, mProjection, mSelectionClause, selectionArgsChrome, mSortOrder);
mCur.moveToFirst();
String title = "";
String url = "";
String DATE = "";
if (mCur.moveToFirst() && mCur.getCount() > 0) {
boolean cont = true;
while (mCur.isAfterLast() == false && cont) {
title = mCur.getString(mCur.getColumnIndex(Browser.BookmarkColumns.TITLE));
url = mCur.getString(mCur.getColumnIndex(Browser.BookmarkColumns.URL));
DATE = mCur.getString(mCur.getColumnIndex(Browser.BookmarkColumns.DATE));
mc.writeDataToDB("URL", mc.ConvertFromEpoch(DATE), url, title,"");
mCur.moveToNext();
}
mc.insertPref("ChromeHistoryDate", cr.getString(cr.getColumnIndex("DATE")));
}}
can I get the default browser and then the chrome? I did try to change the "Browser.BOOKMARKS_URI" to uri- "content://com.android.browser/bookmarks", but it didn't worked.
any suggestions?
I suppose you're using a ContentObserver. Something like the following:
//Query values:
static final String[] projection = new String[] { BookmarkColumns.URL, BookmarkColumns.TITLE, BookmarkColumns.VISITS, BookmarkColumns.DATE };
static final String selection = Browser.BookmarkColumns.BOOKMARK + " = 0";
static final String sortOrder = Browser.BookmarkColumns.DATE;
private static class BrowserHistoryObserver extends ContentObserver {
public BrowserObserver(Handler handler) {
super(handler);
}
#Override
public void onChange(boolean selfChange) {
onChange(selfChange, null);
}
#Override
public void onChange(boolean selfChange, Uri uri) {
super.onChange(selfChange);
//Retrieve all the visited URLs:
final Cursor cursor = getContentResolver().query(Browser.BOOKMARKS_URI, projection, selection, null, sortOrder);
cursor.moveToFirst();
while ( !cursor.isAfterLast() ) {
final String url = cursor.getString(cursor.getColumnIndex(projection[0]));
final String title = cursor.getString(cursor.getColumnIndex(projection[1]));
//visits = ... (cursor.getColumnIndex(projection[2]))
//date = ... (cursor.getColumnIndex(projection[3]))
Log.d(TAG, title + " : " + url + "\n");
cursor.moveToNext();
}
//Close the cursor:
cursor.close();
}
}
And you register/unregister it with something like:
browserHistoryObserver = new BrowserHistoryObserver(new Handler());
getContentResolver().registerContentObserver(Browser.BOOKMARKS_URI, true, browserObserver);
...
getContentResolver().unregisterContentObserver(browserHistoryObserver);
The code above, of course, works for the default Android browser (indeed I've always used Browser.BOOKMARKS_URI). If you want to make it working for Google Chrome, you just need to replace Browser.BOOKMARKS_URI with Uri.parse("content://com.android.chrome.browser/bookmarks").
Note that you will have to replace it in both getContentResolver().registerContentObserver(...) and getContentResolver().query(...).
Related
I had written a code to fetch contact name, phone number and image from Contacts and to display it on a listview in android. It's working fine but taking more time to load. I had tried to use multi-threading in some parts of the code. But the loading time is not decreased.
Here is the onCreate() method:
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
lvDetail = (ListView) findViewById(R.id.listView1);
fetchcontacts();
lvDetail.setAdapter(new MyBaseAdapter(context, myList));
}
Here is the code for fetch contacts:
private void fetchcontacts() {
// TODO Auto-generated method stub
Cursor cursor = getContentResolver().query(ContactsContract.Contacts.CONTENT_URI, null,
null, null, ContactsContract.Contacts.DISPLAY_NAME + " ASC");
int count = cursor.getCount();
if (count > 0) {
Toast.makeText(context, "count >0", Toast.LENGTH_SHORT).show();
while (cursor.moveToNext()) {
String columnId = ContactsContract.Contacts._ID;
int cursorIndex = cursor.getColumnIndex(columnId);
String id = cursor.getString(cursorIndex);
name = cursor.getString(cursor
.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
Toast.makeText(context, "Toast 1", Toast.LENGTH_SHORT).show();
int numCount = Integer.parseInt(cursor.getString(cursor
.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER)));
if (numCount > 0) {
Toast.makeText(context, "Toast 2", Toast.LENGTH_SHORT).show();
Cursor phoneCursor = getContentResolver().query(
ContactsContract.CommonDataKinds.Phone.CONTENT_URI,null,
CommonDataKinds.Phone.CONTACT_ID+" = ?", new String[] { id
}, ContactsContract.Contacts.DISPLAY_NAME + " ASC");
while (phoneCursor.moveToNext()) {
Toast.makeText(context, "Toast 3", Toast.LENGTH_SHORT).show();
phoneNo = phoneCursor.getString(phoneCursor
.getColumnIndex(ContactsContract.CommonDataKinds.
Phone.NUMBER));
String image_uri = phoneCursor
.getString(phoneCursor
.getColumnIndex(ContactsContract.CommonDataKinds.Phone.PHOTO_URI));
if (image_uri != null) {
Toast.makeText(context, "Toast 4", Toast.LENGTH_SHORT).show();
System.out.println(Uri.parse(image_uri));
try {
bitmap = MediaStore.Images.Media
.getBitmap(this.getContentResolver(),
Uri.parse(image_uri));
// sb.append("\n Image in Bitmap:" + bitmap);
// System.out.println(bitmap);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
Toast.makeText(context, name, Toast.LENGTH_SHORT).show();
getDataInList(name,phoneNo,bitmap);
name=null;
phoneNo=null;
Drawable myDrawable = getResources().getDrawable(R.drawable.star1);
bitmap = ((BitmapDrawable) myDrawable).getBitmap();
}
phoneCursor.close();
}
}
}
Here the setAdapter() function of the listview is working after fetching all the contacts to an ArrayList. do anyone have idea about how to display the contacts during fetching contacts? any sample code?
1.Read the Columns from the Cursor which you required only ,According to your requirement you just need _ID,HAS_PHONE_NUMBER,DISPLAY_NAME ,so change the Cursor reading
Cursor cursor = getContentResolver().query(
ContactsContract.Contacts.CONTENT_URI,
new String[] { ContactsContract.Contacts._ID,
ContactsContract.Contacts.HAS_PHONE_NUMBER,
ContactsContract.Contacts.DISPLAY_NAME }, null, null,
ContactsContract.Contacts.DISPLAY_NAME + " ASC");
2.Dont do the time taking process in the UI thread..Use AsyncTask instead
Note : This two steps will resolve to some extent..but not completely
I made it by reduce repeated query wich is expensive. Best of my solution is that method found all mobile phones and email for each contact and insert to list for every contact values. It is fast as storm now :)
//contact entity
public class MobileContact {
public String name;
public String contact;
public Type type;
public MobileContact(String contact, Type type) {
name = "";
this.contact = contact;
this.type = type;
}
public MobileContact(String name, String contact, Type type) {
this.name = name;
this.contact = contact;
this.type = type;
}
public enum Type {
EMAIL, PHONE
}
#Override
public String toString() {
return "MobileContact{" +
"name='" + name + '\'' +
", contact='" + contact + '\'' +
", type=" + type +
'}';
}
}
// method for collect contacts
public List<MobileContact> getAllContacts() {
log.debug("get all contacts");
List<MobileContact> mobileContacts = new ArrayList<>();
ContentResolver contentResolver = context.getContentResolver();
// add all mobiles contact
Cursor phonesCursor = contentResolver.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, new String[]{ContactsContract.CommonDataKinds.Phone.NUMBER, ContactsContract.CommonDataKinds.Phone.CONTACT_ID}, null, null, null);
while (phonesCursor != null && phonesCursor.moveToNext()) {
String contactId = phonesCursor.getString(phonesCursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.CONTACT_ID));
String phoneNumber = phonesCursor.getString(phonesCursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER)).replace(" ", "");
mobileContacts.add(new MobileContact(contactId, phoneNumber, MobileContact.Type.PHONE));
}
if (phonesCursor != null) {
phonesCursor.close();
}
// add all email contact
Cursor emailCursor = contentResolver.query(ContactsContract.CommonDataKinds.Email.CONTENT_URI, new String[]{ContactsContract.CommonDataKinds.Email.DATA, ContactsContract.CommonDataKinds.Email.CONTACT_ID}, null, null, null);
while (emailCursor != null && emailCursor.moveToNext()) {
String contactId = emailCursor.getString(emailCursor.getColumnIndex(ContactsContract.CommonDataKinds.Email.CONTACT_ID));
String email = emailCursor.getString(emailCursor.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));
mobileContacts.add(new MobileContact(contactId, email, MobileContact.Type.EMAIL));
}
if (emailCursor != null) {
emailCursor.close();
}
// get contact name map
Map<String, String> contactMap = new HashMap<>();
Cursor contactsCursor = contentResolver.query(ContactsContract.Contacts.CONTENT_URI, new String[]{ContactsContract.Contacts._ID, ContactsContract.Contacts.DISPLAY_NAME, ContactsContract.Contacts.HAS_PHONE_NUMBER}, null, null, ContactsContract.Contacts.DISPLAY_NAME);
while (contactsCursor != null && contactsCursor.moveToNext()) {
String contactId = contactsCursor.getString(contactsCursor.getColumnIndex(ContactsContract.Contacts._ID));
String contactName = contactsCursor.getString(contactsCursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
contactMap.put(contactId, contactName);
}
if (phonesCursor != null) {
phonesCursor.close();
}
// replace contactId to display name
for (MobileContact mobileContact : mobileContacts) {
String displayName = contactMap.get(mobileContact.name);
mobileContact.name = displayName != null ? displayName : "";
}
// sort list by name
Collections.sort(mobileContacts, new Comparator<MobileContact>() {
#Override
public int compare(MobileContact c1, MobileContact c2) {
return c1.name.compareTo(c2.name);
}
});
return mobileContacts;
}
The contacts in larse size use in backround task.
Uri uri = Uri.withAppendedPath(ContactsContract.PhoneLookup.CONTENT_FILTER_URI, Uri.encode(number[i]));
ContentResolver contentResolver = getContentResolver();
Cursor search = contentResolver.query(uri, new String[]{ContactsContract.PhoneLookup._ID,
ContactsContract.PhoneLookup.DISPLAY_NAME}, null, null, null);
try {
if (search != null && search.getCount() > 0) {
search.moveToNext();
name = search.getString(search.getColumnIndex(ContactsContract.Data.DISPLAY_NAME));
id = search.getString(search.getColumnIndex(ContactsContract.Data._ID));
System.out.println("name" + name + "id" + id);
/* tv_name.setText(name);
tv_id.setText(id);
tv_phone.setText(number);*/
}
} finally {
if (search != null) {
search.close();
}
}
Fastest way for me soo far .
ContentResolver cr = mContext.getContentResolver(); Cursor cursor= mContext.getContentResolver().query(ContactsContract.Contacts.CONTENT_URI, PROJECTION, "HAS_PHONE_NUMBER <> 0", null, null); if (cursor!= null) { final int displayNameIndex = cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME); final int numberIndex = cursor.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER); final int idIndex= cursor.getColumnIndex(ContactsContract.Contacts._ID); String displayName, number = null, idValue; while (cursor.moveToNext()) {
displayName = cursor.getString(displayNameIndex);
idValue= cursor.getString(idIndex);
Cursor phones = mContext.getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null, "contact_id = '" + idValue + "'", null, null);
phones.moveToFirst();
try {
number = phones.getString(phones.getColumnIndex("data1"));
}
catch (CursorIndexOutOfBoundsException e)
{`
}
phones.close();
userList.add(new ContactModel(displayName , number , null , }
EDIT:A list of what I consider important contact details:
1.NAME
2.PHONE NUMBER
3.EMAIL ADDRESS
4.WEBSITE
5.PHYSICAL ADDRESS
I would prefer to do this using a pre-fetched contactId...using only one cursor to get all of the data specified.I,preferably would like to find the right query to do this:
I would like to get all of the important details of a Contact at once,I am using the following code to do this:
public void getAllDataByContactId(int contactId)
{
Log.d(TAG, "Seriously scared it might not work");
String phoneNo="Phone disconnected";
String email="Email could not be delivered";
String website="Website 404";
String address="Number 13,Dark Street,Area 51,Bermuda Trianlge";
String name="Clint Eastwood";
int hasPhoneNumber;
String selection=ContactsContract.Data.CONTACT_ID+"=?";
String[] selectionArgs={String.valueOf(contactId)};
Cursor c=context.getContentResolver().query(ContactsContract.Data.CONTENT_URI, null,selection, selectionArgs,ContactsContract.Data.TIMES_CONTACTED);
if(c!=null && c.getCount()>0)
{
while(c.moveToNext())
{
phoneNo=c.getString(c.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
Log.d(TAG, "Phone number: "+phoneNo);
email=c.getString(c.getColumnIndex(ContactsContract.CommonDataKinds.Email.ADDRESS));
Log.d(TAG, "Email: "+email);
website=c.getString(c.getColumnIndex(ContactsContract.CommonDataKinds.Website.URL));
Log.d(TAG, "Website :"+website);
address=c.getString(c.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.FORMATTED_ADDRESS));
name=c.getString(c.getColumnIndex(ContactsContract.CommonDataKinds.StructuredName.DISPLAY_NAME));
Log.d(TAG, "Name :"+name);
}
}
}
However,although this does not throw an error it shows many rows consisting of an empty string interspresed with the actual values.How do I write a query that cuts out the noise?
I have tried this and this gets me all the values:
String selection=ContactsContract.Data.CONTACT_ID+"=? AND "+ContactsContract.Data.MIMETYPE+"=? OR "+ContactsContract.Data.MIMETYPE+"=? OR "+ContactsContract.Data.MIMETYPE+"=? OR "+ContactsContract.Data.MIMETYPE+"=? OR "+ContactsContract.Data.MIMETYPE+"=?";
String[] selectionArgs={String.valueOf(contactId),ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE,ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE,ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE,ContactsContract.CommonDataKinds.Website.CONTENT_ITEM_TYPE,ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_ITEM_TYPE};
Too late to answer, but maybe it can help someone in the future.
My solution for this question with only one while cycle and query:
private void fetchContacts(ContentResolver contentResolver) {
if (contentResolver == null) return;
Cursor cursor = contentResolver.query(ContactsContract.Data.CONTENT_URI,
null, null, null, null);
if (cursor == null || cursor.getCount() <= 0) {
return;
}
String prevId = "";
String contactId = "";
PersonContact personContact = null;
while (cursor.moveToNext()) {
String company = "";
String columnName = cursor.getString(cursor.getColumnIndex("mimetype"));
if (columnName.equals(ContactsContract.CommonDataKinds.Organization.CONTENT_ITEM_TYPE)) {
company = cursor.getString(cursor.getColumnIndex("data1"));
}
String email = "";
if (columnName.equals(ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE)) {
email = cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));
}
String phone = "";
if (columnName.equals(ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE)) {
phone = cursor.getString(cursor.getColumnIndex("data1"));
}
String first = "";
String last = "";
if (columnName.equals(ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)) {
first = cursor.getString(cursor.getColumnIndex("data2"));
last = cursor.getString(cursor.getColumnIndex("data3"));
}
if (!prevId.equals(contactId)) {
if (!TextUtils.isEmpty(prevId)) {
addFilteredList(personContact);
allContacts.put(prevId, personContact);
}
prevId = contactId;
personContact = new PersonContact();
} else {
if (personContact != null) {
personContact.id = prevId;
if (TextUtils.isEmpty(personContact.company)) personContact.company = company;
if (TextUtils.isEmpty(personContact.firstName)) personContact.firstName = first;
if (TextUtils.isEmpty(personContact.lastName)) personContact.lastName = last;
if (!TextUtils.isEmpty(email) && personContact.emails.size() == 0) {
personContact.emails.add(email);
}
if (!TextUtils.isEmpty(phone) && personContact.phoneNumbers.size() == 0) {
personContact.phoneNumbers.add(phone);
}
}
}
contactId = cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.CONTACT_ID));
}
cursor.close();
}
As you can see, I used the prevId field, because cursor.moveToNext performs several times for one contact (once for first and last names, one for phone, etc.). After each iteration, I check the previous contact identifier with the current identifier and, if it is false, I update the fields in the personContact model.
May not be the best solution. But this is how I achieved it.
ArrayList<String> fnameList = new ArrayList<>();
ArrayList<String> lnameList = new ArrayList<>();
ArrayList<String> mnumList = new ArrayList<>();
ArrayList<String> hnumList = new ArrayList<>();
ArrayList<String> wnumList = new ArrayList<>();
ArrayList<String> mailList = new ArrayList<>();
final DynamoDBMapper dynamoDBMapper = AWSMobileClient.defaultMobileClient().getDynamoDBMapper();
final ContactsDO firstItem = new ContactsDO(); // Initialize the Notes Object
firstItem.setUserId(AWSMobileClient.defaultMobileClient().getIdentityManager().getCachedUserID());
String email = null;
Uri CONTENT_URI = ContactsContract.Contacts.CONTENT_URI;
String _ID = ContactsContract.Contacts._ID;
String HAS_PHONE_NUMBER = ContactsContract.Contacts.HAS_PHONE_NUMBER;
Uri EmailCONTENT_URI = ContactsContract.CommonDataKinds.Email.CONTENT_URI;
String EmailCONTACT_ID = ContactsContract.CommonDataKinds.Email.CONTACT_ID;
String DATA = ContactsContract.CommonDataKinds.Email.DATA;
StringBuffer output = new StringBuffer();
ContentResolver contentResolver = this.getContentResolver();
Cursor cursor = contentResolver.query(CONTENT_URI, null, null, null, null);
// Loop for every contact in the phone
if (cursor.getCount() > 0) {
while (cursor.moveToNext()) {
int hasPhoneNumber = Integer.parseInt(cursor.getString(cursor.getColumnIndex(HAS_PHONE_NUMBER)));
if (hasPhoneNumber > 0) {
String contact_id = cursor.getString(cursor.getColumnIndex(_ID));
// Query and loop for every phone number of the contact
Cursor pCur = contentResolver.query(
ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID + " = ?",
new String[]{contact_id}, ContactsContract.CommonDataKinds.Phone.NUMBER);
int flag = 0;
assert pCur != null;
while (pCur.moveToNext()) {
String mobileNum = pCur.getString(pCur.getColumnIndex(
ContactsContract.CommonDataKinds.Phone.NUMBER));
if (flag == 0) {
if(mobileNum!=null){
mnumList.add(mobileNum);}
} else if (flag == 1) {
if(mobileNum!=null){
hnumList.add(mobileNum);}
} else if (flag == 2) {
if(mobileNum!=null){
wnumList.add(mobileNum);}
}
flag++;
}
if(flag==1){
hnumList.add("");
wnumList.add("");
Log.e("Set","Both added");
}
if(flag==2){
wnumList.add("");
Log.e("Set","W added");
}
pCur.close();
}
}
}
cursor.close();
String MIME = ContactsContract.Data.MIMETYPE + "=?";
String[] params = new String[]{ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE};
final Cursor nameCur = contentResolver.query(
ContactsContract.Data.CONTENT_URI,
null,
MIME,
params,
ContactsContract.CommonDataKinds.StructuredName.DISPLAY_NAME);
assert nameCur != null;
int i = 0;
while (nameCur.moveToNext()){
String fname = "";
String lname = "";
fname = nameCur.getString(nameCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredName.GIVEN_NAME));
lname = nameCur.getString(nameCur.getColumnIndex(ContactsContract.CommonDataKinds.StructuredName.FAMILY_NAME));
Log.e("In While","All the time");
if(fname!=null){
fnameList.add(fname);
Log.e("Put","Value Fname "+fname);}
if(lname!=null) {
lnameList.add(lname);
Log.e("Put","Value Lname "+lname);
}
if(fname==null){
fnameList.add(" ");
}
if(lname==null){
lnameList.add(" ");
}
i++;
}
nameCur.close();
Cursor cursorB = contentResolver.query(CONTENT_URI, null, null, null, null);
// Loop for every contact in the phone
if (cursorB.getCount() > 0) {
while (cursorB.moveToNext()) {
// Query and loop for every email of the contact
String[] paramEmail = new String[]{ContactsContract.CommonDataKinds.Email.CONTENT_TYPE};
Cursor emailCursor = contentResolver.query(EmailCONTENT_URI, null, ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?", paramEmail, ContactsContract.CommonDataKinds.Email.DISPLAY_NAME);
int j=0;
while (emailCursor.moveToNext()) {
email = emailCursor.getString(emailCursor.getColumnIndex(ContactsContract.CommonDataKinds.Email.ADDRESS));
mailList.add(email);
Log.e("Email",email);
j++;
}
if(j==0){
mailList.add("");
Log.e("Email","Dummy Added");
}
emailCursor.close();
output.append("\n");
}
}cursorB.close();
Cursor cursorD = contentResolver.query(CONTENT_URI, null, null, null, null);
// Loop for every contact in the phone
if (cursorD.getCount() > 0) {
while (cursorD.moveToNext()) {
String contact_id = cursorD.getString(cursorD.getColumnIndex(_ID));
//for url
String newNoteUrl = "";
String whereName3 = ContactsContract.Data.MIMETYPE + " = ?";
String[] whereNameParams3 = new String[]{ContactsContract.CommonDataKinds.Website.CONTENT_ITEM_TYPE};
ContentResolver contentResolverUrl = this.getContentResolver();
try {
Cursor cursorUrl = contentResolverUrl.query(ContactsContract.Data.CONTENT_URI, null, whereName3, new String[]{contact_id}, ContactsContract.CommonDataKinds.Website.URL);
while (cursorUrl.moveToNext()) {
newNoteUrl = cursorUrl.getString(cursorUrl.getColumnIndex(ContactsContract.CommonDataKinds.Website.URL));
Log.e("URL",newNoteUrl);
}
Log.e("URL","Not Getting");
output.append("\nurl " + newNoteUrl);
firstItem.setUrl(newNoteUrl);
cursorUrl.close();
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}}cursorD.close();
Log.e("#######","##########################");
for(int m=0;m<fnameList.size();m++){
Log.e("Contact Val ",fnameList.get(m)+" , "+lnameList.get(m)+" , "+mnumList.get(m)+" , "+hnumList.get(m)+" , "+wnumList.get(m)+" , "+mailList.get(m));
ContactsDO item = new ContactsDO();
item.setUserId(AWSMobileClient.defaultMobileClient().getIdentityManager().getCachedUserID());
item.setFirstName(fnameList.get(m));
item.setLastName(lnameList.get(m));
item.setMobileNumber(mnumList.get(m));
item.setHomeNumber(hnumList.get(m));
item.setWorkNumber(wnumList.get(m));
item.setEmail(mailList.get(m));
try {
//saving to the database
dynamoDBMapper.save(item);
} catch (final AmazonClientException ex) {
Log.e(TAG, "Failed saving item : " + ex.getMessage(), ex);
}
}
In my project getting contacts is taking a long time to load.
What are ways to reduce the time of getting contacts
Assume there are 1000 contacts in my phone.
Right now it is taking more than 2 minutes to load all the contacts
How can I reduce the time to load contacts ?
Any Thoughts?
I referred to the the following link when programming the initial method.
http://www.coderzheaven.com/2011/06/13/get-all-details-from-contacts-in-android/
BETTER SOLUTION HERE.....
private static final String[] PROJECTION = new String[] {
ContactsContract.CommonDataKinds.Phone.CONTACT_ID,
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.CommonDataKinds.Phone.NUMBER
};
.
.
.
ContentResolver cr = getContentResolver();
Cursor cursor = cr.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, PROJECTION, null, null, null);
if (cursor != null) {
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);
}
} finally {
cursor.close();
}
}
CHEERS...:)
Total time will depend upon what fields you are trying to access from the Contacts table.
Accessing less field means less looping , less processing and hence faster results.
Also to speed up your contacts fetch operation you can use the ContentProvideClient instead of calling query on ContentResolver every time. This will make you query the specific table rather than querying first for the required ContentProvider and then to table.
Create an instance of ContentProviderClient
ContentResolver cResolver=context.getContextResolver();
ContentProviderClient mCProviderClient = cResolver.acquireContentProviderClient(ContactsContract.Contacts.CONTENT_URI);
Then reuse this mCProviderClient to get Contacts(data from any ContentProvider) data on your call.
For example in following method, I am accessing only one field.
private ArrayList<String> fetchContactsCProviderClient()
{
ArrayList<String> mContactList = null;
try
{
Cursor mCursor = mCProviderClient.query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);
if (mCursor != null && mCursor.getCount() > 0)
{
mContactList = new ArrayList<String>();
mCursor.moveToFirst();
while (!mCursor.isLast())
{
String displayName = mCursor.getString(mCursor.getColumnIndexOrThrow(ContactsContract.Contacts.DISPLAY_NAME));
mContactList.add(displayName);
mCursor.moveToNext();
}
if (mCursor.isLast())
{
String displayName = mCursor.getString(mCursor.getColumnIndexOrThrow(ContactsContract.Contacts.DISPLAY_NAME));
mContactList.add(displayName);
}
}
mCursor.close();
}
catch (RemoteException e)
{
e.printStackTrace();
mContactList = null;
}
catch (Exception e)
{
e.printStackTrace();
mContactList = null;
}
return mContactList;
}
Load Contact faster like other apps doing.
I have tested this code with multiple contacts its working fine and faster like other apps within 500 ms (within half second or less) I am able to load 1000+ contacts.
Total time will depend upon what fields you are trying to access from the Contacts table.
Mange your query according to your requirement do not access unwanted fields. Accessing less field means less looping , less processing and hence faster results.
Accessing right table in contact it also help to reduce contact loading time.
Query Optimization to load contact more faster use projection
String[] projection = {
ContactsContract.Data.MIMETYPE,
ContactsContract.Data.CONTACT_ID,
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.Contacts.PHOTO_URI,
ContactsContract.Contacts.STARRED,
ContactsContract.RawContacts.ACCOUNT_TYPE,
ContactsContract.CommonDataKinds.Contactables.DATA,
ContactsContract.CommonDataKinds.Contactables.TYPE
};
Selection and selection argument
String selection = ContactsContract.Data.MIMETYPE + " in (?, ?)" + " AND " /*+ ContactsContract.Contacts.IN_VISIBLE_GROUP + " = '" + 1 + "' AND "*/ +
ContactsContract.Data.HAS_PHONE_NUMBER + " = '" + 1 + "'";
String[] selectionArgs = {
ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE,
ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE,
};
To order contacts alphabetically use following code
try {
Collections.sort(listview_address, new Comparator<ContactBook>() {
#Override
public int compare(ContactBook lhs, ContactBook rhs) {
return lhs.name.toUpperCase().compareTo(rhs.name.toUpperCase());
}
});
} catch (Exception e) {
e.printStackTrace();
}
Following is complete source code
public void initeContacts() {
List<ContactBook> listview_address = new LinkedList<ContactBook>();
SparseArray<ContactBook> addressbook_array = null;
{
addressbook_array = new SparseArray<ContactBook>();
long start = System.currentTimeMillis();
String[] projection = {
ContactsContract.Data.MIMETYPE,
ContactsContract.Data.CONTACT_ID,
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.Contacts.PHOTO_URI,
ContactsContract.Contacts.STARRED,
ContactsContract.RawContacts.ACCOUNT_TYPE,
ContactsContract.CommonDataKinds.Contactables.DATA,
ContactsContract.CommonDataKinds.Contactables.TYPE
};
String selection = ContactsContract.Data.MIMETYPE + " in (?, ?)" + " AND " /*+ ContactsContract.Contacts.IN_VISIBLE_GROUP + " = '" + 1 + "' AND "*/ +
ContactsContract.Data.HAS_PHONE_NUMBER + " = '" + 1 + "'";
String[] selectionArgs = {
ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE,
ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE,
};
String sortOrder = ContactsContract.Contacts.SORT_KEY_ALTERNATIVE;
Uri uri = null;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR2) {
uri = ContactsContract.CommonDataKinds.Contactables.CONTENT_URI;
} else {
uri = ContactsContract.Data.CONTENT_URI;
}
// we could also use Uri uri = ContactsContract.Data.CONTENT_URI;
// we could also use Uri uri = ContactsContract.Contact.CONTENT_URI;
Cursor cursor = getActivity().getContentResolver().query(uri, projection, selection, selectionArgs, sortOrder);
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 photo = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Contactables.PHOTO_URI);
final int typeIdx = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Contactables.TYPE);
final int account_type = cursor.getColumnIndex(ContactsContract.RawContacts.ACCOUNT_TYPE);
while (cursor.moveToNext()) {
int contact_id = cursor.getInt(idIdx);
String photo_uri = cursor.getString(photo);
String contact_name = cursor.getString(nameIdx);
String contact_acc_type = cursor.getString(account_type);
int contact_type = cursor.getInt(typeIdx);
String contact_data = cursor.getString(dataIdx);
ContactBook contactBook = addressbook_array.get(contact_id);
/* if (contactBook == null) {
//list contact add to avoid duplication
//load All contacts fro device
//to add contacts number with name add one extra veriable in ContactBook as number and pass contact_data this give number to you (contact_data is PHONE NUMBER)
contactBook = new ContactBook(contact_id, contact_name, getResources(), photo_uri, contact_acc_type, "phone number");
addressbook_array.put(contact_id, contactBook);
listview_address.add(contactBook);
}*/
String Contact_mimeType = cursor.getString(mimeTypeIdx);
//here am checking Contact_mimeType to get mobile number asociated with perticular contact and email adderess asociated
if (Contact_mimeType.equals(ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE)) {
if (contactBook != null) {
contactBook.addEmail(contact_type, contact_data);
}
} else {
if (contactBook == null) {
//list contact add to avoid duplication
//load All contacts fro device
//to add contacts number with name add one extra veriable in ContactBook as number and pass contact_data this give number to you (contact_data is PHONE NUMBER)
contactBook = new ContactBook(contact_id, contact_name, getResources(), photo_uri, contact_acc_type, "phone number");
addressbook_array.put(contact_id, contactBook);
listview_address.add(contactBook);
}
// contactBook.addPhone(contact_type, contact_data);
}
}
cursor.close();
try {
Collections.sort(listview_address, new Comparator<ContactBook>() {
#Override
public int compare(ContactBook lhs, ContactBook rhs) {
return lhs.name.toUpperCase().compareTo(rhs.name.toUpperCase());
}
});
} catch (Exception e) {
e.printStackTrace();
}
}
You can use following code in above code that I have commented .It club the the single contact with its multiple number.To get all number associated with single contact use array in Object class.
if (contactBook == null) {
//irst contact add to avoid duplication
//load All contacts fro device
contactBook = new ContactBook(contact_id, contact_name, getResources(), photo_uri, contact_acc_type, "");
addressbook_array.put(contact_id, contactBook);
listview_address.add(contactBook);
}
String Contact_mimeType = cursor.getString(mimeTypeIdx);
//here am checking Contact_mimeType to get mobile number asociated with perticular contact and email adderess asociated
if (Contact_mimeType.equals(ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE)) {
contactBook.addEmail(contact_type, contact_data);
} else {
contactBook.addPhone(contact_type, contact_data);
}
Object class
public class ContactBook {
public int id;
public Resources res;
public String name;
public String photo;
public String contact_acc_type;
public SparseArray<String> emails;
public SparseArray<String> phones;
/* public LongSparseArray<String> emails;
public LongSparseArray<String> phones;*/
public String header = "";
public ContactBook(int id, String name, Resources res, String photo, String contact_acc_type, String header) {
this.id = id;
this.name = name;
this.res = res;
this.photo = photo;
this.contact_acc_type = contact_acc_type;
this.header = header;
}
#Override
public String toString() {
return toString(false);
}
public String toString(boolean rich) {
//testing method to check ddata
SpannableStringBuilder builder = new SpannableStringBuilder();
if (rich) {
builder.append("id: ").append(Long.toString(id))
.append(", name: ").append("\u001b[1m").append(name).append("\u001b[0m");
} else {
builder.append(name);
}
if (phones != null) {
builder.append("\n\tphones: ");
for (int i = 0; i < phones.size(); i++) {
int type = (int) phones.keyAt(i);
builder.append(ContactsContract.CommonDataKinds.Phone.getTypeLabel(res, type, ""))
.append(": ")
.append(phones.valueAt(i));
if (i + 1 < phones.size()) {
builder.append(", ");
}
}
}
if (emails != null) {
builder.append("\n\temails: ");
for (int i = 0; i < emails.size(); i++) {
int type = (int) emails.keyAt(i);
builder.append(ContactsContract.CommonDataKinds.Email.getTypeLabel(res, type, ""))
.append(": ")
.append(emails.valueAt(i));
if (i + 1 < emails.size()) {
builder.append(", ");
}
}
}
return builder.toString();
}
public void addEmail(int type, String address) {
//this is the array in object class where i am storing contact all emails of perticular contact (single)
if (emails == null) {
// if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
emails = new SparseArray<String>();
emails.put(type, address);
/*} else {
//add emails to array below Jelly bean //use single array list
}*/
}
}
public void addPhone(int type, String number) {
//this is the array in object class where i am storing contact numbers of perticular contact
if (phones == null) {
// if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
phones = new SparseArray<String>();
phones.put(type, number);
/* } else {
//add emails to array below Jelly bean //use single array list
}*/
}
}}
For loading the contacts with mininum time the optimum solution is to use the concept of projection and selection argument while querying the cursor for contacts.
this can be done in following way
void getAllContacts() {
long startnow;
long endnow;
startnow = android.os.SystemClock.uptimeMillis();
ArrayList arrContacts = new ArrayList();
Uri uri = ContactsContract.CommonDataKinds.Phone.CONTENT_URI;
String selection = ContactsContract.Contacts.HAS_PHONE_NUMBER;
Cursor cursor = ctx.getContentResolver().query(uri, new String[]{ContactsContract.CommonDataKinds.Phone.NUMBER, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME, ContactsContract.CommonDataKinds.Phone._ID, ContactsContract.Contacts._ID}, selection, null, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME + " ASC");
cursor.moveToFirst();
while (cursor.isAfterLast() == false) {
String contactNumber = cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
String contactName = cursor.getString(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
int phoneContactID = cursor.getInt(cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone._ID));
int contactID = cursor.getInt(cursor.getColumnIndex(ContactsContract.Contacts._ID));
Log.d("con ", "name " + contactName + " " + " PhoeContactID " + phoneContactID + " ContactID " + contactID)
cursor.moveToNext();
}
cursor.close();
cursor = null;
endnow = android.os.SystemClock.uptimeMillis();
Log.d("END", "TimeForContacts " + (endnow - startnow) + " ms");
}
With above method it took 400ms(less than second) to load contacts where as in normall way it was taking 10-12 sec.
For details imformation this post might help as i took help from it
http://www.blazin.in/2016/02/loading-contacts-fast-from-android.html
If your time increases with your data, then you are probably running a new query to fetch phones/emails for every contact. If you query for the phone/email field using ContactsContract.CommonDataKinds.Phone.NUMBER, then you will just retrieve 1 phone per contact.
The solution is to project the fields and join them by contact id.
Here is my solution in Kotlin (extracting id, name, all phones and emails):
val projection = arrayOf(
ContactsContract.Data.MIMETYPE,
ContactsContract.Data.CONTACT_ID,
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.CommonDataKinds.Contactables.DATA
)
val selection = "${ContactsContract.Data.MIMETYPE} in (?, ?)"
val selectionArgs = arrayOf(
ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE,
ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE)
val contacts = applicationContext
.contentResolver
.query(ContactsContract.Data.CONTENT_URI, projection, selection, selectionArgs, null)
.run {
if (this == null) {
throw IllegalStateException("Cursor null")
}
val contactsById = mutableMapOf<String, LocalContact>()
val mimeTypeField = getColumnIndex(ContactsContract.Data.MIMETYPE)
val idField = getColumnIndex(ContactsContract.Data.CONTACT_ID)
val nameField = getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME)
val dataField = getColumnIndex(ContactsContract.CommonDataKinds.Contactables.DATA)
while (moveToNext()) {
val mimeType = getString(mimeTypeField)
val id = getString(idField)
var contact = contactsById[id]
if (contact == null) {
val name = getString(nameField)
contact = LocalContact(id = id, fullName = name, phoneNumbers = listOf(), emailAddresses = listOf())
}
val data = getString(dataField)
when(getString(mimeTypeField)) {
ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE ->
contact = contact.copy(emailAddresses = contact.emailAddresses + data)
ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE ->
contact = contact.copy(phoneNumbers = contact.phoneNumbers + data)
}
contactsById[id] = contact
}
close()
contactsById.values.toList()
}
And for reference, my LocalContact model:
data class LocalContact(
val id: String,
val fullName: String?,
val phoneNumbers: List<String>,
val emailAddresses: List<String>
)
I think this is a better solution:
public ContentValues getAllContacts() {
ContentValues contacts = new ContentValues();
ContentResolver cr = getContentResolver();
Cursor cur = cr.query(ContactsContract.Contacts.CONTENT_URI, null, null, null, null);
if (cur != null && 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 (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);
if (pCur != null) {
while (pCur.moveToNext()) {
String phoneNo = pCur.getString(pCur.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
contacts.put(phoneNo, name);
}
pCur.close();
}
}
}
cur.close();
}
return contacts;
}
for use it you need to call this lines once:
ContentValues contacts = new ContentValues();
contacts = getAllContacts();
and when you want to get contact name by number, just use:
String number = "12345";
String name = (String) G.contacts.get(number);
this algorithm is a bit faster...
I am trying to get my search values from the android browser with following code:
public void getBrowserHist() {
String[] mColumnStrings =
{ Browser.SearchColumns._ID,
Browser.SearchColumns.SEARCH,
Browser.SearchColumns.DATE
};
Cursor mCur = getContentResolver().query(Browser.SEARCHES_URI,
mColumnStrings, Browser.SearchColumns.SEARCH, null, null);
int url = mCur.getColumnIndex(Browser.SearchColumns.SEARCH);
Log.d(DEBUG_TAG, "Bookmarks count: " + mCur.getCount());
mCur.moveToFirst();
while (!mCur.isAfterLast()) {
Log.v("titleIdx", mCur.getString(url));
mCur.moveToNext();
}
}
The problem is that search result is empty. the mcur.getCount() method returns 0, and I donĀ“t now why. Does anyone have any suggestion?
Cursor cursor = this.context.getContentResolver().query(Browser.SEARCHES_URI, null, null, null, null);
if (cursor.moveToFirst()) {
while (!cursor.isAfterLast()) {
final int indexDate = cursor.getColumnIndex(Browser.SearchColumns.DATE);
final int indexTerm = cursor.getColumnIndex(Browser.SearchColumns.SEARCH);
String date = cursor.getString(indexDate);
String term = cursor.getString(indexTerm);
cursor.moveToNext();
}
}
cursor.close();
I am trying to get the address of the sender but I run into a little problem. If the person that sends the message is the first person in any of the conversations to send one, the query of the content://mms/inbox returns with zero rows?? but when someone sends any other mms message it will return back with the _id fine and i dont understand why the first one wont work right?
private String checkMmsMessages(Context context){
String address = "address";
Cursor curPdu = context.getContentResolver ().query(Uri.parse("content://mms/inbox"), null, null, null, null);
if(curPdu.moveToNext()){ //first MMS message curPdu.moveToNext() is false
String id = curPdu.getString (curPdu.getColumnIndex ("_id"));
Log.v("MMS", "ID1: " + id.toString());
Uri uriAddr = Uri.parse ("content://mms/" + id + "/addr");
Cursor curAddr = context.getContentResolver().query(uriAddr,null,"type=137",null,null);
if(curAddr.moveToNext()){
address = curAddr.getString (curAddr.getColumnIndex ("address"));
Log.v("MMS", "Address1: " + address.toString());
if(address.contentEquals("insert-address-token")){
Cursor curAddr2 = context.getContentResolver().query(uriAddr,null,"type=151", null,null);
if(curAddr2.moveToNext()){
address = curAddr2.getString(curAddr2.getColumnIndex("address"));
}
}
}
}
Log.v("MMS", address.toString());
return address;
}
Also something else that does not make sense is when when i have the phone plugged into the computer and step through the that section with the debugger, that problem does not happen and it gets the address every time.... it only happens when the phone is not connected, i just dont understand?
The problem was I was checking the database before the message was put into the database so I had to put a delay on the check
I think the issue is you are passing a value for selectionArgs instead of null to the query() method. I am not actually calling the mCursor's moveToNext() method in my code but instead I am implementing this logic in the getView() method of a SimpleCursorAdapter.
Uri uri = Uri.parse("content://mms-sms/conversations/" + mThreadId);
String[] projection = new String[] { "body", "person", "sub",
"subject", "retr_st", "type", "date", "ct_cls", "sub_cs",
"_id", "read", "ct_l", "st", "msg_box", "reply_path_present",
"m_cls", "read_status", "ct_t", "status", "retr_txt_cs",
"d_rpt", "error_code", "m_id", "date_sent", "m_type", "v",
"exp", "pri", "service_center", "address", "rr", "rpt_a",
"resp_txt", "locked", "resp_st", "m_size" };
String sortOrder = "normalized_date";
Cursor mCursor = getActivity().getContentResolver().query(uri,projection, null, null, sortOrder);
String messageAddress;
int type;
while (mCursor.moveToNext()) {
String messageId = mCursor.getString(mCursor.getColumnIndex("_id"));
Uri.Builder builder = Uri.parse("content://mms").buildUpon();
builder.appendPath(messageId).appendPath("addr");
Cursor c = mContext.getContentResolver().query(builder.build(), new String[] {
"*"
}, null, null, null);
while (c.moveToNext()) {
messageAddress = c.getString(c.getColumnIndex("address"));
if (!messageAddress.equals("insert-address-token")) {
type = c.getInt(c.getColumnIndex("type"));
c.moveToLast();
}
}
c.close();
}
try this...
private String getAddressNumber(String id) {
String selectionAdd = new String("msg_id=" + id);
String uriStr = MessageFormat.format("content://mms/{0}/addr", id);
Uri uriAddress = Uri.parse(uriStr);
Cursor cursor = getContentResolver().query(uriAddress, null, selectionAdd, null, null);
String phoneNum = null;
if (cursor.moveToFirst()) {
do {
String number = cursor.getString(cursor.getColumnIndex("address"));
if (number != null) {
boolean isNumberFormat = true;
try {
Long.parseLong(number.replace("-", ""));
phoneNum = number;
} catch (NumberFormatException e) { // ex) "insert-address-token"
// if (phoneNum == null) {
// phoneNum = number;
// }
isNumberFormat = false;
}
if (isNumberFormat)
break;
}
} while (cursor.moveToNext());
}
if (cursor != null) {
cursor.close();
}
return phoneNum;
}