示例#1
0
  /* (non-Javadoc)
   * @see com.google.android.maps.MapView#onTouchEvent(android.view.MotionEvent)
   */
  @Override
  public boolean onTouchEvent(MotionEvent ev) {

    int action = ev.getAction();
    int t;

    switch (action) {
      case MotionEvent.ACTION_DOWN:
        clicked = true;
        break;

      case MotionEvent.ACTION_MOVE:
        clicked = false;
        t = ev.getHistorySize();
        geoPoint = getProjection().fromPixels((int) ev.getX(t), (int) ev.getY(t));
        break;

      case MotionEvent.ACTION_UP:
        if (clicked) {
          t = ev.getHistorySize();
          geoPoint = getProjection().fromPixels((int) ev.getX(t), (int) ev.getY(t));
          getController().animateTo(geoPoint);
          invalidate();
          // getPositionBtn.setEnabled(true);
        }
        break;
    }

    // TODO Auto-generated method stub
    return super.onTouchEvent(ev);
  }
  private void track(MotionEvent event) {
    mX.saveTouchPos();
    mY.saveTouchPos();

    for (int i = 0; i < event.getHistorySize(); i++) {
      track(
          event.getHistoricalX(0, i), event.getHistoricalY(0, i), event.getHistoricalEventTime(i));
    }
    track(event.getX(0), event.getY(0), event.getEventTime());

    if (stopped()) {
      if (mState == PanZoomState.PANNING) {
        setState(PanZoomState.PANNING_HOLD);
      } else if (mState == PanZoomState.PANNING_LOCKED) {
        setState(PanZoomState.PANNING_HOLD_LOCKED);
      } else {
        // should never happen, but handle anyway for robustness
        Log.e(LOGTAG, "Impossible case " + mState + " when stopped in track");
        setState(PanZoomState.PANNING_HOLD_LOCKED);
      }
    }

    mX.startPan();
    mY.startPan();
    updatePosition();
  }
示例#3
0
 public boolean onTouch(View view, MotionEvent event) {
   float x = event.getX();
   float y = event.getY();
   switch (event.getAction()) {
     case MotionEvent.ACTION_DOWN:
       path.moveTo(x, y);
       return true;
     case MotionEvent.ACTION_UP:
     case MotionEvent.ACTION_MOVE:
       l = x;
       r = x;
       t = y;
       b = y;
       for (int i = 0; i < event.getHistorySize(); i++) {
         float newX = event.getHistoricalX(i);
         float newY = event.getHistoricalY(i);
         path.lineTo(newX, newY);
         l = newX < l ? newX : l;
         t = newY < t ? newY : t;
         r = newX > r ? newX : r;
         b = newY > b ? newY : b;
       }
       rect.set(l, t, r, b);
       Log.d("TAG", rect.toShortString());
       invalidate(
           (int) rect.left - 5, (int) rect.top - 5, (int) rect.right + 5, (int) rect.bottom + 5);
       break;
     default:
   }
   return super.onTouchEvent(event);
 }
  @Override
  public boolean onTouchEvent(MotionEvent event) {

    float mCurX;
    float mCurY;

    // API level 9 and above supports "Major" property on event which
    // gives
    // the size of the touch area at the point of contact
    // so for now we just hard code
    float TOUCH_AREA_SIZE = penWidth;

    int action = event.getAction();
    if (action != MotionEvent.ACTION_UP && action != MotionEvent.ACTION_CANCEL) {
      int N = event.getHistorySize();
      int P = event.getPointerCount();
      for (int i = 0; i < N; i++) {
        for (int j = 0; j < P; j++) {
          mCurX = event.getHistoricalX(j, i);
          mCurY = event.getHistoricalY(j, i);
          drawPoint(mCurX, mCurY, event.getHistoricalPressure(j, i), TOUCH_AREA_SIZE);
        }
      }
      for (int j = 0; j < P; j++) {
        mCurX = event.getX(j);
        mCurY = event.getY(j);
        drawPoint(mCurX, mCurY, event.getPressure(j), TOUCH_AREA_SIZE);
      }
    }
    unsaved = true;
    return true;
  }
  // @!ANDROID-4
  private static int getAction(int index, MotionEvent event) {
    int action = event.getAction();
    if (action == MotionEvent.ACTION_MOVE) {
      int hsz = event.getHistorySize();
      if (hsz > 0) {
        if (Math.abs(event.getX(index) - event.getHistoricalX(index, hsz - 1)) > 1
            || Math.abs(event.getY(index) - event.getHistoricalY(index, hsz - 1)) > 1) return 1;
        else return 2;
      }
      return 1;
    }

    switch (index) {
      case 0:
        if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_POINTER_1_DOWN)
          return 0;
        if (action == MotionEvent.ACTION_UP || action == MotionEvent.ACTION_POINTER_1_UP) return 3;
        break;

      case 1:
        if (action == MotionEvent.ACTION_POINTER_2_DOWN
            || action == MotionEvent.ACTION_POINTER_DOWN) return 0;
        if (action == MotionEvent.ACTION_POINTER_2_UP || action == MotionEvent.ACTION_POINTER_UP)
          return 3;
        break;

      case 2:
        if (action == MotionEvent.ACTION_POINTER_3_DOWN
            || action == MotionEvent.ACTION_POINTER_DOWN) return 0;
        if (action == MotionEvent.ACTION_POINTER_3_UP || action == MotionEvent.ACTION_POINTER_UP)
          return 3;
        break;
    }
    return 2;
  }
