2

in iOS world, there's a concept of touchUpInside, touch started within a view and user lifted a finger within a view bound.

I see touch vs click (event listeners) in android, and I'd like to know the difference between them.

eugene
  • 39,839
  • 68
  • 255
  • 489

3 Answers3

3

Touch events are much more basic. There's many varieties. The most common being:

DOWN: The user touch the item

MOVE: The user shifts around the item after touching it

UP: The user stops touch the item

CANCEL: The user shifts off the item but is still touching the screen.

In Android, a click event is a composite of touch events. In the case of click it's both DOWN and UP action. There are others that can be found in a GestureDetector. Fling for example is a combination of DOWN, MOVE, and UP in a fast motion that signifies the user swiped the finger really fast.

EDIT:

Clarification on how Android handles the true and false in onTouchEvent().

It's not very well documented, but the way the Views work in Android is that when you touch a View, it will send that touch event from the parent view to all children views. Each child will then send the event to it's children. This is done in the dispatchTouchEvent() method.

When a parent View receives false from the child's onTouchEvent() method, it will no longer send touch events to that child. Meaning that when you're view returns false in onTouchEvent(), your View is really says:

I am done processing touch events and all of my children are done as well.

90% of the time, in onTouchEvent() you would do return super.onTouchEvent() to return the touch values of all the children in the View.

So let's look at your click example. Here's one way to do it in which you return false on a DOWN event, but true on an UP.

  @Override
  public boolean onTouchEvent(MotionEvent event) {

    switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
      return false;
    case MotionEvent.ACTION_UP:
      return true;
      break;
    default:
      return false;
    }
} 

In this case, the parent of this View will receive false immediately. After which, it will stop sending touch events to this View because you said it was done.

Here's another way:

 boolean mPossibleClick = false;

 @Override
  public boolean onTouchEvent(MotionEvent event) {

    switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
      mPossibleClick = true;
      break;
    case MotionEvent.ACTION_UP:
      if(mPossibleClick) {
         // UP event immediately after DOWN. Perform click action
      }
    default:
      mPossibleClick = false;
    }
    return mPossibleClick;
}

It's rather crude, but basically here's what will happen. When the user first touches it, you will receive DOWN which will return true. If the user lifts the finger, it will perform a click action after which will return false because the event is done. If the user moves his finger or any other action is performed, it will return false and the click will be nulled out.

That last one is not the best way to implement a click, but I think it illustrates what I'm trying to say. In real life, move events are extremely common if even for a couple pixels.

DeeV
  • 35,865
  • 9
  • 108
  • 95
  • so If I'd like to capture the 'click event' in touchListener, I should test `down` and `up`? if so, in what way? or testing `up` is enough? – eugene Dec 27 '12 at 16:21
  • You must test `DOWN` in the touch event and return `true` because as soon as a View returns `false` it will stop receiving touch events. When a View returns `false` it means "There's no further touch processing I can do so don't bother asking again". So in this case, you would capture that there was a `DOWN` event, return true, then capture that there was an `UP` event. – DeeV Dec 27 '12 at 16:25
  • `false` and `true` means different than what you said in onTouch. can you elaborate? onTouch() - This returns a boolean to indicate whether your listener consumes this event. The important thing is that this event can have multiple actions that follow each other. So, if you return false when the down action event is received, you indicate that you have not consumed the event and are also not interested in subsequent actions from this event. Thus, you will not be called for any other actions within the event, such as a finger gesture, or the eventual up action event. – eugene Jan 03 '13 at 03:26
  • 1
    I made an edit describing how Android handles true and false in a View's `onTouchEvent()`. Tell me if it's not clear. – DeeV Jan 03 '13 at 04:21
  • thanks for clarification. But touch thing is so perplexing still. http://stackoverflow.com/questions/7449799/how-are-android-touch-events-delivered ` Widgets that are drawn last (on top of other widgets) have chance to process touch in View.onTouchEvent first.` and your explanation ` it will send that touch event from the parent view to all children views` seems to contradict each other?` – eugene Jan 03 '13 at 04:31
  • That's all handled in `dispatchTouchEvent()`. In a parent `View`, the method `dispatchTouchEvent()` will first send the touch event to all the direct children's `dispatchTouchEvent()` methods which will in turn send the same event to their children and so on until it gets to the last child `View` (the one shown in front of all the others). Upon which, that View's `onTouchEvent()` gets called. It will return `true` or `false` to its parent. If you don't override it, then the parent will simply return the value received. Then continue to cascade back up. – DeeV Jan 03 '13 at 04:45
0

onClickListener is used whenever a click event for any view is raised, say for example: click event for Button, ImageButton.

onTouchListener is used whenever you want to implement Touch kind of functionality, say for example if you want to get co-ordinates of screen where you touch exactly.

Definitions:

onClickListner: Interface definition for a callback to be invoked when a view is clicked.

onTouchListener: Interface definition for a callback to be invoked when a touch event is dispatched to this view. The callback will be invoked before the touch event is given to the view.

Details:

onClickListener: http://developer.android.com/reference/android/view/View.OnClickListener.html

onTouchListener: http://developer.android.com/reference/android/view/View.OnTouchListener.html

gurudeb
  • 1,856
  • 22
  • 29
0

refer to the response of PH7

which one is better to use?

It really depends on your requirement. onTouch gives you Motion Event. Thus, you can do a lot of fancy things as it help you separate state of movement. Just to name a few

  • ACTION_UP
  • ACTION_DOWN
  • ACTION_MOVE

Those are common actions we usually implement to get desire result such as dragging view on screen.

On the other hand, onClick doesn't give you much except which view user interacts. onClick is a complete event comprising of focusing,pressing and releasing. So, you have little control over it. One side up is it is very simple to implement.

do we need to implement both?

It is not necessary unless you want to mess up with your user. If you just want simple click event, go for onClick. If you want more than click, go for onTouch. Doing both will complicate the process.

From User point of view, it is unnoticeable if you implement onTouch carefully to look like onClick.

for more details : refer this and this

Community
  • 1
  • 1
Houcine
  • 24,001
  • 13
  • 56
  • 83