处理ScrollView和ListView,GridView之间的冲突,

最好的办法就是继承这两个类,重写他们的onMeasure方法即可:

ListView:

import android.widget.ListView;

/**
* ScrollView中嵌入ListView,让ListView全显示出来
* @author John
*
*/
public class MyListView extends ListView{ public MyListView(android.content.Context context,android.util.AttributeSet attrs){
super(context, attrs);
} /**
* 设置不滚动
*/
public void onMeasure(int widthMeasureSpec, int heightMeasureSpec)
{
int expandSpec = MeasureSpec.makeMeasureSpec(Integer.MAX_VALUE >> 2,
MeasureSpec.AT_MOST);
super.onMeasure(widthMeasureSpec, expandSpec); } }

GridView:

import android.widget.GridView;

public class MyGridView extends GridView {
public MyGridView(android.content.Context context,
android.util.AttributeSet attrs) {
super(context, attrs);
} /**
* 设置不滚动
*/
public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
int expandSpec = MeasureSpec.makeMeasureSpec(Integer.MAX_VALUE >> 2,
MeasureSpec.AT_MOST);
super.onMeasure(widthMeasureSpec, expandSpec); } }

如果是ListView中嵌套GridView也可以用这个办法。简单实用的处理了这个冲突。

下面是重写ScrollView,实现有弹性的ScrollView

/**
* 有弹性的ScrollView
* 实现下拉弹回和上拉弹回
* @author John
*/
public class OwnScroview extends ScrollView { private static final String TAG = "ElasticScrollView"; //移动因子, 是一个百分比, 比如手指移动了100px, 那么View就只移动20px
//目的是达到一个延迟的效果
private static final float MOVE_FACTOR = 0.4f; //松开手指后, 界面回到正常位置需要的动画时间
private static final int ANIM_TIME = 300; //ScrollView的子View, 也是ScrollView的唯一一个子View
private View contentView; //手指按下时的Y值, 用于在移动时计算移动距离
//如果按下时不能上拉和下拉, 会在手指移动时更新为当前手指的Y值
private float startY; //用于记录正常的布局位置
private Rect originalRect = new Rect(); //手指按下时记录是否可以继续下拉
private boolean canPullDown = false; //手指按下时记录是否可以继续上拉
private boolean canPullUp = false; //在手指滑动的过程中记录是否移动了布局
private boolean isMoved = false; public OwnScroview(Context context) {
super(context);
} public OwnScroview(Context context, AttributeSet attrs) {
super(context, attrs);
} @Override
protected void onFinishInflate() {
if (getChildCount() > 0) {
contentView = getChildAt(0);
}
} @Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
super.onLayout(changed, l, t, r, b); if(contentView == null) return; //ScrollView中的唯一子控件的位置信息, 这个位置信息在整个控件的生命周期中保持不变
originalRect.set(contentView.getLeft(), contentView.getTop(), contentView
.getRight(), contentView.getBottom());
} /**
* 在触摸事件中, 处理上拉和下拉的逻辑
*/
@Override
public boolean dispatchTouchEvent(MotionEvent ev) { if (contentView == null) {
return super.dispatchTouchEvent(ev);
} int action = ev.getAction(); switch (action) {
case MotionEvent.ACTION_DOWN: //判断是否可以上拉和下拉
canPullDown = isCanPullDown();
canPullUp = isCanPullUp(); //记录按下时的Y值
startY = ev.getY();
break; case MotionEvent.ACTION_UP: if(!isMoved) break; //如果没有移动布局, 则跳过执行 // 开启动画
TranslateAnimation anim = new TranslateAnimation(0, 0, contentView.getTop(),
originalRect.top);
anim.setDuration(ANIM_TIME); contentView.startAnimation(anim); // 设置回到正常的布局位置
contentView.layout(originalRect.left, originalRect.top,
originalRect.right, originalRect.bottom); //将标志位设回false
canPullDown = false;
canPullUp = false;
isMoved = false; break;
case MotionEvent.ACTION_MOVE: //在移动的过程中, 既没有滚动到可以上拉的程度, 也没有滚动到可以下拉的程度
if(!canPullDown && !canPullUp) {
startY = ev.getY();
canPullDown = isCanPullDown();
canPullUp = isCanPullUp(); break;
} //计算手指移动的距离
float nowY = ev.getY();
int deltaY = (int) (nowY - startY); //是否应该移动布局
boolean shouldMove =
(canPullDown && deltaY > 0) //可以下拉, 并且手指向下移动
|| (canPullUp && deltaY< 0) //可以上拉, 并且手指向上移动
|| (canPullUp && canPullDown); //既可以上拉也可以下拉(这种情况出现在ScrollView包裹的控件比ScrollView还小) if(shouldMove){
//计算偏移量
int offset = (int)(deltaY * MOVE_FACTOR); //随着手指的移动而移动布局
contentView.layout(originalRect.left, originalRect.top + offset,
originalRect.right, originalRect.bottom + offset); isMoved = true; //记录移动了布局
} break;
default:
break;
} return super.dispatchTouchEvent(ev);
} /**
* 判断是否滚动到顶部
*/
private boolean isCanPullDown() {
return getScrollY() == 0 ||
contentView.getHeight() < getHeight() + getScrollY();
} /**
* 判断是否滚动到底部
*/
private boolean isCanPullUp() {
return contentView.getHeight() <= getHeight() + getScrollY();
} }

