读书人

Android ScrollView与ListView,GridVi

发布时间: 2012-10-17 10:25:46 作者: rapoo

Android ScrollView与ListView,GridView共存冲突解决方案

我们在真实项目中通常会遇到ListView或者GridView嵌套在ScrollView中问题。但是做的时候会发现,一旦两者进行嵌套,即会发生冲突。得不到我们希望的效果。由于ListView和GridView本身都继承于ScrollView,一旦在ScrollView中嵌套ScrollView,那么里面的ScrollView高度计算就会出现问题。我们也就无法得到想要的效果。下面进入正题,我们将分别讨论ScrollView中嵌套ListView和FGridView的情况:

核心解决方案: 重写ListView或者GridView的OnMesure 方法:

@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {// TODO Auto-generated method stubint expandSpec = MeasureSpec.makeMeasureSpec(                 Integer.MAX_VALUE >> 2, MeasureSpec.AT_MOST); super.onMeasure(widthMeasureSpec, expandSpec);}


一、ScrollView中嵌套ListView

BlogScrollViewActivity.java代码:

package com.csdn.blog.scrollview;import android.app.Activity;import android.os.Bundle;import android.view.View;import android.view.ViewGroup;import android.widget.ArrayAdapter;import android.widget.BaseAdapter;import android.widget.GridView;import android.widget.ImageView;import android.widget.LinearLayout;import android.widget.ListView;import android.widget.ScrollView;import android.widget.LinearLayout.LayoutParams;import android.widget.TextView;public class BlogScrollViewActivity extends Activity {    /** Called when the activity is first created. *///MyGridView  grid;ImageView image;ScrollView scroll;String[] texts=new String[]{"无线","通话设置","声音","显示","位置",                    "应用","账户","隐私权","存储","语言","游戏","娱乐","电影","音乐",                    "辅助功能","日期"};/*ArrayAdapter<String> adapter;*/TestListView list;LinearLayout.LayoutParams lp;    @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);        init();    }    void init(){    list=(TestListView)findViewById(R.id.list);    image=(ImageView)findViewById(R.id.image);    list.setAdapter(new GridAdapter(this));    scroll=(ScrollView)findViewById(R.id.scroll);    scroll.requestChildFocus(image, null);    }    private class GridAdapter extends BaseAdapter{    Activity context;    public GridAdapter(Activity context){    this.context=context;    }@Overridepublic int getCount() {// TODO Auto-generated method stubreturn texts.length;}@Overridepublic Object getItem(int position) {// TODO Auto-generated method stubreturn null;}@Overridepublic long getItemId(int position) {// TODO Auto-generated method stubreturn 0;}@Overridepublic View getView(int position, View convertView, ViewGroup parent) {// TODO Auto-generated method stubViewHolder holder=null;if(convertView==null){convertView=context.getLayoutInflater().inflate(R.layout.item, null);holder=new ViewHolder();holder.text=(TextView)convertView.findViewById(R.id.grid_text);convertView.setTag(holder);}else{holder=(ViewHolder)convertView.getTag();}holder.text.setText(texts[position]);return convertView;}class ViewHolder {TextView text;}        }}


TestListView.java代码如下:

package com.csdn.blog.scrollview;import android.content.Context;import android.util.AttributeSet;import android.view.View.MeasureSpec;import android.widget.ListView;public class TestListView extends ListView{public TestListView(Context context) {super(context);// TODO Auto-generated constructor stub}public TestListView(Context context, AttributeSet attrs) {super(context, attrs);// TODO Auto-generated constructor stub}public TestListView(Context context, AttributeSet attrs, int defStyle) {super(context, attrs, defStyle);// TODO Auto-generated constructor stub}@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {// TODO Auto-generated method stubint expandSpec = MeasureSpec.makeMeasureSpec(                 Integer.MAX_VALUE >> 2, MeasureSpec.AT_MOST); super.onMeasure(widthMeasureSpec, expandSpec);}}


main.xml代码:

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:orientation="vertical" android:background="#FFFFFF" > <ScrollView android:layout_height="fill_parent" android:layout_width="fill_parent" android:fadingEdgeLength="0dp" android:scrollbars="none" android:id="@+id/scroll"> <LinearLayout android:layout_height="fill_parent" android:layout_width="fill_parent" android:orientation="vertical" > <ImageView android:id="@+id/image" android:layout_height="150dp" android:layout_width="fill_parent" android:padding="2dp" android:scaleType="centerCrop" android:src="@drawable/fruit"

/> <com.csdn.blog.scrollview.TestListView android:id="@+id/list" android:layout_height="fill_parent" android:layout_width="fill_parent" android:fadingEdgeLength="0dp" android:scrollbars="none" /> </LinearLayout> </ScrollView>

</LinearLayout>

效果图如下:


Android ScrollView与ListView,GridView共处冲突解决方案

这里我的布局方式是上面一张图片,下面放置listView。

对于此种布局方式,可以通过另外一种方式避免此问题。由于ListView有addHeadView()方法,那么我们可以直接将上面想加入的View通过 getLayoutInflater().inflate(this,R.layout.***) 加入到ListView的顶部即可。

二、ScrollView中嵌套GridView的解决方案。

ScrollView中嵌套GridView ,最简单的方法就是重写GridView方法,使其在绘制时重新计算GridView高度

MyGridView.java代码如下:

package com.csdn.blog.scrollview;import android.content.Context;import android.util.AttributeSet;import android.widget.GridView;public class MyGridView extends GridView{public MyGridView(Context context, AttributeSet attrs, int defStyle) {super(context, attrs, defStyle);// TODO Auto-generated constructor stub}public MyGridView(Context context, AttributeSet attrs) {super(context, attrs);// TODO Auto-generated constructor stub}public MyGridView(Context context) {super(context);// TODO Auto-generated constructor stub}@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {// TODO Auto-generated method stubint expandSpec = MeasureSpec.makeMeasureSpec(                 Integer.MAX_VALUE >> 2, MeasureSpec.AT_MOST);         super.onMeasure(widthMeasureSpec, expandSpec); }}


main.xml代码如下:

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:layout_width="fill_parent"    android:layout_height="fill_parent"    android:orientation="vertical"     android:background="#FFFFFF"    >    <ScrollView        android:layout_height="fill_parent"        android:layout_width="fill_parent"        android:fadingEdgeLength="0dp"        android:scrollbars="none"        android:id="@+id/scroll">        <LinearLayout            android:layout_height="fill_parent"            android:layout_width="fill_parent"            android:orientation="vertical"            >    <ImageView        android:id="@+id/image"        android:layout_height="150dp"        android:layout_width="fill_parent"        android:padding="2dp"        android:scaleType="centerCrop"        android:src="@drawable/fruit"        />    <com.csdn.blog.scrollview.MyGridView        android:layout_marginTop="10dp"        android:id="@+id/grid"        android:layout_height="fill_parent"        android:layout_width="fill_parent"        android:fadingEdgeLength="0dp"        android:scrollbars="none"        android:numColumns="3"        />        </LinearLayout>    </ScrollView></LinearLayout>


主类主要就是GridVIew数据绑定。简单贴下代码:

package com.csdn.blog.scrollview;import android.app.Activity;import android.os.Bundle;import android.view.View;import android.view.ViewGroup;import android.widget.ArrayAdapter;import android.widget.BaseAdapter;import android.widget.GridView;import android.widget.ImageView;import android.widget.LinearLayout;import android.widget.ListView;import android.widget.ScrollView;import android.widget.LinearLayout.LayoutParams;import android.widget.TextView;public class BlogScrollViewActivity extends Activity {    /** Called when the activity is first created. */MyGridView  grid;ImageView image;ScrollView scroll;String[] texts=new String[]{"无线","通话设置","声音","显示","位置",                    "应用","账户","隐私权","存储","语言","游戏","娱乐","电影","音乐",                    "辅助功能","日期"};ArrayAdapter<String> adapter;LinearLayout.LayoutParams lp;    @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);        init();    }    void init(){    image=(ImageView)findViewById(R.id.image);    grid=(MyGridView)findViewById(R.id.grid);    grid.setAdapter(new GridAdapter(this));    scroll=(ScrollView)findViewById(R.id.scroll);    scroll.requestChildFocus(image, null);    }    private class GridAdapter extends BaseAdapter{    Activity context;    public GridAdapter(Activity context){    this.context=context;    }@Overridepublic int getCount() {// TODO Auto-generated method stubreturn texts.length;}@Overridepublic Object getItem(int position) {// TODO Auto-generated method stubreturn null;}@Overridepublic long getItemId(int position) {// TODO Auto-generated method stubreturn 0;}@Overridepublic View getView(int position, View convertView, ViewGroup parent) {// TODO Auto-generated method stubViewHolder holder=null;if(convertView==null){convertView=context.getLayoutInflater().inflate(R.layout.item, null);holder=new ViewHolder();holder.image=(ImageView)convertView.findViewById(R.id.grid_image);holder.text=(TextView)convertView.findViewById(R.id.grid_text);convertView.setTag(holder);}else{holder=(ViewHolder)convertView.getTag();}holder.image.setImageResource(R.drawable.meinv);holder.text.setText(texts[position]);return convertView;}class ViewHolder {ImageView image;TextView text;}        }}


上述代码中 scroll.requestChildFocus(image, null); 此句主要是修复了程序进入时GridView会滑动到顶端的小bug。

效果图如下:

Android ScrollView与ListView,GridView共处冲突解决方案

读书人网 >Android

热点推荐