正 常来说,在ScrollView添加一个ListView后在真机上只会显示ListView的一行多一点,我也不理解为什么会这样,后来我把 ListView的layout_height改成400dip,而不是用match_parent和wrap_content,我发现这样的话 ListView就显示的多了很多。所以就产生了把ListView所有的item的高度算出来给ListView设置的想法。下面是代码:

源码:http://www.jinhusns.com/Products/Download/?type=xcj

Java代码  

  1. public void setListViewHeightBasedOnChildren(ListView listView) {

  2. ListAdapter listAdapter = listView.getAdapter();

  3. if (listAdapter == null) {

  4. return;

  5. }

  6. int totalHeight = 0;

  7. for (int i = 0; i < listAdapter.getCount(); i++) {

  8. View listItem = listAdapter.getView(i, null, listView);

  9. listItem.measure(0, 0);

  10. totalHeight += listItem.getMeasuredHeight();

  11. }

  12. ViewGroup.LayoutParams params = listView.getLayoutParams();

  13. params.height = totalHeight + (listView.getDividerHeight() * (listAdapter.getCount() - 1));

  14. params.height += 5;//if without this statement,the listview will be a little short

  15. listView.setLayoutParams(params);

  16. }

在代码的倒数第二行二我又给加了5个像素,这是因为我在listview的属性里面添加了padding=5dip。 
然后每次ListView的数据一有变化就用这个函数设置一下就好了,不过这样总感觉效率很低,希望有达人给指点一下。

简单来说就是把layout_height写死,这种办法也很适用于GridView(如果能估计得出GridView的高度的话)。

listview与ScrollView老问题的另类解法 
http://www.eoeandroid.com/thread-42893-1-1.html 

几天一直被listview怎么合理的放进scorllview中的问题困扰,尝试过把listview放入scorllview中的朋友都知
道,被放入的listview显示是有问题的,无论怎么设置layout都只显示大概2行的高度,看起来很郁闷,更别说美观了,后来上网查询了一下,解决

方法有的是用linearlayout替换listview,还有修改onmeasure的,我比较懒个人感觉很麻烦不喜欢,终于想出了一个还算和谐的解
决方法:xml中的textlist设置如下:

Java代码  

  1. <?xml version="1.0" encoding="UTF-8"?>

  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

  3. android:layout_width="fill_parent"

  4. android:layout_height="wrap_content"

  5. android:orientation="vertical"

  6. android:background="#44444444">

  7. <ScrollView

  8. android:layout_width="fill_parent"

  9. android:layout_height="wrap_content">

  10. <LinearLayout

  11. android:id="@+id/ll1"

  12. android:layout_width="fill_parent"

  13. android:layout_height="wrap_content"

  14. android:scrollbars="vertical"

  15. android:orientation="vertical"

  16. android:paddingLeft="15dp"

  17. android:paddingRight="15dp"

  18. android:paddingTop="30dp"

  19. android:paddingBottom="30dp"

  20. android:background="#ff888888">

  21. <TextView

  22. android:text="あ"

  23. android:textColor="#ffeeeeee"

  24. android:textSize="18sp"

  25. android:layout_width="fill_parent"

  26. android:layout_height="wrap_content"></TextView>

  27. <ListView

  28. android:scrollbars="none"

  29. android:stackFromBottom="true"

  30. android:id="@+id/lv0"

  31. android:layout_width="fill_parent"

  32. android:layout_height="20dp"></ListView>

  33. </LinearLayout>

  34. </ScrollView>

  35. </LinearLayout>

其中的textview是我做的东西要用到的,和方法无关可以不看,然后就是在java中重新设置listview的高度了,目的是把listview“撑”开: 
LinearLayout.LayoutParams  lp5 =new LinearLayout.LayoutParam(LayoutParams.FILL_PARENT, listItem.size()*51-1); 

中第一个属性不必说了,第二个是为了计算listview要设置的总高度用的,51是我事先设置好的一行的高度(50)+每行之间的间隔(1)
而得来的,listItem.size()是我要显示的行数,用.setLayoutParams(lp5);来重新设置高度,其他别的设置跟以前一样,
想要源码我整理完之后贴出来

如果不想写死 ,Android 解决ListView 和 ScrollView 共存冲突的问题 
http://labs.chinamobile.com/mblog/532767_72693?wralxianxrnx 
http://blog.liaoxiaoqi.com/?p=503

下面是我的一个实现 步骤:

  • 1、继承LinearLayout,既然会冲突那就不用ListView 改成线性布局做动态布局效果

  • 2、继承BaseAdapter ,可以参照一下Android app源码中 Widget 目录下的SimpleAdapter 为前面扩展的LinearLayout做数据。

  • 3、模拟数据填充扩展后的BaseAdapter 为扩展后的LinearLayout 加载数据

