I have a ViewFlipper where one of the views is a ListView. To move back and forth between the views, I have a GestureListener that detects left and right swipes. Sometimes the left & right swipes interfere with the ListView. That is, when I want to switch to the next view by swiping left/right, I may accidentally click on an item in my list.
Is there a good way to prevent this interference?
Have a look at http://android-journey.blogspot.com/2010/01/android-gestures.html.
The SimpleGestureListener from this page is a great solution to gesture detection. When run in dynamic mode (the default), it intercepts touch events that are determined to be gestures to prevent them from performing other actions. Other touch events are not interfered with.
If you are only interested in swipe gestures I recommend disabling the code for detecting tapping and only listening for swipes.
If you want something a little snazzier than a ViewFlipper (something more like the Android home screen) try out this new addition to the Android compatibility libs: http://android-developers.blogspot.com/2011/08/horizontal-view-swiping-with-viewpager.html?m=1
Related
I have a horizontal slider in my app, and I want to make it so that if you have the slider selected, you can do the two-fingered swipe up or down gesture from anywhere on the screen (The scroll up or down gesture) to move the slider left or right. I haven't been able to find anything through google about how to change vertical swipe behavior for Talkback and was wondering if there was in fact a way to change this.
I'd really suggest not doing this, it isn't how Android works so it will confuse your users, and be a big source of bugs as any behavior like this can cause touch errors on completely separate views. I just fixed a problem on something similar in my company's app.
But if you really want to do this- your root ViewGroup needs to intercept touch events if there are two fingers down and it moves far enough to qualify. Read https://developer.android.com/training/gestures/viewgroup#intercept for an explanation of how a parent view group can steal touch events from the child. This is the same way ScrollView works to scroll its contents. In fact, looking up the AOSP implementation of ScrollView would give you good example code.
Such as touch the screen and move or use "input swipe" in adb shell, how android system decide to scroll or not and the distance to scroll?
Simple answer. Gesture detection. Scrolling views like ScrollView, ListView and RecyclerView will register to receive onTouchEvent events from the screen. They will then track those events over time to detect things like swipes, including the direction, velocity and acceleration of the swipe.
From there, they can make a decision on whether to scroll, how far to scroll, and in what direction. Each view will do this differently based on how their content is laid out, whether there is additional content that be scrolled to, etc..
In particular ScrollView uses a VelocityTracker to track the series of touch events, and uses that to calculate what to do. There's other options (like the GestureDetector class) available to do simple gesture detection in custom views.
Do yourself a favor, and look at the source code for ScrollView in your IDE.
In particular the onTouchEvent and onInterceptTouchEvent methods.
I've a menu in Android app with several ImageButton (all grouped in a RelativeLayout) and I would like to make it disappear when swiping with finger towards the outside of the screen.
Swiping with finger towards the inside of the screen, instead, the menu should re-appear.
Any suggestion to do this ?
Try writing a gesture detection as given here Fling gesture detection on grid layout and in that code instead of toast write your code.
I cant seem to find the answer to this, mainly because I don't know what it is called.
I am going to expand a few features in my app, currently users can touch and drag to move forward in a list of images. What I want is for the users to "swipe" there finger and then all of these images will move under acceleration and will slowly come to a stop.
Is this a gesture? If so is it the "Fling" gesture?
There are several ways to do so.
Use ListView
Use Gallery
Use ScrollView
Use HorizontalScrollView
Write your custom ViewGroup or View
For the last approach, you have to detect the Fling gesture as you said and handle all the scrolling animations involved.
In case my title wasn't clear enough, I'll explain it in detail:
Say we have a screen filled with multiple buttons (10+), and we press down on one, activating onTouch/onClick. If we now move the finger, without lifting it, I want it to activate any other button it slides over. In this particular case, I want sound to be played when you slide over a virtual piano.
I know about the onTouchListener-solution where you register every ACTION_MOVE and find some boundaries that activates new events, but that's far from optimal if you have multiple buttons and want to allow smooth sliding without delay.
I also read this thread which suggested that we combine the touchListener of the View with a gesturelistener from the activity, but once again, this does not feel at all optimal for my situation.
I have not tried combining touchlistener with gesturelistener yet, but I will go ahead and do so if someone tells me they have no other way of doing this.
In my opinion, the proper way of doing this is to forget about buttons, and create a custom view which draws the entire keyboard. In this view you can handle touch events the way you like. You do not even need the gesture detector, just analyze the action and coordinates of motion events, it's very easy.
I don't understand what you mean about ACTION_MOVE and delays. To minimize delay, react on ACTION_DOWN, and then on ACTION_MOVE if it hovers other keys while in down state. It can't be any faster than that. With buttons there is an important delay because the onClick() event is triggered when the user lift the finger, on ACTION_UP.
Buttons are just not meant to work as you describe. The idea is that if a user taps on a button and then move his finger away at the same time it does not trigger onClick events on other views around. This prevents bogus clicks.
I actually took the "easy" way out and used buttons with an onTouch-method using ACTION_DOWN and ACTION_MOVE with coordinate calculations that combined with event.getX() and event.getY() allows me to detect which button is currently hovered. It's lag free with 13 buttons.