然后再xml中用上就行了。

android 有弹性的ScrollView 简单实现,与处理ScrollView和ListView,GridView之间的冲突的更多相关文章

  1. ScrollView listView gridView 之间的冲突问题

    在ScrollView中的listView gridView添加适配器之后添加//设置gridView整体的高度 public void setListViewHeightBasedOnChildre ...

  2. android scrollview 简单的使用

    以前写的Scrollview ,通常都是与Listview结合使用,不过因复杂可能新手不太懂,网上有许多文章,这里就不贴那个了DEMO了.  写了个简单的供大家参考:这样比较好理解(需要复杂的可以Q我 ...

  3. Android ScrollView嵌套HorizontalScrollView 滑动问题 ScrollView包括GridView显示问题

    今天项目使用到ScrollView嵌套HorizontalScrollView,ScrollView里包括GridView,发现几个问题非常经典.在此记录: 问题1.ScrollView嵌套Horiz ...

  4. Xamarin.Android之引导页的简单制作

    0x01 前言 对于现在大部分的APP,第一次打开刚安装或更新安装的APP都会有几个引导界面,通常这几个引导页是告诉用户 APP有些什么功能或者修改了什么bug.新增了什么功能等等等. 下面就用Xam ...

  5. Android Activity的生命周期简单总结

    Android Activity的生命周期简单总结 这里的内容参考官方的文档,这篇文章的目的不是去总结Activity是如何启动,如何创造,以及暂停和销毁的,而是从实际开发中分析在Activity各个 ...

  6. Android 设计随便说说之简单实践(合理组合)

    上一篇(Android 设计随便说说之简单实践(模块划分))例举了应用商店设计来说明怎么做模块划分.模块划分主要依赖于第一是业务需求,具体是怎么样的业务.应用商店则包括两个业务,就是向用户展示appl ...

  7. 怎样在Android实现桌面清理内存简单Widget小控件

    怎样在Android实现桌面清理内存简单Widget小控件 我们常常会看到类似于360.金山手机卫士一类的软件会带一个widget小控件,显示在桌面上,上面会显示现有内存大小,然后会带一个按键功能来一 ...

  8. Android BLE与终端通信(一)——Android Bluetooth基础API以及简单使用获取本地蓝牙名称地址

    Android BLE与终端通信(一)--Android Bluetooth基础API以及简单使用获取本地蓝牙名称地址 Hello,工作需要,也必须开始向BLE方向学习了,公司的核心技术就是BLE终端 ...

  9. Android peferenceActivity 自己定义标题简单方法

    Android peferenceActivity 自己定义标题简单方法 peferenceActivity 全然使用定义好的布局. 因此不能简单象其他好窗体进行自定,如今我们须要加 一个自己定义标题 ...

随机推荐

  1. 一、Hello World

    刚创建的Android项目是一个基础的Hello World项目,包含一些默认文件,我们需要花一点时间看看最重要的部分: activity_main.xml  -- 这是刚才用Android Stud ...

  2. linux文件权限查看及修改(实用)

    查看Linux文件的权限:ls -l 文件名称 查看linux文件夹的权限:ls -ld 文件夹名称(所在目录) 修改文件及文件夹权限: sudo chmod -(代表类型)×××(所有者)×××(组 ...

  3. MariaDB 在 Windows 下 noinstall 版本的安装和配置

    1. 下载并解压 noinstall 压缩包,假设解压到 D:\APP\mariadb-10.0.17-winx64 目录 下载地址(MariaDB 10.0.17 Stable):llarian.n ...

  4. smarty模板中如何嵌入javascript脚本

    [官方网站](http://www.php100.com/manual/smarty/) 在smarty文件里直接写javascript代码时候,造成500错误. javascript代码有很多的{} ...

  5. [转]解决:Entity Framework + MariaDb(MySql)中文乱码

    转自:http://fenglongsheng.com/post/6640.html 今天写一MVC4+Entity Framework+Mysql的小例子时,发现中文写到数据库里是N个问号(乱码哦~ ...

  6. hdu4449Building Design(三维凸包+平面旋转)

    链接 看了几小时也没看懂代码表示的何意..无奈下来问问考研舍友. 还是考研舍友比较靠谱,分分钟解决了我的疑问. 可能三维的东西在纸面上真的不好表示,网上没有形象的题解,只有简单"明了&quo ...

  7. Gevent中的同步与异步详解

    同步,异步概念 1.同步就是发生调用时,一定等待结果返回,整个调用才结束: 2.异步就是发生调用后,立即返回,不等待结果返回.被调用者通过状态.通知来通知调用者,或通过回调函数处理这个调用. 查询 1 ...

  8. jQurey Plugin

    ; (function ($, window, document, undefined) { "use strict"; var defaults = { name: " ...

  9. JavaScript实现输入验证(简单的用户注册)

    1.先写用户注册页面userrAdd.jsp <body> <center> <form name="f1" id="f1" ac ...

  10. html文件里引入文件html文件

    导入通用的代码除了使用php外 iframe在很多界面使用起来比较方便 比如说要写导航 在好几个界面都要用这个导航 可以用iframe引用 实例:这个header.html是我写的一个导航界面 在in ...