I have written an OBJ/MTL parser and I’m trying to render an object.
The problem is that some textures are misaligned/askew and I have no idea why. On some textures it seems fine, however on others, it does not – it looks as if the texture coordinates are outside the [0, 1] range, which I’m told is fine, as in some cases it should do clamp/wrap; however it seems as if this takes place when it shouldn’t.
I have verified that the data contained in my data structures is correct as loaded from the OBJ and MTL file.
I have verified that the OBJ file can be rendered without the artifacts I see in my program – I used dhpoware’s renderer for this.
EDIT: Of interest is perhaps that all textures are not only upside down (which I why I use the negative u and v values to correct for this) but also laterally reversed – i.e. mirrored. Could this be part of the solution to why I’m getting the other problems with the textures being askew and misaligned?
for(int i = 0; i < obj_data1.num_faces; i++) {
if(mtl_data1.textures[obj_data1.faces[i]->material_index]->hasTexture) {
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, mtl_data1.textures[obj_data1.faces[i]->material_index]->texture_ID[0]);
textures_enabled = 1;
}
else {
if(textures_enabled) {
glDisable(GL_TEXTURE_2D);
textures_enabled = 0;
}
}
if(wrld.model_lighting) {
glMaterialfv(GL_FRONT, GL_AMBIENT, mtl_data1.textures[obj_data1.faces[i]->material_index]->Ka);
glMaterialfv(GL_FRONT, GL_DIFFUSE, mtl_data1.textures[obj_data1.faces[i]->material_index]->Kd);
glMaterialfv(GL_FRONT, GL_SPECULAR, mtl_data1.textures[obj_data1.faces[i]->material_index]->Ks);
}
glBegin(GL_TRIANGLES);
for(int j = 0; j < obj_data1.faces[i]->length; j += 3) {
glNormal3f(obj_data1.normals[obj_data1.faces[i]->indices[j + 2] - 1].x, obj_data1.normals[obj_data1.faces[i]->indices[j + 2] - 1].y, obj_data1.normals[obj_data1.faces[i]->indices[j + 2] - 1].z);
if(mtl_data1.textures[obj_data1.faces[i]->material_index]->hasTexture) {
glTexCoord2f(-obj_data1.texture_coordinates[obj_data1.faces[i]->indices[j + 1] - 1].u, -obj_data1.texture_coordinates[obj_data1.faces[i]->indices[j + 1] - 1].v);
}
glVertex3f(obj_data1.vertices[obj_data1.faces[i]->indices[j] - 1].x, obj_data1.vertices[obj_data1.faces[i]->indices[j] - 1].y, obj_data1.vertices[obj_data1.faces[i]->indices[j] - 1].z);
}
glEnd();
}
Does this approach seem to be the right idea? Am I missing something crucial and simple?
If it helps, my structs are:
struct vector {
double x;
double y;
double z;
};
struct vertex {
double x;
double y;
double z;
};
struct texture_coordinate {
double u;
double v;
};
struct texture {
int width;
int height;
char filename[MAX_FILENAME_LENGTH];
char name[MAX_FILENAME_LENGTH];
float Ka[4]; // Ambient
float Kd[4]; // Diffuse
float Ks[4]; // Specular
unsigned int texture_ID[1];
_Bool hasTexture;
};
struct face {
int *indices;
int length;
int material_index;
struct texture text;
};
struct objdata {
int num_vertices;
struct vertex *vertices;
int num_normals;
struct vector *normals;
int num_texture_coordinates;
struct texture_coordinate *texture_coordinates;
double max_vt;
double min_vt;
int num_faces;
struct face **faces;
float translation_x;
float translation_y;
float translation_z;
float rotations_x;
float rotations_y;
float rotations_z;
};
struct mtldata {
int num_textures;
int index;
struct texture **textures;
};