示例#6
0
 @Override
 public boolean onTouchEvent(final ViewGroup view, final MotionEvent event) {
   if (mIsVerticalScrolling && !mController.isScrolling() || mShouldDisableScroll) return true;
   switch (event.getAction()) {
     case MotionEvent.ACTION_DOWN:
       {
         mTempDeltaX = 0;
         mTotalMoveX = 0;
         mTotalMoveY = 0;
         mActualMoveX = 0;
         mIsVerticalScrolling = false;
         mController.reset();
         break;
       }
     case MotionEvent.ACTION_MOVE:
       {
         final int hist_size = event.getHistorySize();
         if (hist_size == 0) {
           break;
         }
         final float distanceX = mTempDeltaX = event.getX() - event.getHistoricalX(0);
         mActualMoveX = mTotalMoveX += mTempDeltaX;
         mController.scrollBy((int) -distanceX);
         break;
       }
   }
   return true;
 }
 // The following methods are taken from the controller sample on the
 // Android Developer web site:
 // https://developer.android.com/training/game-controllers/controller-input.html
 private void dispatchMotionEvent(int id, MotionEvent event) {
   if (id != -1) {
     final int historySize = event.getHistorySize();
     for (int i = 0; i < historySize; i++) {
       processMouseInput(id, event, i);
     }
     processMouseInput(id, event, -1);
   }
 }
示例#8
0
  /**
   * Extracts the touch point data from a MotionEvent, converts each point into a marshallable
   * object and passes the set of points to the JNI layer to be transmitted to the remote host.
   *
   * @param event The event to send to the remote host for injection. NOTE: This object must be
   *     updated to represent the remote machine's coordinate system before calling this function.
   */
  public void sendTouchEvent(MotionEvent event) {
    int action = event.getActionMasked();
    TouchEventData.EventType touchEventType = TouchEventData.EventType.fromMaskedAction(action);
    List<TouchEventData> touchEventList = new ArrayList<TouchEventData>();

    if (action == MotionEvent.ACTION_MOVE) {
      // In order to process all of the events associated with an ACTION_MOVE event, we need
      // to walk the list of historical events in order and add each event to our list, then
      // retrieve the current move event data.
      int pointerCount = event.getPointerCount();
      int historySize = event.getHistorySize();
      for (int h = 0; h < historySize; ++h) {
        for (int p = 0; p < pointerCount; ++p) {
          touchEventList.add(
              new TouchEventData(
                  event.getPointerId(p),
                  event.getHistoricalX(p, h),
                  event.getHistoricalY(p, h),
                  event.getHistoricalSize(p, h),
                  event.getHistoricalSize(p, h),
                  event.getHistoricalOrientation(p, h),
                  event.getHistoricalPressure(p, h)));
        }
      }

      for (int p = 0; p < pointerCount; p++) {
        touchEventList.add(
            new TouchEventData(
                event.getPointerId(p),
                event.getX(p),
                event.getY(p),
                event.getSize(p),
                event.getSize(p),
                event.getOrientation(p),
                event.getPressure(p)));
      }
    } else {
      // For all other events, we only want to grab the current/active pointer.  The event
      // contains a list of every active pointer but passing all of of these to the host can
      // cause confusion on the remote OS side and result in broken touch gestures.
      int activePointerIndex = event.getActionIndex();
      touchEventList.add(
          new TouchEventData(
              event.getPointerId(activePointerIndex),
              event.getX(activePointerIndex),
              event.getY(activePointerIndex),
              event.getSize(activePointerIndex),
              event.getSize(activePointerIndex),
              event.getOrientation(activePointerIndex),
              event.getPressure(activePointerIndex)));
    }

    if (!touchEventList.isEmpty()) {
      mInjector.sendTouchEvent(touchEventType, touchEventList.toArray(new TouchEventData[0]));
    }
  }
