Java Code Examples for android.view.MotionEvent#getHistoricalY()

The following examples show how to use android.view.MotionEvent#getHistoricalY() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: VerticalElasticityBounceEffect.java    From elasticity with BSD 2-Clause "Simplified" License 5 votes vote down vote up
public boolean init(View view, MotionEvent event) {

            // We must have history available to calc the dx. Normally it's there - if it isn't temporarily,
            // we declare the event 'invalid' and expect it in consequent events.
            if (event.getHistorySize() == 0) {
                return false;
            }

            // Allow for counter-orientation-direction operations (e.g. item swiping) to run fluently.
            final float dy = event.getY(0) - event.getHistoricalY(0, 0);
            final float dx = event.getX(0) - event.getHistoricalX(0, 0);
            if (Math.abs(dx) > Math.abs(dy)) {
                return false;
            }

            if( dy == 0.f  ) { // just click event
                return false;
            }

//            mAbsOffset = view.getTranslationY();
            mAbsOffset = getViewOffset(view);
            mDeltaOffset = dy;
            mDir = mDeltaOffset > 0;
            Log.d("wxy-motion", String.format("mAbsOffset %s mDeltaOffset %s", mAbsOffset, mDeltaOffset));
            Log.d("wxy-motion","mDir = " + mDir);
            return true;
        }
 
Example 2
Source File: UsMotionEvent.java    From walt with Apache License 2.0 5 votes vote down vote up
public UsMotionEvent(MotionEvent event, long baseTime, int pos) {
    createTime = RemoteClockInfo.microTime() - baseTime;
    this.baseTime = baseTime;
    slot = pos;
    action = MotionEvent.ACTION_MOVE; // Only MOVE events get bundled with history

    kernelTime = getHistoricalEventTimeMicro(event, pos) - baseTime;
    x = event.getHistoricalX(pos);
    y = event.getHistoricalY(pos);
}
 
Example 3
Source File: MapView.java    From Androzic with GNU General Public License v3.0 5 votes vote down vote up
@Override
public boolean onTrackballEvent(MotionEvent event)
{
	int action = event.getAction();
	switch (action)
	{
		case MotionEvent.ACTION_UP:
			setFollowingThroughContext(!isFollowing);
			break;
		case MotionEvent.ACTION_MOVE:
			if (!isFollowing)
			{
				int n = event.getHistorySize();
				final float scaleX = event.getXPrecision();
				final float scaleY = event.getYPrecision();
				int dx = (int) (-event.getX() * scaleX);
				int dy = (int) (-event.getY() * scaleY);
				for (int i = 0; i < n; i++)
				{
					dx += -event.getHistoricalX(i) * scaleX;
					dy += -event.getHistoricalY(i) * scaleY;
				}
				if (Math.abs(dx) > 0 || Math.abs(dy) > 0)
				{
					onDragFinished(dx, dy);
				}
			}
			break;
	}

	/*
	 * for (MapOverlay mo : this.overlays) if (mo.onTrackballEvent(event,
	 * this)) return true;
	 */

	return true;
}
 
Example 4
Source File: WXGesture.java    From weex-uikit with MIT License 5 votes vote down vote up
/**
 * Get event's location in Document's (Page) coordinate.
 * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/pageX">pageX</a>
 * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/pageY">pageY</a>
 * @param motionEvent the original motionEvent
 * @param pointerIndex pointerIndex
 * @param position if motionEvent.getHistoricalSize()!=0, the is the index of historical event,
 *                 otherwise this is {@link #CUR_EVENT} which indicates historicalSize is zero
 * @return the event location in page's coordinate.
 */
private PointF getEventLocInPageCoordinate(MotionEvent motionEvent, int pointerIndex, int position) {
  float eventX, eventY;
  if (position == CUR_EVENT) {
    eventX = motionEvent.getX(pointerIndex);
    eventY = motionEvent.getY(pointerIndex);
  } else {
    eventX = motionEvent.getHistoricalX(pointerIndex, position);
    eventY = motionEvent.getHistoricalY(pointerIndex, position);
  }
  return getEventLocInPageCoordinate(eventX, eventY);
}
 
Example 5
Source File: CollaborativeDrawingView.java    From video-quickstart-android with MIT License 4 votes vote down vote up
@SuppressLint("ClickableViewAccessibility")
@Override
public boolean onTouchEvent(MotionEvent event) {
    // Only handle touch events when enabled
    if (!isEnabled()) {
        return false;
    }

    float eventX = event.getX();
    float eventY = event.getY();
    int actionEvent = event.getAction();

    // Notify listener of action event
    if (listener != null) {
        listener.onTouchEvent(actionEvent, eventX, eventY);
    }

    // Process action event
    switch (actionEvent) {
        case MotionEvent.ACTION_DOWN:
            path.moveTo(eventX, eventY);
            lastTouchX = eventX;
            lastTouchY = eventY;
            // There is no end point yet, so don't waste cycles invalidating.
            return true;
        case MotionEvent.ACTION_MOVE:
        case MotionEvent.ACTION_UP:
            // Start tracking the dirty region.
            resetDirtyRect(eventX, eventY);

            /*
             * When the hardware tracks events faster than they are delivered, the event will
             * contain a history of those skipped points.
             */
            int historySize = event.getHistorySize();
            for (int i = 0; i < historySize; i++) {
                float historicalX = event.getHistoricalX(i);
                float historicalY = event.getHistoricalY(i);
                expandDirtyRect(historicalX, historicalY);
                path.lineTo(historicalX, historicalY);
            }
            // After replaying history, connect the line to the touch point.
            path.lineTo(eventX, eventY);
            break;
        default:
            Log.d(TAG, "Ignored touch event: " + event.toString());
            return false;
    }

    // Include half the stroke width to avoid clipping.
    invalidate(
            (int) (dirtyRect.left - HALF_STROKE_WIDTH),
            (int) (dirtyRect.top - HALF_STROKE_WIDTH),
            (int) (dirtyRect.right + HALF_STROKE_WIDTH),
            (int) (dirtyRect.bottom + HALF_STROKE_WIDTH));
    lastTouchX = eventX;
    lastTouchY = eventY;
    return true;
}
 
Example 6
Source File: VerticalOverScrollBounceEffectDecoratorTest.java    From overscroll-decor with BSD 2-Clause "Simplified" License 4 votes vote down vote up
/**
 * When over-scroll has already started (downwards in this case) and suddenly the user changes
 * their mind and scrolls a bit in the other direction:
 * <br/>We expect the <b>touch to still be intercepted</b> in that case, and the <b>overscroll to remain in effect</b>.
 */
@Test
public void onTouchMoveAction_dragUpWhenDownOverscolled_continueOverscrollingUpwards() {

    // Arrange

    // In down & up drag tests we use equal ratios to avoid the effect's under-scroll handling
    final float touchDragRatioFwd = 3f;
    final float touchDragRatioBck = 3f;

    // Bring UUT to a downwrads-overscroll state
    when(mViewAdapter.isInAbsoluteStart()).thenReturn(true);
    when(mViewAdapter.isInAbsoluteEnd()).thenReturn(false);

    VerticalOverScrollBounceEffectDecorator uut = getUUT(touchDragRatioFwd, touchDragRatioBck);
    MotionEvent eventMoveRight = createLongDownwardsMoveEvent();
    uut.onTouch(mView, eventMoveRight);
    reset(mView);
    float startTransY = (eventMoveRight.getY() - eventMoveRight.getHistoricalY(0)) / touchDragRatioFwd;
    when(mView.getTranslationY()).thenReturn(startTransY);

    // Create the up-drag event
    MotionEvent eventMoveUpwards = createShortUpwardsMoveEvent();

    // Act

    boolean ret = uut.onTouch(mView, eventMoveUpwards);

    // Assert

    float expectedTransY = startTransY +
            (eventMoveUpwards.getY() - eventMoveUpwards.getHistoricalY(0)) / touchDragRatioBck;
    verify(mView).setTranslationY(expectedTransY);
    verify(mView, never()).setTranslationX(anyFloat());
    assertTrue(ret);
    assertEquals(STATE_DRAG_START_SIDE, uut.getCurrentState());

    // State-change listener called only once?
    verify(mStateListener).onOverScrollStateChange(eq(uut), eq(STATE_IDLE), eq(STATE_DRAG_START_SIDE));
    verify(mStateListener).onOverScrollStateChange(eq(uut), anyInt(), anyInt());
    // Update-listener called exactly twice?
    verify(mUpdateListener).onOverScrollUpdate(eq(uut), eq(STATE_DRAG_START_SIDE), eq(startTransY));
    verify(mUpdateListener).onOverScrollUpdate(eq(uut), eq(STATE_DRAG_START_SIDE), eq(expectedTransY));
    verify(mUpdateListener, times(2)).onOverScrollUpdate(eq(uut), anyInt(), anyFloat());
}
 
