ListView Adapter with arbitrary number of row types (Don't know the number of different row types)

房东的猫 提交于 2019-11-27 15:25:17

You need to override getViewItemType and getViewTypeCount.

getItemViewType(int position) - returns information which layout type you should use based on position

Then you inflate layout only if it's null and determine type using getItemViewType.

Example :

   private static final int TYPE_ITEM1 = 0;
   private static final int TYPE_ITEM2 = 1;
   private static final int TYPE_ITEM3 = 2;
    @Override; 
    public int getItemViewType(int position) 
    {
    int type;
    if (position== 0){ // your condition
        type = TYPE_ITEM1;  //type 0 for header
    } else if(position == 1){
        type = TYPE_ITEM2; //type 1 for message
    }else {
        type = TYPE_ITEM3; //type 2 for Quote
    }
    return type;
    }
@Override
public int getViewTypeCount() {
    return 3;    //three different layouts to be inflated
}

In getView

 int type= getItemViewType(i); // determine type using position.
 switch (type) {
 case TYPE_ITEM1: 
    view= mInflater.inflate(R.layout.post_header_layout, null);   // inflate layout for header
 break;
 case TYPE_ITEM2:
     view = mInflater.inflate(R.layout.post_text_layout, null); //   inflate layout for quote
 break;
 case TYPE_ITEM3:
      quote = mInflater.inflate(R.layout.post_quote_layout, null);  //   inflate layout for message
 break;    
 .... 

You need to use a View Holder for smooth scrolling and performance.

http://developer.android.com/training/improving-layouts/smooth-scrolling.html

You can check the tutorial below

http://android.amberfog.com/?p=296

First of all you want to reuse convertView that has been passed as one of the argument. This way you can avoid inflating the item View.

Secondly, you could use something as ViewHolder to store references to your inner Views. Using ViewHolder will increase performance whether you are inflating view or finding them by id as both methods are very expensive.

Set the ViewHolder as a Tag on item View.

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    View view;
    ViewHolder viewHolder;

    // if possible reuse view
    if (convertView == null) {
        final LayoutInflater inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        view = inflater.inflate(resource, parent, false);
        viewHolder = new ViewHolder(mInflater.inflate(R.layout.post_header_layout, null));
        view.setTag(viewHolder);
    } else {
        // reuse view
        view = convertView;
        viewHolder = (ViewHolder) view.getTag();
    }

    //set text, listeners, icon, etc.

    return view;
}

The ViewHolder is just private inner class storing referenced to view.

private static class ViewHolder {

    private final View view;

    private ViewHolder(View view) {
        this.view = view;
    }
}

Talk about ListView usage was given at Google IO 2010.

The inflater needs to know the real type of the futur parent ViewGroup, therefore the following code is erroneous:

view = mInflater.inflate(R.layout.forum_post,null);

and instead, you should use this one:

view = mInflater.inflate(R.layout.forum_post,viewGroup,false);

Same thing for the other inflate: use the real parent (view in this case) or another viewGroup which is of the same type as the (futur) parent; otherwise the LayoutParameters will not be set to the right type and the values that you have specified in your XML code will be lost (never used).

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!