示例#9
0
  @Override
  public boolean onTouchEvent(MotionEvent event) {

    float mCurX;
    float mCurY;

    ArrayList<Point> eraserpoints = new ArrayList<Point>();

    int action = event.getAction();
    if (action != MotionEvent.ACTION_UP && action != MotionEvent.ACTION_CANCEL) {
      // Log.d(TAG, "PEN UP");
    }
    if (action == MotionEvent.ACTION_DOWN) {
      // start recording points
      mCurrentPath = new Path();
      mCurrentPath.moveTo(event.getX(), event.getY());
    }
    if (action == MotionEvent.ACTION_MOVE) {
      // start recording points
      int N = event.getHistorySize();
      int P = event.getPointerCount();
      for (int i = 0; i < N; i++) {
        for (int j = 0; j < P; j++) {
          mCurX = event.getHistoricalX(j, i);
          mCurY = event.getHistoricalY(j, i);

          if (mEraserMode == true) {
            if (eraserpoints != null) {
              eraserpoints.add(new Point(Math.round(mCurX), Math.round(mCurY)));
            } else {
              Log.e(TAG, "no eraserpoints array defined, skipping adding erase point");
            }
          } else {
            if (mCurrentPath != null) {
              mCurrentPath.lineTo(mCurX, mCurY);
            } else {
              Log.e(TAG, "NO PATH TO ADD POINT" + mCurX + "," + mCurY);
            }
          }
        }
      }

      if (mCurrentPath != null) {
        mCurrentPath.lineTo(event.getX(), event.getY());
        mCanvas.drawPath(mCurrentPath, (mEraserMode == true ? mEraserPainter : mPenPainter));
        invalidate();
      } else {
        Log.e(TAG, "Missing CurrentPath object");
      }
    }
    mUnsaved = true;
    return true;
  }
示例#10
0
 public void c(MotionEvent paramMotionEvent) {
   int j = paramMotionEvent.getHistorySize();
   int i = 0;
   while (i < j) {
     a(
         paramMotionEvent.getActionMasked(),
         paramMotionEvent.getHistoricalX(0, i),
         paramMotionEvent.getHistoricalY(0, i));
     i += 1;
   }
   a(paramMotionEvent.getActionMasked(), paramMotionEvent.getX(), paramMotionEvent.getY());
 }