Example 7
Source File: DrawableView.java    From UltimateAndroid with Apache License 2.0 4 votes vote down vote up
@Override
public boolean onTouchEvent(MotionEvent event) {
    float eventX = event.getX();
    float eventY = event.getY();

    switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:
            path.moveTo(eventX, eventY);
            lastTouchX = eventX;
            lastTouchY = eventY;
            // There is no end point yet, so don't waste cycles invalidating.
            return true;

        case MotionEvent.ACTION_MOVE:
        case MotionEvent.ACTION_UP:
            // Start tracking the dirty region.
            resetDirtyRect(eventX, eventY);

            // When the hardware tracks events faster than they are delivered, the
            // event will contain a history of those skipped points.
            int historySize = event.getHistorySize();
            for (int i = 0; i < historySize; i++) {
                float historicalX = event.getHistoricalX(i);
                float historicalY = event.getHistoricalY(i);
                expandDirtyRect(historicalX, historicalY);
                path.lineTo(historicalX, historicalY);
            }

            // After replaying history, connect the line to the touch point.
            path.lineTo(eventX, eventY);
            break;

        default:
            Logs.d("Ignored touch event: " + event.toString());
            return false;
    }

    // Include half the stroke width to avoid clipping.
    invalidate(
            (int) (dirtyRect.left - HALF_STROKE_WIDTH),
            (int) (dirtyRect.top - HALF_STROKE_WIDTH),
            (int) (dirtyRect.right + HALF_STROKE_WIDTH),
            (int) (dirtyRect.bottom + HALF_STROKE_WIDTH));

    lastTouchX = eventX;
    lastTouchY = eventY;

    return true;
}
 
Example 8
Source File: LockPatternViewEx.java    From android-lockpattern with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when
    // the device
    // is busy...
    final float radius = mPathWidth;
    final int historySize = event.getHistorySize();
    mTmpInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        final float x = i < historySize ? event.getHistoricalX(i) : event
                .getX();
        final float y = i < historySize ? event.getHistoricalY(i) : event
                .getY();
        Cell hitCell = detectAndAddHit(x, y);
        final int patternSize = mPattern.size();
        if (hitCell != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // note current x and y for rubber banding of in progress patterns
        final float dx = Math.abs(x - mInProgressX);
        final float dy = Math.abs(y - mInProgressY);
        if (dx > DRAG_THRESHHOLD || dy > DRAG_THRESHHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Cell> pattern = mPattern;
            final Cell lastCell = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastCell.column);
            float lastCellCenterY = getCenterYForRow(lastCell.row);

            // Adjust for drawn segment from last cell to (x,y). Radius
            // accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's
            // previous cell
            if (hitCell != null) {
                final float width = mSquareWidth * 0.5f;
                final float height = mSquareHeight * 0.5f;
                final float hitCellCenterX = getCenterXForColumn(hitCell.column);
                final float hitCellCenterY = getCenterYForRow(hitCell.row);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous
            // location
            mTmpInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a
    // certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTmpInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTmpInvalidateRect);
    }
}
 
Example 9
Source File: VerticalOverScrollBounceEffectDecoratorTest.java    From overscroll-decor with BSD 2-Clause "Simplified" License 4 votes vote down vote up
/**
 * When over-scroll has already started (upwards in this case) and suddenly the user changes
 * their mind and scrolls a bit in the other direction:
 * <br/>We expect the <b>touch to still be intercepted</b> in that case, and the <b>overscroll to remain in effect</b>.
 */
@Test
public void onTouchMoveAction_dragDownWhenUpOverscolled_continueOverscrollingDownwards() {

    // Arrange

    // In up & down drag tests we use equal ratios to avoid the effect's under-scroll handling
    final float touchDragRatioFwd = 3f;
    final float touchDragRatioBck = 3f;

    // Bring UUT to an upwards-overscroll state
    when(mViewAdapter.isInAbsoluteStart()).thenReturn(false);
    when(mViewAdapter.isInAbsoluteEnd()).thenReturn(true);

    VerticalOverScrollBounceEffectDecorator uut = getUUT(touchDragRatioFwd, touchDragRatioBck);
    MotionEvent eventMoveUp = createLongUpwardsMoveEvent();
    uut.onTouch(mView, eventMoveUp);
    reset(mView);

    float startTransY = (eventMoveUp.getY() - eventMoveUp.getHistoricalY(0)) / touchDragRatioFwd;
    when(mView.getTranslationY()).thenReturn(startTransY);

    // Create the down-drag event
    MotionEvent eventMoveDown = createShortDownwardsMoveEvent();

    // Act

    boolean ret = uut.onTouch(mView, eventMoveDown);

    // Assert

    float expectedTransY = startTransY + (eventMoveDown.getY() - eventMoveDown.getHistoricalY(0)) / touchDragRatioBck;
    verify(mView).setTranslationY(expectedTransY);
    verify(mView, never()).setTranslationX(anyFloat());
    assertTrue(ret);
    assertEquals(STATE_DRAG_END_SIDE, uut.getCurrentState());

    // State-change listener called only once?
    verify(mStateListener).onOverScrollStateChange(eq(uut), eq(STATE_IDLE), eq(STATE_DRAG_END_SIDE));
    verify(mStateListener).onOverScrollStateChange(eq(uut), anyInt(), anyInt());
    // Update-listener called exactly twice?
    verify(mUpdateListener).onOverScrollUpdate(eq(uut), eq(STATE_DRAG_END_SIDE), eq(startTransY));
    verify(mUpdateListener).onOverScrollUpdate(eq(uut), eq(STATE_DRAG_END_SIDE), eq(expectedTransY));
    verify(mUpdateListener, times(2)).onOverScrollUpdate(eq(uut), anyInt(), anyFloat());
}
 
Example 10
Source File: Actor.java    From Backboard with Apache License 2.0 4 votes vote down vote up
@Override
@SuppressLint("ClickableViewAccessibility")
public boolean onTouch(@NonNull final View v, @NonNull final MotionEvent event) {

	final boolean retVal;

	if (!mMotionListenerEnabled || mMotions.isEmpty()) {

		if (mOnTouchListener != null) {
			retVal = mOnTouchListener.onTouch(v, event);
		} else {
			retVal = false;
		}

		return retVal;
	}

	for (Motion motion : mMotions) {
		for (EventImitator imitator : motion.imitators) {
			imitator.imitate(v, event);
		}
	}

	if (mOnTouchListener != null) {
		retVal = mOnTouchListener.onTouch(v, event);
	} else {
		retVal = true;
	}

	if (mRequestDisallowTouchEvent) {
		// prevents parent from scrolling or otherwise stealing touch events
		v.getParent().requestDisallowInterceptTouchEvent(true);
	}

	if (v.isClickable()) {
		if (event.getEventTime() - event.getDownTime()
				> ViewConfiguration.getLongPressTimeout()) {
			v.setPressed(false);

			return true;
		}

		if (event.getHistorySize() > 0) {
			final float deltaX = event.getHistoricalX(event.getHistorySize() - 1) - event.getX();
			final float deltaY = event.getHistoricalY(event.getHistorySize() - 1) - event.getY();

			// if user has moved too far, it is no longer a click
			final boolean removeClickState = Math.pow(deltaX, 2) + Math.pow(deltaY, 2)
					> Math.pow(MAX_CLICK_DISTANCE, 2);

			v.setPressed(!removeClickState);

			return removeClickState;
		} else {
			return false;
		}
	}

	return retVal;
}
 
Example 11
Source File: LockPatternView.java    From xmpp with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when the device
    // is busy...
    final float radius = (mSquareWidth * mDiameterFactor * 0.5f);
    final int historySize = event.getHistorySize();
    mTmpInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        final float x = i < historySize ? event.getHistoricalX(i) : event.getX();
        final float y = i < historySize ? event.getHistoricalY(i) : event.getY();
        Cell hitCell = detectAndAddHit(x, y);
        final int patternSize = mPattern.size();
        if (hitCell != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // note current x and y for rubber banding of in progress patterns
        final float dx = Math.abs(x - mInProgressX);
        final float dy = Math.abs(y - mInProgressY);
        if (dx > DRAG_THRESHHOLD || dy > DRAG_THRESHHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Cell> pattern = mPattern;
            final Cell lastCell = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastCell.column);
            float lastCellCenterY = getCenterYForRow(lastCell.row);

            // Adjust for drawn segment from last cell to (x,y). Radius accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's previous cell
            if (hitCell != null) {
                final float width = mSquareWidth * 0.5f;
                final float height = mSquareHeight * 0.5f;
                final float hitCellCenterX = getCenterXForColumn(hitCell.column);
                final float hitCellCenterY = getCenterYForRow(hitCell.row);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous location
            mTmpInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTmpInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTmpInvalidateRect);
    }
}
 
