1 package com.example.android.rs.nbody_gl; 2 3 import javax.microedition.khronos.egl.EGLConfig; 4 import javax.microedition.khronos.opengles.GL10; 5 6 import android.content.Context; 7 import android.opengl.GLES20; 8 import android.opengl.GLSurfaceView; 9 import android.opengl.Matrix; 10 import android.util.Log; 11 import android.view.KeyEvent; 12 import android.view.MotionEvent; 13 14 public class BasicGLRenderer implements GLSurfaceView.Renderer { 15 16 private static final String TAG = "BasicGLRenderer"; 17 private Swarm mSwarm; 18 Context mContext; 19 private final float[] mMVPMatrix = new float[16]; 20 private final float[] mProjectionMatrix = new float[16]; 21 private final float[] mViewMatrix = new float[16]; 22 private final float[] mRotationMatrix = new float[16]; 23 private float mAngle; 24 25 GLSurfaceView mGLSurfaceView; 26 27 public BasicGLRenderer(Context context, GLSurfaceView view) { 28 mContext = context; 29 mGLSurfaceView = view; 30 } 31 32 @Override 33 public void onSurfaceCreated(GL10 unused, EGLConfig config) { 34 GLES20.glClearColor(0.0f, 0.0f, 0.0f, 1.0f); 35 GLES20.glEnable(GLES20.GL_DEPTH_TEST); 36 37 if (mSwarm != null) { 38 mSwarm.onPause(); 39 } 40 mSwarm = new Swarm(mContext, mGLSurfaceView); 41 mSwarm.onSurfaceCreated(); 42 mSwarm.onResume(); 43 } 44 45 @Override 46 public void onDrawFrame(GL10 unused) { 47 float[] scratch = new float[16]; 48 49 GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT | GLES20.GL_DEPTH_BUFFER_BIT); 50 Matrix.setLookAtM(mViewMatrix, 0, 51 0, 0, -3, 0f, 52 0f, 0f, 0f, 53 1.0f, 0.0f); 54 Matrix.multiplyMM(mMVPMatrix, 0, mProjectionMatrix, 0, mViewMatrix, 0); 55 56 mSwarm.draw(mMVPMatrix); 57 58 Matrix.setRotateM(mRotationMatrix, 0, mAngle, 0, 0, 1.0f); 59 Matrix.multiplyMM(scratch, 0, mMVPMatrix, 0, mRotationMatrix, 0); 60 61 } 62 63 @Override 64 public void onSurfaceChanged(GL10 unused, int width, int height) { 65 GLES20.glViewport(0, 0, width, height); 66 float ratio = (float) width / height; 67 Matrix.frustumM(mProjectionMatrix, 0, -ratio / 10, ratio / 10, -.1f, .1f, .1f, 200); 68 } 69 70 public static int loadShader(int type, String shaderCode) { 71 int shader = GLES20.glCreateShader(type); 72 GLES20.glShaderSource(shader, shaderCode); 73 GLES20.glCompileShader(shader); 74 75 return shader; 76 } 77 78 public static void checkGlError(String glOperation) { 79 int error; 80 while ((error = GLES20.glGetError()) != GLES20.GL_NO_ERROR) { 81 Log.e(TAG, glOperation + ": glError " + error); 82 throw new RuntimeException(glOperation + ": glError " + error); 83 } 84 } 85 86 public float getAngle() { 87 return mAngle; 88 } 89 90 public void setAngle(float angle) { 91 mAngle = angle; 92 } 93 94 public void onResume() { 95 if (mSwarm != null) { 96 mSwarm.onResume(); 97 } 98 } 99 100 public void onPause() { 101 if (mSwarm != null) { 102 mSwarm.onPause(); 103 } 104 } 105 106 public void onTouchEvent(MotionEvent e) { 107 mSwarm.onTouchEvent(e); 108 } 109 110 public void onJoystick(float dx, float dy) { 111 mSwarm.onJoystick(dx, dy); 112 } 113 114 public void onKeyDown(int keyCode, KeyEvent event) { 115 116 mSwarm.onKeyDown(keyCode, event); 117 } 118 }