onInterceptTouchEvent view of the relationship between calls and onTouchEvent Detailed

 http://blog.csdn.net/lvxiangan/article/details/9309927

Honestly, these two small stuff is too much trouble, it is difficult to understand, that my own api documentation dizziness, find a lot of information on the Internet, before we know how it is, to sum up here, just remember this principle It will be very clear:

1, onInterceptTouchEvent () for processing events (similar to pre-treatment, of course, may not process) and the transmission direction changing events, i.e. events continue to decide whether to allow Touch down (child control) transmission, but returns a True ( behalf of the event will be processed in the current viewGroup in), then passed down the road to be cut off (all child controls Touch will not have the opportunity to participate in the event), and passes control to the current events of onTouchEvent () processing; returns false, the event to onInterceptTouchEvent child control ()

2, onTouchEvent () to handle the event, the return value determines whether the control current consumption (consume) of this event, which means that the current control after processing the Touch event, whether to continue the event also allows Touch Up (parent control) pass, but a return True, you do not have to worry about their own parent control to handle the Touch event. Returns true, then passed up to the parent control (Note:?! You may feel if consumed it matter, anyway, I have for the event written handling code answer is a difference between such premise ACTION_MOVE or ACTION_UP happen is certain that ever happened ACTION_DOWN, if you do not consume ACTION_DOWN, then the system will think ACTION_DOWN did not happen, so ACTION_MOVE or ACTION_UP not be captured.)

Concepts

