Last active
November 25, 2018 10:27
-
-
Save amoshyc/5b9b465163323c3c240aab13f8867c03 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#version 410 | |
layout(location = 0) out vec4 fragColor; | |
uniform mat4 um4mv; | |
uniform mat4 um4p; | |
in VertexData | |
{ | |
vec3 N; // eye space normal | |
vec3 L; // eye space light vector | |
vec3 H; // eye space halfway vector | |
vec2 texcoord; | |
} vertexData; | |
uniform sampler2D tex; | |
void main() | |
{ | |
vec3 texColor = texture(tex,vertexData.texcoord).rgb; | |
fragColor = vec4(texColor, 1.0); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include "../Externals/Include/Include.h" | |
#define MENU_TIMER_START 1 | |
#define MENU_TIMER_STOP 2 | |
#define MENU_EXIT 3 | |
GLubyte timer_cnt = 0; | |
bool timer_enabled = true; | |
unsigned int timer_speed = 16; | |
using namespace glm; | |
using namespace std; | |
mat4 view; | |
mat4 projection; | |
mat4 model; | |
GLint um4p; | |
GLint um4mv; | |
GLint um4tex; | |
GLuint program; | |
char** loadShaderSource(const char* file) | |
{ | |
FILE* fp = fopen(file, "rb"); | |
fseek(fp, 0, SEEK_END); | |
long sz = ftell(fp); | |
fseek(fp, 0, SEEK_SET); | |
char *src = new char[sz + 1]; | |
fread(src, sizeof(char), sz, fp); | |
src[sz] = '\0'; | |
char **srcp = new char*[1]; | |
srcp[0] = src; | |
return srcp; | |
} | |
void freeShaderSource(char** srcp) | |
{ | |
delete srcp[0]; | |
delete srcp; | |
} | |
struct Shape { | |
GLuint vao; | |
GLuint vbo_xyz; | |
GLuint vbo_nml; | |
GLuint vbo_uv; | |
GLuint ibo; | |
int materialId; | |
int indexCount; | |
}; | |
vector<Shape> m; | |
vector<GLuint> vbo_texs; | |
void My_LoadModel() { | |
const aiScene *scene = aiImportFile("sponza.obj", aiProcessPreset_TargetRealtime_MaxQuality); | |
for (unsigned int i = 0; i < scene->mNumMaterials; ++i) { | |
aiMaterial *material = scene->mMaterials[i]; | |
aiString texturePath; | |
texture_data tex; | |
if (material->GetTexture(aiTextureType_DIFFUSE, 0, &texturePath) == aiReturn_SUCCESS) { | |
// load width, height and data from texturePath.C_Str(); | |
tex = load_png(texturePath.C_Str()); | |
cout << "Load " << texturePath.C_Str() << ":" << tex.width << ", " << tex.height << endl; | |
} | |
else { | |
// load some default image as default_diffuse_tex | |
tex = load_png("me.png"); | |
cout << "Load me.png" << ":" << tex.width << ", " << tex.height << endl; | |
} | |
GLuint vbo_tex; | |
glGenTextures(1, &vbo_tex); | |
glBindTexture(GL_TEXTURE_2D, vbo_tex); | |
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA32F, tex.width, tex.height, 0, GL_RGBA, GL_UNSIGNED_BYTE, tex.data); | |
glGenerateMipmap(GL_TEXTURE_2D); | |
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); | |
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); | |
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); | |
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); | |
// save material… | |
vbo_texs.push_back(vbo_tex); | |
} | |
for (unsigned int i = 0; i < scene->mNumMeshes; ++i) { | |
aiMesh *mesh = scene->mMeshes[i]; | |
Shape shape; | |
glGenVertexArrays(1, &shape.vao); | |
glBindVertexArray(shape.vao); | |
vector<float> vertices; | |
vector<float> normals; | |
vector<float> uvs; | |
vector<unsigned int> indices; | |
for (unsigned int v = 0; v < mesh->mNumVertices; v++) { | |
vertices.push_back(mesh->mVertices[v][0]); | |
vertices.push_back(mesh->mVertices[v][1]); | |
vertices.push_back(mesh->mVertices[v][2]); | |
normals.push_back(mesh->mNormals[v][0]); | |
normals.push_back(mesh->mNormals[v][1]); | |
normals.push_back(mesh->mNormals[v][2]); | |
uvs.push_back(mesh->mTextureCoords[0][v][0]); | |
uvs.push_back(mesh->mTextureCoords[0][v][1]); | |
} | |
for (unsigned int f = 0; f < mesh->mNumFaces; f++) { | |
indices.push_back(mesh->mFaces[f].mIndices[0]); | |
indices.push_back(mesh->mFaces[f].mIndices[1]); | |
indices.push_back(mesh->mFaces[f].mIndices[2]); | |
} | |
glGenBuffers(1, &shape.vbo_xyz); | |
glBindBuffer(GL_ARRAY_BUFFER, shape.vbo_xyz); | |
glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(float), &vertices[0], GL_STATIC_DRAW); | |
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0); | |
glGenBuffers(1, &shape.vbo_nml); | |
glBindBuffer(GL_ARRAY_BUFFER, shape.vbo_nml); | |
glBufferData(GL_ARRAY_BUFFER, normals.size() * sizeof(float), &normals[0], GL_STATIC_DRAW); | |
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 0, 0); | |
glGenBuffers(1, &shape.vbo_uv); | |
glBindBuffer(GL_ARRAY_BUFFER, shape.vbo_uv); | |
glBufferData(GL_ARRAY_BUFFER, uvs.size() * sizeof(float), &uvs[0], GL_STATIC_DRAW); | |
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 0, 0); | |
glGenBuffers(1, &shape.ibo); | |
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, shape.ibo); | |
glBufferData(GL_ELEMENT_ARRAY_BUFFER, indices.size() * sizeof(unsigned int), &indices[0], GL_STATIC_DRAW); | |
glEnableVertexAttribArray(0); | |
glEnableVertexAttribArray(1); | |
glEnableVertexAttribArray(2); | |
shape.materialId = mesh->mMaterialIndex; | |
shape.indexCount = mesh->mNumFaces * 3; | |
// save shape… | |
m.push_back(shape); | |
} | |
aiReleaseImport(scene); | |
} | |
void My_Init() | |
{ | |
glClearColor(0.5f, 0.5f, 0.5f, 1.0f); | |
glEnable(GL_DEPTH_TEST); | |
// glEnable(GL_CULL_FACE); | |
glDepthFunc(GL_LEQUAL); | |
program = glCreateProgram(); | |
GLuint vertexShader = glCreateShader(GL_VERTEX_SHADER); | |
GLuint fragmentShader = glCreateShader(GL_FRAGMENT_SHADER); | |
char** vertexShaderSource = loadShaderSource("vertex.vs.glsl"); | |
char** fragmentShaderSource = loadShaderSource("fragment.fs.glsl"); | |
glShaderSource(vertexShader, 1, vertexShaderSource, NULL); | |
glShaderSource(fragmentShader, 1, fragmentShaderSource, NULL); | |
freeShaderSource(vertexShaderSource); | |
freeShaderSource(fragmentShaderSource); | |
glCompileShader(vertexShader); | |
glCompileShader(fragmentShader); | |
shaderLog(vertexShader); | |
shaderLog(fragmentShader); | |
glAttachShader(program, vertexShader); | |
glAttachShader(program, fragmentShader); | |
glLinkProgram(program); | |
um4p = glGetUniformLocation(program, "um4p"); | |
um4mv = glGetUniformLocation(program, "um4mv"); | |
um4tex = glGetUniformLocation(program, "tex"); | |
glUseProgram(program); | |
My_LoadModel(); | |
} | |
// GLUT callback. Called to draw the scene. | |
void My_Display() | |
{ | |
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); | |
glUseProgram(program); | |
glUniformMatrix4fv(um4mv, 1, GL_FALSE, value_ptr(view * model)); | |
glUniformMatrix4fv(um4p, 1, GL_FALSE, value_ptr(projection)); | |
glActiveTexture(GL_TEXTURE0); | |
glUniform1i(um4tex, 0); | |
for (const Shape& s: m) { | |
auto vbo_tex = vbo_texs[s.materialId]; | |
glBindVertexArray(s.vao); | |
glBindTexture(GL_TEXTURE_2D, vbo_tex); | |
glDrawElements(GL_TRIANGLES, s.indexCount, GL_UNSIGNED_INT, 0); | |
} | |
glutSwapBuffers(); | |
} | |
void My_Reshape(int width, int height) | |
{ | |
glViewport(0, 0, width, height); | |
float viewportAspect = (float)width / (float)height; | |
projection = perspective(radians(60.0f), viewportAspect, 0.1f, 1000.0f); | |
view = lookAt(vec3(-10.0f, 0.0f, 0.0f), vec3(1.0f, 1.0f, 0.0f), vec3(0.0f, 1.0f, 0.0f)); | |
} | |
void My_Timer(int val) | |
{ | |
timer_cnt++; | |
glutPostRedisplay(); | |
if(timer_enabled) | |
{ | |
glutTimerFunc(timer_speed, My_Timer, val); | |
} | |
} | |
void My_Keyboard(unsigned char key, int x, int y) | |
{ | |
printf("Key %c is pressed at (%d, %d)\n", key, x, y); | |
if (key == 'q') { | |
exit(0); | |
} | |
// if (key == 'd') | |
// { | |
// temp = temp + vec3(0, 0, 1); | |
// } | |
// else if (key == 'a') | |
// { | |
// temp = temp - vec3(0, 0, 1); | |
// } | |
// else if (key == 'w') | |
// { | |
// temp = temp + vec3(1, 0, 0); | |
// } | |
// else if (key == 's') | |
// { | |
// temp = temp - vec3(1, 0, 0); | |
// } | |
} | |
void My_SpecialKeys(int key, int x, int y) | |
{ | |
switch(key) | |
{ | |
case GLUT_KEY_F1: | |
printf("F1 is pressed at (%d, %d)\n", x, y); | |
break; | |
case GLUT_KEY_PAGE_UP: | |
printf("Page up is pressed at (%d, %d)\n", x, y); | |
break; | |
case GLUT_KEY_LEFT: | |
printf("Left arrow is pressed at (%d, %d)\n", x, y); | |
break; | |
default: | |
printf("Other special key is pressed at (%d, %d)\n", x, y); | |
break; | |
} | |
} | |
void My_Menu(int id) | |
{ | |
switch(id) | |
{ | |
case MENU_TIMER_START: | |
if(!timer_enabled) | |
{ | |
timer_enabled = true; | |
glutTimerFunc(timer_speed, My_Timer, 0); | |
} | |
break; | |
case MENU_TIMER_STOP: | |
timer_enabled = false; | |
break; | |
case MENU_EXIT: | |
exit(0); | |
break; | |
default: | |
break; | |
} | |
} | |
int main(int argc, char *argv[]) | |
{ | |
#ifdef __APPLE__ | |
// Change working directory to source code path | |
chdir(__FILEPATH__("/../Assets/")); | |
#endif | |
// Initialize GLUT and GLEW, then create a window. | |
//////////////////// | |
glutInit(&argc, argv); | |
#ifdef _MSC_VER | |
glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH); | |
#else | |
glutInitDisplayMode(GLUT_3_2_CORE_PROFILE | GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH); | |
#endif | |
glutInitWindowPosition(100, 100); | |
glutInitWindowSize(600, 600); | |
glutCreateWindow("Practice"); // You cannot use OpenGL functions before this line; The OpenGL context must be created first by glutCreateWindow()! | |
#ifdef _MSC_VER | |
glewInit(); | |
#endif | |
dumpInfo(); | |
My_Init(); | |
// Create a menu and bind it to mouse right button. | |
int menu_main = glutCreateMenu(My_Menu); | |
int menu_timer = glutCreateMenu(My_Menu); | |
int menu_new = glutCreateMenu(My_Menu); | |
glutSetMenu(menu_main); | |
glutAddSubMenu("Timer", menu_timer); | |
glutAddMenuEntry("Exit", MENU_EXIT); | |
glutSetMenu(menu_timer); | |
glutAddMenuEntry("Start", MENU_TIMER_START); | |
glutAddMenuEntry("Stop", MENU_TIMER_STOP); | |
glutSetMenu(menu_main); | |
glutAttachMenu(GLUT_RIGHT_BUTTON); | |
// Register GLUT callback functions. | |
glutDisplayFunc(My_Display); | |
glutReshapeFunc(My_Reshape); | |
glutKeyboardFunc(My_Keyboard); | |
glutSpecialFunc(My_SpecialKeys); | |
glutTimerFunc(timer_speed, My_Timer, 0); | |
// Enter main event loop. | |
glutMainLoop(); | |
return 0; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#version 410 | |
layout(location = 0) in vec3 iv3vertex; | |
layout(location = 1) in vec3 iv3normal; | |
layout(location = 2) in vec2 iv2tex_coord; | |
uniform mat4 um4mv; | |
uniform mat4 um4p; | |
out VertexData | |
{ | |
vec3 N; // eye space normal | |
vec3 L; // eye space light vector | |
vec3 H; // eye space halfway vector | |
vec2 texcoord; | |
} vertexData; | |
void main() | |
{ | |
gl_Position = um4p * um4mv * vec4(iv3vertex, 1.0); | |
vertexData.texcoord = iv2tex_coord; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment