Java 如何在Android api 11+的Android列表视图中显示联系人

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/18199359/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 23:14:19  来源:igfitidea点击:

how to display contacts in a listview in Android for Android api 11+

javaandroidlistviewsimplecursoradapter

提问by Terence Chow

I'm sorry if this looks like the same question a million times...but a google search for this provides no results, just a bunch of outdated tutorials using managedQueryand other deprecated solutions...

如果这看起来像一百万次相同的问题,我很抱歉......但是谷歌搜索没有提供任何结果,只是一堆使用过时的教程managedQuery和其他已弃用的解决方案......

I went through the android developer training for retrieving a contact list, but the tutorial is incomplete and even downloading the sample code doesn't help because the sample code is for more advanced contact list manipulation (search, etc.)

接受了检索联系人列表android 开发人员培训,但教程不完整,甚至下载示例代码也无济于事,因为示例代码用于更高级的联系人列表操作(搜索等)

In any case, there is no reason why there should not be a simple solution to this so I'm hoping someone can answer here because I'm sure this has been done a million times and I'm sure dozens of other beginning android developers would appreciate this.

无论如何,没有理由不应该有一个简单的解决方案,所以我希望有人能在这里回答,因为我确定这已经完成了一百万次,而且我确定还有其他几十个刚开始的 android 开发人员会欣赏这一点。

I have followed the tutorial to the best of my knowledge by no contacts show up. I think the biggest thing is that the TO_IDSis an integer array that points to android.R.id.text1. I'm confused how that is supposed to somehow pull an array of contact names.

据我所知,我已经按照教程进行了操作,没​​有出现任何联系人。我认为最重要的是它TO_IDS是一个指向android.R.id.text1. 我很困惑这应该如何以某种方式拉出一组联系人姓名。

Also, I'm confused why a textview is needed when the end goal is to display a listview...In the tutorial, we have mContactsList which is a list view...But we populate the list view with an adapter pointing to R.layout.contact_list_itemwhich is just textviews populated by TO_IDS, an array of integers.

另外,我很困惑为什么当最终目标是显示列表视图时需要 textview ......在本教程中,我们有 mContactsList 它是一个列表视图......但是我们用一个指向R.layout.contact_list_item它的适配器填充列表视图只是由整数数组 TO_IDS 填充的文本视图。

mContactsList = (ListView) getActivity().findViewById(R.layout.contact_list_view);
mCursorAdapter = new SimpleCursorAdapter(
            getActivity(),
            R.layout.contact_list_item,
            null,
            FROM_COLUMNS, TO_IDS,
            0);
mContactList.setAdapter(mCursorAdapter);

What am I doing wrong and how do I simply display the contact list in a listview?

我做错了什么,如何简单地在列表视图中显示联系人列表?

EDIT: adding in my code:

编辑:添加我的代码:

in my fragment class:

在我的片段类中:

public class MyFragment extends Fragment implements
    LoaderManager.LoaderCallbacks<Cursor>{

private static final String[] FROM_COLUMNS = {ContactsContract.Contacts.DISPLAY_NAME_PRIMARY };
private static final int[] TO_IDS = {android.R.id.text1};
ListView mContactList;
private SimpleCursorAdapter mCursorAdapter;

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState){
    return inflater.inflate(R.layout.contact_list_view,container,false);
}

@Override
public void onActivityCreated(Bundle savedInstanceState){
    super.onActivityCreated(savedInstanceState);
    mContactsList = (ListView) getActivity().findViewById(R.layout.contact_list_view);
    mCursorAdapter = new SimpleCursorAdapter(
            getActivity(),
            R.layout.contact_list_item,
            null,
            FROM_COLUMNS, TO_IDS,
            0);
    mContactList.setAdapter(mCursorAdapter);

}

@Override
public Loader<Cursor> onCreateLoader(int i, Bundle bundle) {
    return null;
}

@Override
public void onLoadFinished(Loader<Cursor> cursorLoader, Cursor cursor) {

}

@Override
public void onLoaderReset(Loader<Cursor> cursorLoader) {

}
}

in my activity_main.xml:

在我的 activity_main.xml 中:

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

    <fragment
            android:id ="@+id/contactListFragment"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="1"
            android:name="preamble.myapp.MyFragment"/>
</LinearLayout>

in my contact_list_view xml :

在我的 contact_list_view xml 中:

<?xml version="1.0" encoding="utf-8"?>
<ListView   xmlns:android="http://schemas.android.com/apk/res/android"
            android:id="@android:id/list"
            android:layout_height="match_parent"
            android:layout_width="match_parent"/>

In my contact_list_item xml

在我的 contact_list_item xml 中

<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
            android:id="@android:id/text1"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"/>

finally for contact_list_layout xml:

最后是contact_list_layout xml:

What do I put in the contact_list_layout.xml? Is this just an empty <LinearLayout>? It's not clear in the tutorial how this xml is handled. It says this XML is the fragment, but if it's the fragment, why did we define a listviewalready in the contact_list_view.xml?

我在里面放什么contact_list_layout.xml?这只是一个空的<LinearLayout>吗?教程中并不清楚这个xml是如何处理的。它说这个 XML 是片段,但如果是片段,为什么我们listviewcontact_list_view.xml.

采纳答案by zapl

Small stripped down example for displaying the contacts name in a ListView. Below Fragmentextends ListFragmentwhich has a default layout. You don't need to specify your own. The layout for list items is also taken from Android's default layouts (android.R.layout.simple_list_item_1) which is a simple single line of text per item.

用于在 .csv 文件中显示联系人姓名的小型精简示例ListView。下面的Fragment扩展ListFragment具有默认布局。您不需要指定自己的。列表项的布局也取自 Android 的默认布局 ( android.R.layout.simple_list_item_1),它是每个项目的简单单行文本。

import android.content.Context;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.ContactsContract.Contacts;
import android.support.v4.app.ListFragment;
import android.support.v4.app.LoaderManager.LoaderCallbacks;
import android.support.v4.content.CursorLoader;
import android.support.v4.content.Loader;
import android.support.v4.widget.CursorAdapter;
import android.support.v4.widget.SimpleCursorAdapter;

public class ContactListFragment extends ListFragment implements LoaderCallbacks<Cursor> {

    private CursorAdapter mAdapter;

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

        // create adapter once
        Context 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.
        mAdapter = new SimpleCursorAdapter(context, layout, c, FROM, TO, flags);
    }

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

        // each time we are started use our listadapter
        setListAdapter(mAdapter);
        // and tell loader manager to start loading
        getLoaderManager().initLoader(0, null, this);
    }

    // columns requested from the database
    private static final String[] PROJECTION = {
        Contacts._ID, // _ID is always required
        Contacts.DISPLAY_NAME_PRIMARY // that's what we want to display
    };

    // and name should be displayed in the text1 textview in item layout
    private static final String[] FROM = { Contacts.DISPLAY_NAME_PRIMARY };
    private static final int[] TO = { android.R.id.text1 };

    @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,
                null,
                null,
                null);
    }

    @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) {
        // on reset take any old cursor away
        mAdapter.swapCursor(null);
    }
}