wfobj/WFObj.h
2011-04-24 23:28:53 -04:00

121 lines
3.0 KiB
C++

#ifndef WFOBJ_H
#define WFOBJ_H
#include <GL/gl.h>
#include <vector>
#include <string>
#include <map>
class WFObj
{
public:
/* types */
class Buffer
{
public:
Buffer() : m_alloc(false) {}
~Buffer() { if (m_alloc) delete data; }
uint8_t *data;
size_t length;
void alloc(size_t sz)
{
length = sz;
data = new uint8_t[sz];
m_alloc = true;
}
protected:
bool m_alloc;
};
typedef bool (*loadfile_t)(const char *fname, Buffer & buff);
typedef GLuint (*loadtexture_t)(const char *fname);
enum { VERTEX, VERTEX_TEXTURE, VERTEX_NORMAL, VERTEX_TYPES };
/* constructors */
WFObj(loadfile_t lf = NULL, loadtexture_t lt = NULL);
~WFObj();
/* methods */
bool load(const char *fname);
bool load(const Buffer &buff);
const float * const getAABB() { return m_aabb; }
void draw();
protected:
/* types */
class Vertex
{
public:
float operator[](int idx) const { return data[idx]; }
float & operator[](int idx) { return data[idx]; }
float * getData() { return data; }
private:
float data[4];
};
class VertexRef
{
public:
VertexRef() : vertex(0), texture(0), normal(0) {}
int vertex;
int texture;
int normal;
bool operator<(const VertexRef & other) const;
};
class Face
{
public:
VertexRef vertices[3];
};
class Material
{
public:
enum {
MAT_SHININESS = 0x01,
MAT_AMBIENT = 0x02,
MAT_DIFFUSE = 0x04,
MAT_SPECULAR = 0x08,
MAT_TEXTURE = 0x10
};
Material() : flags(0) {}
GLfloat shininess;
GLfloat ambient[4];
GLfloat diffuse[4];
GLfloat specular[4];
std::string texture;
int flags;
};
/* methods */
void clear();
void processInputLine(const std::string & input);
Vertex readVertex(const std::vector<std::string> & parts);
std::vector<Face> readFaces(const std::vector<std::string> & parts);
VertexRef readVertexRef(const std::string ref);
void updateAABB();
static bool loadfile(const char *path, Buffer & buff);
std::string getLine(const Buffer & buff, size_t idx, size_t *update_idx);
void loadMaterial(const std::string & name);
bool buildVBO();
void renderMaterial(const Material & m);
/* variables */
std::vector<Vertex> m_vertices[VERTEX_TYPES];
std::map< std::string, std::vector< Face > > m_faces;
std::map< std::string, std::pair<int, int> > m_face_indices;
std::map< std::string, Material > m_materials;
float m_aabb[6];
std::string m_path;
loadfile_t m_loadfile;
loadtexture_t m_loadtexture;
std::string m_current_material_name;
bool m_valid;
GLuint m_data_vbo, m_index_vbo;
};
#endif