示例#11
0
 @Override
 public boolean onTouch(final View view, final MotionEvent event) {
   switch (event.getAction()) {
     case MotionEvent.ACTION_DOWN:
       {
         mTempDeltaX = 0;
         mTotalMoveX = 0;
         mIsScrolling = false;
         // final View layout = mParent.getRightPaneLayout();
         mShouldDisableScroll =
             !(mContext instanceof DualPaneActivity
                 && ((DualPaneActivity) mContext).isRightPaneUsed());
         if (!mShouldDisableScroll) {
           mController.reset();
         } else return false;
         break;
       }
     case MotionEvent.ACTION_MOVE:
       {
         if (mShouldDisableScroll) return false;
         final int hist_size = event.getHistorySize();
         if (hist_size == 0) {
           break;
         }
         final float distanceX = mTempDeltaX = event.getX() - event.getHistoricalX(0);
         mTotalMoveX += mTempDeltaX;
         if (Math.abs(mTotalMoveX) >= mScaledTouchSlop) {
           mIsScrolling = true;
         }
         if (mIsScrolling) {
           mController.scrollBy((int) -distanceX);
         }
         break;
       }
     case MotionEvent.ACTION_UP:
       {
         if (mIsScrolling) {
           mController.release(-mTempDeltaX, -mTotalMoveX);
         }
         mTempDeltaX = 0;
         mTotalMoveX = 0;
         mIsScrolling = false;
         if (mShouldDisableScroll) {
           mShouldDisableScroll = false;
           return false;
         }
         mShouldDisableScroll = false;
         break;
       }
   }
   return true;
 }
 protected MotionEvent createLongLeftMoveEvent() {
   MotionEvent event = mock(MotionEvent.class);
   when(event.getAction()).thenReturn(MotionEvent.ACTION_MOVE);
   when(event.getX()).thenReturn(50f);
   when(event.getY()).thenReturn(150f);
   when(event.getX(0)).thenReturn(50f);
   when(event.getY(0)).thenReturn(150f);
   when(event.getHistorySize()).thenReturn(1);
   when(event.getHistoricalX(eq(0))).thenReturn(100f);
   when(event.getHistoricalY(eq(0))).thenReturn(200f);
   when(event.getHistoricalX(eq(0), eq(0))).thenReturn(100f);
   when(event.getHistoricalY(eq(0), eq(0))).thenReturn(200f);
   return event;
 }
  @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:
        Log.d("default", "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;
  }
 /**
  * Add a user's movement to the tracker. You should call this for the initial {@link
  * MotionEvent#ACTION_DOWN}, the following {@link MotionEvent#ACTION_MOVE} events that you
  * receive, and the final {@link MotionEvent#ACTION_UP}. You can, however, call this for whichever
  * events you desire.
  *
  * @param ev The MotionEvent you received and would like to track.
  */
 public void addMovement(MotionEvent ev) {
   final int mN = ev.getHistorySize();
   if (++mLastTouch >= NUM_PAST) {
     mLastTouch = 0;
   }
   for (int i = 0; i < mN; ++i) {
     mPastX[mLastTouch] = ev.getHistoricalX(i);
     mPastY[mLastTouch] = ev.getHistoricalY(i);
     mPastTime[mLastTouch] = ev.getHistoricalEventTime(i);
     if (++mLastTouch >= NUM_PAST) {
       mLastTouch = 0;
     }
   }
   mPastX[mLastTouch] = ev.getX();
   mPastY[mLastTouch] = ev.getY();
   mPastTime[mLastTouch] = ev.getEventTime();
 }
  @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;
        return true;

      case MotionEvent.ACTION_MOVE:

      case MotionEvent.ACTION_UP:
        resetDirtyRect(eventX, eventY);
        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);
        }
        path.lineTo(eventX, eventY);
        break;

      default:
        return false;
    }

    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;
  }
示例#16
0
 @Override
 public boolean onInterceptTouchEvent(final ViewGroup view, final MotionEvent event) {
   mShouldDisableScroll =
       !(isTouchEventHandled(view, event)
           || mContext instanceof DualPaneActivity
               && ((DualPaneActivity) mContext).isRightPaneUsed());
   switch (event.getAction()) {
     case MotionEvent.ACTION_DOWN:
       {
         mFirstDownHandled = !mShouldDisableScroll;
         mTempDeltaX = 0;
         mTotalMoveX = 0;
         mTotalMoveY = 0;
         mActualMoveX = 0;
         mIsVerticalScrolling = false;
         if (mFirstDownHandled) {
           mParent.animateOpen();
         }
         break;
       }
     case MotionEvent.ACTION_MOVE:
       {
         final int hist_size = event.getHistorySize();
         if (hist_size == 0) {
           break;
         }
         mTempDeltaX = event.getX() - event.getHistoricalX(0);
         mTotalMoveX += mTempDeltaX;
         final float deltaY = event.getY() - event.getHistoricalY(0);
         mTotalMoveY += deltaY;
         if (Math.abs(mTempDeltaX) > Math.abs(deltaY)
             && !mIsVerticalScrolling
             && Math.abs(mTotalMoveX) >= mScaledTouchSlop) return true;
         if (Math.abs(mTempDeltaX) < Math.abs(deltaY)
             && Math.abs(mTotalMoveY) >= mScaledTouchSlop) {
           mIsVerticalScrolling = true;
           return false;
         }
         break;
       }
   }
   return false;
 }