第一步:新建LinearLayoutForListView 类使其扩展LinearLayout重写以下两个方法:

Java代码  

  1. public LinearLayoutForListView(Context context) {

  2. super(context);

  3. }

  4. public LinearLayoutForListView(Context context, AttributeSet attrs) {

  5. super(context, attrs);

  6. }

这两个方法可选,不过建议都写上,第一个方法可以让我们通过 编程的方式 实例化出来,第二个方法可以允许我们通过 XML的方式注册 控件,可以在第二个方法里面为扩展的复合组件加属性。为其添加get / set 方法

Java代码  

  1. /**

  2. * 获取Adapter

  3. *

  4. * @return adapter

  5. */

  6. public AdapterForLinearLayout getAdpater() {

  7. return adapter;

  8. }

  9. /**

  10. * 设置数据

  11. *

  12. * @param adpater

  13. */

  14. public void setAdapter(AdapterForLinearLayout adpater) {

  15. this.adapter = adpater;

  16. bindLinearLayout();

  17. }

  18. /**

  19. * 获取点击事件

  20. *

  21. * @return

  22. */

  23. public OnClickListener getOnclickListner() {

  24. return onClickListener;

  25. }

  26. /**

  27. * 设置点击事件

  28. *

  29. * @param onClickListener

  30. */

  31. public void setOnclickLinstener(OnClickListener onClickListener) {

  32. this.onClickListener = onClickListener;

  33. }

  34. sp;

第二步:新建AdapterForLinearLayout 类继承自BaseAdapter,并为其添加构造函数

Java代码  

  1. private LayoutInflater mInflater;

  2. private int resource;

  3. private List<? extends Map<String, ?>> data;

  4. private String[] from;

  5. private int[] to;

  6. public AdapterForLinearLayout(Context context,

  7. List<? extends Map<String, ?>> data, int resouce, String[] from,

  8. int[] to) {

  9. this.data = data;

  10. this.resource = resouce;

  11. this.data = data;

  12. this.from = from;

  13. this.to = to;

  14. this.mInflater = (LayoutInflater) context

  15. .getSystemService(Context.LAYOUT_INFLATER_SERVICE);

  16. }


构造函数模仿 simpleAdapter 通过传进来的resouce 为布局设置数据。通过继承BaseAdapter
重要的实现方法在下面getView ,此方法判断通过传进来的 String[] from 与 int[] to 为分别查找出View
并为View 设置相应的Text,代码如下:

Java代码  

  1. @Override

  2. public View getView(int position, View convertView, ViewGroup parent) {

  3. // TODO Auto-generated method stub

  4. convertView = mInflater.inflate(resource, null);

  5. Map<String, ?> item = data.get(position);

  6. int count = to.length;

  7. for (int i = 0; i < count; i++) {

  8. View v = convertView.findViewById(to[i]);

  9. bindView(v, item, from[i]);

  10. }

  11. convertView.setTag(position);

  12. return convertView;

  13. }

  14. /**

  15. * 绑定视图

  16. * @param view

  17. * @param item

  18. * @param from

  19. */

  20. private void bindView(View view, Map<String, ?> item, String from) {

  21. Object data = item.get(from);

  22. if (view instanceof TextView) {

  23. ((TextView) view).setText(data == null ? "" : data.toString());

  24. }

  25. }

Tip:

  • BindView 方法是一个自定义方法,在方法体内可以为通过判断使本类更具灵活性,如上,你不仅可以判断是TextView 并且可以传入任何你想要的View 只要在方法体内加入相应判断即可,数据可以通过data 做相应处理,具体如何操作读者可另行测试。

  • convertView.setTag(position); 此句代码为View 设置tag 在以后我们可以通过 getTag 找出下标,后文有介绍如何通过下标操作数据。

下面是两个类的全部代码,读者可以无须更改直接使用:

