Example usage for android.view MotionEvent ACTION_POINTER_2_DOWN

List of usage examples for android.view MotionEvent ACTION_POINTER_2_DOWN

Introduction

In this page you can find the example usage for android.view MotionEvent ACTION_POINTER_2_DOWN.

Prototype

int ACTION_POINTER_2_DOWN

To view the source code for android.view MotionEvent ACTION_POINTER_2_DOWN.

Click Source Link

Usage

From source file:xiaofan.llongimageview.view.SubsamplingScaleImageView.java

/**
 * Handle touch events. One finger pans, and two finger pinch and zoom plus panning.
 *//*  w  w w.j ava  2 s.c o  m*/
@Override
public boolean onTouchEvent(MotionEvent event) {
    PointF vCenterEnd;
    float vDistEnd;
    // During non-interruptible anims, ignore all touch events
    if (anim != null && !anim.interruptible) {
        getParent().requestDisallowInterceptTouchEvent(true);
        return true;
    } else {
        anim = null;
    }

    // Abort if not ready
    if (vTranslate == null) {
        return true;
    }
    // Detect flings, taps and double taps
    if (detector == null || detector.onTouchEvent(event)) {
        return true;
    }

    int touchCount = event.getPointerCount();
    switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
    case MotionEvent.ACTION_POINTER_1_DOWN:
    case MotionEvent.ACTION_POINTER_2_DOWN:
        anim = null;
        getParent().requestDisallowInterceptTouchEvent(true);
        maxTouchCount = Math.max(maxTouchCount, touchCount);
        if (touchCount >= 2) {
            if (zoomEnabled) {
                // Start pinch to zoom. Calculate distance between touch points and center point of the pinch.
                float distance = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1));
                scaleStart = scale;
                vDistStart = distance;
                vTranslateStart = new PointF(vTranslate.x, vTranslate.y);
                vCenterStart = new PointF((event.getX(0) + event.getX(1)) / 2,
                        (event.getY(0) + event.getY(1)) / 2);
            } else {
                // Abort all gestures on second touch
                maxTouchCount = 0;
            }
            // Cancel long click timer
            handler.removeMessages(MESSAGE_LONG_CLICK);
        } else {
            // Start one-finger pan
            vTranslateStart = new PointF(vTranslate.x, vTranslate.y);
            vCenterStart = new PointF(event.getX(), event.getY());

            // Start long click timer
            handler.sendEmptyMessageDelayed(MESSAGE_LONG_CLICK, 600);
        }
        return true;
    case MotionEvent.ACTION_MOVE:
        boolean consumed = false;
        if (maxTouchCount > 0) {
            if (touchCount >= 2) {
                // Calculate new distance between touch points, to scale and pan relative to start values.
                vDistEnd = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1));
                vCenterEnd = new PointF((event.getX(0) + event.getX(1)) / 2,
                        (event.getY(0) + event.getY(1)) / 2);

                if (zoomEnabled && (distance(vCenterStart.x, vCenterEnd.x, vCenterStart.y, vCenterEnd.y) > 5
                        || Math.abs(vDistEnd - vDistStart) > 5 || isPanning)) {
                    isZooming = true;
                    isPanning = true;
                    consumed = true;

                    scale = Math.min(maxScale, (vDistEnd / vDistStart) * scaleStart);

                    if (scale <= minScale()) {
                        // Minimum scale reached so don't pan. Adjust start settings so any expand will zoom in.
                        vDistStart = vDistEnd;
                        scaleStart = minScale();
                        vCenterStart = vCenterEnd;
                        vTranslateStart = vTranslate;
                    } else if (panEnabled) {
                        // Translate to place the source image coordinate that was at the center of the pinch at the start
                        // at the center of the pinch now, to give simultaneous pan + zoom.
                        float vLeftStart = vCenterStart.x - vTranslateStart.x;
                        float vTopStart = vCenterStart.y - vTranslateStart.y;
                        float vLeftNow = vLeftStart * (scale / scaleStart);
                        float vTopNow = vTopStart * (scale / scaleStart);
                        vTranslate.x = vCenterEnd.x - vLeftNow;
                        vTranslate.y = vCenterEnd.y - vTopNow;
                    } else if (sRequestedCenter != null) {
                        // With a center specified from code, zoom around that point.
                        vTranslate.x = (getWidth() / 2) - (scale * sRequestedCenter.x);
                        vTranslate.y = (getHeight() / 2) - (scale * sRequestedCenter.y);
                    } else {
                        // With no requested center, scale around the image center.
                        vTranslate.x = (getWidth() / 2) - (scale * (sWidth() / 2));
                        vTranslate.y = (getHeight() / 2) - (scale * (sHeight() / 2));
                    }

                    fitToBounds(true);
                    refreshRequiredTiles(false);
                }
            } else if (!isZooming) {
                // One finger pan - translate the image. We do this calculation even with pan disabled so click
                // and long click behaviour is preserved.
                float dx = Math.abs(event.getX() - vCenterStart.x);
                float dy = Math.abs(event.getY() - vCenterStart.y);
                if (dx > 5 || dy > 5 || isPanning) {
                    consumed = true;
                    vTranslate.x = vTranslateStart.x + (event.getX() - vCenterStart.x);
                    vTranslate.y = vTranslateStart.y + (event.getY() - vCenterStart.y);

                    float lastX = vTranslate.x;
                    float lastY = vTranslate.y;
                    fitToBounds(true);
                    if (lastX == vTranslate.x || (lastY == vTranslate.y && dy > 10) || isPanning) {
                        isPanning = true;
                    } else if (dx > 5) {
                        // Haven't panned the image, and we're at the left or right edge. Switch to page swipe.
                        maxTouchCount = 0;
                        handler.removeMessages(MESSAGE_LONG_CLICK);
                        getParent().requestDisallowInterceptTouchEvent(false);
                    }

                    if (!panEnabled) {
                        vTranslate.x = vTranslateStart.x;
                        vTranslate.y = vTranslateStart.y;
                        getParent().requestDisallowInterceptTouchEvent(false);
                    }

                    refreshRequiredTiles(false);
                }
            }
        }
        if (consumed) {
            handler.removeMessages(MESSAGE_LONG_CLICK);
            invalidate();
            return true;
        }
        break;
    case MotionEvent.ACTION_UP:
    case MotionEvent.ACTION_POINTER_UP:
    case MotionEvent.ACTION_POINTER_2_UP:
        handler.removeMessages(MESSAGE_LONG_CLICK);
        if (maxTouchCount > 0 && (isZooming || isPanning)) {
            if (isZooming && touchCount == 2) {
                // Convert from zoom to pan with remaining touch
                isPanning = true;
                vTranslateStart = new PointF(vTranslate.x, vTranslate.y);
                if (event.getActionIndex() == 1) {
                    vCenterStart = new PointF(event.getX(0), event.getY(0));
                } else {
                    vCenterStart = new PointF(event.getX(1), event.getY(1));
                }
            }
            if (touchCount < 3) {
                // End zooming when only one touch point
                isZooming = false;
            }
            if (touchCount < 2) {
                // End panning when no touch points
                isPanning = false;
                maxTouchCount = 0;
            }
            // Trigger load of tiles now required
            refreshRequiredTiles(true);
            return true;
        }
        if (touchCount == 1) {
            isZooming = false;
            isPanning = false;
            maxTouchCount = 0;
        }
        return true;
    }
    return super.onTouchEvent(event);
}

