Swiperefreshlayout and Bannerview Carousel Conflict Resolution

Source: Internet
Author: User
Tags abs gety

Swiperefreshlayout and Convenientbanner AD Carousel event conflict resolution

Look at the layout, analyze the layout, this layout is very regular home layout, a swiperefreshlayout drop-down to refresh the package with a head of the ListView. Where head has an ad-carousel control that can swipe left and right, and drop-down refreshes to swipe up and down.

If used directly, you will find that when you swipe left and right, it is not sensitive and sometimes touches the pull-down refresh.

Can find Taobao those ads, left and right swipe very smooth, up and down swipe down to refresh does not affect the advertising carousel. This is the blog to solve a problem, to solve the ad bar left and right sliding and drop-down refresh conflict.

Our ideal treatment is that we just want to pull down directly (the x direction does not have a big change) is the drop-down refresh, the other big moves of the left and right sliding, all belong to the advertisement carousel.



In this way, we first determine that processing event processing is divided into 2 cases.

A, a straight slide, the x-coordinate around a small change. (drop-down refresh)

B, swipe left or right, diagonal slide (ad bar)

The target was determined and the situation in 2 was clarified. We start from the drop-down refresh source, because this way of thinking more clear, compare event delivery, first passed from the parent class to the subclass. That process is no longer detailed, do not understand can look at other excellent blog, this is good: http://blog.csdn.net/hyp712/article/details/8777835

View Swiperefreshlayout source, where onintercepttouchevent interception is the focus


