使用notifyDataSetChanged()更新ExpandableListView

首先简要介绍我的代码,我希望它是可以理解的:

  • 我有一个名为ToDoElement的类有几个variables。
  • 我有另一个叫ToDoListe类来pipe理ArrayList中的ToDoElement
  • ToDoListe包含方法deleteElement()从ArrayList中删除一个ToDoElement
  • 在我的主要活动liste_activity我创build了一个ToDoListe对象,并填充了一些ToDoElement对象。
  • 在同一个活动中,我有一个ExpandableListView和我自己的Adapter,名字是expListAdapter
  • 适配器通过获取ToDoElement的stringvariables来创buildGroupviews和Childviews。
  • 我为列表中的每个组项目创build了一个ContextMenu,其中我使用了deleteElement()方法。

好的,现在是我的问题

在我使用方法deleteElement()我想更新我的List,因为ToDoListe ArrayList的数据发生了变化。 所以我打电话expListAdapter.notifyDataSetChanged()
但是,然后我的整个活动崩溃,原因:“ IndexOutOfBoundException:无效的索引4,大小是4 ”(我有5个ToDoELement项目在我的列表中,之前删除其中之一)。
我知道那是因为我的一个for循环,但我不知道为什么。

代码片段:

创buildToDoListe的新对象:

 private static ToDoListe Liste = new ToDoListe(); 

类ToDoListe(只是重要的方法):

 public class ToDoListe { private ArrayList<ToDoElement> ToDoListe; public ToDoListe() { ToDoListe = new ArrayList<ToDoElement>(); } public void newElement(ToDoElement element){ ToDoListe.add(element); } public void deleteElement(int nummer) { ToDoListe.remove(nummer); } public int AnzahlElemente() { return ToDoListe.size(); } } 

定义列表适配器:

 expListAdapter = new MyListAdapter(this, createGroupList(), createChildList()); setListAdapter( expListAdapter ); 

为列表创buildArrayLists适配器:

 // creates the list with the group items private List createGroupList() { ArrayList result = new ArrayList(); for (int i=0; i < Liste.AnzahlElemente(); i++) { result.add(Liste.getElement(i).getUeberschrift()); } return result; } // creates the list with the child items private List createChildList() { ArrayList result = new ArrayList(); for(int i=0; i < Liste.AnzahlElemente(); i++) { ArrayList secList = new ArrayList(); for( int n = 1 ; n <= 3 ; n++ ) { if (Liste.getElement(i).getStichpunkt(n).length() != 0){ secList.add( "- " + Liste.getElement(i).getStichpunkt(n)); } } result.add( secList ); } return result; } 

我自己的列表适配器(只是重要的方法):

 public class MyListAdapter extends BaseExpandableListAdapter{ private ArrayList<String> ueberschriften; private ArrayList<ArrayList<String>> stichpunkte; private LayoutInflater inflater; public MyListAdapter(Context context, List _ueberschriften, List _stichpunkte) { this.ueberschriften = (ArrayList)_ueberschriften; this.stichpunkte = (ArrayList)_stichpunkte; inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); } public View getChildView(int groupPosition, int childPosition, boolean isLastChild, View convertView, ViewGroup parent) { if (convertView == null) { convertView = inflater.inflate(R.layout.item_child, null); } TextView tv = (TextView) convertView.findViewById(R.id.item_child_title); tv.setText(liste_activity.getListe().getElement(groupPosition).getStichpunkt(childPosition)); return convertView; } public View getGroupView(int groupPosition, boolean isExpanded, View convertView, ViewGroup parent) { if (convertView == null) { convertView = inflater.inflate(R.layout.item_group, null); } TextView tv = (TextView)convertView.findViewById(R.id.item_group_title); tv.setText(liste_activity.getListe().getElement(groupPosition).getUeberschrift()); return convertView; } 

使用notifyDataSetChanged():

 Liste.deleteElement(groupPos); expListAdapter.notifyDataSetChanged(); 

非常感谢您的关注!

Solutions Collecting From Web of "使用notifyDataSetChanged()更新ExpandableListView"

您需要将某种DeleteMethod添加到Adapter并手动从Adapter删除项目,不仅将其从List删除。

每次使用notifyDataSetChanged()刷新视图时, Adapter都会调用List的循环。 Adapter List由于您所做的更改而获得空值。

调用超级在你的registerDataSetObserver meke notifyDataSetChanged()运行良好。

 @Override public void registerDataSetObserver(DataSetObserver observer) { super.registerDataSetObserver(observer); } 

你应该调用expListAdapter.notifyDataSetInvalidated()

expListAdapter.notifyDataSetChanged()只会更新您的意见,为每个项目的新值(在任何元素没有变化)

即它会再次调用你的getChildViewgetGroupView每个项目。