2017-02-16 47 views
0

我使用下面的代碼來顯示一個OBJ模型,我需要根據用戶手勢來移動它,但onObjectPicked()永遠不會被調用,只是onNoObjectPicked()onObjectPicked從來沒有呼籲Rajawali

出了什麼問題?我能檢測到模型特定部分的點擊嗎?

import android.content.Context; 
import android.graphics.Color; 
import android.support.annotation.NonNull; 
import android.util.Log; 
import android.view.MotionEvent; 

import org.rajawali3d.Object3D; 
import org.rajawali3d.cameras.Camera; 
import org.rajawali3d.lights.DirectionalLight; 
import org.rajawali3d.loader.LoaderOBJ; 
import org.rajawali3d.loader.ParsingException; 
import org.rajawali3d.materials.textures.TextureManager; 
import org.rajawali3d.math.Matrix4; 
import org.rajawali3d.math.vector.Vector3; 
import org.rajawali3d.renderer.Renderer; 
import org.rajawali3d.util.GLU; 
import org.rajawali3d.util.ObjectColorPicker; 
import org.rajawali3d.util.OnObjectPickedListener; 

import javax.microedition.khronos.opengles.GL10; 

/** 
* Created by juliano on 2/15/2017. 
*/ 

public class CarRenderer extends Renderer implements OnObjectPickedListener { 
    public Context mContext; 

    private Camera mCamera; 
    private Object3D mSelectedObject; 
    private ObjectColorPicker mPicker; 
    private Matrix4 mViewMatrix; 
    private Matrix4 mProjectionMatrix; 
    private int[] mViewport; 
    private double[] mNearPos4; 
    private double[] mFarPos4; 
    private Vector3 mNearPos; 
    private Vector3 mFarPos; 
    private Vector3 mNewObjPos; 


    public CarRenderer(Context context) { 
     super(context); 
     mContext = context; 
    } 

    @Override 
    protected void initScene() { 
     getCurrentScene().setBackgroundColor(Color.WHITE); 

     DirectionalLight key = new DirectionalLight(-8, 8, 8); 
     key.setPosition(new Vector3(8,8,8)); 
     key.setPower(8); 
     getCurrentScene().addLight(key); 

     mCamera = getCurrentCamera(); 
     mCamera.setPosition(12, 12, 12); 
     mCamera.setLookAt(Vector3.ZERO); 

     mViewport = new int[] { 0, 0, getViewportWidth(), getViewportHeight() }; 
     mViewMatrix = getCurrentCamera().getViewMatrix(); 
     mProjectionMatrix = getCurrentCamera().getProjectionMatrix(); 
     mNearPos4 = new double[4]; 
     mFarPos4 = new double[4]; 
     mNearPos = new Vector3(); 
     mFarPos = new Vector3(); 
     mNewObjPos = new Vector3(); 

     try { 
      mPicker = new ObjectColorPicker(this); 
      mPicker.setOnObjectPickedListener(this); 

      LoaderOBJ parser = new LoaderOBJ(mContext.getResources(), TextureManager.getInstance(), R.raw.ferrari_obj); 
      parser.parse(); 

      Object3D o = parser.getParsedObject(); 
      getCurrentScene().addChild(o); 
      mPicker.registerObject(o); 

     } catch (ParsingException e) { 
      e.printStackTrace(); 
     } 

    } 

    @Override 
    public void onRenderSurfaceSizeChanged(GL10 gl, int width, int height) { 
     super.onRenderSurfaceSizeChanged(gl, width, height); 
     mViewport[2] = getViewportWidth(); 
     mViewport[3] = getViewportHeight(); 
     mViewMatrix = getCurrentCamera().getViewMatrix(); 
     mProjectionMatrix = getCurrentCamera().getProjectionMatrix(); 
    } 

    @Override 
    public void onOffsetsChanged(float xOffset, float yOffset, float xOffsetStep, float yOffsetStep, int xPixelOffset, int yPixelOffset) { 

    } 

    @Override //This method moves the camera using direct touch events. Tracking a flick and turning it into a procedural animation for smoothing 
    public void onTouchEvent(MotionEvent me) { 
    } 

    @Override 
    public void onObjectPicked(@NonNull Object3D object) { 
     mSelectedObject = object; 
    } 

    @Override 
    public void onNoObjectPicked() { 
     Log.d("CarRenderer", "No object picked"); 
    } 

    public void getObjectAt(float x, float y) { 
     mPicker.getObjectAt(x, y); 
    } 

    public void moveSelectedObject(float x, float y) { 
     if (mSelectedObject == null) 
      return; 

     // 
     // -- unproject the screen coordinate (2D) to the camera's near plane 
     // 

     GLU.gluUnProject(x, getViewportHeight() - y, 0, mViewMatrix.getDoubleValues(), 0, 
       mProjectionMatrix.getDoubleValues(), 0, mViewport, 0, mNearPos4, 0); 

     // 
     // -- unproject the screen coordinate (2D) to the camera's far plane 
     // 

     GLU.gluUnProject(x, getViewportHeight() - y, 1.f, mViewMatrix.getDoubleValues(), 0, 
       mProjectionMatrix.getDoubleValues(), 0, mViewport, 0, mFarPos4, 0); 

     // 
     // -- transform 4D coordinates (x, y, z, w) to 3D (x, y, z) by dividing 
     // each coordinate (x, y, z) by w. 
     // 

     mNearPos.setAll(mNearPos4[0]/mNearPos4[3], mNearPos4[1] 
       /mNearPos4[3], mNearPos4[2]/mNearPos4[3]); 
     mFarPos.setAll(mFarPos4[0]/mFarPos4[3], 
       mFarPos4[1]/mFarPos4[3], mFarPos4[2]/mFarPos4[3]); 

     // 
     // -- now get the coordinates for the selected object 
     // 

     double factor = (Math.abs(mSelectedObject.getZ()) + mNearPos.z) 
       /(getCurrentCamera().getFarPlane() - getCurrentCamera() 
       .getNearPlane()); 

     mNewObjPos.setAll(mFarPos); 
     mNewObjPos.subtract(mNearPos); 
     mNewObjPos.multiply(factor); 
     mNewObjPos.add(mNearPos); 

     mSelectedObject.setX(mNewObjPos.x); 
     mSelectedObject.setY(mNewObjPos.y); 
    } 

    public void stopMovingSelectedObject() { 
     mSelectedObject = null; 
    } 
} 

回答

0

另外補充一點從活動調用的時候,觸摸事件被解僱的方法:

@Override 
public boolean onTouchEvent(MotionEvent event) { 
    // TODO Auto-generated method stub 
    renderer.onTouchEvent(event); 
    return super.onTouchEvent(event); 
}