Compare commits
4 Commits
visualisat
...
main
Author | SHA1 | Date |
---|---|---|
|
63c44f9f7a | |
|
dd201108e6 | |
|
6ccfb7e818 | |
|
cced3c5c83 |
|
@ -7,7 +7,8 @@ src_files = [
|
||||||
'./src/main.c',
|
'./src/main.c',
|
||||||
'./src/shader.c',
|
'./src/shader.c',
|
||||||
'./src/log.c',
|
'./src/log.c',
|
||||||
'./src/matrix-math.c'
|
'./src/matrix-math.c',
|
||||||
|
'./src/wavefrontobj.c'
|
||||||
]
|
]
|
||||||
|
|
||||||
executable('cg1',
|
executable('cg1',
|
||||||
|
|
|
@ -0,0 +1,34 @@
|
||||||
|
# Blender 4.4.3
|
||||||
|
# www.blender.org
|
||||||
|
o Cube
|
||||||
|
v 1.000000 1.000000 -1.000000
|
||||||
|
v 1.000000 -1.000000 -1.000000
|
||||||
|
v 1.000000 1.000000 1.000000
|
||||||
|
v 1.000000 -1.000000 1.000000
|
||||||
|
v -1.000000 1.000000 -1.000000
|
||||||
|
v -1.000000 -1.000000 -1.000000
|
||||||
|
v -1.000000 1.000000 1.000000
|
||||||
|
v -1.000000 -1.000000 1.000000
|
||||||
|
vn -0.0000 1.0000 -0.0000
|
||||||
|
vn -0.0000 -0.0000 1.0000
|
||||||
|
vn -1.0000 -0.0000 -0.0000
|
||||||
|
vn -0.0000 -1.0000 -0.0000
|
||||||
|
vn 1.0000 -0.0000 -0.0000
|
||||||
|
vn -0.0000 -0.0000 -1.0000
|
||||||
|
vt 1.000000 0.000000
|
||||||
|
vt 0.000000 1.000000
|
||||||
|
vt 0.000000 0.000000
|
||||||
|
vt 1.000000 1.000000
|
||||||
|
s 0
|
||||||
|
f 5/1/1 3/2/1 1/3/1
|
||||||
|
f 3/1/2 8/2/2 4/3/2
|
||||||
|
f 7/1/3 6/2/3 8/3/3
|
||||||
|
f 2/1/4 8/2/4 6/3/4
|
||||||
|
f 1/1/5 4/2/5 2/3/5
|
||||||
|
f 5/1/6 2/2/6 6/3/6
|
||||||
|
f 5/1/1 7/4/1 3/2/1
|
||||||
|
f 3/1/2 7/4/2 8/2/2
|
||||||
|
f 7/1/3 5/4/3 6/2/3
|
||||||
|
f 2/1/4 4/4/4 8/2/4
|
||||||
|
f 1/1/5 3/4/5 4/2/5
|
||||||
|
f 5/1/6 1/4/6 2/2/6
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
107
src/main.c
107
src/main.c
|
@ -11,6 +11,7 @@
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "shader.h"
|
#include "shader.h"
|
||||||
#include "matrix-math.h"
|
#include "matrix-math.h"
|
||||||
|
#include "wavefrontobj.h"
|
||||||
|
|
||||||
#define STATUS_INTERVAL 0.5
|
#define STATUS_INTERVAL 0.5
|
||||||
#define PI 3.14159f
|
#define PI 3.14159f
|
||||||
|
@ -18,8 +19,7 @@
|
||||||
GLuint program;
|
GLuint program;
|
||||||
|
|
||||||
GLuint vertexArrayObject;
|
GLuint vertexArrayObject;
|
||||||
|
GLuint numVertices;
|
||||||
GLuint indexBuffer;
|
|
||||||
|
|
||||||
GLuint initialWindowWidth = 800;
|
GLuint initialWindowWidth = 800;
|
||||||
GLuint initialWindowHeight = 600;
|
GLuint initialWindowHeight = 600;
|
||||||
|
@ -122,47 +122,15 @@ void init(void) {
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
GLfloat vertices[] = {
|
DEBUG("Loading OBJ File");
|
||||||
// X // Y
|
ParsedObjFile f = readObjFile("obj/smooth_monkey.obj");
|
||||||
1.0f, 1.0f, 1.0f,
|
numVertices = f.length * sizeof(face) / sizeof(vertex);
|
||||||
1.0f, 1.0f, -1.0f,
|
|
||||||
1.0f, -1.0f, 1.0f,
|
|
||||||
1.0f, -1.0f, -1.0f,
|
|
||||||
-1.0f, 1.0f, 1.0f,
|
|
||||||
-1.0f, 1.0f, -1.0f,
|
|
||||||
-1.0f, -1.0f, 1.0f,
|
|
||||||
-1.0f, -1.0f, -1.0f,
|
|
||||||
};
|
|
||||||
|
|
||||||
GLuint restart = 128;
|
|
||||||
glEnable(GL_PRIMITIVE_RESTART);
|
|
||||||
glPrimitiveRestartIndex(restart);
|
|
||||||
|
|
||||||
GLuint indices[] = {
|
|
||||||
1, 0, 2,
|
|
||||||
1, 2, 3,
|
|
||||||
|
|
||||||
4, 0, 1,
|
|
||||||
5, 4, 1,
|
|
||||||
|
|
||||||
5, 1, 7,
|
|
||||||
1, 3, 7,
|
|
||||||
|
|
||||||
5, 7, 6,
|
|
||||||
4, 5, 6,
|
|
||||||
|
|
||||||
0, 4, 6,
|
|
||||||
2, 0, 6,
|
|
||||||
|
|
||||||
3, 2, 6,
|
|
||||||
7, 3, 6
|
|
||||||
};
|
|
||||||
|
|
||||||
DEBUG("Creating vertext buffer");
|
DEBUG("Creating vertext buffer");
|
||||||
GLuint vertexBuffer;
|
GLuint vertexBuffer;
|
||||||
glGenBuffers(1, &vertexBuffer);
|
glGenBuffers(1, &vertexBuffer);
|
||||||
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
|
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
|
||||||
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
|
glBufferData(GL_ARRAY_BUFFER, f.length * sizeof(face), f.faces, GL_STATIC_DRAW);
|
||||||
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
||||||
|
|
||||||
DEBUG("Creating vertex array object");
|
DEBUG("Creating vertex array object");
|
||||||
|
@ -177,17 +145,21 @@ void init(void) {
|
||||||
3, // number of values to read
|
3, // number of values to read
|
||||||
GL_FLOAT, // type of value
|
GL_FLOAT, // type of value
|
||||||
GL_FALSE, // if values are normalised
|
GL_FALSE, // if values are normalised
|
||||||
3 * sizeof(GLfloat), // stride - distance between vertices
|
sizeof(vertex), // stride - distance between vertices
|
||||||
0 // start offset
|
0 // start offset
|
||||||
);
|
);
|
||||||
glEnableVertexAttribArray(0);
|
glEnableVertexAttribArray(0);
|
||||||
|
|
||||||
DEBUG("Creating index buffer");
|
glVertexAttribPointer(
|
||||||
glGenBuffers(1, &indexBuffer);
|
1,
|
||||||
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
|
3,
|
||||||
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);
|
GL_FLOAT,
|
||||||
|
GL_FALSE,
|
||||||
|
sizeof(vertex),
|
||||||
|
(void*)offsetof(vertex, normal)
|
||||||
|
);
|
||||||
|
glEnableVertexAttribArray(1);
|
||||||
|
|
||||||
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
|
|
||||||
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
||||||
glBindVertexArray(0);
|
glBindVertexArray(0);
|
||||||
|
|
||||||
|
@ -208,30 +180,11 @@ void init(void) {
|
||||||
|
|
||||||
GLfloat currentHue = 0.0f;
|
GLfloat currentHue = 0.0f;
|
||||||
|
|
||||||
void drawCube(vec3 position, mat4 initialModelMatrix, mat4 viewMatrix) {
|
|
||||||
mat4 modelMatrix;
|
|
||||||
mat4 modelViewMatrix;
|
|
||||||
|
|
||||||
mat4Translate(modelMatrix, initialModelMatrix, position);
|
|
||||||
|
|
||||||
// combine model and view matrix to model-view matrix
|
|
||||||
mat4Multiply(modelViewMatrix, viewMatrix, modelMatrix);
|
|
||||||
|
|
||||||
// send modelView and projection matrix to shader
|
|
||||||
GLuint modelViewLocation = glGetUniformLocation(program, "uModelView");
|
|
||||||
glUniformMatrix4fv(modelViewLocation, 1, GL_FALSE, modelViewMatrix);
|
|
||||||
|
|
||||||
// draw cube
|
|
||||||
glBindVertexArray(vertexArrayObject);
|
|
||||||
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
|
|
||||||
glDrawElements(GL_TRIANGLES, 48, GL_UNSIGNED_INT, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
void draw(void) {
|
void draw(void) {
|
||||||
updateStatusDisplay();
|
updateStatusDisplay();
|
||||||
|
|
||||||
// counter for animation
|
// counter for animation
|
||||||
currentHue += 0.0005f;
|
currentHue += 0.005f;
|
||||||
if (currentHue > 1.0) currentHue = 0.0f;
|
if (currentHue > 1.0) currentHue = 0.0f;
|
||||||
|
|
||||||
// clear colour and depth buffer
|
// clear colour and depth buffer
|
||||||
|
@ -244,7 +197,7 @@ void draw(void) {
|
||||||
mat4 viewMatrix;
|
mat4 viewMatrix;
|
||||||
|
|
||||||
// mat4Identity(viewMatrix);
|
// mat4Identity(viewMatrix);
|
||||||
vec3 cameraPos = {0.0f, 1.0f, 1.3f};
|
vec3 cameraPos = {cos(currentHue * M_PI * 2), 0.0f, sin(currentHue * M_PI * 2)};
|
||||||
vec3 cameraLookAt = {0.0f, 0.2f, 0.0f};
|
vec3 cameraLookAt = {0.0f, 0.2f, 0.0f};
|
||||||
vec3 cameraUp = {0.0f, 1.0f, 0.0f};
|
vec3 cameraUp = {0.0f, 1.0f, 0.0f};
|
||||||
mat4BuildLookAt(viewMatrix, cameraPos, cameraLookAt, cameraUp);
|
mat4BuildLookAt(viewMatrix, cameraPos, cameraLookAt, cameraUp);
|
||||||
|
@ -255,26 +208,18 @@ void draw(void) {
|
||||||
|
|
||||||
// build model Matrix
|
// build model Matrix
|
||||||
mat4 modelMatrix;
|
mat4 modelMatrix;
|
||||||
vec3 scale;
|
mat4 modelViewMatrix;
|
||||||
vec3 position;
|
|
||||||
|
|
||||||
float scales[] = {0.5f, 0.4f, 0.3f, 0.2f, 0.1f, 0.09f, 0.08f, 0.07f, 0.06f, 0.05f};
|
vec3 scale = {0.2f, 0.2f, 0.2f};
|
||||||
for (int i = 0; i < 10; i++) {
|
|
||||||
mat4Identity(modelMatrix);
|
|
||||||
|
|
||||||
vec3Set(scale, scales[i], 0.05f, scales[i]);
|
mat4Identity(modelMatrix);
|
||||||
mat4Scale(modelMatrix, modelMatrix, scale);
|
mat4Scale(modelMatrix, modelMatrix, scale);
|
||||||
|
mat4Multiply(modelViewMatrix, viewMatrix, modelMatrix);
|
||||||
mat4RotateY(modelMatrix, modelMatrix, currentHue * 2 * M_PI + (i / 5.0f * M_PI));
|
|
||||||
|
|
||||||
vec3Set(position, 0.0f, i * 0.05f, 0.0f);
|
|
||||||
mat4Translate(modelMatrix, modelMatrix, position);
|
|
||||||
|
|
||||||
drawCube(position, modelMatrix, viewMatrix);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
glUniformMatrix4fv(glGetUniformLocation(program, "uModelView"), 1, GL_FALSE, modelViewMatrix);
|
||||||
|
|
||||||
|
glBindVertexArray(vertexArrayObject);
|
||||||
|
glDrawArrays(GL_TRIANGLES, 0, numVertices);
|
||||||
}
|
}
|
||||||
|
|
||||||
void framebuffer_size_callback(GLFWwindow* window, int width, int height) {
|
void framebuffer_size_callback(GLFWwindow* window, int width, int height) {
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
#include "matrix-math.h"
|
#include "matrix-math.h"
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* overwrites a 4x4 matrix with the identity matrix
|
* overwrites a 4x4 matrix with the identity matrix
|
||||||
|
@ -195,6 +196,7 @@ void mat4BuildProjection(mat4 out, GLfloat r, GLfloat l, GLfloat t, GLfloat b, G
|
||||||
out[11] = -1.0f / n;
|
out[11] = -1.0f / n;
|
||||||
|
|
||||||
out[14] = - 2.0f * f / (f - n);
|
out[14] = - 2.0f * f / (f - n);
|
||||||
|
out[15] = 0.0f;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -420,6 +422,18 @@ void vec3Set(vec3 out, GLfloat x, GLfloat y, GLfloat z) {
|
||||||
out[2] = z;
|
out[2] = z;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void vec3Multiply(vec3 out, vec3 in, GLfloat x) {
|
||||||
|
out[0] = in[0] * x;
|
||||||
|
out[1] = in[1] * x;
|
||||||
|
out[2] = in[2] * x;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void vec2Subtract(vec2 out, vec2 a, vec2 b) {
|
||||||
|
out[0] = a[0] - b[0];
|
||||||
|
out[1] = a[1] - b[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void mat3Copy(mat3 src, mat3 dst) {
|
void mat3Copy(mat3 src, mat3 dst) {
|
||||||
for (int i = 0; i < 9; i++) {
|
for (int i = 0; i < 9; i++) {
|
||||||
|
@ -457,7 +471,6 @@ void mat3Minor(mat3 out, mat3 in) {
|
||||||
result[4] = in[0] * in[8] - in[2] * in[6];
|
result[4] = in[0] * in[8] - in[2] * in[6];
|
||||||
result[5] = in[0] * in[7] - in[1] * in[6];
|
result[5] = in[0] * in[7] - in[1] * in[6];
|
||||||
|
|
||||||
|
|
||||||
result[6] = in[1] * in[5] - in[2] * in[4];
|
result[6] = in[1] * in[5] - in[2] * in[4];
|
||||||
result[7] = in[0] * in[5] - in[2] * in[3];
|
result[7] = in[0] * in[5] - in[2] * in[3];
|
||||||
result[8] = in[0] * in[4] - in[1] * in[3];
|
result[8] = in[0] * in[4] - in[1] * in[3];
|
||||||
|
|
|
@ -9,10 +9,12 @@
|
||||||
|
|
||||||
typedef GLfloat vec4[4];
|
typedef GLfloat vec4[4];
|
||||||
typedef GLfloat vec3[3];
|
typedef GLfloat vec3[3];
|
||||||
|
typedef GLfloat vec2[2];
|
||||||
|
|
||||||
typedef GLfloat mat4[16];
|
typedef GLfloat mat4[16];
|
||||||
typedef GLfloat mat3[9];
|
typedef GLfloat mat3[9];
|
||||||
|
|
||||||
|
|
||||||
extern void mat4Identity(mat4 mat);
|
extern void mat4Identity(mat4 mat);
|
||||||
extern void mat4Copy(mat4 src, mat4 dst);
|
extern void mat4Copy(mat4 src, mat4 dst);
|
||||||
extern void mat4Empty(mat4 mat);
|
extern void mat4Empty(mat4 mat);
|
||||||
|
@ -36,6 +38,9 @@ extern void vec3Normalise(vec3 out, vec3 in);
|
||||||
extern GLfloat vec3Length(vec3 in);
|
extern GLfloat vec3Length(vec3 in);
|
||||||
extern GLfloat vec3DotProduct(vec3 a, vec3 b);
|
extern GLfloat vec3DotProduct(vec3 a, vec3 b);
|
||||||
extern void vec3Set(vec3 out, GLfloat x, GLfloat y, GLfloat z);
|
extern void vec3Set(vec3 out, GLfloat x, GLfloat y, GLfloat z);
|
||||||
|
extern void vec3Multiply(vec3 out, vec3 in, GLfloat x);
|
||||||
|
|
||||||
|
extern void vec2Subtract(vec2 out, vec2 a, vec2 b);
|
||||||
|
|
||||||
extern void mat3Copy(mat3 src, mat3 dst);
|
extern void mat3Copy(mat3 src, mat3 dst);
|
||||||
extern void mat3Inverse(mat3 out, mat3 in);
|
extern void mat3Inverse(mat3 out, mat3 in);
|
||||||
|
|
|
@ -1,15 +1,6 @@
|
||||||
#version 330 core
|
#version 330 core
|
||||||
vec3 colors[6] = vec3[6](
|
in vec3 vNormal;
|
||||||
vec3(1.0, 0.5, 0.5),
|
|
||||||
vec3(0.5, 1.0, 0.5),
|
|
||||||
vec3(0.5, 0.5, 1.0),
|
|
||||||
vec3(1.0, 1.0, 0.5),
|
|
||||||
vec3(1.0, 0.5, 1.0),
|
|
||||||
vec3(0.5, 1.0, 1.0)
|
|
||||||
);
|
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
// hacky solution to give each side a different colour
|
gl_FragColor = vec4(vNormal * 0.5 + vec3(0.5), 1.0);
|
||||||
int side = gl_PrimitiveID / 2;
|
|
||||||
gl_FragColor = vec4(colors[side], 1.0);
|
|
||||||
}
|
}
|
|
@ -1,8 +1,12 @@
|
||||||
#version 330 core
|
#version 330 core
|
||||||
layout (location = 0) in vec3 aPosition;
|
layout (location = 0) in vec3 aPosition;
|
||||||
|
layout (location = 1) in vec3 aNormal;
|
||||||
uniform mat4 uModelView;
|
uniform mat4 uModelView;
|
||||||
uniform mat4 uProjection;
|
uniform mat4 uProjection;
|
||||||
|
|
||||||
|
out vec3 vNormal;
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
|
vNormal = aNormal;
|
||||||
gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);
|
gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);
|
||||||
}
|
}
|
|
@ -0,0 +1,242 @@
|
||||||
|
#include <GL/glew.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "wavefrontobj.h"
|
||||||
|
|
||||||
|
#define OBJ_LINE_BUFFER_SIZE 256
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* ADJUSTMENT NEEDED FOR
|
||||||
|
* - Face Definitions other than vertex/texture/normal
|
||||||
|
* - Vertex positions including w
|
||||||
|
* - Any faces using vertices yet to be defined
|
||||||
|
* (File is read top to bottom. A face using a vertex
|
||||||
|
* defined underneath it in the file will not work)
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
void storeFace(
|
||||||
|
face* f,
|
||||||
|
vec3 v1, vec2 vt1, vec3 vn1,
|
||||||
|
vec3 v2, vec2 vt2, vec3 vn2,
|
||||||
|
vec3 v3, vec2 vt3, vec3 vn3
|
||||||
|
) {
|
||||||
|
|
||||||
|
memcpy(&f->v1.position, v1, sizeof(vec3));
|
||||||
|
memcpy(&f->v2.position, v2, sizeof(vec3));
|
||||||
|
memcpy(&f->v3.position, v3, sizeof(vec3));
|
||||||
|
|
||||||
|
memcpy(&f->v1.normal, vn1, sizeof(vec3));
|
||||||
|
memcpy(&f->v2.normal, vn2, sizeof(vec3));
|
||||||
|
memcpy(&f->v3.normal, vn3, sizeof(vec3));
|
||||||
|
|
||||||
|
memcpy(&f->v1.texture, vt1, sizeof(vec2));
|
||||||
|
memcpy(&f->v2.texture, vt2, sizeof(vec2));
|
||||||
|
memcpy(&f->v3.texture, vt3, sizeof(vec2));
|
||||||
|
}
|
||||||
|
|
||||||
|
// void storeTB(face* f,
|
||||||
|
// vec3 v1, vec2 vt1, vec3 vn1,
|
||||||
|
// vec3 v2, vec2 vt2, vec3 vn2,
|
||||||
|
// vec3 v3, vec2 vt3, vec3 vn3
|
||||||
|
// ) {
|
||||||
|
// // https://www.opengl-tutorial.org/intermediate-tutorials/tutorial-13-normal-mapping/
|
||||||
|
// vec3 deltaPos1;
|
||||||
|
// vec3 deltaPos2;
|
||||||
|
|
||||||
|
// vec3Subtract(deltaPos1, v2, v1);
|
||||||
|
// vec3Subtract(deltaPos1, v3, v1);
|
||||||
|
|
||||||
|
// vec2 deltaTex1;
|
||||||
|
// vec2 deltaTex2;
|
||||||
|
|
||||||
|
// vec2Subtract(deltaTex1, vt2, vt1);
|
||||||
|
// vec2Subtract(deltaTex2, vt3, vt1);
|
||||||
|
|
||||||
|
// GLfloat r = 1.0f / (deltaTex1[0] * deltaTex2[1] - deltaTex1[1] * deltaTex2[0]);
|
||||||
|
|
||||||
|
// vec3Multiply(deltaPos1, deltaPos1, deltaTex2[1]);
|
||||||
|
// vec3Multiply(deltaPos2, deltaPos2, deltaTex1[1]);
|
||||||
|
|
||||||
|
// vec3 tangent;
|
||||||
|
// vec3Subtract(tangent, deltaPos1, deltaPos2);
|
||||||
|
// vec3Multiply(tangent, tangent, r);
|
||||||
|
|
||||||
|
// memcpy(&f->v1.tangent, &tangent, sizeof(vec3));
|
||||||
|
// memcpy(&f->v2.tangent, &tangent, sizeof(vec3));
|
||||||
|
// memcpy(&f->v3.tangent, &tangent, sizeof(vec3));
|
||||||
|
// }
|
||||||
|
|
||||||
|
ParsedObjFile readObjFile(char* path) {
|
||||||
|
ParsedObjFile parsedFile;
|
||||||
|
|
||||||
|
FILE* fp = fopen(path, "r");
|
||||||
|
|
||||||
|
if (fp == NULL) {
|
||||||
|
fprintf(stderr, "File could not be opened: %s", path);
|
||||||
|
parsedFile.faces = NULL;
|
||||||
|
parsedFile.length = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint numVertices = 0;
|
||||||
|
uint numVertexNormals = 0;
|
||||||
|
uint numFaces = 0;
|
||||||
|
uint numTextureCoords = 0;
|
||||||
|
|
||||||
|
char buf[OBJ_LINE_BUFFER_SIZE];
|
||||||
|
|
||||||
|
while (fgets(buf, OBJ_LINE_BUFFER_SIZE, fp)) {
|
||||||
|
if (buf[0] == 'v') {
|
||||||
|
if (buf[1] == ' ') {
|
||||||
|
numVertices++;
|
||||||
|
} else if (buf[1] == 't') {
|
||||||
|
numTextureCoords++;
|
||||||
|
} else if (buf[1] == 'n') {
|
||||||
|
numVertexNormals++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (buf[0] == 'f') {
|
||||||
|
int numSpaces = 0;
|
||||||
|
for (int i = 0; i < strlen(buf); i++) {
|
||||||
|
if (buf[i] == ' ') {
|
||||||
|
numSpaces++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
numFaces += numSpaces - 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// printf("Vertices: %d\nFaces: %d\nNormals:%d\nTextures:%d\n", numVertices, numFaces, numVertexNormals, numTextureCoords);
|
||||||
|
|
||||||
|
vec3* vertices = (vec3*) malloc(sizeof(vec3) * numVertices);
|
||||||
|
vec3* normals = (vec3*) malloc(sizeof(vec3) * numVertexNormals);
|
||||||
|
|
||||||
|
vec2* textures = (vec2*) malloc(sizeof(vec2) * numTextureCoords);
|
||||||
|
|
||||||
|
face* faces = (face*) malloc(sizeof(face) * numFaces);
|
||||||
|
|
||||||
|
parsedFile.faces = faces;
|
||||||
|
parsedFile.length = numFaces;
|
||||||
|
|
||||||
|
rewind(fp);
|
||||||
|
|
||||||
|
uint curVertex = 0;
|
||||||
|
uint curNormal = 0;
|
||||||
|
uint curFace = 0;
|
||||||
|
uint curTexture = 0;
|
||||||
|
|
||||||
|
while (fgets(buf, OBJ_LINE_BUFFER_SIZE, fp)) {
|
||||||
|
if (buf[0] == 'v') {
|
||||||
|
if (buf[1] == ' ') {
|
||||||
|
|
||||||
|
sscanf(buf,
|
||||||
|
"v %f %f %f",
|
||||||
|
&vertices[curVertex][0],
|
||||||
|
&vertices[curVertex][1],
|
||||||
|
&vertices[curVertex][2]
|
||||||
|
);
|
||||||
|
curVertex++;
|
||||||
|
|
||||||
|
} else if (buf[1] == 't') {
|
||||||
|
|
||||||
|
int readValues = sscanf(buf,
|
||||||
|
"vt %f %f",
|
||||||
|
&textures[curTexture][0],
|
||||||
|
&textures[curTexture][1]
|
||||||
|
);
|
||||||
|
|
||||||
|
if (readValues != 2) {
|
||||||
|
textures[curTexture][1] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
curTexture++;
|
||||||
|
|
||||||
|
|
||||||
|
} else if (buf[1] == 'n') {
|
||||||
|
|
||||||
|
sscanf(buf,
|
||||||
|
"vn %f %f %f",
|
||||||
|
&normals[curNormal][0],
|
||||||
|
&normals[curNormal][1],
|
||||||
|
&normals[curNormal][2]
|
||||||
|
);
|
||||||
|
curNormal++;
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (buf[0] == 'f') {
|
||||||
|
int v1, v2, v3;
|
||||||
|
int vt1, vt2, vt3;
|
||||||
|
int vn1, vn2, vn3;
|
||||||
|
|
||||||
|
sscanf(buf,
|
||||||
|
"f %d/%d/%d %d/%d/%d %d/%d/%d",
|
||||||
|
&v1, &vt1, &vn1,
|
||||||
|
&v2, &vt2, &vn2,
|
||||||
|
&v3, &vt3, &vn3
|
||||||
|
);
|
||||||
|
|
||||||
|
storeFace(&faces[curFace],
|
||||||
|
vertices[v1 - 1], textures[vt1 - 1], normals[vn1 - 1],
|
||||||
|
vertices[v2 - 1], textures[vt2 - 1], normals[vn2 - 1],
|
||||||
|
vertices[v3 - 1], textures[vt3 - 1], normals[vn3 - 1]
|
||||||
|
);
|
||||||
|
|
||||||
|
// storeTB(&faces[curFace],
|
||||||
|
// vertices[v1 - 1], textures[vt1 - 1], normals[vn1 - 1],
|
||||||
|
// vertices[v2 - 1], textures[vt2 - 1], normals[vn2 - 1],
|
||||||
|
// vertices[v3 - 1], textures[vt3 - 1], normals[vn3 - 1]
|
||||||
|
// );
|
||||||
|
|
||||||
|
curFace++;
|
||||||
|
|
||||||
|
int numSpaces = 0;
|
||||||
|
for (int i = 0; i < strlen(buf); i++) {
|
||||||
|
if (buf[i] == ' ') {
|
||||||
|
numSpaces++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (numSpaces == 4) {
|
||||||
|
// storeTB(&faces[curFace],
|
||||||
|
// vertices[v1 - 1], textures[vt1 - 1], normals[vn1 - 1],
|
||||||
|
// vertices[v2 - 1], textures[vt2 - 1], normals[vn2 - 1],
|
||||||
|
// vertices[v3 - 1], textures[vt3 - 1], normals[vn3 - 1]
|
||||||
|
// );
|
||||||
|
|
||||||
|
sscanf(buf,
|
||||||
|
"f %d/%d/%d %*d/%*d/%*d %d/%d/%d %d/%d/%d",
|
||||||
|
&v1, &vt1, &vn1,
|
||||||
|
&v2, &vt2, &vn2,
|
||||||
|
&v3, &vt3, &vn3
|
||||||
|
);
|
||||||
|
|
||||||
|
storeFace(&faces[curFace],
|
||||||
|
vertices[v1 - 1], textures[vt1 - 1], normals[vn1 - 1],
|
||||||
|
vertices[v2 - 1], textures[vt2 - 1], normals[vn2 - 1],
|
||||||
|
vertices[v3 - 1], textures[vt3 - 1], normals[vn3 - 1]
|
||||||
|
);
|
||||||
|
|
||||||
|
curFace++;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// TODO: textures
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
free(vertices);
|
||||||
|
free(normals);
|
||||||
|
fclose(fp);
|
||||||
|
|
||||||
|
return parsedFile;
|
||||||
|
}
|
||||||
|
|
||||||
|
void clearParsedFile(ParsedObjFile file) {
|
||||||
|
free(file.faces);
|
||||||
|
}
|
|
@ -0,0 +1,30 @@
|
||||||
|
#ifndef WAVEFRONTOBJ_H
|
||||||
|
#define WAVEFRONTOBJ_H
|
||||||
|
|
||||||
|
#include <GL/glew.h>
|
||||||
|
#include "matrix-math.h"
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
vec3 position;
|
||||||
|
vec3 normal;
|
||||||
|
vec2 texture;
|
||||||
|
// vec3 tangent;
|
||||||
|
} vertex;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
vertex v1;
|
||||||
|
vertex v2;
|
||||||
|
vertex v3;
|
||||||
|
} face;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
face* faces;
|
||||||
|
GLuint length;
|
||||||
|
} ParsedObjFile;
|
||||||
|
|
||||||
|
|
||||||
|
extern ParsedObjFile readObjFile(char* path);
|
||||||
|
extern void clearParsedFile(ParsedObjFile file);
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
Loading…
Reference in New Issue