2016-08-15 6 views
0

Я пишу приложение, которое отображает карту. Пользователь может масштабировать и панорамировать. Карта поворачивается в соответствии с величиной магнитометра (карта вращается в противоположном направлении вращения устройства).Android. OpenGl ES. panning/scrolling

Для масштабирования я использую ScaleGestureDetector и передающий масштабный коэффициент в Matrix.scaleM.

Для панорамирования Я использую этот код:

сторона GlSurfaceView:

private void handlePanAndZoom(MotionEvent event) { 
    int action = MotionEventCompat.getActionMasked(event); 
    // Get the index of the pointer associated with the action. 
    int index = MotionEventCompat.getActionIndex(event); 
    int xPos = (int) MotionEventCompat.getX(event, index); 
    int yPos = (int) MotionEventCompat.getY(event, index); 

    mScaleDetector.onTouchEvent(event); 

    switch (action) { 
     case MotionEvent.ACTION_DOWN: 
      mRenderer.handleStartPan(xPos, yPos); 
      break; 
     case MotionEvent.ACTION_MOVE: 
      if (!mScaleDetector.isInProgress()) { 
       mRenderer.handlePan(xPos, yPos); 
      } 
      break; 
    } 
} 

сторона Renderer:

private static final PointF mPanStart = new PointF(); 
public void handleStartPan(final int x, final int y) { 
    runOnGlThread(new Runnable() { 
     @Override 
     public void run() { 
      windowToWorld(x, y, mPanStart); 
     } 
    }); 
} 

private static final PointF mCurrentPan = new PointF(); 
public void handlePan(final int x, final int y) { 
    runOnGlThread(new Runnable() { 
     @Override 
     public void run() { 
      windowToWorld(x, y, mCurrentPan); 
      float dx = mCurrentPan.x - mPanStart.x; 
      float dy = mCurrentPan.y - mPanStart.y; 
      mOffsetX += dx; 
      mOffsetY += dy; 
      updateModelMatrix(); 
      mPanStart.set(mCurrentPan); 
     } 
    }); 
} 

функция windowToWorld использует gluUnProject и работает, потому что я использую его для многие другие задачи. UpdateModelMatrix:

private void updateModelMatrix() { 
    Matrix.setIdentityM(mScaleMatrix,0); 
    Matrix.scaleM(mScaleMatrix, 0, mScale, mScale, mScale); 

    Matrix.setRotateM(mRotationMatrix, 0, mAngle, 0, 0, 1.0f); 

    Matrix.setIdentityM(mTranslationMatrix,0); 
    Matrix.translateM(mTranslationMatrix, 0, mOffsetX, mOffsetY, 0); 

    // Model = Scale * Rotate * Translate 
    Matrix.multiplyMM(mIntermediateMatrix, 0, mScaleMatrix, 0, mRotationMatrix, 0); 
    Matrix.multiplyMM(mModelMatrix, 0, mIntermediateMatrix, 0, mTranslationMatrix, 0); 
} 

же mModelMatrix используется в gluUnproject функции windowToWorld для точечного перевода.

Так моя проблема два раза:

  1. Панорамирование происходит в два раза медленнее, чем движение пальца на экране
  2. устройства В какой-то момент, когда непрерывное панорамирование в течение нескольких секунд (делая круги на экране, например) карта начинает «дрожать». Амплитуда этого встряхивания становится все больше и больше. Похоже, какое-то значение добавляется в итерации handlePan и вызывает этот эффект.

Любая идея, почему это происходит?

Благодарим вас, Грег.

ответ

0

Ну, проблема с моим кодом эта линия:

 mPanStart.set(mCurrentPan); 

Просто потому, что я тащу в мировой системе координат, и изменение смещения, но текущее местоположение остается неизменным. Это была моя ошибка.

Снятие этой линии исправит все.