您的位置:首页 > 移动开发 > Android开发

Android ListView监听上下滑动(判断是否显示返回顶部按钮)

2016-03-08 17:56 831 查看
在有些listview上面和ScrollView上,当滑动到底部的时候,在右下角会出现一个回到顶部的按钮,提供更好的用户体验。

效果图如下:



布局

先说布局,可以用帧布局Framelayout,也可以用相对布局relativelayout.看下listview的布局文件:

[html] view
plain copy

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

xmlns:tools="http://schemas.android.com/tools"

android:layout_width="match_parent"

android:layout_height="match_parent"

android:background="@android:color/white" >

<ListView

android:id="@+id/my_listView"

android:layout_width="fill_parent"

android:layout_height="wrap_content"

android:layout_marginLeft="10dp"

android:layout_marginRight="10dp" />

<Button

android:id="@+id/top_btn"

android:layout_width="50dp"

android:layout_height="50dp"

android:visibility="gone"

android:layout_alignParentBottom="true"

android:layout_alignParentRight="true"

android:layout_marginBottom="6dp"

android:layout_marginRight="6dp"

android:background="@drawable/top_btn_bg"

android:gravity="center"

android:text="顶" />

</RelativeLayout>

Listview 回到顶部的活动代码

是从网上找到的代码,作者为:zihao

[java] view
plain copy

/**

* 主界面

*

* @author zihao

* @details 因为有些手机是有虚拟按键的(在计算屏幕分辨率的时候,有些可以去除掉虚拟区域的区域->如三星,有些不行->如MX3),为了计算的准确性,

* 各位可以设置Activity为Theme

* .NoTitleBar.Fullscreen填满屏幕(解决类似MX3这种在计算过程中把虚拟键盘算入屏幕高度的)。

*/

public class ListActivity extends Activity implements OnClickListener {

private ListView listView;// List数据列表

private Button toTopBtn;// 返回顶部的按钮

private MyAdapter adapter;

private boolean scrollFlag = false;// 标记是否滑动

private int lastVisibleItemPosition = 0;// 标记上次滑动位置

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

setContentView(R.layout.activity_list);

initView();

}

/**

* 初始化视图

*/

private void initView() {

listView = (ListView) findViewById(R.id.my_listView);

toTopBtn = (Button) findViewById(R.id.top_btn);

adapter = new MyAdapter(this, getTitleDatas());

listView.setAdapter(adapter);

toTopBtn.setOnClickListener(this);

listView.setOnScrollListener(new OnScrollListener() {

@Override

public void onScrollStateChanged(AbsListView view, int scrollState) {

// TODO Auto-generated method stub

switch (scrollState) {

// 当不滚动时

case OnScrollListener.SCROLL_STATE_IDLE:// 是当屏幕停止滚动时

scrollFlag = false;

// 判断滚动到底部

if (listView.getLastVisiblePosition() == (listView

.getCount() - 1)) {

toTopBtn.setVisibility(View.VISIBLE);

}

// 判断滚动到顶部

if (listView.getFirstVisiblePosition() == 0) {

toTopBtn.setVisibility(View.GONE);

}

break;

case OnScrollListener.SCROLL_STATE_TOUCH_SCROLL:// 滚动时

scrollFlag = true;

break;

case OnScrollListener.SCROLL_STATE_FLING:// 是当用户由于之前划动屏幕并抬起手指,屏幕产生惯性滑动时

scrollFlag = false;

break;

}

}

/**

* firstVisibleItem:当前能看见的第一个列表项ID(从0开始)

* visibleItemCount:当前能看见的列表项个数(小半个也算) totalItemCount:列表项共数

*/

@Override

public void onScroll(AbsListView view, int firstVisibleItem,

int visibleItemCount, int totalItemCount) {

// 当开始滑动且ListView底部的Y轴点超出屏幕最大范围时,显示或隐藏顶部按钮

if (scrollFlag

&& ScreenUtil.getScreenViewBottomHeight(listView) >= ScreenUtil

.getScreenHeight(ListActivity.this)) {

if (firstVisibleItem > lastVisibleItemPosition) {// 上滑

toTopBtn.setVisibility(View.VISIBLE);

} else if (firstVisibleItem < lastVisibleItemPosition) {// 下滑

toTopBtn.setVisibility(View.GONE);

} else {

return;

}

lastVisibleItemPosition = firstVisibleItem;

}

}

});

}

/**

* 获取标题数据列表

*

* @return

*/

private List<String> getTitleDatas() {

List<String> titleArray = new ArrayList<String>();

for (int i = 0; i < 30; i++) {

titleArray.add("这是第" + i + "个item");

}

return titleArray;

}

/**

* 滚动ListView到指定位置

*

* @param pos

*/

private void setListViewPos(int pos) {

if (android.os.Build.VERSION.SDK_INT >= 8) {

listView.smoothScrollToPosition(pos);

} else {

listView.setSelection(pos);

}

}

@Override