示例#17
0
 /**
  * adjust header padding according to motion event
  *
  * @param ev
  */
 private void adjustHeaderPadding(MotionEvent ev) {
   // adjust header padding according to motion event history
   int pointerCount = ev.getHistorySize();
   if (isVerticalFadingEdgeEnabled()) {
     setVerticalScrollBarEnabled(false);
   }
   for (int i = 0; i < pointerCount; i++) {
     if (currentHeaderStatus == HEADER_STATUS_DROP_DOWN_TO_LOAD
         || currentHeaderStatus == HEADER_STATUS_RELEASE_TO_LOAD) {
       headerLayout.setPadding(
           headerLayout.getPaddingLeft(),
           (int)
               (((ev.getHistoricalY(i) - actionDownPointY) - headerOriginalHeight)
                   / headerPaddingTopRate),
           headerLayout.getPaddingRight(),
           headerLayout.getPaddingBottom());
     }
   }
 }
示例#18
0
  @Override
  public boolean onTouchEvent(MotionEvent event) {
    //// System.out.println("flipStarted" + flipStarted);
    if (flipStarted) {
      return false;
    }
    //        if (header.isSourceSelectMode()) {
    //            header.onTouchEvent(event);
    //        }
    if (enlargedMode) {
      current.onTouchEvent(event);
    }

    switch (event.getAction()) {
      case MotionEvent.ACTION_MOVE:
        if (event.getHistorySize() > 0 && !flipStarted) {
          if (GestureUtil.flipRight(event)) {
            lastFlipDirection = ACTION_HORIZONTAL;
            flipPage(false);
          } else if (GestureUtil.flipUp(event)) {
            lastFlipDirection = ACTION_VERTICAL;
            flipPage(false);
          } else if (GestureUtil.flipLeft(event)) {
            lastFlipDirection = ACTION_HORIZONTAL;
            flipPage(true);
          } else if (GestureUtil.flipDown(event)) {
            lastFlipDirection = ACTION_VERTICAL;
            flipPage(true);
          }

        } else {
          //                    if (header.isSourceSelectMode())
          header.onTouchEvent(event);
          //                    pageIndexView.onTouchEvent(event);
        }
        break;
      default:
        break;
    }

    return true;
  }
    /**
     * Process trackball events. Used mainly for fine-tuned color adjustment, or alternatively to
     * switch between slider controls.
     */
    @Override
    public boolean dispatchTrackballEvent(MotionEvent event) {
      float x = event.getX();
      float y = event.getY();

      // A longer event history implies faster trackball movement.
      // Use it to infer a larger jump and therefore faster palette/slider adjustment.
      int jump = event.getHistorySize() + 1;

      switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:
          {
          }
          break;
        case MotionEvent.ACTION_MOVE:
          {
            // NEW_METHOD_WORK_NEEDED_HERE
            // To add a new method, replicate and extend the appropriate entry in this list,
            // depending on whether you use 1D or 2D controllers
            switch (mMethod) {
              case METHOD_HS_V_PALETTE:
                if (mFocusedControl == 0) {
                  changeHSPalette(x, y, jump);
                } else if (mFocusedControl == 1) {
                  if (y < 0) changeSlider(mFocusedControl, true, jump);
                  else if (y > 0) changeSlider(mFocusedControl, false, jump);
                }
                break;
            }
          }
          break;
        case MotionEvent.ACTION_UP:
          {
          }
          break;
      }

      return true;
    }
  private void applyHeaderPadding(MotionEvent ev) {
    // getHistorySize has been available since API 1
    int pointerCount = ev.getHistorySize();

    for (int p = 0; p < pointerCount; p++) {
      if (mRefreshState == RELEASE_TO_REFRESH) {
        if (isVerticalFadingEdgeEnabled()) {
          setVerticalScrollBarEnabled(false);
        }

        int historicalY = (int) ev.getHistoricalY(p);

        // Calculate the padding to apply, we divide by 1.7 to
        // simulate a more resistant effect during pull.
        int topPadding = (int) (((historicalY - mLastMotionY) - mRefreshViewHeight) / 1.7);

        mRefreshView.setPadding(
            mRefreshView.getPaddingLeft(),
            topPadding,
            mRefreshView.getPaddingRight(),
            mRefreshView.getPaddingBottom());
      }
    }
  }
 private int detectSwipe(MotionEvent move) {
   final int historySize = move.getHistorySize();
   final int pointerCount = move.getPointerCount();
   for (int p = 0; p < pointerCount; p++) {
     final int pointerId = move.getPointerId(p);
     final int i = findIndex(pointerId);
     if (i != UNTRACKED_POINTER) {
       for (int h = 0; h < historySize; h++) {
         final long time = move.getHistoricalEventTime(h);
         final float x = move.getHistoricalX(p, h);
         final float y = move.getHistoricalY(p, h);
         final int swipe = detectSwipe(i, time, x, y);
         if (swipe != SWIPE_NONE) {
           return swipe;
         }
       }
       final int swipe = detectSwipe(i, move.getEventTime(), move.getX(p), move.getY(p));
       if (swipe != SWIPE_NONE) {
         return swipe;
       }
     }
   }
   return SWIPE_NONE;
 }
