1

У меня есть активность, которая должна отображать контакты телефона Android в формате ListView, который является фрагментом внутри моей деятельности AddressBook.java. Я смог получить список, чтобы отображать имена, но ничего больше. Я чувствую, что я рядом, но мне трудно найти работу. В моих XML-файлах (у меня 4) у меня есть активность XML (есть только фрагмент), ListView XML (contact_list_view.xml), а затем типичная строка для ListView, которую я называю своим Item XML (contacts_list_item.xml). Но как мне подключить все эти представления к виду моей активности? Я думаю, что у меня есть фрагмент внутри операции OK, так как список имен работает, но не уверен, как получить фотографию и электронную почту для отображения. Я знаю, что в моем основном коде тоже что-то отсутствует, ContactFragments.java.Display ContactContracts Name, Email, Photo в ListView, используя Fragment - Android

Одна проблема, мне пришлось отфильтровать мои контакты по имени, иначе каждое электронное письмо в каждом приложении на моем телефоне опубликует, что не то, что я хочу. Я хочу, чтобы контакты в приложении Android Contacts отображались, поэтому я надеюсь, что это не мешает другим деталям контактов показывать.

Ниже мой код, я не показываю свою активность AddressBook.java, потому что я использую только представление XML, чтобы отображать в нем свой фрагмент, используя теги фрагментов (что отлично работает, потому что я как минимум получаю имена контактов).

Я искал широкий и широкий ответы на это сообщение в Интернете, но есть так много частей, я не мог найти, как решить мою конкретную ситуацию. Я надеюсь использовать мой код, который у меня уже есть, и отредактировать его минимально (по сравнению с внедрением совершенно нового способа достижения этого с помощью других классов и т. Д.). Если у вас есть идеи, я буду очень благодарен.

ContactsFragment.java

package org.azurespot.practiceapp.addressbook; 

import android.app.ListFragment; 
import android.app.LoaderManager.LoaderCallbacks; 
import android.content.ContentUris; 
import android.content.CursorLoader; 
import android.content.Loader; 
import android.database.Cursor; 
import android.net.Uri; 
import android.os.Bundle; 
import android.provider.ContactsContract; 
import android.provider.ContactsContract.Contacts; 
import android.view.LayoutInflater; 
import android.view.View; 
import android.view.ViewGroup; 
import android.widget.CursorAdapter; 
import android.widget.ImageView; 
import android.widget.ListView; 
import android.widget.SimpleCursorAdapter; 

import com.example.practiceapp.R; 

/* 
* Taken from http://stackoverflow.com/questions/18199359/how-to-display-contacts-in-a-listview-in-android-for-android-api-11 
*/ 

