Planet-Miner/src/main.c

208 lines
5.9 KiB
C

#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <math.h>
#include <GL/glew.h>
#include <GLFW/glfw3.h>
GLFWwindow* window;
#include <cglm/struct.h>
#include "worldgen.h"
#define WINW 800
#define WINH 450
#define FOV 1.4f
#define SHADER_BUF_SIZE 1000
GLuint loadShaders(const char*, const char*);
static GLfloat vertexBufferData[1000];
void setVertexBufferData(GLfloat*, unsigned int*, unsigned int);
int main()
{
glewExperimental = true;
if( !glfwInit() )
{
fprintf( stderr, "Failed to initialize GLFW :(\n" );
return -1;
}
glfwWindowHint(GLFW_SAMPLES, 4);
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
window = glfwCreateWindow(WINW, WINH, "Planet Miner", NULL, NULL);
if( window == NULL )
{
fprintf( stderr, "Failed to create window. If you are using an Intel GPU, please note that they are not compatible with OpenGL 3.3\n" );
glfwTerminate();
return -1;
}
glfwMakeContextCurrent(window);
glewExperimental = true;
if( glewInit() != GLEW_OK )
{
fprintf( stderr, "Failed to initialize GLEW\n" );
getchar();
glfwTerminate();
return -1;
}
glfwSetInputMode(window, GLFW_STICKY_KEYS, GL_TRUE);
glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
GLuint vertexArrayID;
glGenVertexArrays(1, &vertexArrayID);
glBindVertexArray(vertexArrayID);
GLuint programID = loadShaders( "src/shader.vert", "src/shader.frag" );
GLuint matrixID = glGetUniformLocation(programID, "MVP");
mat4s projection = glms_perspective(FOV, 16.0f / 9.0f, 0.1f, 100.0f);
vec3s eye = {0.0f, 0.0f, 5.0f};
vec3s center = {0.0f, 0.0f, 0.0f};
vec3s up = {0.0f, 1.0f, 0.0f};
vec3s planetPos = {0.0f, 0.0f, 0.0f};
worldMesh* mesh = generateWorld(planetPos);
setVertexBufferData(mesh->vertices, mesh->triangles, mesh->triangleArrayCount);
GLuint vertexbuffer;
glGenBuffers(1, &vertexbuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertexBufferData), vertexBufferData, GL_STATIC_DRAW);
vec3s direction = {0.0f, 0.0f, -5.0f};
printf("Entering main loop\n");
do
{
glClear( GL_COLOR_BUFFER_BIT );
mat4s view = glms_lookat(eye, center, up);
mat4s model = glms_mat4_identity();
mat4s mvp = glms_mat4_mul(glms_mat4_mul(projection, view), model);
glUseProgram(programID);
glUniformMatrix4fv(matrixID, 1, GL_FALSE, &mvp);
glEnableVertexAttribArray(0);
glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
glVertexAttribPointer(
0,
3,
GL_FLOAT,
GL_FALSE,
0,
(void*)0
);
glDrawArrays(GL_TRIANGLES, 0, 20*3);
glDisableVertexAttribArray(0);
glfwSwapBuffers(window);
glfwPollEvents();
}
while( (glfwGetKey(window, GLFW_KEY_Q) != GLFW_PRESS
&& glfwGetKey(window, GLFW_KEY_ESCAPE) != GLFW_PRESS)
&& !glfwWindowShouldClose(window));
glDeleteBuffers(1, &vertexbuffer);
glDeleteProgram(programID);
glDeleteVertexArrays(1, &vertexArrayID);
glfwTerminate();
return 0;
}
GLuint loadShaders(const char* vertexShaderPath, const char* fragmentShaderPath)
{
char* vertexShaderCode = readTextFile( vertexShaderPath );
char* fragmentShaderCode = readTextFile( fragmentShaderPath );
GLuint vertexShaderID = glCreateShader(GL_VERTEX_SHADER);
GLuint fragmentShaderID = glCreateShader(GL_FRAGMENT_SHADER);
GLint result = GL_FALSE;
int infoLogLength;
printf("Compiling vertex shader...\n");
glShaderSource(vertexShaderID, 1, &vertexShaderCode, NULL);
glCompileShader(vertexShaderID);
glGetShaderiv(vertexShaderID, GL_COMPILE_STATUS, &result);
glGetShaderiv(vertexShaderID, GL_INFO_LOG_LENGTH, &infoLogLength);
if( infoLogLength > 0 )
{
char vertexShaderErrorMessage[infoLogLength + 1];
glGetShaderInfoLog(vertexShaderID, infoLogLength, NULL, &vertexShaderErrorMessage);
printf("%s\n", &vertexShaderErrorMessage);
}
printf("Compiling fragment shader...\n");
glShaderSource(fragmentShaderID, 1, &fragmentShaderCode, NULL);
glCompileShader(fragmentShaderID);
glGetShaderiv(fragmentShaderID, GL_COMPILE_STATUS, &result);
glGetShaderiv(fragmentShaderID, GL_INFO_LOG_LENGTH, &infoLogLength);
if( infoLogLength > 0 )
{
char fragmentShaderErrorMessage[infoLogLength + 1];
glGetShaderInfoLog(fragmentShaderID, infoLogLength, NULL, &fragmentShaderErrorMessage);
printf("%s\n", &fragmentShaderErrorMessage);
}
printf("Linking program\n");
GLuint programID = glCreateProgram();
glAttachShader(programID, vertexShaderID);
glAttachShader(programID, fragmentShaderID);
glLinkProgram(programID);
glGetProgramiv(programID, GL_LINK_STATUS, &result);
glGetProgramiv(programID, GL_INFO_LOG_LENGTH, &infoLogLength);
if( infoLogLength > 0 )
{
char programErrorMessage[infoLogLength + 1];
glGetProgramInfoLog(programID, infoLogLength, NULL, &programErrorMessage);
printf("%s\n", &programErrorMessage);
}
free( vertexShaderCode );
free( fragmentShaderCode );
glDetachShader( programID, vertexShaderID );
glDetachShader( programID, fragmentShaderID );
glDeleteShader( vertexShaderID );
glDeleteShader( fragmentShaderID );
return programID;
}
void setVertexBufferData(GLfloat* vertices, unsigned int* triangles, unsigned int triangleCount)
{
for( int i = 0; i < triangleCount; ++i )
{
vertexBufferData[i*3] = vertices[triangles[i]*3];
vertexBufferData[i*3 + 1] = vertices[triangles[i]*3 + 1];
vertexBufferData[i*3 + 2] = vertices[triangles[i]*3 + 2];
}
}