Intercept Touch events in Android - android

How do I intercept touch events in Android, ensuring that the existing touch workflow is not impacted. Basically I want to add some touch visualizer so as to know where the user is touching on the screen whereby ensuring that if the user is trying to scroll the tableview, touch visualizer is shown as the user drags his finger but also the tableview scrolls with ease.
In iOS, there is one method sendEvent of class UIWindow does this exactly. Not sure if Android has anything similar.
Thanks

Override Activity.dispatchTouchEvent() and do your touch handling there. Always return super.dispatchTouchEvent() to make sure it gets handled the normal way after your logic executes.
#Override
public boolean dispatchTouchEvent(MotionEvent event) {
/* your code here */
return super.dispatchTouchEvent(event);
}

http://developer.android.com/reference/android/view/View.OnTouchListener.html have alook at this link. It is pretty straight forward. Google it there is lots of example on it.
yourview.setOnTouchListener(new View.OnTouchListener() {
#Override
public boolean onTouch(View v, MotionEvent event) {
return false;
}
});

Related

OnSignleTapUp event fires twice

I have a Xamarin Android application with a GestureDetector. On my device (Sony Xperia S5303) and in emulators it works fine. However, on a Samsung Galaxy tablet, the OnSingleTapUp event is fired twice, even though I touch the screen just once. Since the event is checked by the OnSingleTapConfirmed, and the device behaves as if two taps were made, the following method is never called:
public bool OnSingleTapUp(MotionEvent e)
{
if (PersistentContext.LoggedPlayer.Token)
{
if (simpleOnGestureListener.OnSingleTapConfirmed(e))
{
Move(e);
}
return true;
}
return false;
}
The strange thing is, that when clicking on a button, the button method is called just once. Can anybody tell me what might cause this strange behaviour and how to avoid it?
You need to use onSingleTapConfirmed(MotionEvent event) instead. This way android makes sure it's a single tap and doesn't fire the event twice.
Edit: if you are determined to use onSingleTapUp(MotionEvent event), then you can use event.getEventTime()and if the time difference between the first and second events is less than a THRESHOLD like 200ms or something, consider it the unwanted second-time fired tap and ignore it.
Edit 2: Since I don't use Xamarin I might be totally wrong but I think you need to change your code like this: (I mean forget onSingleTapUp completely and move wyour whole code into onSingleTapConfirmed)
#Override
public boolean onSingleTapConfirmed(MotionEvent event) {
if (PersistentContext.LoggedPlayer.Token)
{
Move(e);
return true;
}
return false;
}
Hope it helps and Good Luck!

Developing for Google Glass with HTML5 (beginner)

I'm new to programming for Google Glass. I really like the cards possibilities (https://glass-python-starter-demo.appspot.com/) and it's great that I can submit HTML.
Because the project I'm working on (for which I would like to use Glass) is an online platform, I would like to be able to work from the website. As I found out, I can detect (from the user agent) that Glass is being used (http://www.googleglass.gs/quick-tip-google-glass-web-browser-user-agent/)
So, now my question in two parts.
1) Can I create an Android app that's actually a 'browser without a toolbar' so that I can direct directly to a webpage, but that functions as an app so that I can have it in the menu (after: "ok Glass")?
2) Can I use voice commands in the above app?
PS:
I know this is a beginner question, but -with exception from the Glass Cards option- it's hard to find a starting point for this.
So if I understand you correctly, you want to do this following:
1) Create an app that is basically just a browser.
2) Have the link that opens be to your website where the app is actually contained.
3) Use voice commands to control this app.
All to bypass having to code in java/xml so you can code in the language you know better and then run it online, and just have one line of code creating the browser in the actual app code.
Yes, you can create an app that is just a browser.
Yes, you can have it link to your website and then have it stay there.
I think that it will be much harder for you to interact with the website. The default browser controls are tap to click, hold 2 fingers down and move your head to move "mouse" around the current screen, slide up and down to scroll.
If you want to control the app, you'd have to implement your own gesturedetector, override the default actions taken each time you do something, and then for each action send something to your website to let it know that you just did something.
You could use voice recognition for controls as well.
Either way, you'll need a gesturedetector to override the default controls for the browser if you decide to use the standard one. Here is what you'd need for that:
At the very top, you'll have
private GestureDetector gestureDetector;
Then in your onCreate method, you'll need to create your gestureDetector. I like to have a method to create it farther down. It is just cleaner that way for me.
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
gestureDetector = createGestureDetector(this);
}
And then the method to actually create the GestureDetector:
private GestureDetector createGestureDetector(Context context) {
GestureDetector gestureDetectorTemp = new GestureDetector(context, new GestureDetector.OnGestureListener() {
#Override
public boolean onDown(MotionEvent motionEvent) {
return false;
}
#Override
public void onShowPress(MotionEvent motionEvent) {
return false;
}
#Override
public boolean onSingleTapUp(MotionEvent motionEvent) {
//communicate to the website that you tapped, and have it handle the tap
Log.v("APP_TAG","Someone tapped me!");
return false;
}
#Override
public boolean onScroll(MotionEvent motionEvent, MotionEvent motionEvent2, float distanceX, float distanceY) {
return false;
}
#Override
public void onLongPress(MotionEvent motionEvent) {
return false;
}
#Override
public boolean onFling(MotionEvent motionEvent, MotionEvent motionEvent2, float v, float v2) { //fling = a single slide
return false;
}
});
return gestureDetectorTemp;
}
Notice that each method that was overriden has a "return false" in it. The boolean you are returning represents whether or not the event is to be consumed.
In other words, if you look at onSingleTapUp, we have a Log.v that will print out "Someone tapped me!" when you tap the screen. By returning false, you are letting whatever else was going to occur based on a tao (in the case of a browser, a "click" of the mouse) occur. If you return true, nothing else will occur. The event won't be reported to the other default methods. So to nullify all of the default controls of the browser, you would just change all of the return statements there to "return true", indicating that the event was consumed and that no further action is necessary!
I hope that helped a bit. If you goal is to completely bypass the entire android coding platform and just develop in the browser and then link the app to the browser, I don't think you'll be able to do it completely just because of the nature of Glass. There is no touch screen with lots of different buttons and a keyboard, etc. You'll need to do at least some glass development to get it to work.