1, onInterceptTouchEvent () is used to process events (emphasis onInterceptTouchEvent this event is to start from the parent to the child controls transfer of control, until there is no intercept or to view the event, and then back from the child to the parent control, this is onTouch's) (similar to the pre-treatment, of course, can not handle), and change the direction of events passed, that is, to decide whether to allow the event to continue down Touch (child controls) transfer, but a return (on behalf of True events in the current viewGroup will be processed), then pass it down the road is cut off (all child controls Touch will not have the opportunity to participate in the event), and passes the event to onTouchEvent current control () processing; returns false, to put the events of the child controls onInterceptTouchEvent ()

2, onTouchEvent () to handle the event (this event is focused on onTouch from child control back to the parent control, layers pass down), the return value determines whether the control current consumption (consume) of this event, that is in the current control after processing the Touch event, whether to continue the event also allows Touch up (parent control) delivery. Return false, then passed up to the parent control, detail touch point is that this event will give the parent control, then back up to the event that triggered here touch, will not be passed to its child controls. If the parent control is still false, then touch the handle to give the parent control parent control, then up the event handler in the parent control parent control, it does not trigger below.

Returns true, if it is a child control returns true, then it's touch events are handled here, the parent control is not processed because it does not receive child controls passed his touch, the quilt controls to intercepted. (Long-winded so much here is to enhance memory, the two events are so much trouble to understand, let alone to remember, I certainly remember all of a sudden you forget the ^ 0 ^)

(Note: you may feel if consumed it matter, anyway, I have for the event written handling code answer is a difference between such premise ACTION_MOVE or ACTION_UP happen is certain that ever happened ACTION_DOWN, if you do not consume ACTION_DOWN, then?! The system will think ACTION_DOWN did not happen, so ACTION_MOVE or ACTION_UP not be captured.)

Details

onInterceptTouchEvent () is a method ViewGroup, the purpose is to conduct a relevant event to intercept before the system and its various childView ViewGroup trigger onTouchEvent (), Android design ideas so well understood, due ViewGroup will contain a number of childView, therefore need to be able to monitor the opportunity to unify the various touch events, and therefore can not control that contains pure sub-view is not of this method, such as LinearLayout there, TextView no.

onInterceptTouchEvent () is also very simple, if you override this method in ViewGroup where it can be intercepted on the various touch event. But how to intercept, whether all touch events need to intercept it is more complicated, touch events in onInterceptTouchEvent () transfer mechanism between the various childView and onTouchEvent and depends entirely on onInterceptTouchEvent () and onTouchEvent () return value. And, with the return value for the down event directly affects the transmission and reception and subsequent move up event.

About the return of value, the basic rule is very clear, if the return true, it indicates that the method consumes this incident, if return false, it indicates that the method does not deal completely, the event still needs to be passed down in some way to continue to wait deal with.

  

onInterceptTouchEvent () is a method ViewGroup, the purpose is related to events prior to the first interception ViewGroup its various childView trigger onTouchEvent in the system ().

  1. down event is first delivered to onInterceptTouchEvent () method

  2. If the ViewGroup of onInterceptTouchEvent () return false after receiving the down event processing is complete, then the follow-up move, up and other events will continue to be delivered before the ViewGroup, only after and down the event passed to onTouchEvent ultimate objective view of the same ( )deal with.

  3. If the ViewGroup of onInterceptTouchEvent () return after receiving down event processing is complete true, then the subsequent move, up will not be passed to other events onInterceptTouchEvent (), but down, and the events are passed to onTouchEvent same ViewGroup () Processing , noted that the target view will not receive any events.

  4. If you eventually need to deal with onTouchEvent view event () returns false, then the event will be delivered to onTouchEvent on a level view of () processing.

  5. If you eventually need to deal with onTouchEvent view event () returns true, then the subsequent events will continue to be passed to the view of onTouchEvent () processing. 

    Just look at the official documentation explains, will be able to clearly understand the relationship between these two functions and the use of absolutely experienced master framework.
    Otherwise, you need a case to explain. Suppose we have such a layout, very typical

    1. <com.test.LayoutView1 xmlns:android="http://schemas.android.com/apk/res/android"  
    2.     android:orientation="vertical" android:layout_width="fill_parent"  
    3.     android:layout_height="fill_parent">  
    4.     <com.test.LayoutView2  
    5.         android:orientation="vertical"android:layout_width="fill_parent"   
    6.         android:layout_height="fill_parent" android:gravity="center">  
    7.         <com.test.MyTextView  
    8.             android:layout_width="wrap_content"   android:layout_height="wrap_content"  
    9.       />  
    10.     </com.test.LayoutView2>  
    11. </com.test.LayoutView1>
     

    FIG explained using an example of the layout:


    Usually peripheral layoutview1, layoutview2, but the layout of the container does not need to respond to the touch screen click event, just click on the appropriate Mytextview need. But this is only normal circumstances, some special layout of peripheral vessels may have to respond to, or even let go inside mytextview response. A special case is more dynamic response object replacement.
    So first of all look at the default touch pass flow of events between the two functions. As shown below:

    If you just want MyTextView to respond to touch events, let MyTextView of OnTouchEvent returns true, then the flow of events becomes as shown below, you can see layoutview1, layoutview2 has not entered OnTouchEvent:

    Another situation in which the peripheral vessels want to handle touch events alone, then it should be returned in the corresponding function onInterceptTouchEvent true, pledged to intercept touch events, such as intercepted layoutview1 processing, the processing flow becomes as shown below:

    And so on, we can get a variety of specific circumstances, view the entire layout of the class hierarchy have the opportunity to intercept, and can tell the periphery of the container view has intercepted priority right.

    When we do have some applications when the relatively more complex interactive touch-screen effect, often need to dynamically change processing objects touch event, such as launcher desktop stand and the main menu (see below), slide the screen from start to stop slide among process, only a peripheral view of the container can handle touch event, otherwise it will mistakenly click on the application icon or widget. on the other hand you need to be able to respond icons (sub-view) of the touch event in a stationary state. Framework in the following code removal abslistview

    1. public boolean onInterceptTouchEvent(MotionEvent ev) {
    2.         int action = ev.getAction();
    3.         switch (action & MotionEvent.ACTION_MASK) {
    4.         case MotionEvent.ACTION_DOWN: {
    5.  
    6.             if (touchMode == TOUCH_MODE_FLING) {
    7.                 return to true ; // Fling state intercepted touch, because in the sliding state, not to view the sub-process   
    8.             }
    9.             break;
    10.         }
    11.         case MotionEvent.ACTION_MOVE: {
    12.             switch (mTouchMode) {
    13.             case TOUCH_MODE_DOWN:
    14.                 final int pointerIndex = ev.findPointerIndex(mActivePointerId);
    15.                 final int  y  = ( int )  ff . TIDE ( pointerIndex );  
    16.                 if (startScrollIfNeeded(- mMotionY)) {
    17.                     return to true ; // start sliding state, intercepting touch events, not to deal with sub-view 
    18.                 }
    19.                 break;
    20.             }
    21.             break;
    22.         }
    23. }

    to sum up:

    By merely an overview of official documents it is difficult to understand the purpose of onInterceptTouchEvent function only through the interpretation of this abstract rules, together with the graphic in order to obtain this important knowledge. Obviously, the default is to return false, not intercepted. After returning true, the back-end flow control event would not have a chance to handle touch events, and the default for each event stream processing function as a node, the node returns true as long as the subsequent event is ended, so would like to well understood.

    onInterceptTouchEvent is defined in ViewGroup inside. Android layout in the layout of these classes are generally inherited. onInterceptTouchEvent gesture is used to intercept events, each gesture event will first call onInterceptTouchEvent. 
    onInterceptTouchEvent () for processing event and events to change the transmission direction. Event passes the return value is false to onInterceptTouchEvent child control (); event is passed to the current onTouchEvent control when the return value is true (), rather than being passed on to the child control, which is called the Intercept (cut-off).
    onTouchEvent () to handle the event, the return value determines whether the control current consumption (consume) of this event. You might want to ask whether the consumer and the difference between you, anyway, I've written for the event handling code? The answer is a difference! For example, the premise ACTION_MOVE or ACTION_UP happen is certain that ever happened ACTION_DOWN, if you do not consume ACTION_DOWN, then the system will think ACTION_DOWN did not happen, so ACTION_MOVE or ACTION_UP not be captured.

ViewGroup in the onInterceptTouchEvent default value is false in order to pass View events in the onTouchEvent.

ViewGroup in the onTouchEvent default value is false.

View Lane onTouchEvent return the default value is true. So as to perform multiple touch events.

 

 

This post last edited by the sun.shine at 2013-3-22 18:17 

1. First understand a common sense: View not onInterceptTouchEvent event, and ViewGroup these three events have, after the viewgroup inherit View before adding a method called onIntercepTouchEvent . 
As can be seen from the literal meaning, onInterceptTouchEvent interceptor is used to intercept events with, dispatchTouchEvent is used to distribute event, onTouchEvent is used to handle the event. 
We can easily see, you should go first dispatchTouchEvent then go onTouchEvent. It is called as soon as OnInterceptTouchEven when? 
To better understand these three events, from the simple to the complex, starting with a sub-view, a viewgroup, then viewgroup there are sub-view. 2. For a View is concerned, the event is go to the View dispatchTouchEvent, then go onTouchEvent (also may not go). When it does not go onTouchEvent? When rewriting dispatchTouchEvent, do not go directly super.dispatchTouchEvent returns false, it will not go onTouchEvent. Of course, this is a violation of android architecture common sense, is not recommended for the general dispatchTouchEvent rewritten. However, through this case we can conclude that such a conclusion. In view of the arrival time of the event, go dispatchTouchEvent, in dispatchTouchEvent system it calls Ontouch view of the method,
If it returns true down event this onTouch method where the dispatchTouchEvent method also returns true, and the subsequent move events, up events are passed onTouch.
The return value after the event and move up events, onTouch return what dispatchTouchEvent nothing to return. Conversely, when if first down pass to ontouch the event, ontouch returns false, since then the event will not pass over, that is, will not go dispatchTouchEvent. Will not go ontouchevent.

3. For a ViewGroup terms (no sub-view time): trend of events is dispatchTouchEvent-> onInterceptTouchEvent-> onTouchEvent we will find them with the view of logic is no different, just go down when the event onInterceptTouchEvent will be in the middle, and here no matter what onInterceptTouchEvent return
will operate as it does not interfere 2. describe it, do onInterceptTouchEvent this method is useless?
4. When Viewgroup in view of the child when there down to the event: viewgroup.dispatchTouchEvent-> viewgroup.onInterceptTouchEvent
-> If the return true-> viewgroup.onTouch ------------------------------- branch 1
| -> If the return false- > view.dispatchTouchEvent branch 2 branch 1: move or go up after the event is: viewgroup.dispatchTouchEvent-> viewgroup.ontouch ontouch return here no matter what, are the trend branch 2: down event to view.dispatchTouchEvent-> view .onTouch-> return true-> branch 3 | -> return false-> viewgroup.ontouch-> return true-> move, up events such as viewgroup.dispatchTouchEvent-> viewgroup.ontouch | -> returns false, not the viewgroup receive subsequent events the branch 3: returns true view of the sub-onTouch, represents the sub-view can accept the event, the next event to be Move: viewgroup.dispatchTouchEvent-> viewgroup.onInterceptTouchEvent return? If it returns false, after the move, up will go so viewgroup.dispatchTouchEvent-> viewgroup.onInterceptTouchEvent-> view.dispatchTouchEvent-> view.ontouch if it was true, move to snatch event of the sub view. The next trend is: mandatory events and pass Cancel UP event to view, view.dispatchTouchEvent-> view.ontouch (ignoring what it returns)
-> Move event and then left viewgroup: viewgroup.dispatchTouchEvent-> viewgroup.ontouch this phenomenon we should listview or scrollview had seen, that is, when the user presses a button scrollview, the discovery button made the appropriate response (highlight the button),
but when hold to drag it and found the interface rolling, this is because onInterceptTouchEvent robbed the event!
 

 Stopping event and distribute events:

Copy the code
MyLinearLayout the extends the LinearLayout {class public 


    public MyLinearLayout (the Context context, AttributeSet attrs) { 
        Super (context, attrs); 
    } 

    / ** 
     * interrupt event 
     * / 
    @Override 
    public Boolean onInterceptTouchEvent (the MotionEvent EV) { 
        return to true; 
    } 

    / ** 
     * distribution event 
     * / 
    @Override 
    public boolean dispatchTouchEvent (MotionEvent EV) { 
        return super.dispatchTouchEvent (EV); 
    } 
    
    / ** 
     * simultaneously implement multiple ListView control triggering event 
     * / 
    @Override 
    public boolean onTouchEvent (MotionEvent event) {
        
        int width=getWidth()/getChildCount();
        int height = getHeight();
        int count=getChildCount();
        
        float eventX = event.getX();
        
        if (eventX<width){    // 滑动左边的 listView
            event.setLocation(width/2, event.getY());
            getChildAt(0).dispatchTouchEvent(event);//移动位置后,分发事件
            return true;
            
        } else if (eventX > width && eventX < 2 * width) { //滑动中间的 listView  
            float eventY = event.getY();
            if (eventY < height / 2) {
                event.setLocation(width / 2, event.getY());
                for (int i = 0; i < count; i++) {
                    View child = getChildAt(i);
                    try {
                        child.dispatchTouchEvent(event);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                    
                }
                return true;
            } else if (eventY > height / 2) {
                event.setLocation(width / 2, event.getY());
                try {
                    getChildAt(1).dispatchTouchEvent(event);
                } catch (Exception e) {
                    e.printStackTrace();
                }
                return true;
            }
        }else if (eventX>2*width){
            event.setLocation(width/2, event.getY());
            getChildAt(2).dispatchTouchEvent(event);
            return true;
        }
  
        return true;
    }
    
}

 

Guess you like

Origin www.cnblogs.com/awkflf11/p/12635429.html