From source file:com.bizcom.vc.widget.cus.SubsamplingScaleImageView.java

/**
 * Handle touch events. One finger pans, and two finger pinch and zoom plus
 * panning.//from  w w w  .  j  av  a  2 s .  c o  m
 */
@Override
public boolean onTouchEvent(MotionEvent event) {
    PointF vCenterEnd;
    float vDistEnd;
    // During non-interruptible anims, ignore all touch events
    if (anim != null && !anim.interruptible) {
        getParent().requestDisallowInterceptTouchEvent(true);
        return true;
    } else {
        anim = null;
    }

    // Abort if not ready
    if (vTranslate == null) {
        return true;
    }
    // Detect flings, taps and double taps
    if (detector == null || detector.onTouchEvent(event)) {
        return true;
    }

    int touchCount = event.getPointerCount();
    switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
    case MotionEvent.ACTION_POINTER_1_DOWN:
    case MotionEvent.ACTION_POINTER_2_DOWN:
        anim = null;
        getParent().requestDisallowInterceptTouchEvent(true);
        maxTouchCount = Math.max(maxTouchCount, touchCount);
        if (touchCount >= 2) {
            if (zoomEnabled) {
                // Start pinch to zoom. Calculate distance between touch
                // points and center point of the pinch.
                float distance = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1));
                scaleStart = scale;
                vDistStart = distance;
                vTranslateStart = new PointF(vTranslate.x, vTranslate.y);
                vCenterStart = new PointF((event.getX(0) + event.getX(1)) / 2,
                        (event.getY(0) + event.getY(1)) / 2);
            } else {
                // Abort all gestures on second touch
                maxTouchCount = 0;
            }
            // Cancel long click timer
            handler.removeMessages(MESSAGE_LONG_CLICK);
        } else {
            // Start one-finger pan
            vTranslateStart = new PointF(vTranslate.x, vTranslate.y);
            vCenterStart = new PointF(event.getX(), event.getY());

            // Start long click timer
            handler.sendEmptyMessageDelayed(MESSAGE_LONG_CLICK, 600);
        }
        return true;
    case MotionEvent.ACTION_MOVE:
        boolean consumed = false;
        if (maxTouchCount > 0) {
            if (touchCount >= 2) {
                // Calculate new distance between touch points, to scale and
                // pan relative to start values.
                vDistEnd = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1));
                vCenterEnd = new PointF((event.getX(0) + event.getX(1)) / 2,
                        (event.getY(0) + event.getY(1)) / 2);

                if (zoomEnabled && (distance(vCenterStart.x, vCenterEnd.x, vCenterStart.y, vCenterEnd.y) > 5
                        || Math.abs(vDistEnd - vDistStart) > 5 || isPanning)) {
                    isZooming = true;
                    isPanning = true;
                    consumed = true;

                    scale = Math.min(maxScale, (vDistEnd / vDistStart) * scaleStart);

                    if (scale <= minScale()) {
                        // Minimum scale reached so don't pan. Adjust start
                        // settings so any expand will zoom in.
                        vDistStart = vDistEnd;
                        scaleStart = minScale();
                        vCenterStart = vCenterEnd;
                        vTranslateStart = vTranslate;
                    } else if (panEnabled) {
                        // Translate to place the source image coordinate
                        // that was at the center of the pinch at the start
                        // at the center of the pinch now, to give
                        // simultaneous pan + zoom.
                        float vLeftStart = vCenterStart.x - vTranslateStart.x;
                        float vTopStart = vCenterStart.y - vTranslateStart.y;
                        float vLeftNow = vLeftStart * (scale / scaleStart);
                        float vTopNow = vTopStart * (scale / scaleStart);
                        vTranslate.x = vCenterEnd.x - vLeftNow;
                        vTranslate.y = vCenterEnd.y - vTopNow;
                    } else if (sRequestedCenter != null) {
                        // With a center specified from code, zoom around
                        // that point.
                        vTranslate.x = (getWidth() / 2) - (scale * sRequestedCenter.x);
                        vTranslate.y = (getHeight() / 2) - (scale * sRequestedCenter.y);
                    } else {
                        // With no requested center, scale around the image
                        // center.
                        vTranslate.x = (getWidth() / 2) - (scale * (sWidth() / 2));
                        vTranslate.y = (getHeight() / 2) - (scale * (sHeight() / 2));
                    }

                    fitToBounds(true);
                    refreshRequiredTiles(false);
                }
            } else if (!isZooming) {
                // One finger pan - translate the image. We do this
                // calculation even with pan disabled so click
                // and long click behaviour is preserved.
                float dx = Math.abs(event.getX() - vCenterStart.x);
                float dy = Math.abs(event.getY() - vCenterStart.y);
                if (dx > 5 || dy > 5 || isPanning) {
                    consumed = true;
                    vTranslate.x = vTranslateStart.x + (event.getX() - vCenterStart.x);
                    vTranslate.y = vTranslateStart.y + (event.getY() - vCenterStart.y);

                    float lastX = vTranslate.x;
                    float lastY = vTranslate.y;
                    fitToBounds(true);
                    if (lastX == vTranslate.x || (lastY == vTranslate.y && dy > 10) || isPanning) {
                        isPanning = true;
                    } else if (dx > 5) {
                        // Haven't panned the image, and we're at the left
                        // or right edge. Switch to page swipe.
                        maxTouchCount = 0;
                        handler.removeMessages(MESSAGE_LONG_CLICK);
                        getParent().requestDisallowInterceptTouchEvent(false);
                    }

                    if (!panEnabled) {
                        vTranslate.x = vTranslateStart.x;
                        vTranslate.y = vTranslateStart.y;
                        getParent().requestDisallowInterceptTouchEvent(false);
                    }

                    refreshRequiredTiles(false);
                }
            }
        }
        if (consumed) {
            handler.removeMessages(MESSAGE_LONG_CLICK);
            invalidate();
            return true;
        }
        break;
    case MotionEvent.ACTION_UP:
    case MotionEvent.ACTION_POINTER_UP:
    case MotionEvent.ACTION_POINTER_2_UP:
        handler.removeMessages(MESSAGE_LONG_CLICK);
        if (maxTouchCount > 0 && (isZooming || isPanning)) {
            if (isZooming && touchCount == 2) {
                // Convert from zoom to pan with remaining touch
                isPanning = true;
                vTranslateStart = new PointF(vTranslate.x, vTranslate.y);
                if (event.getActionIndex() == 1) {
                    vCenterStart = new PointF(event.getX(0), event.getY(0));
                } else {
                    vCenterStart = new PointF(event.getX(1), event.getY(1));
                }
            }
            if (touchCount < 3) {
                // End zooming when only one touch point
                isZooming = false;
            }
            if (touchCount < 2) {
                // End panning when no touch points
                isPanning = false;
                maxTouchCount = 0;
            }
            // Trigger load of tiles now required
            refreshRequiredTiles(true);
            return true;
        }
        if (touchCount == 1) {
            isZooming = false;
            isPanning = false;
            maxTouchCount = 0;
        }
        return true;
    }
    return super.onTouchEvent(event);
}