Example 12
Source File: LockPatternView.java    From android-lockpattern with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when
    // the device
    // is busy...
    final float radius = mPathWidth;
    final int historySize = event.getHistorySize();
    mTmpInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        final float x = i < historySize ? event.getHistoricalX(i) : event
                .getX();
        final float y = i < historySize ? event.getHistoricalY(i) : event
                .getY();
        Cell hitCell = detectAndAddHit(x, y);
        final int patternSize = mPattern.size();
        if (hitCell != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // note current x and y for rubber banding of in progress patterns
        final float dx = Math.abs(x - mInProgressX);
        final float dy = Math.abs(y - mInProgressY);
        if (dx > DRAG_THRESHHOLD || dy > DRAG_THRESHHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Cell> pattern = mPattern;
            final Cell lastCell = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastCell.column);
            float lastCellCenterY = getCenterYForRow(lastCell.row);

            // Adjust for drawn segment from last cell to (x,y). Radius
            // accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's
            // previous cell
            if (hitCell != null) {
                final float width = mSquareWidth * 0.5f;
                final float height = mSquareHeight * 0.5f;
                final float hitCellCenterX = getCenterXForColumn(hitCell.column);
                final float hitCellCenterY = getCenterYForRow(hitCell.row);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous
            // location
            mTmpInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a
    // certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTmpInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTmpInvalidateRect);
    }
}
 
Example 13
Source File: LockPatternView.java    From GestureLock with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when the device
    // is busy...
    final float radius = (mSquareWidth * mDiameterFactor * 0.5f);
    final int historySize = event.getHistorySize();
    mTmpInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        final float x = i < historySize ? event.getHistoricalX(i) : event.getX();
        final float y = i < historySize ? event.getHistoricalY(i) : event.getY();
        Cell hitCell = detectAndAddHit(x, y);
        final int patternSize = mPattern.size();
        if (hitCell != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // note current x and y for rubber banding of in progress patterns
        final float dx = Math.abs(x - mInProgressX);
        final float dy = Math.abs(y - mInProgressY);
        if (dx > DRAG_THRESHHOLD || dy > DRAG_THRESHHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Cell> pattern = mPattern;
            final Cell lastCell = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastCell.column);
            float lastCellCenterY = getCenterYForRow(lastCell.row);

            // Adjust for drawn segment from last cell to (x,y). Radius accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's previous cell
            if (hitCell != null) {
                final float width = mSquareWidth * 0.5f;
                final float height = mSquareHeight * 0.5f;
                final float hitCellCenterX = getCenterXForColumn(hitCell.column);
                final float hitCellCenterY = getCenterYForRow(hitCell.row);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous location
            mTmpInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTmpInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTmpInvalidateRect);
    }
}
 
