I'm learning OpenGL ES 2.0 for Android, and after some familiarization with the programming order I'm trying to draw 2 triangles on the screen, from 2 different objects. It's very simple, but it's not working, only my "triangle2" is drawn on the screen.
Could you help?
Class 1
public class MainActivity extends Activity {
GLSurfaceView myGLSurfaceView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
myGLSurfaceView = new GLSurfaceView(this);
myGLSurfaceView.setEGLContextClientVersion(2);
myGLSurfaceView.setRenderer(new RendererClass());
setContentView(myGLSurfaceView);
}
}
Class 2 - Triangle 1
public class ObjectTriangle {
int BYTES_PER_FLOAT = 4;
int shaderProgram;
FloatBuffer vertexInBuffer;
public ObjectTriangle(){
float[] vertexArray = {
0.0f, 0.5f, 1.0f, 0.0f, 0.0f,
0.0f, -0.5f, 0.0f, 1.0f, 0.0f,
0.5f, 0.0f, 0.0f, 0.0f, 1.0f
};
vertexInBuffer = ByteBuffer.allocateDirect(vertexArray.length*BYTES_PER_FLOAT)
.order(ByteOrder.nativeOrder())
.asFloatBuffer()
.put(vertexArray);
}
public void inicializeObjectShaders(){
String vertexShaderCode = "attribute vec4 a_Position;"
+ "attribute vec4 a_Color;"
+ "varying vec4 v_Color;"
+ "void main(){"
+ "gl_Position = a_Position;"
+ "v_Color = a_Color;"
+ "}";
String fragmentShaderCode = "precision mediump float;"
+ "varying vec4 v_Color;"
+ "void main(){"
+ "gl_FragColor = v_Color;"
+ "}";
int vertexShaderID = GLES20.glCreateShader(GLES20.GL_VERTEX_SHADER);
int fragmentShaderID = GLES20.glCreateShader(GLES20.GL_FRAGMENT_SHADER);
GLES20.glShaderSource(vertexShaderID, vertexShaderCode);
GLES20.glShaderSource(fragmentShaderID, fragmentShaderCode);
GLES20.glCompileShader(vertexShaderID);
GLES20.glCompileShader(fragmentShaderID);
shaderProgram = GLES20.glCreateProgram();
GLES20.glAttachShader(shaderProgram, vertexShaderID);
GLES20.glAttachShader(shaderProgram, fragmentShaderID);
GLES20.glLinkProgram(shaderProgram);
}
public void setVertexAttribPointer(){
int aPositionLocation = glGetAttribLocation(shaderProgram, "a_Position");
int aColorLocation = glGetAttribLocation(shaderProgram, "a_Color");
vertexInBuffer.position(0);
glVertexAttribPointer(aPositionLocation, 2, GL_FLOAT, false, (2+3)*BYTES_PER_FLOAT, vertexInBuffer);
glEnableVertexAttribArray(aPositionLocation);
vertexInBuffer.position(2);
glVertexAttribPointer(aColorLocation, 3, GL_FLOAT, false, (2+3)*BYTES_PER_FLOAT, vertexInBuffer);
glEnableVertexAttribArray(aColorLocation);
}
public void useProgram(){
GLES20.glUseProgram(shaderProgram);
}
public void draw(){
glDrawArrays(GL_TRIANGLES, 0, 3);
}
}
Class 3 - Triangle 2 (99% equals triangle1, only changes the location of 1 vertex)
public class ObjectTriangle2 {
int BYTES_PER_FLOAT = 4;
int shaderProgram;
FloatBuffer vertexInBuffer;
public ObjectTriangle2(){
float[] vertexArray = {
0.0f, 0.5f, 1.0f, 0.0f, 0.0f,
-0.5f, 0.0f, 0.0f, 1.0f, 0.0f,
0.0f, -0.5f, 0.0f, 0.0f, 1.0f
};
vertexInBuffer = ByteBuffer.allocateDirect(vertexArray.length*BYTES_PER_FLOAT)
.order(ByteOrder.nativeOrder())
.asFloatBuffer()
.put(vertexArray);
}
public void inicializeObjectShaders(){
String vertexShaderCode = "attribute vec4 a_Position;"
+ "attribute vec4 a_Color;"
+ "varying vec4 v_Color;"
+ "void main(){"
+ "gl_Position = a_Position;"
+ "v_Color = a_Color;"
+ "}";
String fragmentShaderCode = "precision mediump float;"
+ "varying vec4 v_Color;"
+ "void main(){"
+ "gl_FragColor = v_Color;"
+ "}";
int vertexShaderID = GLES20.glCreateShader(GLES20.GL_VERTEX_SHADER);
int fragmentShaderID = GLES20.glCreateShader(GLES20.GL_FRAGMENT_SHADER);
GLES20.glShaderSource(vertexShaderID, vertexShaderCode);
GLES20.glShaderSource(fragmentShaderID, fragmentShaderCode);
GLES20.glCompileShader(vertexShaderID);
GLES20.glCompileShader(fragmentShaderID);
shaderProgram = GLES20.glCreateProgram();
GLES20.glAttachShader(shaderProgram, vertexShaderID);
GLES20.glAttachShader(shaderProgram, fragmentShaderID);
GLES20.glLinkProgram(shaderProgram);
}
public void setVertexAttribPointer(){
int aPositionLocation = glGetAttribLocation(shaderProgram, "a_Position");
int aColorLocation = glGetAttribLocation(shaderProgram, "a_Color");
vertexInBuffer.position(0);
glVertexAttribPointer(aPositionLocation, 2, GL_FLOAT, false, (2+3)*BYTES_PER_FLOAT, vertexInBuffer);
glEnableVertexAttribArray(aPositionLocation);
vertexInBuffer.position(2);
glVertexAttribPointer(aColorLocation, 3, GL_FLOAT, false, (2+3)*BYTES_PER_FLOAT, vertexInBuffer);
glEnableVertexAttribArray(aColorLocation);
}
public void useProgram(){
GLES20.glUseProgram(shaderProgram);
}
public void draw(){
glDrawArrays(GL_TRIANGLES, 0, 3);
}
}
Class 4 - The Renderer
public class RendererClass implements Renderer {
ObjectTriangle triangle;
ObjectTriangle2 triangle2;
@Override
public void onSurfaceCreated(GL10 arg0, EGLConfig config) {
GLES20.glClearColor(0.0f, 0.5f, 1.0f, 1.0f);
triangle = new ObjectTriangle();
triangle.inicializeObjectShaders();
triangle.setVertexAttribPointer();
triangle2 = new ObjectTriangle2();
triangle2.inicializeObjectShaders();
triangle2.setVertexAttribPointer();
}
@Override
public void onSurfaceChanged(GL10 arg0, int width, int height) {
glViewport(0, 0, width, height);
}
@Override
public void onDrawFrame(GL10 glUnused) {
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
triangle.useProgram();
triangle.draw();
triangle2.useProgram();
triangle2.draw();
}
}