From source file:me.ccrama.redditslide.Views.SubsamplingScaleImageView.java

/**
 * Handle touch events. One finger pans, and two finger pinch and zoom plus panning.
 *//*from  w w w .j a v a2  s  .c o  m*/
@Override
@SuppressWarnings("deprecation")
public boolean onTouchEvent(@NonNull MotionEvent event) {
    // During non-interruptible anims, ignore all touch events
    if (anim != null && !anim.interruptible) {
        getParent().requestDisallowInterceptTouchEvent(true);
        return true;
    } else {
        if (anim != null && anim.listener != null) {
            try {
                anim.listener.onInterruptedByUser();
            } catch (Exception e) {
                Log.w(TAG, "Error thrown by animation listener", e);
            }
        }
        anim = null;
    }

    // Abort if not ready
    if (vTranslate == null) {
        return true;
    }
    // Detect flings, taps and double taps
    if (!isQuickScaling && (detector == null || detector.onTouchEvent(event))) {
        isZooming = false;
        isPanning = false;
        maxTouchCount = 0;
        return true;
    }

    if (vTranslateStart == null) {
        vTranslateStart = new PointF(0, 0);
    }
    if (vCenterStart == null) {
        vCenterStart = new PointF(0, 0);
    }

    int touchCount = event.getPointerCount();
    switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
    case MotionEvent.ACTION_POINTER_1_DOWN:
    case MotionEvent.ACTION_POINTER_2_DOWN:
        anim = null;
        getParent().requestDisallowInterceptTouchEvent(true);
        maxTouchCount = Math.max(maxTouchCount, touchCount);
        if (touchCount >= 2) {
            if (zoomEnabled) {
                // Start pinch to zoom. Calculate distance between touch points and center point of the pinch.
                float distance = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1));
                scaleStart = scale;
                vDistStart = distance;
                vTranslateStart.set(vTranslate.x, vTranslate.y);
                vCenterStart.set((event.getX(0) + event.getX(1)) / 2, (event.getY(0) + event.getY(1)) / 2);
            } else {
                // Abort all gestures on second touch
                maxTouchCount = 0;
            }
            // Cancel long click timer
            handler.removeMessages(MESSAGE_LONG_CLICK);
        } else if (!isQuickScaling) {
            // Start one-finger pan
            vTranslateStart.set(vTranslate.x, vTranslate.y);
            vCenterStart.set(event.getX(), event.getY());

            // Start long click timer
            handler.sendEmptyMessageDelayed(MESSAGE_LONG_CLICK, 600);
        }
        return true;
    case MotionEvent.ACTION_MOVE:
        boolean consumed = false;
        if (maxTouchCount > 0) {
            if (touchCount >= 2) {
                // Calculate new distance between touch points, to scale and pan relative to start values.
                float vDistEnd = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1));
                float vCenterEndX = (event.getX(0) + event.getX(1)) / 2;
                float vCenterEndY = (event.getY(0) + event.getY(1)) / 2;

                if (zoomEnabled && (distance(vCenterStart.x, vCenterEndX, vCenterStart.y, vCenterEndY) > 5
                        || Math.abs(vDistEnd - vDistStart) > 5 || isPanning)) {
                    isZooming = true;
                    isPanning = true;
                    consumed = true;

                    setScale(Math.min(maxScale, (vDistEnd / vDistStart) * scaleStart));

                    if (scale <= minScale()) {
                        // Minimum scale reached so don't pan. Adjust start settings so any expand will zoom in.
                        vDistStart = vDistEnd;
                        scaleStart = minScale();
                        vCenterStart.set(vCenterEndX, vCenterEndY);
                        vTranslateStart.set(vTranslate);
                    } else if (panEnabled) {
                        // Translate to place the source image coordinate that was at the center of the pinch at the start
                        // at the center of the pinch now, to give simultaneous pan + zoom.
                        float vLeftStart = vCenterStart.x - vTranslateStart.x;
                        float vTopStart = vCenterStart.y - vTranslateStart.y;
                        float vLeftNow = vLeftStart * (scale / scaleStart);
                        float vTopNow = vTopStart * (scale / scaleStart);
                        vTranslate.x = vCenterEndX - vLeftNow;
                        vTranslate.y = vCenterEndY - vTopNow;
                    } else if (sRequestedCenter != null) {
                        // With a center specified from code, zoom around that point.
                        vTranslate.x = (getWidth() / 2) - (scale * sRequestedCenter.x);
                        vTranslate.y = (getHeight() / 2) - (scale * sRequestedCenter.y);
                    } else {
                        // With no requested center, scale around the image center.
                        vTranslate.x = (getWidth() / 2) - (scale * (sWidth() / 2));
                        vTranslate.y = (getHeight() / 2) - (scale * (sHeight() / 2));
                    }

                    fitToBounds(true);
                    refreshRequiredTiles(false);
                }
            } else if (isQuickScaling) {
                // One finger zoom
                // Stole Google's Magical Formula to make sure it feels the exact same
                float dist = Math.abs(vCenterStart.y - event.getY()) * 2 + quickScaleThreshold;

                if (quickScaleLastDistance == -1F)
                    quickScaleLastDistance = dist;
                boolean isUpwards = event.getY() > quickScaleLastPoint.y;
                quickScaleLastPoint.set(0, event.getY());

                float spanDiff = (Math.abs(1 - (dist / quickScaleLastDistance)) * 0.5F);

                if (spanDiff > 0.03f || quickScaleMoved) {
                    quickScaleMoved = true;

                    float multiplier = 1;
                    if (quickScaleLastDistance > 0) {
                        multiplier = isUpwards ? (1 + spanDiff) : (1 - spanDiff);
                    }

                    setScale(Math.max(minScale(), Math.min(maxScale, scale * multiplier)));

                    if (panEnabled) {
                        float vLeftStart = vCenterStart.x - vTranslateStart.x;
                        float vTopStart = vCenterStart.y - vTranslateStart.y;
                        float vLeftNow = vLeftStart * (scale / scaleStart);
                        float vTopNow = vTopStart * (scale / scaleStart);
                        vTranslate.x = vCenterStart.x - vLeftNow;
                        vTranslate.y = vCenterStart.y - vTopNow;
                    } else if (sRequestedCenter != null) {
                        // With a center specified from code, zoom around that point.
                        vTranslate.x = (getWidth() / 2) - (scale * sRequestedCenter.x);
                        vTranslate.y = (getHeight() / 2) - (scale * sRequestedCenter.y);
                    } else {
                        // With no requested center, scale around the image center.
                        vTranslate.x = (getWidth() / 2) - (scale * (sWidth() / 2));
                        vTranslate.y = (getHeight() / 2) - (scale * (sHeight() / 2));
                    }
                }

                quickScaleLastDistance = dist;

                fitToBounds(true);
                refreshRequiredTiles(false);

                consumed = true;
            } else if (!isZooming) {
                // One finger pan - translate the image. We do this calculation even with pan disabled so click
                // and long click behaviour is preserved.
                float dx = Math.abs(event.getX() - vCenterStart.x);
                float dy = Math.abs(event.getY() - vCenterStart.y);
                if (dx > 5 || dy > 5 || isPanning) {
                    consumed = true;
                    vTranslate.x = vTranslateStart.x + (event.getX() - vCenterStart.x);
                    vTranslate.y = vTranslateStart.y + (event.getY() - vCenterStart.y);

                    float lastX = vTranslate.x;
                    float lastY = vTranslate.y;
                    fitToBounds(true);
                    boolean atXEdge = lastX != vTranslate.x;
                    boolean edgeXSwipe = atXEdge && dx > dy && !isPanning;
                    boolean yPan = lastY == vTranslate.y && dy > 15;
                    if (!edgeXSwipe && (!atXEdge || yPan || isPanning)) {
                        isPanning = true;
                    } else if (dx > 5) {
                        // Haven't panned the image, and we're at the left or right edge. Switch to page swipe.
                        maxTouchCount = 0;
                        handler.removeMessages(MESSAGE_LONG_CLICK);
                        getParent().requestDisallowInterceptTouchEvent(false);
                    }

                    if (!panEnabled) {
                        vTranslate.x = vTranslateStart.x;
                        vTranslate.y = vTranslateStart.y;
                        getParent().requestDisallowInterceptTouchEvent(false);
                    }

                    refreshRequiredTiles(false);
                }
            }
        }
        if (consumed) {
            handler.removeMessages(MESSAGE_LONG_CLICK);
            invalidate();
            return true;
        }
        break;
    case MotionEvent.ACTION_UP:
    case MotionEvent.ACTION_POINTER_UP:
    case MotionEvent.ACTION_POINTER_2_UP:
        handler.removeMessages(MESSAGE_LONG_CLICK);
        if (isQuickScaling) {
            isQuickScaling = false;
            if (!quickScaleMoved) {
                doubleTapZoom(quickScaleCenter, vCenterStart);
            }
        }
        if (maxTouchCount > 0 && (isZooming || isPanning)) {
            if (isZooming && touchCount == 2) {
                // Convert from zoom to pan with remaining touch
                isPanning = true;
                vTranslateStart.set(vTranslate.x, vTranslate.y);
                if (event.getActionIndex() == 1) {
                    vCenterStart.set(event.getX(0), event.getY(0));
                } else {
                    vCenterStart.set(event.getX(1), event.getY(1));
                }
            }
            if (touchCount < 3) {
                // End zooming when only one touch point
                isZooming = false;
            }
            if (touchCount < 2) {
                // End panning when no touch points
                isPanning = false;
                maxTouchCount = 0;
            }
            // Trigger load of tiles now required
            refreshRequiredTiles(true);
            return true;
        }
        if (touchCount == 1) {
            isZooming = false;
            isPanning = false;
            maxTouchCount = 0;
        }
        return true;
    }
    return super.onTouchEvent(event);
}

From source file:processing.core.PApplet.java

/**
 * Take action based on a motion event. Internally updates mouseX, mouseY,
 * mousePressed, and mouseEvent. Then it calls the event type with no
 * params, i.e. mousePressed() or mouseReleased() that the user may have
 * overloaded to do something more useful.
 *//*from   ww  w. j  a v  a 2s  . c  om*/
protected void handleMotionEvent(PMotionEvent pme) {
    pmotionX = emotionX;
    pmotionY = emotionY;
    motionX = pme.motionX[0];
    motionY = pme.motionY[0];
    motionPressure = pme.motionPressure[0];

    // replace previous mouseX/Y with the last from the event handlers
    pmouseX = emouseX;
    pmouseY = emouseY;
    mouseX = pme.mouseX[0];
    mouseY = pme.mouseY[0];

    // this used to only be called on mouseMoved and mouseDragged
    // change it back if people run into trouble
    if (firstMotion) {
        pmouseX = mouseX;
        pmouseY = mouseY;
        dmouseX = mouseX; // set it as the first value to be used inside
                          // draw() too
        dmouseY = mouseY;

        pmotionX = motionX;
        pmotionY = motionY;
        dmotionX = motionX;
        dmotionY = motionY;

        firstMotion = false;
    }

    if (ppointersX.length < numPointers) {
        ppointersX = new float[numPointers];
        ppointersY = new float[numPointers];
        ppointersPressure = new float[numPointers];
    }
    arrayCopy(pointersX, ppointersX);
    arrayCopy(pointersY, ppointersY);
    arrayCopy(pointersPressure, ppointersPressure);

    numPointers = pme.numPointers;
    if (pointersX.length < numPointers) {
        pointersX = new float[numPointers];
        pointersY = new float[numPointers];
        pointersPressure = new float[numPointers];
    }
    arrayCopy(pme.motionX, pointersX);
    arrayCopy(pme.motionY, pointersY);
    arrayCopy(pme.motionPressure, pointersPressure);

    // Triggering the appropriate event methods
    if (pme.action == MotionEvent.ACTION_DOWN || (!mousePressed && numPointers == 1)) {
        // First pointer is down
        mousePressed = true;
        onePointerGesture = true;
        twoPointerGesture = false;
        downMillis = millis();
        downX = pointersX[0];
        downY = pointersY[0];

        mousePressed();
        pressEvent();

    } else if ((pme.action == MotionEvent.ACTION_POINTER_DOWN && numPointers == 2)
            || (pme.action == MotionEvent.ACTION_POINTER_2_DOWN) || // 2.3
            // seems
            // to
            // use
            // this
            // action
            // constant
            // (supposedly
            // deprecated)
            // instead
            // of
            // ACTION_POINTER_DOWN
            (pnumPointers == 1 && numPointers == 2)) { // 2.1 just uses MOVE
        // as the action
        // constant, so the
        // only way to know
        // we have a new
        // pointer is to
        // compare the
        // counters.

        // An additional pointer is down (we keep track of multitouch only
        // for 2 pointers)
        onePointerGesture = false;
        twoPointerGesture = true;

    } else if ((pme.action == MotionEvent.ACTION_POINTER_UP && numPointers == 2)
            || (pme.action == MotionEvent.ACTION_POINTER_2_UP) || // 2.1
            // doesn't
            // use
            // the
            // ACTION_POINTER_UP
            // constant,
            // but
            // this
            // one,
            // apparently
            // deprecated
            // in
            // newer
            // versions
            // of
            // the
            // SDK.
            (twoPointerGesture && numPointers < 2)) { // Sometimes it seems
        // that it doesn't
        // generate the up
        // event.
        // A previously detected pointer is up

        twoPointerGesture = false; // Not doing a 2-pointer gesture anymore,
        // but neither a 1-pointer.

    } else if (pme.action == MotionEvent.ACTION_MOVE) {
        // Pointer motion

        if (onePointerGesture) {
            if (mousePressed) {
                mouseDragged();
                dragEvent();
            } else {
                mouseMoved();
                moveEvent();
            }
        } else if (twoPointerGesture) {
            float d0 = PApplet.dist(ppointersX[0], ppointersY[0], ppointersX[1], ppointersY[1]);
            float d1 = PApplet.dist(pointersX[0], pointersY[0], pointersX[1], pointersY[1]);

            if (0 < d0 && 0 < d1) {
                float centerX = 0.5f * (pointersX[0] + pointersX[1]);
                float centerY = 0.5f * (pointersY[0] + pointersY[1]);

                zoomEvent(centerX, centerY, d0, d1);
            }
        }

    } else if (pme.action == MotionEvent.ACTION_UP) {
        // Final pointer is up
        mousePressed = false;
        mouseReleased();

        float upX = pointersX[0];
        float upY = pointersY[0];
        float gestureLength = PApplet.dist(downX, downY, upX, upY);

        int upMillis = millis();
        int gestureTime = upMillis - downMillis;

        if (onePointerGesture) {

            // First, lets determine if this 1-pointer event is a tap
            boolean tap = gestureLength <= MAX_TAP_DISP && gestureTime <= MAX_TAP_DURATION;
            if (tap) {
                mouseClicked();
                tapEvent(downX, downY);
            } else if (MIN_SWIPE_LENGTH <= gestureLength && gestureTime <= MAX_SWIPE_DURATION) {
                swipeEvent(downX, downY, upX, upY);
            } else {
                mouseReleased();
                releaseEvent();
            }

        } else {
            mouseReleased();
            releaseEvent();
        }

        onePointerGesture = twoPointerGesture = false;
    } else if (pme.action == MotionEvent.ACTION_CANCEL) {
        // Current gesture is canceled.
        onePointerGesture = twoPointerGesture = false;
        mousePressed = false;

        mouseReleased();
        releaseEvent();
    } else {
        // System.out.println("Unknown MotionEvent action: " + action);
    }

    pnumPointers = numPointers;

    if (pme.action == MotionEvent.ACTION_MOVE) {
        emotionX = motionX;
        emotionY = motionY;
        emouseX = mouseX;
        emouseY = mouseY;
    }
}