Java代码  

  1. LinearLayoutForListView

  2. package  com.terry.widget;

  3. import  android.content.Context;

  4. import  android.util.AttributeSet;

  5. import  android.util.Log;

  6. import  android.view.View;

  7. import  android.widget.LinearLayout;

  8. public   class  LinearLayoutForListView  extends  LinearLayout {

  9. private  AdapterForLinearLayout adapter;

  10. private  OnClickListener onClickListener  =   null ;

  11. /**

  12. * 绑定布局

  13. */

  14. public   void  bindLinearLayout() {

  15. int  count  =  adapter.getCount();

  16. for  ( int  i  =   0 ; i  <  count; i ++ ) {

  17. View v  =  adapter.getView(i,  null ,  null );

  18. v.setOnClickListener( this .onClickListener);

  19. if  (i  ==  count  -   1 ) {

  20. LinearLayout ly  =  (LinearLayout) v;

  21. ly.removeViewAt( 2 );

  22. }

  23. addView(v, i);

  24. }

  25. Log.v( " countTAG " ,  ""   +  count);

  26. }

  27. public  LinearLayoutForListView(Context context) {

  28. super (context);

  29. }

  30. public  LinearLayoutForListView(Context context, AttributeSet attrs) {

  31. super (context, attrs);

  32. }

  33. /**

  34. * 获取Adapter

  35. *

  36. *  @ return  adapter

  37. */

  38. public  AdapterForLinearLayout getAdpater() {

  39. return  adapter;

  40. }

  41. /**

  42. * 设置数据

  43. *

  44. *  @ param  adpater

  45. */

  46. public   void  setAdapter(AdapterForLinearLayout adpater) {

  47. this .adapter  =  adpater;

  48. bindLinearLayout();

  49. }

  50. /**

  51. * 获取点击事件

  52. *

  53. *  @ return

  54. */

  55. public  OnClickListener getOnclickListner() {

  56. return  onClickListener;

  57. }

  58. /**

  59. * 设置点击事件

  60. *

  61. *  @ param  onClickListener

  62. */

  63. public   void  setOnclickLinstener(OnClickListener onClickListener) {

  64. this .onClickListener  =  onClickListener;

  65. }

  66. }

Java代码  

  1. AdapterForLinearLayout

  2. package  com.terry.widget;

  3. import  java.util.List;

  4. import  java.util.Map;

  5. import  android.content.Context;

  6. import  android.view.LayoutInflater;

  7. import  android.view.View;

  8. import  android.view.ViewGroup;

  9. import  android.widget.BaseAdapter;

  10. import  android.widget.TextView;

  11. public   class  AdapterForLinearLayout  extends  BaseAdapter {

  12. private  LayoutInflater mInflater;

  13. private   int  resource;

  14. private  List <?   extends  Map < String,  ?>>  data;

  15. private  String[] from;

  16. private   int [] to;

  17. public  AdapterForLinearLayout(Context context,

  18. List <?   extends  Map < String,  ?>>  data,  int  resouce, String[] from,

  19. int [] to) {

  20. this .data  =  data;

  21. this .resource  =  resouce;

  22. this .data  =  data;

  23. this .from  =  from;

  24. this .to  =  to;

  25. this .mInflater  =  (LayoutInflater) context

  26. .getSystemService(Context.LAYOUT_INFLATER_SERVICE);

  27. }

  28. @ Override

  29. public   int  getCount() {

  30. //  TODO Auto-generated method stub

  31. return  data.size();

  32. }

  33. @ Override

  34. public  Object getItem( int  position) {

  35. //  TODO Auto-generated method stub

  36. return  data.get(position);

  37. }

  38. @ SuppressWarnings( " unchecked " )

  39. public  String get( int  position, Object key) {

  40. Map < String,  ?>  map  =  (Map < String,  ?> ) getItem(position);

  41. return  map.get(key).toString();

  42. }

  43. @ Override

  44. public   long  getItemId( int  position) {

  45. //  TODO Auto-generated method stub

  46. return  position;

  47. }

  48. @ Override

  49. public  View getView( int  position, View convertView, ViewGroup parent) {

  50. //  TODO Auto-generated method stub

  51. convertView  =  mInflater.inflate(resource,  null );

  52. Map < String,  ?>  item  =  data.get(position);

  53. int  count  =  to.length;

  54. for  ( int  i  =   0 ; i  <  count; i ++ ) {

  55. View v  =  convertView.findViewById(to[i]);

  56. bindView(v, item, from[i]);

  57. }

  58. convertView.setTag(position);

  59. return  convertView;

  60. }

  61. /**

  62. * 绑定视图

  63. *  @ param  view

  64. *  @ param  item

  65. *  @ param  from

  66. */

  67. private   void  bindView(View view, Map < String,  ?>  item, String from) {

  68. Object data  =  item.get(from);

  69. if  (view  instanceof  TextView) {

  70. ((TextView) view).setText(data  ==   null   ?   ""  : data.toString());

  71. }

  72. }

  73. }

对应的XML 如下:

Java代码  

  1. <? xml version="1.0" encoding="UTF-8" ?>

  2. < LinearLayout  xmlns:android ="http://schemas.android.com/apk/res/android"

  3. android:orientation ="vertical"  android:layout_width ="fill_parent"

  4. android:layout_height ="fill_parent" >

  5. < TextView  android:id ="@ +id/TextView01"

  6. android:layout_marginLeft ="10px"  android:textAppearance ="?android:attr/textAppearanceLarge"

  7. android:layout_width ="wrap_content"  android:layout_height ="wrap_content" >

  8. </ TextView >

  9. < TextView  android:id ="@ +id/TextView02"  android:layout_width ="wrap_content"

  10. android:textAppearance ="?android:attr/textAppearanceSmall"

  11. android:layout_marginLeft ="10px"  android:layout_height ="wrap_content" >

  12. </ TextView >

  13. < View  android:layout_height ="1px"  android:background ="#FFFFFF"

  14. android:layout_width ="fill_parent" ></ View >

  15. </ LinearLayout >

第三步:主页面使用控件并为其设置数据

  • XML如下:

    Java代码  

    1. < com.terry.widget.LinearLayoutForListView

    2. android:orientation ="vertical"  android:layout_width ="450px"

    3. android:layout_height ="fill_parent"  android:id ="@ +id/ListView01" >

    4. </ com.terry.widget.LinearLayoutForListView >

  • 加载数据如下:

    Java代码  

    1. lv  =  (LinearLayoutForListView) findViewById(R.id.ListView01);

    2. for  ( int  i  =   0 ; i  <   10 ; i ++ ) {

    3. HashMap < String, Object >  map  =   new  HashMap < String, Object > ();

    4. map.put( " key_name " ,  " name "   +  i);

    5. map.put( " value_name " ,  " value "   +  i);

    6. list.add(map);

    7. }

    8. final  AdapterForLinearLayout Layoutadpater  =   new  AdapterForLinearLayout(

    9. this , list, R.layout.test,  new  String[] {  " key_name " ,

    10. " value_name "  },  new   int [] { R.id.TextView01,

    11. R.id.TextView02 });

  • 事件操作,并通过下标得到数据源:

    Java代码  

    Tip:get方法是在Layoutadpater 封装的一个通过下标获取相应数据的方法请参考上文。

    1. lv.setOnclickLinstener( new  OnClickListener() {

    2. @ Override

    3. public   void  onClick(View v) {

    4. //  TODO Auto-generated method stub

    5. Toast.makeText(

    6. BlueToothActivity. this ,

    7. Layoutadpater.get(Integer.parseInt(v.getTag()

    8. .toString()),  " key_name " ),  1000 ).show();

    9. }

    10. });

    11. lv.setAdapter(Layoutadpater);

至此完成。有碰到这个问题的朋友可以试试。

有人的总结如下:

只要在设置ListView的Adapter后调用此静态方法即可让ListView正确的显示在其父ListView的ListItem中。但是要注意

的是,子ListView的每个Item必须是LinearLayout,不能是其他的,因为其他的Layout(如RelativeLayout)没有
重写onMeasure(),所以会在onMeasure()时抛出异常。
  在ScrollView中嵌套ListView(或者
ScrollView)的另外一个问题就是,子ScrollView中无法滑动的(如果它没有显
示完全的话),因为滑动事件会被父ScrollView吃掉,如果想要让子ScrollView也可以滑动,只能强行截取滑动事件,有牛人在论坛 中发过代码说可以。虽然我没有亲自试过,但估计是可行的。
 
 虽然在ScrollView中显示ScrollView在技术上的难题可以攻破,但是这样的设计却是非常差的用户体验因为用户会不容易看到和操作子
ScrollView中的内容。比如好的设计是,父ListView的每个Item只显示概括性的描述,然后点击其Item会进入另外一个页面来详细描述
和展示以及对这个Item的操作。
 源码:http://www.jinhusns.com/Products/Download/?type=xcj
于是找到另外两种比较简单的方法,而且又没有影响的:
1.在ScrollView中添加一属性 android:fillViewport="true" ,这样就可以让ListView全屏显示了
2.指定ListView的高度 android:layout_height="420dp" ;

