기존 코드에서 변경되는 부분은 거의 없다. 렌더러(Renderder)에서 위치를 이동시키는 행렬을 하나 더 추가하고 그것을 카메라 뷰와 합치면 된다.
먼저 터치 이벤트를 등록해야한다.
publicclassMyGLSurfaceViewextendsGLSurfaceView {...privatefloat mPreviousX;privatefloat mPreviousY; @OverridepublicbooleanonTouchEvent(MotionEvent e) {// MotionEvent reports input details from the touch screen// and other input controls. In this case, you are only// interested in events where the touch position changed.float x =e.getX();float y =e.getY();switch (e.getAction()) {caseMotionEvent.ACTION_MOVE:float dx = mPreviousX - x;float dy = mPreviousY - y;mRenderer.translate(dx, dy,0f); // translaterequestRender(); } mPreviousX = x; mPreviousY = y;returntrue; }}
터치 이벤트가 발생할 때마다 이동한 만큼 변위값을 렌더러에 넘겨준다.
publicclassMyGLRendererimplementsGLSurfaceView.Renderer {...privatefinalfloat[] mTranslateMatrix =newfloat[16];privateint screenHeight;privateint screenWidth; @OverridepublicvoidonSurfaceCreated(GL10 unused,EGLConfig config) {...Matrix.setIdentityM(mTranslateMatrix,0); } @OverridepublicvoidonSurfaceChanged(GL10 unused,int width,int height) {this.screenWidth= width;this.screenHeight= height;... } @OverridepublicvoidonDrawFrame(GL10 unused) {float[] scratch =newfloat[16];...// Combine the translated matrix with the projection and camera viewMatrix.multiplyMM(scratch,0, mMVPMatrix,0, mTranslateMatrix,0);// Draw trianglemTriangle.draw(scratch); }publicvoidtranslate(float dx,float dy,float dz) {Matrix.translateM(mTranslateMatrix,0, dx *2f/ screenHeight, dy *2f/ screenHeight, dz *2f/ screenHeight); }}
... 부분은 기존의 코드와 동일하다.
터치의 변위값, 즉 드래그한 만큼 mTranslateMatrix 에 반영한다. 그리고 onDrawFrame() 에서, 이동을 위해 추가한 행렬 mTranslateMatrix 도 결합시켜 그리도록 한다.
주의할 점은, mTranslateMatrix 의 최초 상태를 단위 행렬(Identity Matrix)로 만들어주고 시작해야한다.
추가로 살필 수 있는 부분으로는, dx * 2f / screenHeight 라는 수식이다.
터치의 변위값은 화면의 좌표계를 사용했다. 화면 비율에 맡게 가로/세로값으로 좌표계를 수정했었으니 그에 맞게 다시 변환해준 것이다.