Intereting Posts
Цвет текста уведомления в Galaxy S 2.3.3 Как получить доступ к строке с использованием динамического имени строки в android (аналогично eval в javascript)? Метод тестирования единицы измерения, который содержит выражение лямбда Android Studio Отключить отмену шумоподавления HTC Как traceroute в оболочке adb? Android: битмапы, загруженные из галереи, поворачиваются в ImageView Рисование масштабированных растровых изображений на SurfaceView – без сглаживания Преобразовать в lambda из выражения rx java Закрытие приложения с кнопкой «Выход» Гибридные мобильные приложения, как правило, считаются уступающими по отношению к собственным приложениям разработчиками в технологической отрасли? GooglePlayServicesUtil.getErrorDialog имеет значение null Почему Intent.createChooser () нуждается в BroadcastReceiver и как реализовать? Невозможно выполнить скриншот в Android L программно Получить широту и долготу от названия города Запросы Ajax терпят неудачу после обновления до Кордовы 5.0 + cordova-android@4.0

Android: ClassCastException при добавлении заголовка в ExpandableListView

Я пытаюсь добавить заголовок в ExpandableListView следующим образом:

headerView = View.inflate(this, R.layout.header, null); expandableListView.addHeaderView(headerView); expandableListView.setAdapter(new SectionedAdapter(this)); 

Это дает мне следующую ошибку:

  12-08 16:23:42.354: ERROR/AndroidRuntime(421): Caused by:java.lang.ClassCastException: android.widget.LinearLayout$LayoutParams 12-08 16:23:42.354: ERROR/AndroidRuntime(421): at android.widget.ListView.clearRecycledState(ListView.java:504) 12-08 16:23:42.354: ERROR/AndroidRuntime(421): at android.widget.ListView.resetList(ListView.java:490) 12-08 16:23:42.354:ERROR/AndroidRuntime(421):at android.widget.ListView.setAdapter(ListView.java:422) 12-08 16:23:42.354:ERROR/AndroidRuntime(421): at android.widget.ExpandableListView.setAdapter(ExpandableListView.java:475) 

Это происходит при вызове expandableListView.setAdapter(new SectionedAdapter(this)) , но я не могу понять, почему. Есть идеи?

Хорошо, я понял это. Я избавился от ошибки времени выполнения, запрограммировав настройку LayoutParams View в LayoutParams ListView, например:

 headerView.setLayoutParams(new ListView.LayoutParams(ListView.LayoutParams.FILL_PARENT, ListView.LayoutParams.WRAP_CONTENT)); 

Перед добавлением представления. Причина заключается в документах Android:

http://developer.android.com/reference/android/view/View.html#setLayoutParams(android.view.ViewGroup.LayoutParams)

В котором говорится, что:

Эти параметры поставляются родительскому элементу этого представления, определяя, как это должно быть организовано. Существует много подклассов ViewGroup.LayoutParams, и они соответствуют различным подклассам ViewGroup, которые отвечают за организацию своих детей.

Поэтому в основном, если вы добавляете представление в другое, вы ДОЛЖНЫ установить LayoutParams представления в тип LayoutParams, который использует родительский элемент, или вы получите ошибку времени выполнения.

Несмотря на то, что вышеприведенный ответ может работать для многих, есть еще лучшее объяснение. ClassCastException – это нормальное поведение после вызова listview.addHeaderView или listview.addFooterView .

Причина в том, что первоначальный адаптер обернут в HeaderViewListAdapter . Чтобы ваш адаптер использовал этот код.

 YourAdapter ya = (YourAdapter) ((HeaderViewListAdapter)lv.getAdapter()).getWrappedAdapter(); 

Код, взятый отсюда

В моем случае это не сработало. Я должен был установить footerView в свой списокView перед настройкой его адаптера. Сначала я инициализировал свой loadView из файла макета в методе OnCreate:

 LayoutInflater layoutInflater = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE); loadingView = layoutInflater.inflate(R.layout.loading_view, null); 

Затем я использовал это обходное решение в том же методе:

 this.setIsLoading(true); listView.setAdapter(adapter); this.setIsLoading(false); 

где

 private void setIsLoading(boolean isLoading) { this.isLoading = isLoading; if (isLoading) { listView.addFooterView(loadingView); } else { listView.removeFooterView(loadingView); } } 

Вы должны поместить родительское представление в свое завышенное представление.

 ListView listview = (ListView) findViewById(R.id.listview); headerView = View.inflate(this, R.layout.header, listview, false); // set listview as parent view listview.addHeaderView(headerview);