ScrollView与ListView冲突解决的更多相关文章

  1. ScrollView 和 ListView 冲突解决方案

    网上说了很多阿,什么linearLayout 实现listView 什么的.还设置高什么的. 其实,你们可能忘记了,如果出现 ScrollView 和 ListView 同时出现,那就是设计错误了. ...

  2. Android ScrollView 嵌套 ListView、 ListView 嵌套ScrollView Scroll事件冲突解决办法

    本人菜鸟一名,最近工作了,开始学习Android. 最近在做项目的时候,UX给了个design,大概就是下拉刷新的ListView中嵌套了ScrollView,而且还要在ScrollView中添加动画 ...

  3. Android之ScrollView嵌套ListView冲突

    在ScrollView中嵌套使用ListView,ListView只会显示一行多一点.两者进行嵌套,即会发生冲突.由于ListView本身都继承于ScrollView,一旦在ScrollView中嵌套 ...

  4. 冲突--ScrollView嵌套ListView冲突问题的最优解决方案

    项目做多了之后,会发现其实 ScrollView嵌套ListVew或者GridView等很常用,但是你也会发现各种奇怪问题产生.根据个人经验现在列出常见问题以及代码最少最简单的解决方法. 问题一 :  ...

  5. ScrollView嵌套ListView冲突问题的最优解决方式

    项目做多了之后.会发现事实上ScrollView嵌套ListVew或者GridView等非经常常使用,可是你也会发现各种奇怪问题产生.依据个人经验如今列出常见问题以及代码最少最简单的解决方法. 问题一 ...

  6. Android之ScrollView嵌套ListView冲突 (listView只显示一行)

    在ScrollView中嵌套使用ListView,ListView只会显示一行多一点.两者进行嵌套,即会发生冲突.由于ListView本身都继承于ScrollView,一旦在ScrollView中嵌套 ...

  7. 解决ScrollView嵌到listView冲突问题

    方法一: 把下面的方法放在绑定适配器操作的下面就行. /** * 重新计算ListView的高度,解决ScrollView和ListView两个View都有滚动的效果,在嵌套使用时起冲突的问题 * @ ...

  8. Android——MeasureSpec学习 - 解决ScrollView嵌套ListView和GridView冲突的方法

      原文地址:http://blog.csdn.net/yuhailong626/article/details/20639217   在自定义View和ViewGroup的时候,我们经常会遇到int ...

  9. ScrollView嵌套使用ListView冲突的解决与分析

    因为ScrollView与ListView都是具有滚动条的控件,所以嵌套在一起使用的时候可能会出现事件的冲突,比如我就遇见了ListView中只显示一条数据的问题.解决的办法,就是自定义了一个List ...

随机推荐

  1. 如何在施工物料管理Web系统中处理大量数据并显示

    最近在开发施工物料管理系统,其中涉及大量的物料信息需要管理和汇总,数据量非常庞大.之前尝试自己通过将原始数据,加工处理建模,在后台代码中通过分组.转置再显示到 Web 页面中,但自己编写的代码量非常大 ...

  2. Atitit vod click event design flow  视频点播系统点击事件文档

    Atitit vod click event design flow  视频点播系统点击事件文档 重构规划1 Click cate1 Click  mov4 重构规划 事件注册,与事件分发管理器分开 ...

  3. Atitit.eclipse 4.3 4.4  4.5 4.6新特性

    Atitit intellij idea的使用总结attilax 1. ideaIC-2016.2.4.exe1 1.1. Ij vs eclipse市场份额1 1.2. Ij的优点(方便的支持gro ...

  4. 更新日志 - BugHD 新增邮件告警功能

    最近 BugHD 又新增了一些功能,包括邮件告警. issue 分享. issue 备注等,同时也做了性能优化.希望能够帮助你更高效地收集解决应用崩溃. BugHD 新增功能 1.邮件告警 除了 We ...

  5. iOS-------应用性能调优的25个建议和技巧

    性能对 iOS 应用的开发尤其重要,如果你的应用失去反应或者很慢,失望的用户会把他们的失望写满App Store的评论.然而由于iOS设备的限制,有时搞好性能是一件难事.开发过程中你会有很多需要注意的 ...

  6. Android 代码混淆之部分类不混淆的技巧

    在编写Android程序之后,我们通常要代码进行混淆编码,这样才能保证市场上我们的应用不会被别人进行反编译,然后破解,所以此时需要在发布正式版本的时候,有一些类事不能混淆的,比如实现了 Seriali ...

  7. VS报错:_CRT_SECURE_NO_WARNINGS

    常见报错:warning C4996: 'fopen': This function or variable may be unsafe. Consider using fopen_s instead ...

  8. 基于asp.net+MINIUI的项目----在线学习系统

    1 数据库列的自动计算: 描述:一张选课表,其中有学习的开始时间和结束时间,一个列用来计算学习的总时间(小时) 解决:选择该列 属性:计算列规范:公式:(datediff(hour,[StartTim ...

  9. CSS 性能

    http://boagworld.com/dev/why-you-should-care-about-css-page-performance/ http://css-tricks.com/effic ...

  10. hibernate(二)annotation第一个示例

    一.在数据库中创建teacher表(数据库hibernate) create table teache( id int auto_increment primary key, name ), titl ...