示例#22
0
  private void handleActionMove(MotionEvent event) {
    // Handle all recent motion events so we don't skip any cells even when the device
    // is busy...
    final int historySize = event.getHistorySize();
    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();
      final int patternSizePreHitDetect = mPattern.size();
      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 + dy > mSquareWidth * 0.01f) {
        float oldX = mInProgressX;
        float oldY = mInProgressY;

        mInProgressX = x;
        mInProgressY = y;

        if (mPatternInProgress && patternSize > 0) {
          final ArrayList<Cell> pattern = mPattern;
          final float radius = mSquareWidth * mDiameterFactor * 0.5f;

          final Cell lastCell = pattern.get(patternSize - 1);

          float startX = getCenterXForColumn(lastCell.column);
          float startY = getCenterYForRow(lastCell.row);

          float left;
          float top;
          float right;
          float bottom;

          final Rect invalidateRect = mInvalidate;

          if (startX < x) {
            left = startX;
            right = x;
          } else {
            left = x;
            right = startX;
          }

          if (startY < y) {
            top = startY;
            bottom = y;
          } else {
            top = y;
            bottom = startY;
          }

          // Invalidate between the pattern's last cell and the current location
          invalidateRect.set(
              (int) (left - radius),
              (int) (top - radius),
              (int) (right + radius),
              (int) (bottom + radius));

          if (startX < oldX) {
            left = startX;
            right = oldX;
          } else {
            left = oldX;
            right = startX;
          }

          if (startY < oldY) {
            top = startY;
            bottom = oldY;
          } else {
            top = oldY;
            bottom = startY;
          }

          // Invalidate between the pattern's last cell and the previous location
          invalidateRect.union(
              (int) (left - radius),
              (int) (top - radius),
              (int) (right + radius),
              (int) (bottom + radius));

          // Invalidate between the pattern's new cell and the pattern's previous cell
          if (hitCell != null) {
            startX = getCenterXForColumn(hitCell.column);
            startY = getCenterYForRow(hitCell.row);

            if (patternSize >= 2) {
              // (re-using hitcell for old cell)
              hitCell = pattern.get(patternSize - 1 - (patternSize - patternSizePreHitDetect));
              oldX = getCenterXForColumn(hitCell.column);
              oldY = getCenterYForRow(hitCell.row);

              if (startX < oldX) {
                left = startX;
                right = oldX;
              } else {
                left = oldX;
                right = startX;
              }

              if (startY < oldY) {
                top = startY;
                bottom = oldY;
              } else {
                top = oldY;
                bottom = startY;
              }
            } else {
              left = right = startX;
              top = bottom = startY;
            }

            final float widthOffset = mSquareWidth / 2f;
            final float heightOffset = mSquareHeight / 2f;

            invalidateRect.set(
                (int) (left - widthOffset),
                (int) (top - heightOffset),
                (int) (right + widthOffset),
                (int) (bottom + heightOffset));
          }

          invalidate(invalidateRect);
        } else {
          invalidate();
        }
      }
    }
  }
