将当前的ListView与带有ListView的自定义适配器集成在一起以允许多个视图 [英] Integrating current ListView with a Custom Adapter with ListView to allow multiple views

查看:130
本文介绍了将当前的ListView与带有ListView的自定义适配器集成在一起以允许多个视图的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我当前的项目包括带有自定义适配器的ListView。但是,我现在有兴趣向ListView中添加多种类型的视图,但是经过几次尝试,我无法将两个代码源一起添加到一起以成功集成它们。

The current project I have includes a ListView with a Custom Adapter. However, I am now interested in adding multiple types of views to my ListView but after several attempts I have been unable to add the two sources of code together to successfully integrate them.

具有多个视图的ListView上的文章:用于多个视图的ListView文章

Article on ListView with multiple views: ListView Article for multiple views

当前代码中的自定义适配器从另一个名为getData的类中检索数据,该类被数据引用。

The custom adapter in my current code retrieves the data from another class called getData which is referenced by "data".

代码摘自文章(具有多个视图的ListView):

Code from article (ListView with multiple views):

public class MultipleItemsList extends ListActivity {

private MyCustomAdapter mAdapter;

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    mAdapter = new MyCustomAdapter();
    for (int i = 1; i < 50; i++) {
        mAdapter.addItem("item " + i);
        if (i % 4 == 0) {
            mAdapter.addSeparatorItem("separator " + i);
        }
    }
    setListAdapter(mAdapter);
}

private class MyCustomAdapter extends BaseAdapter {

    private static final int TYPE_ITEM = 0;
    private static final int TYPE_SEPARATOR = 1;
    private static final int TYPE_MAX_COUNT = TYPE_SEPARATOR + 1;

    private ArrayList mData = new ArrayList();
    private LayoutInflater mInflater;

    private TreeSet mSeparatorsSet = new TreeSet();

    public MyCustomAdapter() {
        mInflater = (LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    }

    public void addItem(final String item) {
        mData.add(item);
        notifyDataSetChanged();
    }

    public void addSeparatorItem(final String item) {
        mData.add(item);
        // save separator position
        mSeparatorsSet.add(mData.size() - 1);
        notifyDataSetChanged();
    }

    @Override
    public int getItemViewType(int position) {
        return mSeparatorsSet.contains(position) ? TYPE_SEPARATOR : TYPE_ITEM;
    }

    @Override
    public int getViewTypeCount() {
        return TYPE_MAX_COUNT;
    }

    @Override
    public int getCount() {
        return mData.size();
    }

    @Override
    public String getItem(int position) {
        return mData.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder holder = null;
        int type = getItemViewType(position);
        System.out.println("getView " + position + " " + convertView + " type = " + type);
        if (convertView == null) {
            holder = new ViewHolder();
            switch (type) {
                case TYPE_ITEM:
                    convertView = mInflater.inflate(R.layout.item1, null);
                    holder.textView = (TextView)convertView.findViewById(R.id.text);
                    break;
                case TYPE_SEPARATOR:
                    convertView = mInflater.inflate(R.layout.item2, null);
                    holder.textView = (TextView)convertView.findViewById(R.id.textSeparator);
                    break;
            }
            convertView.setTag(holder);
        } else {
            holder = (ViewHolder)convertView.getTag();
        }
        holder.textView.setText(mData.get(position));
        return convertView;
    }

}

public static class ViewHolder {
    public TextView textView;
}
}

当前代码(ListView带有自定义适配器):

Current code (ListView with custom adapter):

FragmentA.java

FragmentA.java

package com.example.newsapp;