Using MotionEventCompat in android

I'm looking for an example of how to use MotionEventCompat in Android. I'm using API level 10, which doesn't support if a finger is 'hovering' or 'dragging' onto a view. I need to detect this, preferably from the view itself. Here's some code snippets regarding how I'm trying to use this:
**my class:**
import android.support.v4.view.MotionEventCompat;
public class GridButton extends View
overriding onTouchEvent:
#Override
public boolean onTouchEvent(MotionEvent event) {
super.onTouchEvent(event);
switch (event.getAction() & MotionEventCompat.ACTION_MASK) {
case (MotionEvent.ACTION_DOWN): {
set_active(true);
return true;
}
case (MotionEventCompat.ACTION_HOVER_ENTER): {
set_active(true);
break;
}
}
return false;
}
I based the MotionEventCompat.ACTION_MASK off an example I found somewhere, but it doesn't trigger my code for set_active().
Any help on using this would be appreciated. There's very little about this on the web.
Hover events are sent when the device supports a mouse or touchpad. When the cursor hovers over a view these events are sent to onGenericMotionEvent, not onTouchEvent. They won't help you detect a finger that isn't touching the surface of a capacitive touchscreen or a finger that touched down in a different position and then slid over the view in question. They will never be sent on an API 10 (Android 2.3) device.

Disable parts of the touch screen in android

So I was trying to disable the screen for an app I am making for a brief period using this
#Override
public boolean onTouchEvent(MotionEvent pMotioneEvent) {
if(pMotioneEvent.getY() < TestSprite.getY()){
return false;
}else{
return true;
}
}
but this seems to have no effect. I read around and it seems like in general its a bad idea to disable the touch screen, but I'm still curious to know if there is a way.
Thanks
You could try
requestDisallowInterceptTouchEvent
If you want to check for touchevents in a certain area of your screen, you might want to put this in a View and set a touchEvent Listener to it.

Swipe detection for each row of listview

I have a list of videos located in the sd-card. At this point, I just need help in creating gestures or swipe detection for each row in the list view. Thanks to this question at stackoverflow Fling gesture detection on grid layout, I implemented the gesture on the listview. It now easily detects when the user swipes in the right direction or left direction. But this gesture is for the entire listview. I just want to know how can I implement this swipe detection for individual rows. For example, the application now makes a toast that prints "Right Swipe", "Left Swipe". I just want to make it like "Right Swipe on row no 1", "Left Swipe on Row no 3" etc.. I hope my question was clear.
Looking forward to some helpful replies.
Thanks
Take a look into this answer and use pointToPosition method inside onFling Event
#Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
try {
Toast.makeText( listAdapter.getItem( listView.pointToPosition(Math.round(e1.getX()), Math.round(e1.getY())).toString());
return super.onFling();
} catch( Exception e ) {
// do nothing
}
}
I'm using the per item approach in my solution - take a look here
My swipe detection code might be a bit different from standard swipe detection but it works perfectly for me. And I'm using attached tags to get the item related data.
Hope that helps, but if you do have some questions just let me know and I'll try to explain in more detail.
As Per My Opinion is Use Boolean for the item,When that item is touched set as true,Using onTouchListener,
ListItem.setOnTouchListener(new View.OnTouchListener() {
#Override
public boolean onTouch(View arg0, MotionEvent event) {
click=true;
return click;
}
});`
Then You Can Override This:
#Override
public boolean dispatchTouchEvent(MotionEvent ev){
super.dispatchTouchEvent(ev);
Log.v("Inside", "=====Dispatch Event===");
if(click){
Log.v("Inside", "=====Dispatch Event=T==");
click=false;
return gestureDetector.onTouchEvent(ev);
}else{
return false;
}
}
I think what you're looking for is SwipeView (or perhaps even ViewFlow) rather than standard Android gesture detection.
This question is old, but by now thankfully Jake Wharton backported some code released for ICS here; this should allow you to swipe individual rows: https://github.com/JakeWharton/SwipeToDismissNOA
We implemented swipe detection per row for revealing actions and dismissing items here https://github.com/47deg/android-swipelistview . I hope it helps

Categories

Resources