当它太短滚动滚动型不刷卡 [英] Scrollview doesn't swipe when it's too short to scroll

查看:186
本文介绍了当它太短滚动滚动型不刷卡的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是pretty的新的Andr​​oid应用程序开发,我一直在玩弄采用了Android的SimpleOnGestureListener和ViewFlipper轻扫手势。还有ViewFlipper的3个孩子,并且各自是滚动型。他们都动态填充的活动负载时,他们以后不会改变。在滚动型是其中SimpleOnGestureListeners连接。

I'm pretty new to Android app development, and I've been playing around with swipe gestures using Android's SimpleOnGestureListener and a ViewFlipper. There are 3 children of the ViewFlipper, and each is a ScrollView. They're all dynamically populated when the Activity loads, and they don't change after that. The ScrollView is where the SimpleOnGestureListeners are attached.

下面是我使用的布局:
+ ViewFlipper
++滚动型(×3,一个用于每个页面,每次用以下:)
+++的LinearLayout(垂直)
++++的TextView
++++ TableLayout(动态填充W / TableRows)
++++查看

Here's the layout I'm using:
+ViewFlipper
++ScrollView (x3, one for each page, each with the following:)
+++LinearLayout (vertical)
++++TextView
++++TableLayout (dynamically populated w/TableRows)
++++View

我延长了onFling方法与普通教程code,你可以找到在网上的任何地方,而且它的伟大工程 - 除了当ScrollViews之一没有包含足够的内容进行滚动。

I extended the onFling method with the common tutorial code you can find anywhere online, and it works great--except when one of the ScrollViews doesn't contain enough content to scroll.

我已经缩小的问题,减少了重写,并要求对超级每个人的SimpleOnGestureListener的方法来添加打印到日志触摸检测。

I've narrowed the problem down to touch detection by overriding and calling super on every one of the SimpleOnGestureListener's methods to add a print-to-log.

当我刷卡的卷轴,我得到在onFling等,在onScroll的东西充满了中的onClick在一个页面太短滚动页面上,我在OnShow中$得到中的onClick 在onLong preSSP $ PSS,而这只有当我碰在的过于短滚动型的儿童内容的 - 如果我摸别的地方我没有得到任何事件都没有。

When I swipe on a page that scrolls, I get something full of "in onClick" "in onScroll" "in onFling" etc. On a page that's too short to scroll, I get "in onClick" "in onShowPress" "in onLongPress", and that's only if I'm touching the content within the too-short scrollview's children--if I touch elsewhere I get no events at all.

什么是错的,或者如何检测滑动手势无论是滚动型有多大的想法?

Ideas on what's wrong, or how to detect the swipe gesture no matter how big the ScrollView is?

编辑:我已经决定,当我运行这个在Android 2.2模拟器,而不是Android的2.1u1 DroidX模拟器我一直在使用,它就会消失。这是跨多个环境重现性。

I've determined that when I run this on an Android 2.2 emulator, as opposed to the Android 2.1u1 DroidX emulator I've been using, it goes away. This is reproducible across multiple environments.

我有这方面的一些更深入的了解;它好像onInterceptTouchEvent没有要求时,滚动视图包含一个挡板之内(或WorkspaceView)每一个动作的事件。

I have some more insight on this; it seems as though onInterceptTouchEvent is not called for every motion event when a scrollview is contained within a flipper (or a WorkspaceView).

在特别的,我发现当修改其他视图类来解决这个同样的问题的行为(这是不是唯一的鳍状肢)如下 - 注意,这是Android 2.1的只有:

In particular, the behavior I found while modifying another view class to fix this very same issue (it is not unique to flippers) was as follows--note that this is Android 2.1 only:

如果滚动视图足够长以滚动,所述ACTION_DOWN运动事件被捕获的滚动型,和每个后续ACTION_MOVE事件经过挡板,在那里它被拦截和处理适当的onInterceptTouchEvent。在Android 2.2系统,此行为发生在滚动的长度不管。

If the scrollview is long enough to scroll, the ACTION_DOWN motion event is caught by the ScrollView, and every subsequent ACTION_MOVE event goes through onInterceptTouchEvent of the flipper, where it is intercepted and handled appropriately. In android 2.2, this behavior happens regardless of the scroll length.

