package com.asha.vrlib.model.position; import android.opengl.Matrix; import com.asha.vrlib.model.MDPosition; import static com.asha.vrlib.common.VRUtil.checkGLThread; import static com.asha.vrlib.common.VRUtil.notNull; /** * Created by hzqiujiadi on 2017/4/11. * hzqiujiadi ashqalcn@gmail.com */ public class MDMutablePosition extends MDPosition { private float[] mModelMatrix = null; private float[] mRotationMatrix = null; private static final float[] sSharedTmpMatrix = new float[16]; private float mX; private float mY; private float mZ; private float mAngleX; private float mAngleY; private float mAngleZ; private float mPitch; // x-axis private float mYaw; // y-axis private float mRoll; // z-axis private boolean changed; private MDMutablePosition() { mX = mY = mZ = 0; mAngleX = mAngleY = mAngleZ = 0; mPitch = mYaw = mRoll = 0; changed = true; } public float getPitch() { return mPitch; } public MDMutablePosition setPitch(float pitch) { changed |= this.mPitch != pitch; this.mPitch = pitch; return this; } public float getYaw() { return mYaw; } public MDMutablePosition setYaw(float yaw) { changed |= this.mYaw != yaw; this.mYaw = yaw; return this; } public float getRoll() { return mRoll; } public MDMutablePosition setRoll(float roll) { changed |= this.mRoll != roll; this.mRoll = roll; return this; } public float getX() { return mX; } public MDMutablePosition setX(float x) { changed |= this.mX != x; this.mX = x; return this; } public float getY() { return mY; } public MDMutablePosition setY(float y) { changed |= this.mY != y; this.mY = y; return this; } public float getZ() { return mZ; } public MDMutablePosition setZ(float z) { changed |= this.mZ != z; this.mZ = z; return this; } public float getAngleX() { return mAngleX; } /** * setAngleX * @param angleX in degree * @return self */ public MDMutablePosition setAngleX(float angleX) { changed |= this.mAngleX != angleX; this.mAngleX = angleX; return this; } public float getAngleY() { return mAngleY; } /** * setAngleY * @param angleY in degree * @return self */ public MDMutablePosition setAngleY(float angleY) { changed |= this.mAngleY != angleY; this.mAngleY = angleY; return this; } public float getAngleZ() { return mAngleZ; } /** * setAngleZ * @param angleZ in degree * @return self */ public MDMutablePosition setAngleZ(float angleZ) { changed |= this.mAngleX != angleZ; this.mAngleZ = angleZ; return this; } public static MDMutablePosition newInstance(){ return new MDMutablePosition(); } @Override public String toString() { return "MDPosition{" + "mX=" + mX + ", mY=" + mY + ", mZ=" + mZ + ", mAngleX=" + mAngleX + ", mAngleY=" + mAngleY + ", mAngleZ=" + mAngleZ + ", mPitch=" + mPitch + ", mYaw=" + mYaw + ", mRoll=" + mRoll + '}'; } private void ensure(){ // model if (mModelMatrix == null){ mModelMatrix = new float[16]; Matrix.setIdentityM(mModelMatrix, 0); } if (!changed){ return; } Matrix.setIdentityM(mModelMatrix, 0); Matrix.rotateM(mModelMatrix, 0, getAngleX(), 1.0f, 0.0f, 0.0f); Matrix.rotateM(mModelMatrix, 0, getAngleY(), 0.0f, 1.0f, 0.0f); Matrix.rotateM(mModelMatrix, 0, getAngleZ(), 0.0f, 0.0f, 1.0f); Matrix.translateM(mModelMatrix, 0, getX(),getY(),getZ()); Matrix.rotateM(mModelMatrix, 0, getYaw(), 1.0f, 0.0f, 0.0f); Matrix.rotateM(mModelMatrix, 0, getPitch(), 0.0f, 1.0f, 0.0f); Matrix.rotateM(mModelMatrix, 0, getRoll(), 0.0f, 0.0f, 1.0f); // rotation if (mRotationMatrix != null){ Matrix.multiplyMM(sSharedTmpMatrix, 0, mRotationMatrix, 0, mModelMatrix, 0); System.arraycopy(sSharedTmpMatrix, 0, mModelMatrix, 0, 16); } changed = false; } @Override public void setRotationMatrix(float[] rotationMatrix){ notNull(rotationMatrix, "rotationMatrix can't be null!"); checkGLThread("setRotationMatrix must called in gl thread!"); if (mRotationMatrix == null){ mRotationMatrix = new float[16]; } System.arraycopy(rotationMatrix, 0, mRotationMatrix, 0, 16); changed = true; } @Override public float[] getMatrix() { ensure(); return mModelMatrix; } }