6#include <brenta/logger.hpp>
7#include <brenta/model.hpp>
10using namespace brenta;
18 GL_LINEAR_MIPMAP_LINEAR,
25 this->wrapping = conf.wrapping;
26 this->filtering_min = conf.filtering_min;
27 this->filtering_mag = conf.filtering_mag;
28 this->has_mipmap = conf.has_mipmap;
29 this->mipmap_min = conf.mipmap_min;
30 this->mipmap_mag = conf.mipmap_mag;
31 this->flip = conf.flip;
32 load_model(conf.path);
35void model::draw(types::shader_name_t
shader)
37 for (
unsigned int i = 0; i < meshes.size(); i++)
43void model::load_model(std::string path)
46 Assimp::Importer importer;
47 const aiScene *scene =
48 importer.ReadFile(path, aiProcess_Triangulate | aiProcess_FlipUVs);
50 if (!scene || scene->mFlags & AI_SCENE_FLAGS_INCOMPLETE || !scene->mRootNode)
52 ERROR(
"model::load_model: Could not load model with assimp: {}",
53 importer.GetErrorString());
56 directory = path.substr(0, path.find_last_of(
'/'));
58 process_node(scene->mRootNode, scene);
61void model::process_node(aiNode *node,
const aiScene *scene)
63 for (
unsigned int i = 0; i < node->mNumMeshes; i++)
65 aiMesh *m = scene->mMeshes[node->mMeshes[i]];
66 meshes.push_back(process_mesh(m, scene));
68 for (
unsigned int i = 0; i < node->mNumChildren; i++)
70 process_node(node->mChildren[i], scene);
74mesh model::process_mesh(aiMesh *m,
const aiScene *scene)
76 std::vector<types::vertex> vertices;
77 std::vector<unsigned int> indices;
78 std::vector<types::texture> textures;
80 for (
unsigned int i = 0; i < m->mNumVertices; i++)
84 vector.x = m->mVertices[i].x;
85 vector.y = m->mVertices[i].y;
86 vector.z = m->mVertices[i].z;
87 vertex.position = vector;
89 vector.x = m->mNormals[i].x;
90 vector.y = m->mNormals[i].y;
91 vector.z = m->mNormals[i].z;
92 vertex.normal = vector;
94 if (m->mTextureCoords[0])
97 vec.x = m->mTextureCoords[0][i].x;
98 vec.y = m->mTextureCoords[0][i].y;
99 vertex.tex_coords = vec;
102 vertex.tex_coords = glm::vec2(0.0f, 0.0f);
104 vertices.push_back(vertex);
107 for (
unsigned int i = 0; i < m->mNumFaces; i++)
109 aiFace face = m->mFaces[i];
110 for (
unsigned int j = 0; j < face.mNumIndices; j++)
111 indices.push_back(face.mIndices[j]);
114 aiMaterial *material = scene->mMaterials[m->mMaterialIndex];
115 std::vector<types::texture> diffuseMaps =
116 load_material_textures(material, aiTextureType_DIFFUSE,
"texture_diffuse");
117 textures.insert(textures.end(), diffuseMaps.begin(), diffuseMaps.end());
118 std::vector<types::texture> specularMaps = load_material_textures(
119 material, aiTextureType_SPECULAR,
"texture_specular");
120 textures.insert(textures.end(), specularMaps.begin(), specularMaps.end());
122 return mesh({vertices, indices, textures, this->wrapping, this->filtering_min,
123 this->filtering_mag, this->has_mipmap, this->mipmap_min,
127std::vector<types::texture> model::load_material_textures(aiMaterial *mat,
129 std::string typeName)
131 std::vector<types::texture> textures;
132 for (
unsigned int i = 0; i < mat->GetTextureCount(type); i++)
135 mat->GetTexture(type, i, &str);
137 for (
unsigned int j = 0; j < textures_loaded.size(); j++)
139 if (std::strcmp(textures_loaded[j].path.c_str(), str.C_Str()) == 0)
141 textures.push_back(textures_loaded[j]);
149 std::string path = directory +
"/" + std::string(str.C_Str());
154 textures_loaded.push_back(
texture);
166 this->conf.path = path;
172 this->conf.wrapping = wrapping;
178 this->conf.filtering_min = filtering_min;
184 this->conf.filtering_mag = filtering_mag;
190 this->conf.has_mipmap = has_mipmap;
196 this->conf.mipmap_min = mipmap_min;
202 this->conf.mipmap_mag = mipmap_mag;
208 this->conf.flip = flip;
212model model::builder::build()
214 return model(this->conf);
The Mesh class represents a 3D model.
model()
Empty constructor.
static unsigned int load_texture(std::string path, bool flip=true)
Load a texture from a file.
The Texture struct represents a texture of a 3D model.
The Vertex struct represents a vertex of a 3D model.