示例#23
0
  private void handleMove(MotionEvent event) {
    int activeTarget = -1;
    final int historySize = event.getHistorySize();
    ArrayList<TargetDrawable> targets = mTargetDrawables;
    int ntargets = targets.size();
    float x = 0.0f;
    float y = 0.0f;
    int actionIndex = event.findPointerIndex(mPointerId);

    if (actionIndex == -1) {
      return; // no data for this pointer
    }

    for (int k = 0; k < historySize + 1; k++) {
      float eventX =
          k < historySize ? event.getHistoricalX(actionIndex, k) : event.getX(actionIndex);
      float eventY =
          k < historySize ? event.getHistoricalY(actionIndex, k) : event.getY(actionIndex);
      // tx and ty are relative to wave center
      float tx = eventX - mWaveCenterX;
      float ty = eventY - mWaveCenterY;
      float touchRadius = (float) Math.sqrt(dist2(tx, ty));
      final float scale = touchRadius > mOuterRadius ? mOuterRadius / touchRadius : 1.0f;
      float limitX = tx * scale;
      float limitY = ty * scale;
      double angleRad = Math.atan2(-ty, tx);

      if (!mDragging) {
        trySwitchToFirstTouchState(eventX, eventY);
      }

      if (mDragging) {
        // For multiple targets, snap to the one that matches
        final float snapRadius = mRingScaleFactor * mOuterRadius - mSnapMargin;
        final float snapDistance2 = snapRadius * snapRadius;
        // Find first target in range
        for (int i = 0; i < ntargets; i++) {
          TargetDrawable target = targets.get(i);

          double targetMinRad = (i - 0.5) * 2 * Math.PI / ntargets;
          double targetMaxRad = (i + 0.5) * 2 * Math.PI / ntargets;
          if (target.isEnabled()) {
            boolean angleMatches =
                (angleRad > targetMinRad && angleRad <= targetMaxRad)
                    || (angleRad + 2 * Math.PI > targetMinRad
                        && angleRad + 2 * Math.PI <= targetMaxRad);
            if (angleMatches && (dist2(tx, ty) > snapDistance2)) {
              activeTarget = i;
            }
          }
        }
      }
      x = limitX;
      y = limitY;
    }

    if (!mDragging) {
      return;
    }

    if (activeTarget != -1) {
      switchToState(STATE_SNAP, x, y);
      updateGlowPosition(x, y);
    } else {
      switchToState(STATE_TRACKING, x, y);
      updateGlowPosition(x, y);
    }

    if (mActiveTarget != activeTarget) {
      // Defocus the old target
      if (mActiveTarget != -1) {
        TargetDrawable target = targets.get(mActiveTarget);
        target.setState(TargetDrawable.STATE_INACTIVE);
      }
      // Focus the new target
      if (activeTarget != -1) {
        TargetDrawable target = targets.get(activeTarget);
        target.setState(TargetDrawable.STATE_FOCUSED);
        final AccessibilityManager accessibilityManager =
            (AccessibilityManager) getContext().getSystemService(Context.ACCESSIBILITY_SERVICE);
        if (accessibilityManager.isEnabled()) {
          String targetContentDescription = getTargetDescription(activeTarget);
          announceForAccessibility(targetContentDescription);
        }
      }
    }
    mActiveTarget = activeTarget;
  }
示例#24
0
  @Override
  public boolean onTouchEvent(MotionEvent event) {
    int action = event.getAction();
    switch (action) {
      case MotionEvent.ACTION_DOWN:
        downX = event.getX();
        downY = event.getY();
        if (mPropagateClicks) propagatePressed(true);
        break;

      case MotionEvent.ACTION_MOVE:
        try {
          if (mPropagateClicks) {
            float xDeltaTotal = event.getX() - downX;
            float yDeltaTotal = event.getY() - downY;
            if (Math.abs(xDeltaTotal) >= CLICK_SENSITIVITY
                || Math.abs(yDeltaTotal) >= CLICK_SENSITIVITY) {
              propagatePressed(false);
            }
          }

          float xDelta = event.getX() - downX;
          float yDelta = event.getY() - downY;
          if (event.getHistorySize() > 0) {
            xDelta = event.getX() - event.getHistoricalX(0);
            yDelta = event.getY() - event.getHistoricalY(0);
          }

          if (Math.abs(xDelta) > Math.abs(yDelta)) {
            if (xDelta > 0 && getCurrentItem() == 0 && mPositionOffset == 0) {
              return false;
            } else if (xDelta < 0 && mPositionOffset == 0) {
              if (getAdapter() != null) {
                int current = getCurrentItem();
                int count = getAdapter().getCount();
                if (current >= (count - 1)) {
                  return false;
                }
              }
            }
            NestedViewPager.this.getParent().requestDisallowInterceptTouchEvent(true);
          }
        } catch (Exception e) {
          // nothing
        }
        break;

      case MotionEvent.ACTION_UP:
        if (mPropagateClicks) {
          propagatePressed(false);

          float xDelta = event.getX() - downX;
          float yDelta = event.getY() - downY;
          if (Math.abs(xDelta) < CLICK_SENSITIVITY && Math.abs(yDelta) < CLICK_SENSITIVITY) {
            propagateClicked();
          }
        }
        break;
    }
    return super.onTouchEvent(event);
  }