From source file:com.cssweb.android.view.KlineView.java

/**
 * true?,false??/*  w  w  w  . j ava 2  s. c  o m*/
 */
public boolean onTouchEvent(MotionEvent motionEvent) {
    int count = motionEvent.getPointerCount();
    if (count == 2) {//
        isTrackStatus = false;
        if (motionEvent.getAction() == MotionEvent.ACTION_POINTER_1_DOWN
                || motionEvent.getAction() == MotionEvent.ACTION_POINTER_2_DOWN) {
            float x0 = motionEvent.getX(0);
            float x1 = motionEvent.getX(1);
            float y0 = motionEvent.getY(0);
            float y1 = motionEvent.getY(1);
            distanceY0 = Math.abs(y1 - y0);
            distanceX0 = Math.abs(x1 - x0);
        }
        if (motionEvent.getAction() == MotionEvent.ACTION_POINTER_1_UP
                || motionEvent.getAction() == MotionEvent.ACTION_POINTER_2_UP) {
            float x0 = motionEvent.getX(0);
            float x1 = motionEvent.getX(1);
            float y0 = motionEvent.getY(0);
            float y1 = motionEvent.getY(1);
            distanceY1 = Math.abs(y1 - y0);
            distanceX1 = Math.abs(x1 - x0);
            if (distanceY1 > distanceY0 && distanceX1 > distanceX0) {
                upHandler();
            } else if (distanceY1 < distanceY0 && distanceX1 < distanceX0) {
                downHandler();
            }
        }
        return false;
    } else if (count == 1) {//??
        switch (motionEvent.getAction()) {
        case MotionEvent.ACTION_DOWN:
            touchesBegan(motionEvent);
            break;

        case MotionEvent.ACTION_MOVE:
            touchesMoved(motionEvent);
            break;

        case MotionEvent.ACTION_UP:
            touchesEnded(motionEvent);
            break;

        }
    }
    return true;
}