情景: 有两个分类,每个分类下的数据用listview显示,分类1需要显示头视图和尾视图,分类2不要显示头视图和尾视图 。两个分类可以来回切换。

实现的步骤: 1. addHeaderView 、 addFooterView,默认显示分类1的数据,setAdapter绑定 

2. 点击分类2时,先removeheaderview、removefooterview,然后setAdapter重新绑定数据

3. 点击分类1时,addHeaderView、addFooterView,然后setAdapter重新绑定数据

修改之前的代码:

   public void addHeaderFooter(){
if(!hasHead){
listview.addHeaderView(tv_head);
hasHead = true;
}
if(!hasFoot){
listview.addFooterView(tv_foot);
hasHead = false;
}
}
@Override
public void onClick(int position) {
Log.d(TAG, "position " + position + " is clicked!");
switch(position){
case 1:
//不需要header和footer
if(hasHead){
listview.removeHeaderView(tv_head);
hasHead = false;
}
if(hasFoot){
listview.removeFooterView(tv_foot);
hasFoot = false;
}
break;
default:
//其余分类都需要
addHeaderFooter();
break;
}

遇到的问题: 

步骤3中addHeaderView时报错:

解决办法:

add之前, setAdapter(null).

查看源码可知:

将adapter置null后,就不会报错了



这样改之后又遇到了一个问题:

步骤3中addFooterView时报错:

追踪源码可知:

此处getAdapter为null(之前调用了setAdapter(null)),所以nullpointer了

为什么会走到这一步呢,查看addFooterView的源码:

调用了mDataSetObserver.onChanged(),

而这个 mDataSetObserver 在哪里呢?见setAdapter源码:

原来,在步骤1中调用了setAdapter设置数据,所以这里的mDataSetObserver就存在了。

所以在setAdapter(null)之后,调用addFooterView时,由于mDataSetObserver依然存在,就会调用mDataSetObserver.onChanged()方法,从而调用getAdapter方法,返回null,再调用getcount时就nullpointer了。

解决办法: 我是在addFooterView之前又绑定了一次,setAdapter,给了一个空的数据源进去,只是确保adapter不为null。 这个方法有点投巧,没找到好的方法。



改正后的代码:

public void addHeaderFooter(){
listview.setAdapter(null);
if(!hasHead){
listview.addHeaderView(tv_head);
hasHead = true;
}
if(!hasFoot){
SimpleAdapter adapter = new SimpleAdapter(this, empty_list, R.layout.funtest_listview_item,
new String[]{ FuntestColumns.name,FuntestColumns.r_count,FuntestColumns.description},
new int[]{R.id.funtest_name, R.id.funtest_hot, R.id.funtest_description});
listview.setAdapter(adapter);
listview.addFooterView(tv_foot);
hasHead = false;
}
}
@Override
public void onClick(int position) {
Log.d(TAG, "position " + position + " is clicked!");
switch(position){
case 1:
//不需要header和footer
if(hasHead){
listview.removeHeaderView(tv_head);
hasHead = false;
}
if(hasFoot){
listview.removeFooterView(tv_foot);
hasFoot = false;
}
break;
default:
//其余分类都需要
addHeaderFooter();
break;
}

总结: 多次调用addHeaderView、addFooterView时

1. addHeaderView之前调用setAdapter(null)

2. addFooterView之前调用setAdapter(adapter); //adapter中传入空数据源

问题解决:listview多次调用addHeaderView和addFooterView的更多相关文章

  1. Android listview addHeaderView 和 addFooterView 详解

    addHeaderView()方法:主要是向listView的头部添加布局addFooterView()方法:主要是向listView的底部添加布局 需要注意的是添加布局的时候应该添加从父容器开始添加 ...

  2. RecyclerView更通用——listView的onItemClick,onLongItemClick,addHeaderView,addFooterView

    一.点击事件 setOnItemClickListener,setOnItemLongClickListener RecyclerView中虽然没有提供上面这两个接口,但是给我们提供了另外一个接口:O ...

  3. ListView在列表的头部和底部添加布局——addHeaderView,addFooterView

    addHeaderView()方法:主要是向listView的头部添加布局addFooterView()方法:主要是向listView的底部添加布局 以addHeaderView为例: View he ...

  4. android listview addHeaderView和addFooterView的注意事项

    1. item内如果有button等控件时,在监听listview的onitemclick事件时,焦点会被item内的button. imagebutton等控件抢走,从而导致在listview设置了 ...

  5. Android 关于ListView中adapter调用notifyDataSetChanged无效的原因

    话说这个问题已经困扰我很久了,一直找不到原因,我以为只要数据变了,调用adapter的notifyDataSetChanged就会更新列表,最近在做微博帐号管理这一块,想着动态更新列表,数据是变了,但 ...

  6. android ListView 多次调用 getView方法

    <ListView            android:layout_width="match_parent"            android:layout_heig ...

  7. Android开发之关于ListView中adapter调用notifyDataSetChanged无效的原因

    1.数据源没有更新,调用notifyDataSetChanged无效. 2.数据源更新了,但是它指向新的引用,调用notifyDataSetChanged无效. 3.数据源更新了,但是adpter没有 ...

  8. C# winfrom listview 多窗口调用

    Form1 private void button1_Click(object sender, EventArgs e) { Form f = new Form2(ref listView1); f. ...

  9. 【Android - 自定义View】之自定义可下拉刷新或上拉加载的ListView

    首先来介绍一下这个自定义View: (1)这个自定义View的名称叫做 RefreshableListView ,继承自ListView类: (2)在这个自定义View中,用户可以设置是否支持下拉刷新 ...

随机推荐

  1. 图解SQL的Join

    原文地址:http://coolshell.cn/articles/3463.html 对于SQL的Join,在学习起来可能是比较乱的.我们知道,SQL的Join语法有很多inner的,有outer的 ...

  2. ES6之主要知识点(二) 变量的解构赋值。默认值

    引自http://es6.ruanyifeng.com/#docs/destructuring 数组解构赋值 默认值 对象解构赋值 用途 1.数组的解构赋值 let [a, b, c] = [1, 2 ...

  3. Android开发 Camera2开发_1_拍照功能开发

    介绍 google已经在Android5.1之后取消了对Camera1的更新,转而提供了功能更加强大的Camera2.虽然新版本依然可以使用Camera1但是,不管是各种机型适配还是拍照参数自定义都是 ...

  4. 适配的js

    /** * Created by fanso2o on 2016/9/7. */$(document).ready(function () { function change() { var html ...

  5. CSS 滤镜效果

    本文所描述的滤镜,指的是 CSS3 出来后的滤镜,不是 IE 系列时代的滤镜,语法如下,还未接触过这个属性的可以先简单到 MDN -- filter 了解下: { filter: blur(5px); ...

  6. 微信小程序——页面滑动事件

    wxml: <view id="id" class = "ball" bindtap = "handletap" bindtouchs ...

  7. 深入浅出 Java Concurrency (9): 锁机制 part 4[转]

    本小节介绍锁释放Lock.unlock(). Release/TryRelease unlock操作实际上就调用了AQS的release操作,释放持有的锁. public final boolean ...

  8. Android中Activity和AppcompatActivity的区别(详细解析)

    转载 https://blog.csdn.net/today_work/article/details/79300181 继承AppCompatActivity的界面. 如下图所示: copy界面代码 ...

  9. Spring Cloud中Eureka开启密码认证

    转载自 https://blog.csdn.net/u011499747/article/details/77410997 Eureka服务端配置 添加spring-boot-starter-secu ...

  10. hbase表内存的分布