ArrayIndexOutOfBoundsException с пользовательским адаптером Android для нескольких видов в ListView

Я пытаюсь создать пользовательский адаптер для моего ListView, поскольку каждый элемент в списке может иметь другое представление (ссылку, переключатель или группу радио), но когда я пытаюсь запустить Activity, в котором используется ListView, я получаю сообщение об ошибке и Приложение останавливается. Приложение предназначено для платформы Android 1.6.

Код:

public class MenuListAdapter extends BaseAdapter { private static final String LOG_KEY = MenuListAdapter.class.getSimpleName(); protected List<MenuItem> list; protected Context ctx; protected LayoutInflater inflater; public MenuListAdapter(Context context, List<MenuItem> objects) { this.list = objects; this.ctx = context; this.inflater = (LayoutInflater)this.ctx.getSystemService(Context.LAYOUT_INFLATER_SERVICE); } @Override public View getView(int position, View convertView, ViewGroup parent) { Log.i(LOG_KEY, "Position: " + position + "; convertView = " + convertView + "; parent=" + parent); MenuItem item = list.get(position); Log.i(LOG_KEY, "Item=" + item ); if (convertView == null) { convertView = this.inflater.inflate(item.getLayout(), null); } return convertView; } @Override public boolean areAllItemsEnabled() { return false; } @Override public boolean isEnabled(int position) { return true; } @Override public int getCount() { return this.list.size(); } @Override public MenuItem getItem(int position) { return this.list.get(position); } @Override public long getItemId(int position) { return position; } @Override public int getItemViewType(int position) { Log.i(LOG_KEY, "getItemViewType: " + this.list.get(position).getLayout()); return this.list.get(position).getLayout(); } @Override public int getViewTypeCount() { Log.i(LOG_KEY, "getViewTypeCount: " + this.list.size()); return this.list.size(); } } 

Ошибка, которую я получаю:

  java.lang.ArrayIndexOutOfBoundsException at android.widget.AbsListView$RecycleBin.addScrapView(AbsListView.java:3523) at android.widget.ListView.measureHeightOfChildren(ListView.java:1158) at android.widget.ListView.onMeasure(ListView.java:1060) at android.view.View.measure(View.java:7703) 

Я знаю, что приложение возвращается из getView и все выглядит по порядку.

Любые идеи о том, что может быть причиной этого, будут оценены.

Благодаря,

Дан

Solutions Collecting From Web of "ArrayIndexOutOfBoundsException с пользовательским адаптером Android для нескольких видов в ListView"

Тип вида элемента, с которого вы возвращаетесь

getItemViewType() is >= getViewTypeCount() .

Принятый ответ правильный. Это то, что я делаю, чтобы избежать проблемы:

 public enum FoodRowType { ONLY_ELEM, FIRST_ELEM, MID_ELEM, LAST_ELEM } @Override public int getViewTypeCount() { return FoodRowType.values().length; } @Override public int getItemViewType(int position) { return rows.get(position).getViewType(); //returns one of the above types } 

Причина, скорее всего, потому, что метод getItemViewType возвращает неправильные значения! Каждая строка в списке – это один вид. В то время как scrooling getItemViewType достигает большего, чем количество просмотров.

Что делать? Как избежать проблемы?

Сначала определите представление (строку) в вашем списке, которое показано первым. Если прокрутка использует уравнение модулятора

  @Override public int getItemViewType(int position) { return choseType(position);//function to use modular equation } @Override public int getViewTypeCount() { return 10; } 

В этом примере есть десять представлений (10 строк).

 private int choseType(int position){ if(position%10==0) return 0; else if(position%10==1) return 1; else if(position%10==2) return 2; else if(position%10==3) return 3; else if(position%10==4) return 4; else if(position%10==5) return 5; else if(position%10==6) return 6; else if(position%10==7) return 7; else if(position%10==8) return 8; else return 9; } 

Важный

Некоторые пользователи упомянули о другом вопросе о методе stackoverflow, который

Public int getViewTypeCount () и public int getItemViewType (int position) fix, как Tooglebutton, автоматически активировать проверку состояния true на scrooling .. Это большая ошибка. Если вы не хотите, чтобы автоматическая enbale на scrool просто делала

 toogleButton.setChecked(false); 

По методу переопределения getView.