[Java] View Plain copy print? @Override    public boolean onintercepttouchevent (Motionevent ev)  {       ensuretarget ();          final int  action = motioneventcompat.getactionmasked (EV);          if   (Mreturningtostart && action == motionevent.action_down)  {           mReturningToStart = false;        }          if  (!isenabled ()  | |  mreturningtostart | |  canchildscrollup ()                | |  mrefreshing | |  mnestedscrollinprogress)  {           // fail  fast if we ' Re not in a state where a swipe is possible            return false;       }           switch  (action)  {           case  motionevent.action_down:                Settargetoffsettopandbottom (Moriginaloffsettop - mcircleview.gettop (),  true);                mActivePointerId =  Motioneventcompat.getpointerid (ev, 0);                mIsBeingDragged = false;                final float initialdowny = getmotioneventy (ev,  Mactivepointerid);     &NBsp;         if  (initialdowny == -1)  {                    return  false;               }               minitialdowny = initialdowny ;               break;               case MotionEvent.ACTION_MOVE:                if  (mactivepointerid ==  Invalid_pointer)  {                    LOG.E (log_tag,  "Got action_move event but don ' T have  an active&nbsP;pointer id. ");                     return false;               }                   final float  y = getmotioneventy (Ev, mactivepointerid);                if  (y == -1)  {                    return false;               }                final float yDiff = y -  minitialdowny;               if  ( ydiff  > mtouchslop && !misbeingdragged)  {                    minitialmotiony = minitialdowny  + mTouchSlop;                    mIsBeingDragged = true;                    mprogress.setalpha (STARTING_PROGRESS_ALPHA);                }                break;               case MotionEventCompat.ACTION_POINTER_UP:                onsecondarypointerup (EV);                break;              case  MotionEvent.ACTION_UP:           case  motionevent.action_cancel:                misbeingdragged = false;                mActivePointerId = INVALID_POINTER;                break;       }           return mIsBeingDragged;  }  

@Override public boolean onintercepttouchevent (motionevent ev) {ensuretarget ();

    Final int action = motioneventcompat.getactionmasked (EV);
    if (mreturningtostart && action = = motionevent.action_down) {Mreturningtostart = false; } if (!isenabled () | | mreturningtostart | | canchildscrollup () | | | mrefreshing | | mnestedscrollinprogress)
    {//Fail fast if we ' re not in a state where a swipe is possible return false; } switch (action) {Case MotionEvent.ACTION_DOWN:setTargetOffsetTopAndBottom (moriginaloffsettop
            -Mcircleview.gettop (), true);
            Mactivepointerid = Motioneventcompat.getpointerid (EV, 0);
            Misbeingdragged = false;
            Final float Initialdowny = getmotioneventy (EV, Mactivepointerid);
            if (Initialdowny = =-1) {return false;
            } minitialdowny = Initialdowny;

        Break Case Motionevent.action_movE:if (Mactivepointerid = = Invalid_pointer) {log.e (Log_tag, "Got action_move event but don ' t
                Has an active pointer ID. ");
            return false;
            Final float y = getmotioneventy (ev, Mactivepointerid);
            if (y = =-1) {return false;
            } final Float Ydiff = y-minitialdowny;
                if (Ydiff > Mtouchslop &&!misbeingdragged) {minitialmotiony = Minitialdowny + mtouchslop;
                Misbeingdragged = true;
            Mprogress.setalpha (Starting_progress_alpha);

        } break;
            Case MotionEventCompat.ACTION_POINTER_UP:onSecondaryPointerUp (EV);

        Break
            Case MotionEvent.ACTION_UP:case MotionEvent.ACTION_CANCEL:mIsBeingDragged = false;
            Mactivepointerid = Invalid_pointer;
    Break
} return misbeingdragged; }

Above a series of logic, the last misbeingdragged is to return to think whether to intercept the event, we are in this method, we first judge, if the x-coordinate change is greater than the y-coordinate changes, then we think that this is left and right sliding, the dropdown refresh does not handle. (You can also make other judgments, the test has x>y effect is good)

We created a custom view called Refreshlayout to inherit Swiperefreshlayout, and re-onintercepttouchevent the method. (This is the following lines of code, which returns false and then the drop-down refresh control does not perform the Ontouchevent event)

[Java] View Plain copy print? float lastx = 0;   float lasty = 0;   Boolean ismovepic  = false;   @Override    public boolean onintercepttouchevent (motionevent  ev)  {                if  (Ev.getaction ( )  ==motionevent.action_down) {           lastx =  ev.getx ();           lasty = ev.gety ();            ismovepic = false;            return super.onintercepttouchevent (EV);        }          final int action =  motioneventcompat.getactionmasked (EV);       vlog.v (Ev.getX ()  +  "-" + ev.gety ());          int x2 =  (int)   Math.Abs (Ev.getx ()  - lastx);       int y2 =  (int)   Math.Abs (Ev.gety ()  - lasty);          //slide picture minimum distance check        VLOG.V ("slip Gap  - >"  + x2 +  "–"  + y2);        if  (x2>y2) {            if  (x2>=100) ismovepic = true;            return false;       }          // Whether to move the picture (drop-down refresh not processed)        if  (ismovepic) {            VLOG.V ("slip Gap  - >"  + x2 +  "–"  + y2);     &Nbsp;      return false;       }          boolean isok = super.onintercepttouchevent (EV);          vlog.v ("isok ->"  + isok);           return isok;  }  

float lastx = 0;
float lasty = 0;
Boolean ismovepic = false;
@Override Public
Boolean onintercepttouchevent (motionevent ev) {



    if (ev.getaction () ==motionevent.action_ Down) {
        lastx = Ev.getx ();
        Lasty = Ev.gety ();
        Ismovepic = false;
        return super.onintercepttouchevent (EV);
    }

    Final int action = motioneventcompat.getactionmasked (EV);
    VLOG.V (Ev.getx () + "---" + ev.gety ());

    int x2 = (int) math.abs (Ev.getx ()-LASTX);
    int y2 = (int) math.abs (ev.gety ()-lasty);

    Slide picture minimum distance check
    vlog.v ("slip gap->" + x2 + "--" + y2);
    if (x2>y2) {
        if (x2>=100) Ismovepic = true;
        return false;
    }

    Whether to move the picture (the dropdown refresh is not processed)
    if (ismovepic) {
        vlog.v ("sliding gap->" + x2 + "--" + y2);
        return false;
    }

    Boolean isOK = super.onintercepttouchevent (EV);

    VLOG.V ("isOK" + isOK);

    return isok;
}


Above judgment, in order to effect better, joined the Ismovepic judgment, this judgment is also very simple, that is if I hold the picture, and then slide a little bit, and then always drop, beyond the position of the ad bar, so that the ad bar can not handle the click event beyond the location, there is a bug, The drop-down refresh will appear again. So if you set it to slide left and right, the y-coordinate changes even more than 100 (100 can be set freely, I have set 100, the test effect is good), that is, out of the banner position, we can not let the drop-down refresh appears.

After adding this judgment, the gesture strokes are very sensitive.


PS: According to this idea, in fact, the other drop-down refresh control, the approximate event conflict resolution idea is similar, there is a better way to leave a message to discuss.


Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.