Example 14
Source File: MultiTouchController.java    From Androzic with GNU General Public License v3.0 4 votes vote down vote up
/** Process incoming touch events */
public boolean onTouchEvent(MotionEvent event) {
	try {
		int pointerCount = multiTouchSupported ? (Integer) m_getPointerCount.invoke(event) : 1;
		if (DEBUG)
			Log.i("MultiTouch", "Got here 1 - " + multiTouchSupported + " " + mMode + " " + handleSingleTouchEvents + " " + pointerCount);
		if (mMode == MODE_NOTHING && !handleSingleTouchEvents && pointerCount == 1)
			// Not handling initial single touch events, just pass them on
			return false;
		if (DEBUG)
			Log.i("MultiTouch", "Got here 2");

		// Handle history first (we sometimes get history with ACTION_MOVE events)
		int action = event.getAction();
		int histLen = event.getHistorySize() / pointerCount;
		for (int histIdx = 0; histIdx <= histLen; histIdx++) {
			// Read from history entries until histIdx == histLen, then read from current event
			boolean processingHist = histIdx < histLen;
			if (!multiTouchSupported || pointerCount == 1) {
				// Use single-pointer methods -- these are needed as a special case (for some weird reason) even if
				// multitouch is supported but there's only one touch point down currently -- event.getX(0) etc. throw
				// an exception if there's only one point down.
				if (DEBUG)
					Log.i("MultiTouch", "Got here 3");
				xVals[0] = processingHist ? event.getHistoricalX(histIdx) : event.getX();
				yVals[0] = processingHist ? event.getHistoricalY(histIdx) : event.getY();
				pressureVals[0] = processingHist ? event.getHistoricalPressure(histIdx) : event.getPressure();
			} else {
				// Read x, y and pressure of each pointer
				if (DEBUG)
					Log.i("MultiTouch", "Got here 4");
				int numPointers = Math.min(pointerCount, MAX_TOUCH_POINTS);
				if (DEBUG && pointerCount > MAX_TOUCH_POINTS)
					Log.i("MultiTouch", "Got more pointers than MAX_TOUCH_POINTS");
				for (int ptrIdx = 0; ptrIdx < numPointers; ptrIdx++) {
					int ptrId = (Integer) m_getPointerId.invoke(event, ptrIdx);
					pointerIds[ptrIdx] = ptrId;
					// N.B. if pointerCount == 1, then the following methods throw an array index out of range exception,
					// and the code above is therefore required not just for Android 1.5/1.6 but also for when there is
					// only one touch point on the screen -- pointlessly inconsistent :(
					xVals[ptrIdx] = (Float) (processingHist ? m_getHistoricalX.invoke(event, ptrIdx, histIdx) : m_getX.invoke(event, ptrIdx));
					yVals[ptrIdx] = (Float) (processingHist ? m_getHistoricalY.invoke(event, ptrIdx, histIdx) : m_getY.invoke(event, ptrIdx));
					pressureVals[ptrIdx] = (Float) (processingHist ? m_getHistoricalPressure.invoke(event, ptrIdx, histIdx) : m_getPressure
							.invoke(event, ptrIdx));
				}
			}
			// Decode event
			decodeTouchEvent(pointerCount, xVals, yVals, pressureVals, pointerIds, //
					/* action = */processingHist ? MotionEvent.ACTION_MOVE : action, //
					/* down = */processingHist ? true : action != MotionEvent.ACTION_UP //
							&& (action & ((1 << ACTION_POINTER_INDEX_SHIFT) - 1)) != ACTION_POINTER_UP //
							&& action != MotionEvent.ACTION_CANCEL, //
					processingHist ? event.getHistoricalEventTime(histIdx) : event.getEventTime());
		}

		return true;
	} catch (Exception e) {
		// In case any of the introspection stuff fails (it shouldn't)
		Log.e("MultiTouchController", "onTouchEvent() failed", e);
		return false;
	}
}
 
Example 15
Source File: SignatureView3Fast.java    From codeexamples-android with Eclipse Public License 1.0 4 votes vote down vote up
@Override
public boolean onTouchEvent(MotionEvent event) {
  float eventX = event.getX();
  float eventY = event.getY();

  switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
      path.moveTo(eventX, eventY);
      lastTouchX = eventX;
      lastTouchY = eventY;
      // There is no end point yet, so don't waste cycles invalidating.
      return true;

    case MotionEvent.ACTION_MOVE:
    case MotionEvent.ACTION_UP:
      // Start tracking the dirty region.
      resetDirtyRect(eventX, eventY);

      // When the hardware tracks events faster than they are delivered, the
      // event will contain a history of those skipped points.
      int historySize = event.getHistorySize();
      for (int i = 0; i < historySize; i++) {
        float historicalX = event.getHistoricalX(i);
        float historicalY = event.getHistoricalY(i);
        expandDirtyRect(historicalX, historicalY);
        path.lineTo(historicalX, historicalY);
      }

      // After replaying history, connect the line to the touch point.
      path.lineTo(eventX, eventY);
      break;

    default:
      return false;
  }

  // Include half the stroke width to avoid clipping.
  invalidate(
      (int) (dirtyRect.left - HALF_STROKE_WIDTH),
      (int) (dirtyRect.top - HALF_STROKE_WIDTH),
      (int) (dirtyRect.right + HALF_STROKE_WIDTH),
      (int) (dirtyRect.bottom + HALF_STROKE_WIDTH));
  
  lastTouchX = eventX;
  lastTouchY = eventY;

  return true;
}
 
