当前位置:   article > 正文

android 中view 的OnTouchListener和OnClickListener的区别_android touchlistener clicklistener

android touchlistener clicklistener

有时候会迷惑,OnTouchListener和OnClickListener究竟有什么区别。 通过源码分析一下。

一,OnTouchListener的触发逻辑

代码在View类 中

  1. public boolean dispatchTouchEvent(MotionEvent event) {
  2. if (mInputEventConsistencyVerifier != null) {
  3. mInputEventConsistencyVerifier.onTouchEvent(event, 0);
  4. }
  5. if (onFilterTouchEventForSecurity(event)) {
  6. //noinspection SimplifiableIfStatement
  7. ListenerInfo li = mListenerInfo;
  8. if (li != null && li.mOnTouchListener != null && (mViewFlags & ENABLED_MASK) == ENABLED
  9. && li.mOnTouchListener.onTouch(this, event)) {
  10. return true;
  11. }
  12. if (onTouchEvent(event)) {
  13. return true;
  14. }
  15. }
  16. if (mInputEventConsistencyVerifier != null) {
  17. mInputEventConsistencyVerifier.onUnhandledEvent(event, 0);
  18. }
  19. return false;
  20. }

分发touch事件时 先判断mOnTouchListener .onTouch() 是否处理了 事件,如果方法返回true(处理了),则不向下传递。

所以OnTouchListener 的触发时机是:手指一触摸就会触发。 action_down的时候就会触发。而且touchListener的字面意思"触碰监听"也比较贴切 。


二,OnClickListener的触发逻辑

代码也在View类 中

  1. public boolean onTouchEvent(MotionEvent event) {
  2. ...
  3. if (((viewFlags & CLICKABLE) == CLICKABLE ||
  4. (viewFlags & LONG_CLICKABLE) == LONG_CLICKABLE)) {
  5. switch (event.getAction()) {
  6. case MotionEvent.ACTION_UP:
  7. boolean prepressed = (mPrivateFlags & PREPRESSED) != 0;
  8. if ((mPrivateFlags & PRESSED) != 0 || prepressed) {
  9. // take focus if we don't have it already and we should in
  10. // touch mode.
  11. boolean focusTaken = false;
  12. if (isFocusable() && isFocusableInTouchMode() && !isFocused()) {
  13. focusTaken = requestFocus();
  14. }
  15. if (prepressed) {
  16. // The button is being released before we actually
  17. // showed it as pressed. Make it show the pressed
  18. // state now (before scheduling the click) to ensure
  19. // the user sees it.
  20. setPressed(true);
  21. }
  22. if (!mHasPerformedLongPress) {
  23. // This is a tap, so remove the longpress check
  24. removeLongPressCallback();
  25. // Only perform take click actions if we were in the pressed state
  26. if (!focusTaken) {
  27. // Use a Runnable and post this rather than calling
  28. // performClick directly. This lets other visual state
  29. // of the view update before click actions start.
  30. if (mPerformClick == null) {
  31. mPerformClick = new PerformClick();
  32. }
  33. if (!post(mPerformClick)) {
  34. performClick();//触发点
  35. }
  36. }
  37. }
  38. ...
  39. }


下面看触发点performClick()

  1. public boolean performClick() {
  2. sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_CLICKED);
  3. ListenerInfo li = mListenerInfo;
  4. if (li != null && li.mOnClickListener != null) {
  5. playSoundEffect(SoundEffectConstants.CLICK);
  6. li.mOnClickListener.onClick(this);//触发点击事件
  7. return true;
  8. }
  9. return false;
  10. }


在onTouch()的事件处理的逻辑中,手指抬起 action_up 时,符合click的条件,则触发mOnClickListener的逻辑。


总结:

OnTouchListener的触发点:action_down 手指按下时

OnClickListener的触发点:action_up 手指抬起时

OnTouchListener 处理逻辑在OnClickListener之前,  所以OnTouchListener 的onTouch()如果返回true, 则 onTouchEvent ()中所有逻辑失效,当然OnClickListener也不会触发。




声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/繁依Fanyi0/article/detail/111368
推荐阅读
相关标签
  

闽ICP备14008679号