返回2.1:如果滚动视图不够长滚动的ACTION_DOWN运动事件的没有的挂在滚动视图,而是回来的鳍状肢的的onTouchEvent。同样的手势所有后续ACTION_MOVE事件的的的onInterceptTouchEvent功能,并直接进入的onTouchEvent功能!

Back to 2.1: If the scrollview is not long enough to scroll, the ACTION_DOWN motion event is not caught by the scrollview, but instead comes back to the onTouchEvent of the flipper. All subsequent ACTION_MOVE events of the same gesture skip the onInterceptTouchEvent function and go straight to the onTouchEvent function!

我解决这个问题的方法是采取我在的onTouchEvent功能的ACTION_MOVE事件和重构它到它自己的方法。这样一来,我可以的onTouchEvent调用onInterceptTouchEvent其次是功能,如果它检测到事件有previously了未处理的。

The way I resolved this was to take the functionality I had in onTouchEvent for ACTION_MOVE events and refactor it into its own method. In this way, I can have onTouchEvent call onInterceptTouchEvent followed by that functionality if it detects that the event has previously gone unhandled.

case MotionEvent.ACTION_MOVE:

                if (touchState == TOUCH_STATE_SCROLLING) {
                    handleScrollMove(ev);
                } else {
    //              Log.d("workspace","caught a move touch event but not scrolling");
                    //NOTE:  We will never hit this case in Android 2.2.  This is to fix a 2.1 bug.
                    //We need to do the work of interceptTouchEvent here because we don't intercept the move
                    //on children who don't scroll.

                    Log.d("workspace","handling move from onTouch");

                    if(onInterceptTouchEvent(ev) && touchState == TOUCH_STATE_SCROLLING){
                        handleScrollMove(ev);
                    }

                }

                break;

这是从WorkspaceView.java(Android的Workspace.java的修改,在谷歌上的code中的雄-意见的项目发现,现在这里:<一href="http://stackoverflow.com/questions/2501307/horizontal-tabish-scroll-between-views/4336295#4336295">Horizontal 标签视图之间十岁上下滚动的)。在我们收到移动事件,我们正在滚动(这只是如果我们特意选择了拦截 - 也就是说,它的拦截功能被设置,所以我们一直到拦截功能的话)的情况下,我们执行此举的行为,我们的愿望。如果我们这里收到一个移动事件,我们不滚动,那么我们发送事件背透onIntercept,然后看看我们现在设置为滚动。如果是这样,我们执行的操作。

This is from WorkspaceView.java (a modification of Android's Workspace.java, found at the andro-views project on google code, and now here: Horizontal "tab"ish scroll between views ). In the case that we receive a move event, and we are scrolling (which only happens if we have deliberately chosen to intercept it--ie, it's set in the intercept function, so we've been to the intercept function already) we perform the move behavior we desire. If we receive a move event here and we are not scrolling, then we send the event back through onIntercept, and then see if we're now set to scrolling. If so, we perform the action.

这是不优雅,但它的作品!

It's not elegant, but it works!

推荐答案

我需要创建一个扩展的滚动型的新类,并用这样的:

I needed to create a new class that extended ScrollView, and used this:

@Override
public boolean onTouchEvent(MotionEvent event) {
    super.onTouchEvent(event);
    return gestureDetector.onTouchEvent(event);
}

@Override 
public boolean dispatchTouchEvent(MotionEvent ev){
    gestureDetector.onTouchEvent(ev);
    super.dispatchTouchEvent(ev); 
    return true;
} 

我不知道为什么,但如果我尝试在dispatchTouchEvent返回任何东西,但真(顺理成章的事情会一直到

I have no idea why, but if I try to return anything but true in dispatchTouchEvent (the logical thing would have been to

return (gestureDetector.onTouchEvent(ev) || super.dispatchTouchEvent(ev)); 

如果我理解正确),这是行不通的,这确实。

if I understand properly), it doesn't work, and this does.

这篇关于当它太短滚动滚动型不刷卡的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