public class FragmentA extends Fragment{

getData data = getData.getMyData();

public Integer ArticleID;

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {

    View V = inflater.inflate(R.layout.fragment_a, container, false);

    ListView listView = (ListView)V.findViewById(R.id.list)

      CustomList adapter = new
            CustomList(getActivity(), data.Headline.toArray(new String[data.Headline.size()]), data.Description.toArray(new String[data.Description.size()]), data.BitmapList.toArray(new Bitmap[data.BitmapList.size()]), data.ArticleID.toArray(new Integer[data.ArticleID.size()]));     
      listView.setAdapter(adapter);
      listView.setOnItemClickListener(this); //Removed on click item event code.

    return V;

}

CustomList.java

CustomList.java

package com.example.newsapp;

public class CustomList extends ArrayAdapter<String>{
private final Activity context;
private final String[] titleId;
private final String[] descriptionId;
private final Bitmap[] pictureid;

public CustomList(Activity context,
String[] Headline, String[] Description, Bitmap[] BitmapList, Integer[] ArticleID) {
super(context, R.layout.single_row, Headline);
this.context = context;
this.titleId = Headline;
this.descriptionId = Description;
this.pictureid = BitmapList;

}
@Override
public View getView(int position, View view, ViewGroup parent) {
LayoutInflater inflater = context.getLayoutInflater();
View rowView= inflater.inflate(R.layout.single_row, null, true);

TextView txtTitle = (TextView) rowView.findViewById(R.id.tvTitle);
TextView txtDescription = (TextView) rowView.findViewById(R.id.tvDescription);
ImageView imageView = (ImageView) rowView.findViewById(R.id.ivIcon);

txtTitle.setText(titleId[position]);
txtDescription.setText(descriptionId[position]);
imageView.setImageBitmap(pictureid[position]);
return rowView;
}

}

编辑:

public class CustomList extends ArrayAdapter<String>{

private final Activity context;
private final String[] titleId;
private final String[] descriptionId;
private final Bitmap[] pictureid;

public CustomList(Activity context,
String[] Headline, String[] Description, Bitmap[] BitmapList, Integer[] ArticleID) {
super(context, R.layout.single_row, Headline);
this.context = context;
this.titleId = Headline;
this.descriptionId = Description;
this.pictureid = BitmapList;

}

@Override
public View getView(int position, View view, ViewGroup parent) {
int viewType = getItemViewType(position);
View rowView = null;
switch(viewType) {
case 0:

    LayoutInflater inflater = context.getLayoutInflater();
    rowView= inflater.inflate(R.layout.single_row, null, true);

    TextView txtTitle = (TextView) rowView.findViewById(R.id.tvTitle);
    TextView txtDescription = (TextView) rowView.findViewById(R.id.tvDescription);
    ImageView imageView = (ImageView) rowView.findViewById(R.id.ivIcon);

    txtTitle.setText(titleId[position]);
    txtDescription.setText(descriptionId[position]);
    imageView.setImageBitmap(pictureid[position]);

case 1:

    LayoutInflater inflater2 = context.getLayoutInflater();
    rowView= inflater2.inflate(R.layout.single_row_loadmore, null, true);
}
    return rowView;
}

@Override
public int getViewTypeCount() {
    return 2; // TODO make this a static final
}

@Override
public int getItemViewType(int position) {
    return position % 2; // 0 or 1
}

}


推荐答案

首先,请注意:您应该创建一个封装标题,描述等的类,并使用这些对象的数组/集合来支持适配器。这比管理许多不同的事物要容易得多,尤其是如果有一天您决定需要某个Article的另一个属性(例如,其类别)。

First, a bit of an aside: you should create a class that encapsulates a headline, description, etc. and use an array/collection of those objects to back your adapter. It will be far easier than managing many disparate arrays of things, especially if one day you decide you need another attribute of an Article (its category, for example).

class Article {
    int id;
    String headline;
    String description;
    Bitmap picture;
}

关于ListView,魔术发生在方法 getItemViewType() getViewTypeCount()。在 getViewTypeCount()中,返回最大行类型数-您发布的文章使用两种行类型,因此返回 2 。在 getItemViewType()中,您返回一个介于零和(viewTypeCount-1)之间的值-在本文中,他的实现可以返回 0 1 ,因为他的viewTypeCount为 2

With regard to your ListView, the magic happens in the methods getItemViewType() and getViewTypeCount(). In getViewTypeCount() you return the maximum number of row types -- the article you posted uses two row types and so returns 2. In getItemViewType() you return a value between zero and (viewTypeCount - 1) -- in the article, his implementation can return 0 or 1 because his viewTypeCount is 2.

如何决定哪种行类型适用于每个项目完全取决于您。例如,如果您只想在每一行上替换视图类型,则可以执行以下操作:

How you decide which row type applies to each item is entirely up to you. If, for example, you wanted to simply alternate view types on every row, you can do this:

@Override
public int getViewTypeCount() {
    return 2; // TODO make this a static final
}

@Override
public int getItemViewType(int position) {
    return position % 2; // 0 or 1
}

在其他应用程序中,您可能会在给定位置以帮助您确定应在 getItemViewtype()中返回什么。

In other applications you would probably inspect the item at the given position to help you determine what should be returned in getItemViewtype().

存在此功能的原因是 getView()提供一个已被回收的行的参数(称为 convertView )。为了给您合适的 convertView ,ListView首先需要知道它是哪种行类型。当您想为具有多种行类型的适配器实现 getView()时,通常看起来像这样:

The reason this functionality exists is that getView() provides a parameter (called convertView) that is a row which has been recycled. In order to give you an appropriate convertView, ListView needs to first know what row type it was. When you want to implement getView() for an adapter with multiple row types, it generally looks something like this:

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    int viewType = getItemViewType(position);
    switch(viewType) {
    case 0:
        return setUpOneViewType(position, convertView, parent);
    case 1:
        return setUpAnotherViewType(position, convertView, parent);
    }
}

请注意,switch语句的情况与可能的情况相对应可以从 getItemViewType()返回的值。这些可能是静态最终成员

Note the cases for the switch statement correspond to the possible values that can be returned from getItemViewType(). These could be static final members.

我强烈建议您观看 ListView的世界。该视频介绍了该主题以及如何在适配器实现中正确使用 convertView

I highly suggest watching The World of ListView. That video covers this topic as well as how to properly use convertView in your adapter implementation.

这篇关于将当前的ListView与带有ListView的自定义适配器集成在一起以允许多个视图的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