public void onClick(View v) {

// TODO Auto-generated method stub

switch (v.getId()) {

case R.id.top_btn:// 点击按钮返回到ListView的第一项

setListViewPos(0);

break;

}

}

}

在上面的代码中,对listview 设置 setOnScrollListener 监听;当有一点滑动(也可以提供一个值)或者是到达底部的时候就出现回到顶部的按钮。

scrollview的代码

有很多知识点:

scrollview的滑动停止监听。
scrollview回到顶部,或者底部的方法。
scrollview到达顶部或者底部的判断方法。

上面的参考连接也都写在注释里面了。

[java] view
plain copy

public class ScrollViewActivity extends Activity implements OnClickListener {

private ScrollView scrollView;// scrollView数据列表

private Button toTopBtn;// 返回顶部的按钮

private int scrollY = 0;// 标记上次滑动位置

private View contentView;

private final String TAG="test";

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

setContentView(R.layout.activity_scroll);

initView();

}

/**

* 初始化视图

*/

private void initView() {

scrollView = (ScrollView) findViewById(R.id.my_scrollView);

if (contentView == null) {

contentView = scrollView.getChildAt(0);

}

toTopBtn = (Button) findViewById(R.id.top_btn);

toTopBtn.setOnClickListener(this);

//http://blog.csdn.net/jiangwei0910410003/article/details/17024287

/******************** 监听ScrollView滑动停止 *****************************/

scrollView.setOnTouchListener(new OnTouchListener() {

private int lastY = 0;

private int touchEventId = -9983761;

Handler handler = new Handler() {

@Override

public void handleMessage(Message msg) {

super.handleMessage(msg);

View scroller = (View) msg.obj;

if (msg.what == touchEventId) {

if (lastY == scroller.getScrollY()) {

handleStop(scroller);

} else {

handler.sendMessageDelayed(handler.obtainMessage(

touchEventId, scroller), 5);

lastY = scroller.getScrollY();

}

}

}

};

public boolean onTouch(View v, MotionEvent event) {

if (event.getAction() == MotionEvent.ACTION_UP) {

handler.sendMessageDelayed(

handler.obtainMessage(touchEventId, v), 5);

}

return false;

}

/**

* ScrollView 停止

*

* @param view

*/

private void handleStop(Object view) {

Log.i(TAG,"handleStop");

ScrollView scroller = (ScrollView) view;

scrollY = scroller.getScrollY();

doOnBorderListener();

}

});

/***********************************************************/

}

/**

* ScrollView 的顶部,底部判断:

* http://www.trinea.cn/android/on-bottom-load-more-scrollview-impl/
*

* 其中getChildAt表示得到ScrollView的child View, 因为ScrollView只允许一个child

* view,所以contentView.getMeasuredHeight()表示得到子View的高度,

* getScrollY()表示得到y轴的滚动距离,getHeight()为scrollView的高度。

* 当getScrollY()达到最大时加上scrollView的高度就的就等于它内容的高度了啊~

*

* @param pos

*/

private void doOnBorderListener() {

Log.i(TAG,ScreenUtil.getScreenViewBottomHeight(scrollView) + " "

+ scrollView.getScrollY()+" "+ ScreenUtil

.getScreenHeight(ScrollViewActivity.this));

// 底部判断

if (contentView != null

&& contentView.getMeasuredHeight() <= scrollView.getScrollY()

+ scrollView.getHeight()) {

toTopBtn.setVisibility(View.VISIBLE);

Log.i(TAG,"bottom");

}

// 顶部判断

else if (scrollView.getScrollY() == 0) {

Log.i(TAG,"top");

}

else if (scrollView.getScrollY() > 30) {

toTopBtn.setVisibility(View.VISIBLE);

Log.i(TAG,"test");

}

}

/**

* 下面我们看一下这个函数: scrollView.fullScroll(ScrollView.FOCUS_DOWN);滚动到底部

* scrollView.fullScroll(ScrollView.FOCUS_UP);滚动到顶部

*

*

* 需要注意的是,该方法不能直接被调用 因为Android很多函数都是基于消息队列来同步,所以需要一部操作,

* addView完之后,不等于马上就会显示,而是在队列中等待处理,虽然很快, 但是如果立即调用fullScroll,

* view可能还没有显示出来,所以会失败 应该通过handler在新线程中更新

*

* http://blog.csdn.net/t12x3456/article/details/12799825
* http://www.tuicool.com/articles/zayIjq
*/

@Override

public void onClick(View v) {

// TODO Auto-generated method stub

switch (v.getId()) {

case R.id.top_btn :

scrollView.post(new Runnable() {

@Override

public void run() {

scrollView.fullScroll(ScrollView.FOCUS_UP);

}

});

toTopBtn.setVisibility(View.GONE);

break;

}

}

}

很多细节都注释在代码里面了,参考链接也已经加上。大家下载下代码执行一下看看。
代码http://download.csdn.net/detail/jjdhshdahhdd/9059757
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: