【问题标题】:Android how to inflate ListView with two different itemsAndroid如何用两个不同的项目膨胀ListView
【发布时间】:2017-08-17 16:06:39
【问题描述】:

我正在尝试使用 ArrayAdapter 使用两种不同的布局来扩展 listView。

我想显示一些用户帖子。如果它包含图片,则使用一种布局,如果它不使用第二种布局。

目前为止

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    Post post = getItem(position);

    boolean noImg = post.mImgUrl1 == null && post.mImgUrl2 == null;

    if (convertView == null){

        if (noImg)
            convertView = LayoutInflater.from(getContext()).inflate(R.layout.post_item_no_img, parent ,false);
        else
            convertView = LayoutInflater.from(getContext()).inflate(R.layout.post_item, parent, false);
    }

    if (noImg == false) {
        mTitle = (TextView) convertView.findViewById(R.id.tv_titlePost);
        mText = (TextView) convertView.findViewById(R.id.tv_textPost);
        mImage = (ImageView) convertView.findViewById(R.id.iv_postimg);
    }

    else {
        mNoImgTitle = (TextView) convertView.findViewById(R.id.tv_noImgTitle);
        mNoImgText = (TextView) convertView.findViewById(R.id.tv_noImgText);
    }

    if (noImg) {
        mNoImgTitle.setText(post.mTitle);
        mNoImgText.setText(post.mText);

        if (post.mImgUrl1 != null)
            Glide.with(mImage.getContext()).load(post.mImgUrl1).into(mImage);

        else  Glide.with(mImage.getContext()).load(post.mImgUrl2).into(mImage);
    }
    else {
        mNoImgTitle.setText(post.mTitle);
        mNoImgText.setText(post.mText);
    }

    return convertView;
}

但我意识到 findViewById 函数无法找到第二个布局的文本视图。它总是返回一个空指针。

我的解决方案是什么?我应该只制作一个布局并以某种方式使用可见性来欺骗它吗?或者有什么办法?

【问题讨论】:

标签: android android-layout listview layout-inflater


【解决方案1】:

getView() 被调用时,您会看到几种不同的场景:

  1. convertView 为空:在这种情况下,只需根据noImg 创建您需要的布局;

  2. convertView 已定义但类型错误。在这种情况下,您需要丢弃旧视图并创建您需要的视图;

  3. convertView 已定义,但类型正确,在这种情况下,我们什么也不做。

以下代码是确保您始终使用正确布局并可以找到您期望的 id 的一种方法。此代码使用膨胀布局中的标签来标识可以检查的布局类型。

if (convertView == null || noImg != (boolean) convertView.getTag()) {
    // Either there is no view defined or it is the wrong type. Create
    // the type we need.
    if (noImg) {
        convertView = LayoutInflater.from(getContext()).inflate(R.layout.post_item_no_img, parent, false);
    } else {
        convertView = LayoutInflater.from(getContext()).inflate(R.layout.post_item, parent, false);
    }
    convertView.setTag(noImg);
}

【讨论】:

    【解决方案2】:

    使用 BaseAdapter,您可以创建更复杂的布局。尝试使用它。

    以下是针对您的情况的使用示例:

    活动:

    public class TestActivity extends AppCompatActivity {
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        String[] data={"false","false","true","true","false","true"};
        ListView listViewTest=(ListView)findViewById(R.id.listViewTest);
        TestAdapter testAdapter=new TestAdapter(data);
        listViewTest.setAdapter(testAdapter);
    }
    }
    

    适配器:

    public class TestAdapter extends BaseAdapter {
    private String[] data;
    
    
    TestAdapter(String data[]) {
        this.data = data;
    }
    
    @Override
    public int getCount() {
        return data.length;
    }
    
    @Override
    public Object getItem(int i) {
        return data[i];
    }
    
    @Override
    public long getItemId(int i) {
        return i;
    }
    
    
    public View getView(int position, View convertView, ViewGroup parent) {
        if (data[position].equals("false")) {
            convertView = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_item_no_img, parent, false);
        } else if (data[position].equals("true")) {
            convertView = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_item_img, parent, false);
        }
        return convertView;
    }
    }
    

    布局:

    activity_main

    <LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical">
    <ListView
        android:id="@+id/listViewTest"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
    </ListView>
    

    list_item_no_img

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/textViewTest"
        android:gravity="center"
        android:layout_centerInParent="true"
        android:textSize="32sp"
        android:text="Test"/>
    </RelativeLayout>
    

    list_item_img

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/textViewTest"
        android:gravity="center"
        android:layout_centerInParent="true"
        android:textSize="32sp"
        android:text="Test"/>
    <ImageView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:src="@mipmap/ic_launcher"
        android:layout_marginStart="5dp"
        android:layout_marginLeft="5dp"
        android:layout_centerVertical="true"
        android:layout_toRightOf="@+id/textViewTest"
        android:layout_toEndOf="@+id/textViewTest" />
    </RelativeLayout>
    

    结果:

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-01-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多