Почему мой ListView ничего не показывает?

У меня очень простой ListView в android и был установлен очень простой адаптер. Моя проблема в том, что в представлении списка ничего не отображается, независимо от адаптера и notifyDataSetChanged();

Вот мой код: XML:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content">
  <TextView android:text="@string/app_name"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  ></TextView>
  <ListView android:id="@+id/selectView"
    android:layout_height="wrap_content"
    android:layout_width="wrap_content">
    </ListView>
</RelativeLayout>

Код операции:

import android.app.Activity;
import android.os.Bundle;
import android.widget.ListView;

import com.androidcourse.phonemapper.R;
import com.androidcourse.phonemapper.model.SelectViewAdapter;

public class SelectActivity extends Activity {

    private ListView mListView;

    private SelectViewAdapter mAdapter;

    @Override
    public void onCreate(Bundle savedState) {
        super.onCreate(savedState);
        setContentView(R.layout.select_activity);
        initializeListView();

    }

    private void initializeListView() {
        mListView = (ListView) findViewById(R.id.selectView);
        mAdapter = new SelectViewAdapter(this);
        mListView.setAdapter(mAdapter);
        mAdapter.notifyDataSetChanged();
    }

    @Override
    public void onResume() {
        super.onResume();
    }
}

И код адаптера:

import android.content.Context;
import android.graphics.Color;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.TextView;

public class SelectViewAdapter extends BaseAdapter {

    private Context mContext;
    private TextView mMockTextView;

    public SelectViewAdapter(Context cnt) {
        mContext = cnt;
        mMockTextView = new TextView(mContext);
        mMockTextView.setText("Test text");
        mMockTextView.setBackgroundColor(Color.CYAN);
    }

    @Override
    public int getCount() {
        return 3;
    }

    @Override
    public Object getItem(int position) {
        return mMockTextView;
    }

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

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        return mMockTextView;
    }

}

Проблема заключается в том, что на экране ничего не отображается. Черный экран (и первый текстовый вид из XML) - это все, что я получаю. Я не вижу mockTextView и его текст. Видимо, я делаю что-то совершенно неправильно, но я не могу понять, что.

Ответ 1

Несколько вещей, о которых я могу думать.

Во-первых, ваш RelativeLayout не имеет относительной информации о местоположении. Я предполагаю, что вы хотели поместить это в LinearLayout с ориентацией, настроенной на вертикаль, от того, что вы описываете. Я предполагаю, что список на самом деле не нарисован, так как он даже не привязан к чему-либо в текущем RelativeLayout. Если вы придерживаетесь RelativeLayout, обязательно поместите идентификатор в текстовое поле app_name и поместите ListView под ним через layout_below.

Решение LinearLayout

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:orientation="vertical"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content">
  <TextView android:text="@string/app_name"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  ></TextView>
  <ListView android:id="@+id/selectView"
    android:layout_height="wrap_content"
    android:layout_width="wrap_content">
    </ListView>
</LinearLayout>

RelativeLayout Решение:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content">
  <TextView
  android:id="@+id/app_name_text" 
  android:text="@string/app_name"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  android:layout_alignParentTop="true"
  ></TextView>
  <ListView android:id="@+id/selectView"
    android:layout_below="@id/app_name_text"
    android:layout_height="wrap_content"
    android:layout_width="wrap_content">
    </ListView>
</RelativeLayout>

Затем ваш getView() возвращает тот же textView для всех 3 индексов. Это не проблема отображения одного и того же представления по нескольким индексам, но с размером списка из трех, я уверен, что на экране может отображаться все три одновременно. И поскольку представление не может быть в нескольких местах за раз, я действительно ожидаю, что это сбой, поэтому я сомневаюсь, что он даже добирается до этого кода. Попробуйте создать новый TextView для каждого getView(). Также у вашего MockTextView нет собственных параметров макета. Таким образом, размещение внутри ячейки listView может и не происходить. Поэтому вы можете дать ему параметры типа AbsListView.LayoutParams(WRAP_CONTENT, WRAP_CONTENT). Опять же, если бы я ожидал, что это ошибка, если она попадет в исходный код.

getView() убрать:

 @Override
    public View getView(int position, View convertView, ViewGroup parent) {
       if(convertView == null) {
          TextView textView = new TextView(parent.getContext());
          textView.setText("Position is:"+position);
          textView.setBackgroundColor(Color.CYAN);
          textView.setLayoutParams(new AbsListView.LayoutParams(WRAP_CONTENT, WRAP_CONTENT);
          convertView = textView;
        }
        return mMockTextView;
    }

И, наконец, высота вашего списка может быть проблематичной. Я не знаю всех сценариев. Если вы в конечном итоге перейдете на LinearLayout, попробуйте установить layout_height в виде списка на 0, а затем установите layout_weight = 1. Это заставляет линейную компоновку раздувать ее на большее пространство.

Весовое решение LinearLayout:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:orientation="vertical"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content">
  <TextView android:text="@string/app_name"
  android:layout_width="wrap_content"
  android:layout_height="wrap_content"
  ></TextView>
  <ListView android:id="@+id/selectView"
    android:layout_weight="1"
    android:layout_height="0dp"
    android:layout_width="wrap_content">
    </ListView>
</LinearLayout>

Ответ 2

Я использовал пример привязки данных из книги Hello Android от Ed Burnette (отличная книга).

Я изменил макет элемента с A RelativeLayout на LinearLayout; однако я не добавил ориентацию, когда внес изменения.

Как только я добавил андроид: ориентация = "вертикальная" все работало нормально.

Два часа моей жизни на этом.

Ответ 3

Пока он не отвечает на этот вопрос, типичной проблемой является раздувание в качестве ресурса адаптера макета на основе родительского LinearLayout с height = wrap_content и каждого элемента LinearLayout с высотой = fill_parent.

Как в

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/parentLayout"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="horizontal" >

<TextView
    android:id="@+id/someText"
    android:layout_width="0dp"
    android:layout_height="fill_parent"
    android:layout_weight="1"/>

Пока он хорошо отображается в Eclipse, каждая строка заканчивается height = 0. Это можно устранить, установив height = wrap_content для одного из дочернего элемента

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/parentLayout"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="horizontal" >

<TextView
    android:id="@+id/someText"
    android:layout_width="0dp"
    android:layout_height="wrap_content"
    android:layout_weight="1"/>