public class ContactsFragment extends ListFragment implements 
           LoaderCallbacks<Cursor>{ 

    private CursorAdapter mAdapter; 
    public ListView listView; 
    public Cursor cursor; 
    // Name should be displayed in the text1 TextView in item layout 
    public static final String[] FROM = { ContactsContract.Contacts 
               .DISPLAY_NAME_PRIMARY }; 
    private static final int[] TO = { android.R.id.text1 }; 
    private android.content.Context context; 
    public View view; 
    public static Uri uri; 


    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 

     // delete list if already there (old version) 
     if (!(listView == null)){ 
      listView.setAdapter(null); 
     } 

     // create adapter once 
     context = getActivity(); 
     int layout = android.R.layout.simple_list_item_1; 
     Cursor c = null; // there is no cursor yet 
     int flags = 0; // no auto-requery! Loader requeries. 

     // put List in adapter 
     mAdapter = new SimpleCursorAdapter(context, layout, c, FROM, TO, flags); 


    } // end onCreate 


    // columns requested from the database 
    private static final String[] PROJECTION = { 
      Contacts._ID, 
      ContactsContract.Contacts.PHOTO_THUMBNAIL_URI, 
      ContactsContract.Contacts.DISPLAY_NAME_PRIMARY, 
      ContactsContract.Contacts.HAS_PHONE_NUMBER, 
      ContactsContract.Contacts.IN_VISIBLE_GROUP 
    }; 

    // this goes in the CursorLoader parameter list, it filters 
    // out only those contacts who have a phone number 
    private static final String SELECTION = 
      ContactsContract.Contacts.HAS_PHONE_NUMBER + "='1'"; 

    // Empty public constructor, required by the system 
    public ContactsFragment() {} 

    // A UI Fragment must inflate its View (all fragments must override onCreateView) 
    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, 
      Bundle savedInstanceState) { 
     // Inflate the fragment layout 
     View view = inflater.inflate(R.layout.contact_list_view, 
      container, false); 
     listView = (ListView) view.findViewById(R.id.list); 

     // set Contact photo to ImageView 
     ContactsFragment frag = new ContactsFragment(); 
     ImageView thumb = (ImageView)view.findViewById(R.id.contact_thumbnail); 
     frag.getPhotoUriFromID(Contacts._ID); 
     thumb.setImageURI(uri); 
     return view; 
    } 

    public void onActivityCreated(Bundle savedInstanceState) { 
     super.onActivityCreated(savedInstanceState); 

     // and tell loader manager to start loading 
     getLoaderManager().initLoader(0, null, this); 

     listView.setAdapter(mAdapter); 
     listView.setFastScrollEnabled(true); 

    } 

    // a CursorLoader does a query in the background 
    @Override 
    public Loader<Cursor> onCreateLoader(int id, Bundle args) { 
     // load from the "Contacts table" 
     Uri contentUri = Contacts.CONTENT_URI; 

     // no sub-selection, no sort order, simply every row 
     // projection says we want just the _id and the name column 
     return new CursorLoader(getActivity(), 
       contentUri, 
       PROJECTION, 
       SELECTION, 
       null, 
       ContactsContract.Contacts.DISPLAY_NAME 
     ); 
    } 

    private Uri getPhotoUriFromID(String id) { 
     try { 
      Cursor cur = context.getContentResolver() 
        .query(ContactsContract.Data.CONTENT_URI, 
          null, 
          ContactsContract.Data.CONTACT_ID 
            + "=" 
            + id 
            + " AND " 
            + ContactsContract.Data.MIMETYPE 
            + "='" 
            + ContactsContract.CommonDataKinds.Photo.CONTENT_ITEM_TYPE 
            + "'", null, null); 
      if (cur != null) { 
       if (!cur.moveToFirst()) { 
        return null; // no photo 
       } 
      } else { 
       return null; // error in cursor process 
      } 
     } catch (Exception e) { 
      e.printStackTrace(); 
      return null; 
     } 
     Uri person = ContentUris.withAppendedId(
       ContactsContract.Contacts.CONTENT_URI, Long.parseLong(id)); 
     uri = Uri.withAppendedPath(person, 
       ContactsContract.Contacts.Photo.CONTENT_DIRECTORY); 
     return uri; 
    } 

    @Override 
    public void onLoadFinished(Loader<Cursor> loader, Cursor data) { 
     // Once cursor is loaded, give it to adapter 
     mAdapter.swapCursor(data); 
    } 

    @Override 
    public void onLoaderReset(Loader<Cursor> loader) { 
     // Delete the reference to the existing Cursor, 
     // so it can recycle it 
     mAdapter.swapCursor(null); 
    } 
} 

contact_list_view.xml

<?xml version="1.0" encoding="utf-8"?> 

<ListView xmlns:android="http://schemas.android.com/apk/res/android" 
    android:id="@+id/list" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" > 
</ListView> 

contacts_list_item

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    android:layout_width="fill_parent" 
    android:layout_height="fill_parent" 
    android:orientation="vertical" > 

     <ImageView 
     android:id="@+id/contact_thumbnail" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:contentDescription="@string/thumbnail" /> 

     <TextView 
      android:id='@+id/text_name' 
      android:layout_width="match_parent" 
      android:layout_height="wrap_content" 
      android:clickable="true"/> 
</LinearLayout> 

ответ

0

Вы должны переопределить метод getView() адаптера и создать собственное представление списка для отображения изображения, имени и электронной почты.

Обратитесь к этой ссылке для получения более подробной информации http://www.androidhive.info/2014/07/android-custom-listview-with-image-and-text-using-volley/

+0

Спасибо Арджун, однако я пытаюсь вытащить из своих «Контакты», что является целым другим зверьком, а не только «ListView». В некоторых учебниках говорится, что 'CursorLoader' имеет свой собственный вид, поэтому мне не нужно его предоставлять. Затем другие говорят, чтобы получить фото/электронную почту из запроса, используя мой «Курсор», обращаясь к таблице классов «ContactContracts.Data». Все еще исследую, но если я узнаю больше, я остановлюсь на этом здесь.Спасибо за эту идею. – Azurespot

0

Предполагая, что курсор возвращается все необходимые данные, похоже, вам просто нужно изменить некоторые из исходных значений при инициализации адаптера. Попробуйте выполнить следующие действия:

public static final String[] FROM = { ContactsContract.Contacts.DISPLAY_NAME_PRIMARY, ContactsContract.Contacts.PHOTO_THUMBNAIL_URI }; 
private static final int[] TO = { R.id.text_name, R.id.contact_thumbnail }; 

int layout = R.layout.contact_list_item; 

Это должно привести к тому, что ваш адаптер отобразит как изображение, так и отображаемое имя. Переопределение метода getView(), предложенного Арджун Сна, не требуется, так как SimpleCursorAdapter поддерживает отображение как TextView, так и ImageView. Если вы хотите добавить письмо, вам необходимо обновить свой XML, чтобы добавить еще один TextView, а затем добавить его в ассоциацию с массивами FROM и TO.

Смежные вопросы