Example 16
Source File: PatternLockView.java    From PatternLockView with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    float radius = mPathWidth;
    int historySize = event.getHistorySize();
    mTempInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        float x = i < historySize ? event.getHistoricalX(i) : event
                .getX();
        float y = i < historySize ? event.getHistoricalY(i) : event
                .getY();
        Dot hitDot = detectAndAddHit(x, y);
        int patternSize = mPattern.size();
        if (hitDot != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // Note current x and y for rubber banding of in progress patterns
        float dx = Math.abs(x - mInProgressX);
        float dy = Math.abs(y - mInProgressY);
        if (dx > DEFAULT_DRAG_THRESHOLD || dy > DEFAULT_DRAG_THRESHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Dot> pattern = mPattern;
            final Dot lastDot = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastDot.mColumn);
            float lastCellCenterY = getCenterYForRow(lastDot.mRow);

            // Adjust for drawn segment from last cell to (x,y). Radius
            // accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's
            // previous cell
            if (hitDot != null) {
                float width = mViewWidth * 0.5f;
                float height = mViewHeight * 0.5f;
                float hitCellCenterX = getCenterXForColumn(hitDot.mColumn);
                float hitCellCenterY = getCenterYForRow(hitDot.mRow);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous
            // location
            mTempInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a
    // certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTempInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTempInvalidateRect);
    }
}
 
Example 17
Source File: LockPatternView.java    From MHViewer with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when the device
    // is busy...
    final float radius = mPathWidth;
    final int historySize = event.getHistorySize();
    mTmpInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        final float x = i < historySize ? event.getHistoricalX(i) : event.getX();
        final float y = i < historySize ? event.getHistoricalY(i) : event.getY();
        Cell hitCell = detectAndAddHit(x, y);
        final int patternSize = mPattern.size();
        if (hitCell != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // note current x and y for rubber banding of in progress patterns
        final float dx = Math.abs(x - mInProgressX);
        final float dy = Math.abs(y - mInProgressY);
        if (dx > DRAG_THRESHHOLD || dy > DRAG_THRESHHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Cell> pattern = mPattern;
            final Cell lastCell = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastCell.column);
            float lastCellCenterY = getCenterYForRow(lastCell.row);

            // Adjust for drawn segment from last cell to (x,y). Radius accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's previous cell
            if (hitCell != null) {
                final float width = mSquareWidth * 0.5f;
                final float height = mSquareHeight * 0.5f;
                final float hitCellCenterX = getCenterXForColumn(hitCell.column);
                final float hitCellCenterY = getCenterYForRow(hitCell.row);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous location
            mTmpInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTmpInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTmpInvalidateRect);
    }
}
 
