Android-->关于ScrollView、ListView嵌套ListeView所出现的问题(心得)

来源:互联网 发布:java 运行jar 依赖包 编辑:程序博客网 时间:2024/06/05 04:38

    ListView是开发过程中经常打交道的控件之一,但是使用过程中需要主要很多事项。譬如,如果ListView的高度不是设置为match_parent或者高度值确定的话,那么在getView()方法你会发现,getView()方法被调用多轮而且所以的ListView item都会跑到不管是否正在屏幕上显示。此时我们所使用的ListView缓存机制感觉就是无效的。自己查了资料发现,如果ListView的高度不确定的话,其实系统是无法很快确定有多少item显示与屏幕上。只有不断的通过measure才能确定,这也导致了getview方法执行多次。所以在使用ListView过程中尽量确定其高度(同时包括其结点上的Parent View),不然对性能是很大的消耗。

   知道了上面所提到的问题,我们就知道了为什么Google不建议ScrollView中嵌套ListView了,因为ScrollView的child View只能是warp_content。当然网上针对嵌套问题也给出了某些解决方案。例如:

public class MyListView extends ListView {  private boolean isOnMeasure = false;  public MyListView(Context context, AttributeSet attrs) {    super(context, attrs);    // TODO Auto-generated constructor stub  }  @Override  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {    // TODO Auto-generated method stub    isOnMeasure = true;    super.onMeasure(widthMeasureSpec, heightMeasureSpec);  }  @Override  protected void onLayout(boolean changed, int l, int t, int r, int b) {    // TODO Auto-generated method stub    isOnMeasure = false;    super.onLayout(changed, l, t, r, b);  }  public boolean isOnMeasure() {    return isOnMeasure;  }}
接着只需要在你的Adapter中getView方法调用就行例如:

  @Override  public View getView(int position, View convertView, ViewGroup parent) {    // TODO Auto-generated method stub    Holder holder = null;    if (convertView == null) {      holder = new Holder();      convertView = LayoutInflater.from(mContext).inflate(R.layout.listview_item, null);      ..........      convertView.setTag(holder);    }    else {      holder = (Holder)convertView.getTag();    }    //一定要在完成convertView初始化之后调用    if ( ((ListView)parent).isOnMeasure()) {      return convertView;    }    ......  }
这种方法,我在ListView中嵌套ListView(将ListView添加到另外ListView的headerView中)测试了下,当每个item的高度是相同的没有问题。如果不同的话就会出现内容显示不全的bug。

所以这种这种方案也不是完美方案。如果需要在ListView的头或尾添加其他View,推荐使用ListView的addHeaderView()方法和BaseAdapter中getItemViewType()方法结合使用。关于BaseAdapter中getItemViewType中网上有很多教程,主要作用是使ListView中的item填充不同的布局。

最后提醒下,对于ListView的嵌套使用一定要慎重,因为坑很多!


3 0