1. Link the GLM Library
- Click here and download the GLM library. I used version 0.9.9.7.
- Unzip the file you downloaded.
- Inside the unzipped folder you will find a subfolder named glm. Move this folder into your project’s cpp folder:
- Open the Project pane from the left side of the IDE.
- Select the Project view.
- Navigate to app->src->main.
- Drag and drop the glm folder onto the cpp folder and click OK.
- Open the CMakeLists.txt file.
- Make the following changes:
cmake_minimum_required(VERSION 3.6.0)
add_library(native-library SHARED main.cpp)
find_library(opengl-lib GLESv3)
find_library(log-lib log)
add_subdirectory(glm)
target_link_libraries(native-library ${opengl-lib} ${log-lib} glm)
2. Create the transformation matrix
- Add the following includes:
#include "glm/vec3.hpp" #include "glm/mat4x4.hpp" #include "glm/gtc/matrix_transform.hpp" #include "glm/gtc/type_ptr.hpp"
2.1 Create the identity matrix
- Modify the Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame function as follows:
extern "C" JNIEXPORT void JNICALL Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame(JNIEnv * env, jobject obj) {
glClear(GL_COLOR_BUFFER_BIT);
glUseProgram(program);
glm::mat4 model = glm::mat4(1.0f);
/* code */
}
2.2 Apply the translation
- Declare the following variables:
/* code */ GLuint program, triangleVAO, triangleVBO; GLint uniformModel; bool movingRight = true; float movingOffset = 0.0f; float movingMaxOffset = 0.5f; float movingStep = 0.015f; /* code */
- Continue modifying the Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame function as follows:
extern "C" JNIEXPORT void JNICALL Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame(JNIEnv * env, jobject obj) {
glClear(GL_COLOR_BUFFER_BIT);
glUseProgram(program);
movingRight ? movingOffset += movingStep : movingOffset -= movingStep;
if (abs(movingOffset) >= movingMaxOffset) {
movingRight = !movingRight;
}
glm::mat4 model = glm::mat4(1.0f);
model = glm::translate(model, glm::vec3(movingOffset, 0.0f, 0.0f));
/* code */
}
2.3 Apply the rotation
- Continue modifying the Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame function as follows:
extern "C" JNIEXPORT void JNICALL Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame(JNIEnv * env, jobject obj) {
/* code */
glm::mat4 model = glm::mat4(1.0f);
model = glm::translate(model, glm::vec3(movingOffset, 0.0f, 0.0f));
model = glm::rotate(model, glm::radians(90.0f), glm::vec3(0.0f, 0.0f, 1.0f));
/* code */
}
This will rotate the object 90 degrees around the axis formed by the origin and the vec3.
2.4 Apply scale
- Continue modifying the Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame function as follows:
extern "C" JNIEXPORT void JNICALL Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame(JNIEnv * env, jobject obj) {
/* code */
glm::mat4 model = glm::mat4(1.0f);
model = glm::translate(model, glm::vec3(movingOffset, 0.0f, 0.0f));
model = glm::rotate(model, glm::radians(90.0f), glm::vec3(0.0f, 0.0f, 1.0f));
model = glm::scale(model, glm::vec3(0.4f, 0.4f, 1.0f));
/* code */
}
Warning
These transformations will occur in reverse order: the object will be scaled first, then rotated and then moved.
3. Modify the vertex shader
You will add a uniform variable to hold the transformation matrix and you will apply the matrix to each vertex.
- Open the main.cpp file.
- Make the following changes to the vertex shader:
static const GLchar vertexShaderSource[] =
"#version 310 es\n"
"layout (location = 0) in vec3 pos;\n"
"uniform mat4 model;\n"
"void main()\n"
"{\n"
"gl_Position = model * vec4(pos, 1.0);\n"
"}\n";
Note
Vertex attributes are different for each vertex. In contrast, uniform variables remain the same for each vertex.
4. Set the uniform variable
- Declare the following variable:
/* code */ GLuint program, triangleVAO, triangleVBO; GLint uniformModel; /* code */
- Modify the createProgram function as follows:
void createProgram() {
/* code */
uniformModel = glGetUniformLocation(program, "model");
return;
}
- Modify the Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame function as follows:
extern "C" JNIEXPORT void JNICALL Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame(JNIEnv * env, jobject obj) {
/* code */
glm::mat4 model = glm::mat4(1.0f);
model = glm::translate(model, glm::vec3(movingOffset, 0.0f, 0.0f));
glUniformMatrix4fv(uniformModel, 1, GL_FALSE, glm::value_ptr(model));
/* code */
}
5. Display the transformation matrix (optional)
- Add the following include:
#include "glm/vec3.hpp" #include "glm/mat4x4.hpp" #include "glm/gtc/matrix_transform.hpp" #include "glm/gtc/type_ptr.hpp" #include "glm/gtx/string_cast.hpp"
- Modify the Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame function as follows:
extern "C" JNIEXPORT void JNICALL Java_dev_anastasioscho_glestriangle_NativeLibrary_nOnDrawFrame(JNIEnv * env, jobject obj) {
/* code */
LOGE("%s", glm::to_string(model).c_str());
glUniformMatrix4fv(uniformModel, 1, GL_FALSE, glm::value_ptr(model));
/* code */
}
Leave a Reply