Example 18
Source File: LockPatternView.java    From android-lockpattern with Apache License 2.0 4 votes vote down vote up
private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when
    // the device
    // is busy...
    final float radius = mPathWidth;
    final int historySize = event.getHistorySize();
    mTmpInvalidateRect.setEmpty();
    boolean invalidateNow = false;
    for (int i = 0; i < historySize + 1; i++) {
        final float x = i < historySize ? event.getHistoricalX(i) : event
                .getX();
        final float y = i < historySize ? event.getHistoricalY(i) : event
                .getY();
        Cell hitCell = detectAndAddHit(x, y);
        final int patternSize = mPattern.size();
        if (hitCell != null && patternSize == 1) {
            mPatternInProgress = true;
            notifyPatternStarted();
        }
        // note current x and y for rubber banding of in progress patterns
        final float dx = Math.abs(x - mInProgressX);
        final float dy = Math.abs(y - mInProgressY);
        if (dx > DRAG_THRESHHOLD || dy > DRAG_THRESHHOLD) {
            invalidateNow = true;
        }

        if (mPatternInProgress && patternSize > 0) {
            final ArrayList<Cell> pattern = mPattern;
            final Cell lastCell = pattern.get(patternSize - 1);
            float lastCellCenterX = getCenterXForColumn(lastCell.column);
            float lastCellCenterY = getCenterYForRow(lastCell.row);

            // Adjust for drawn segment from last cell to (x,y). Radius
            // accounts for line width.
            float left = Math.min(lastCellCenterX, x) - radius;
            float right = Math.max(lastCellCenterX, x) + radius;
            float top = Math.min(lastCellCenterY, y) - radius;
            float bottom = Math.max(lastCellCenterY, y) + radius;

            // Invalidate between the pattern's new cell and the pattern's
            // previous cell
            if (hitCell != null) {
                final float width = mSquareWidth * 0.5f;
                final float height = mSquareHeight * 0.5f;
                final float hitCellCenterX = getCenterXForColumn(hitCell.column);
                final float hitCellCenterY = getCenterYForRow(hitCell.row);

                left = Math.min(hitCellCenterX - width, left);
                right = Math.max(hitCellCenterX + width, right);
                top = Math.min(hitCellCenterY - height, top);
                bottom = Math.max(hitCellCenterY + height, bottom);
            }

            // Invalidate between the pattern's last cell and the previous
            // location
            mTmpInvalidateRect.union(Math.round(left), Math.round(top),
                    Math.round(right), Math.round(bottom));
        }
    }
    mInProgressX = event.getX();
    mInProgressY = event.getY();

    // To save updates, we only invalidate if the user moved beyond a
    // certain amount.
    if (invalidateNow) {
        mInvalidate.union(mTmpInvalidateRect);
        invalidate(mInvalidate);
        mInvalidate.set(mTmpInvalidateRect);
    }
}
 
Example 19
Source File: VerticalOverScrollBounceEffectDecoratorTest.java    From overscroll-decor with BSD 2-Clause "Simplified" License 3 votes vote down vote up
@Test
public void onTouchMoveAction_dragUpInBottomEnd_overscrollUpwards() {

    // Arrange

    MotionEvent event = createShortUpwardsMoveEvent();

    when(mViewAdapter.isInAbsoluteStart()).thenReturn(false);
    when(mViewAdapter.isInAbsoluteEnd()).thenReturn(true);

    VerticalOverScrollBounceEffectDecorator uut = getUUT();

    // Act

    boolean ret = uut.onTouch(mView, event);

    // Assert

    float expectedTransY = (event.getY() - event.getHistoricalY(0)) / DEFAULT_TOUCH_DRAG_MOVE_RATIO_FWD;
    verify(mView).setTranslationY(expectedTransY);
    verify(mView, never()).setTranslationX(anyFloat());
    assertTrue(ret);
    assertEquals(STATE_DRAG_END_SIDE, uut.getCurrentState());

    verify(mStateListener).onOverScrollStateChange(eq(uut), eq(STATE_IDLE), eq(STATE_DRAG_END_SIDE));
    verify(mUpdateListener).onOverScrollUpdate(eq(uut), eq(STATE_DRAG_END_SIDE), eq(expectedTransY));
}
 
Example 20
Source File: VerticalOverScrollBounceEffectDecoratorTest.java    From elasticity with BSD 2-Clause "Simplified" License 3 votes vote down vote up
@Test
public void onTouchMoveAction_dragUpInBottomEnd_overscrollUpwards() throws Exception {

    // Arrange

    MotionEvent event = createShortUpwardsMoveEvent();

    when(mViewAdapter.isInAbsoluteStart()).thenReturn(false);
    when(mViewAdapter.isInAbsoluteEnd()).thenReturn(true);

    VerticalElasticityBounceEffect uut = getUUT();

    // Act

    boolean ret = uut.onTouch(mView, event);

    // Assert

    float expectedTransY = (event.getY() - event.getHistoricalY(0)) / DEFAULT_TOUCH_DRAG_MOVE_RATIO_FWD;
    verify(mView).setTranslationY(expectedTransY);
    verify(mView, never()).setTranslationX(anyFloat());
    assertTrue(ret);
    assertEquals(STATE_DRAG_END_SIDE, uut.getCurrentState());

    verify(mStateListener).onOverScrollStateChange(eq(uut), eq(STATE_IDLE), eq(STATE_DRAG_END_SIDE));
    verify(mUpdateListener).onOverScrollUpdate(eq(uut), eq(STATE_DRAG_END_SIDE), eq(expectedTransY));
}