package gl;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.FloatBuffer;
import java.nio.ShortBuffer;
import javax.microedition.khronos.egl.EGL10;
import javax.microedition.khronos.egl.EGLConfig;
import javax.microedition.khronos.egl.EGLContext;
import javax.microedition.khronos.egl.EGLDisplay;
import android.content.Context;
import android.hardware.SensorManager;
public class GLUtilityClass {
/**
* TODO not efficient to create a new buffer object every time, pass an old
* one if available and use it instead?
*
* @param source
* @return
*/
public static FloatBuffer createAndInitFloatBuffer(float[] source) {
if (source == null)
return null;
/*
* a float is 4 bytes, therefore the number of elements in the array has
* to be multiplied with 4:
*/
ByteBuffer byteBuffer = ByteBuffer.allocateDirect(source.length * 4);
byteBuffer.order(ByteOrder.nativeOrder());
FloatBuffer targetBuffer = byteBuffer.asFloatBuffer();
targetBuffer.put(source);
targetBuffer.position(0);
return targetBuffer;
}
public static ShortBuffer createAndInitShortBuffer(short[] source) {
if (source == null)
return null;
// short is 2 bytes, therefore we multiply the number if
// vertices with 2.
ByteBuffer indiceBiteBuffer = ByteBuffer
.allocateDirect(source.length * 2);
indiceBiteBuffer.order(ByteOrder.nativeOrder());
ShortBuffer targetBuffer = indiceBiteBuffer.asShortBuffer();
targetBuffer.put(source);
targetBuffer.position(0);
return targetBuffer;
}
/**
* this is a copy from
* {@link SensorManager#getRotationMatrixFromVector(float[] R, float[] rotationVector)}
* in newer android versions. Code from:
* http://android.git.kernel.org/?p=platform/frameworks/base
* .git;a=blob;f=core/java/android/hardware/SensorManager.java to keep
* compatibility to older Android versions
*
* TODO the "if lenght==3" stuff could be removed?
*
* @param R
* @param rotationVector
*/
public static void getRotationMatrixFromVector(float[] R,
float[] rotationVector) {
float q0;
float q1 = rotationVector[0];
float q2 = rotationVector[1];
float q3 = rotationVector[2];
if (rotationVector.length == 4) {
q0 = rotationVector[3];
} else {
q0 = 1 - q1 * q1 - q2 * q2 - q3 * q3;
q0 = (q0 > 0) ? (float) Math.sqrt(q0) : 0;
}
float sq_q1 = 2 * q1 * q1;
float sq_q2 = 2 * q2 * q2;
float sq_q3 = 2 * q3 * q3;
float q1_q2 = 2 * q1 * q2;
float q3_q0 = 2 * q3 * q0;
float q1_q3 = 2 * q1 * q3;
float q2_q0 = 2 * q2 * q0;
float q2_q3 = 2 * q2 * q3;
float q1_q0 = 2 * q1 * q0;
if (R.length == 9) {
R[0] = 1 - sq_q2 - sq_q3;
R[1] = q1_q2 - q3_q0;
R[2] = q1_q3 + q2_q0;
R[3] = q1_q2 + q3_q0;
R[4] = 1 - sq_q1 - sq_q3;
R[5] = q2_q3 - q1_q0;
R[6] = q1_q3 - q2_q0;
R[7] = q2_q3 + q1_q0;
R[8] = 1 - sq_q1 - sq_q2;
} else if (R.length == 16) {
R[0] = 1 - sq_q2 - sq_q3;
R[1] = q1_q2 - q3_q0;
R[2] = q1_q3 + q2_q0;
R[3] = 0.0f;
R[4] = q1_q2 + q3_q0;
R[5] = 1 - sq_q1 - sq_q3;
R[6] = q2_q3 - q1_q0;
R[7] = 0.0f;
R[8] = q1_q3 - q2_q0;
R[9] = q2_q3 + q1_q0;
R[10] = 1 - sq_q1 - sq_q2;
R[11] = 0.0f;
R[12] = R[13] = R[14] = 0.0f;
R[15] = 1.0f;
}
}
/**
* source:
*
* http://code.google.com/p/gl2-android/source/browse/trunk/src/com/badlogic
* /gdx/GL2Test.java
*
* @param context
* @return
*/
public static boolean isGL2Available(Context context) {
EGL10 egl = (EGL10) EGLContext.getEGL();
EGLDisplay display = egl.eglGetDisplay(EGL10.EGL_DEFAULT_DISPLAY);
int[] version = new int[2];
egl.eglInitialize(display, version);
int EGL_OPENGL_ES2_BIT = 4;
int[] configAttribs = { EGL10.EGL_RED_SIZE, 4, EGL10.EGL_GREEN_SIZE, 4,
EGL10.EGL_BLUE_SIZE, 4, EGL10.EGL_RENDERABLE_TYPE,
EGL_OPENGL_ES2_BIT, EGL10.EGL_NONE };
EGLConfig[] configs = new EGLConfig[10];
int[] num_config = new int[1];
egl.eglChooseConfig(display, configAttribs, configs, 10, num_config);
egl.eglTerminate(display);
return num_config[0] > 0;
}
}