diff --git a/include/Model.h b/include/Model.h index 901f2c0..353f567 100644 --- a/include/Model.h +++ b/include/Model.h @@ -99,6 +99,8 @@ class Model : public Node Texture texture_diffuse; // Диффузная текстура Texture texture_ambient; // Текстура фонового освщения Texture texture_specular; // Текстура зеркального отражения + Texture texture_heights; // Текстура высот + Texture texture_normals; // Текстура нормалей }; #endif // MODEL_H diff --git a/include/Texture.h b/include/Texture.h index 17d30cc..0aa2a95 100644 --- a/include/Texture.h +++ b/include/Texture.h @@ -10,6 +10,8 @@ enum TexType { TEX_DIFFUSE, TEX_AMBIENT, TEX_SPECULAR, + TEX_HEIGHTS, + TEX_NORMAL, TEX_AVAILABLE_COUNT }; diff --git a/src/Model.cpp b/src/Model.cpp index 86a4954..3f874cc 100644 --- a/src/Model.cpp +++ b/src/Model.cpp @@ -215,6 +215,7 @@ verteces_count(copy.verteces_count), first_index_byteOffset(copy.first_index_byt vertex_vbo(copy.vertex_vbo), index_vbo(copy.index_vbo), normals_vbo(copy.normals_vbo), texCoords_vbo(copy.texCoords_vbo), tangent_vbo(copy.tangent_vbo), bitangent_vbo(copy.bitangent_vbo), texture_diffuse(copy.texture_diffuse), texture_ambient(copy.texture_ambient), texture_specular(copy.texture_specular), +texture_heights(copy.texture_heights), texture_normals(copy.texture_normals), material(copy.material) { @@ -241,6 +242,9 @@ Model& Model::operator=(const Model& other) texture_ambient = other.texture_ambient; texture_specular = other.texture_specular; + texture_heights = other.texture_heights; + texture_normals = other.texture_normals; + material = other.material; return *this; @@ -277,7 +281,8 @@ void Model::render(ShaderProgram &shaderProgram, UBO &material_buffer) texture_diffuse.use(); texture_ambient.use(); texture_specular.use(); - + texture_heights.use(); + texture_normals.use(); // Загружаем данные о материале material_buffer.load(&material, sizeof(material)); @@ -405,6 +410,12 @@ void Model::set_texture(Texture& texture) case TEX_SPECULAR: texture_specular = texture; break; + case TEX_HEIGHTS: + texture_heights = texture; + break; + case TEX_NORMAL: + texture_normals = texture; + break; }; } diff --git a/src/Scene.cpp b/src/Scene.cpp index 7693945..c0a51fa 100644 --- a/src/Scene.cpp +++ b/src/Scene.cpp @@ -222,6 +222,10 @@ Scene loadOBJtoScene(const char* filename, const char* mtl_directory, const char s->set_texture(ambient); Texture specular(TEX_SPECULAR, texture_directory + materials[materials_ids[i]].specular_texname); s->set_texture(specular); + Texture normal(TEX_NORMAL, texture_directory + materials[materials_ids[i]].normal_texname); + s->set_texture(normal); + Texture heights(TEX_HEIGHTS, texture_directory + materials[materials_ids[i]].bump_texname); + s->set_texture(heights); // Материал s->material.ka = pow(glm::vec3(materials[materials_ids[i]].ambient[0], materials[materials_ids[i]].ambient[1], materials[materials_ids[i]].ambient[2]), glm::vec3(1/inv_gamma)); diff --git a/src/Texture.cpp b/src/Texture.cpp index 28817ae..f48cb45 100644 --- a/src/Texture.cpp +++ b/src/Texture.cpp @@ -28,11 +28,34 @@ Texture::Texture(GLuint t, const std::string& filename) // Если изображение успешно считано if (image) { - // Загрузка данных с учетом прозрачности - if (channels == 3) // RGB - glTexImage2D(GL_TEXTURE_2D, 0, GL_SRGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, image); - else if (channels == 4) // RGBA - glTexImage2D(GL_TEXTURE_2D, 0, GL_SRGB_ALPHA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, image); + // Выбор формата с учетом типа текстуры (нормали не sRGB) и числа каналов + GLuint internalformat = GL_RGB, format = GL_RGB; + switch (channels) + { + case 1: + internalformat = format = GL_RED; + break; + case 2: + internalformat = format = GL_RG; + break; + case 3: + format = GL_RGB; + if (type == TEX_NORMAL || type == TEX_HEIGHTS) + internalformat = GL_RGB; + else + internalformat = GL_SRGB; + break; + case 4: + format = GL_RGBA; + if (type == TEX_NORMAL || type == TEX_HEIGHTS) + internalformat = GL_RGBA; + else + internalformat = GL_SRGB_ALPHA; + break; + + } + // Загрузка данных с учетом формата + glTexImage2D(GL_TEXTURE_2D, 0, internalformat, width, height, 0, format, GL_UNSIGNED_BYTE, image); glGenerateMipmap(GL_TEXTURE_2D); // Генерация мипмапа для активной текстуры glBindTexture(GL_TEXTURE_2D, 0); // Отвязка активной текстуры @@ -253,11 +276,34 @@ TextureCube::TextureCube(GLuint t, const std::string (&filename)[6]) // Если изображение успешно считано if (image) { - // Загрузка данных с учетом прозрачности - if (channels == 3) // RGB - glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_SRGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, image); - else if (channels == 4) // RGBA - glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_SRGB_ALPHA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, image); + // Выбор формата с учетом типа текстуры (нормали не sRGB) и числа каналов + GLuint internalformat = GL_RGB, format = GL_RGB; + switch (channels) + { + case 1: + internalformat = format = GL_RED; + break; + case 2: + internalformat = format = GL_RG; + break; + case 3: + format = GL_RGB; + if (type == TEX_NORMAL || type == TEX_HEIGHTS) + internalformat = GL_RGB; + else + internalformat = GL_SRGB; + break; + case 4: + format = GL_RGBA; + if (type == TEX_NORMAL || type == TEX_HEIGHTS) + internalformat = GL_RGBA; + else + internalformat = GL_SRGB_ALPHA; + break; + + } + // Загрузка данных с учетом формата + glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, internalformat, width, height, 0, format, GL_UNSIGNED_BYTE, image); stbi_image_free(image); // Освобождение оперативной памяти } diff --git a/src/main.cpp b/src/main.cpp index 93ac2f6..ab8f7e3 100755 --- a/src/main.cpp +++ b/src/main.cpp @@ -130,7 +130,7 @@ int main(void) gShader.load(GL_FRAGMENT_SHADER, "shaders/gshader.frag"); gShader.link(); // Установим значения текстур - const char* textures_base_shader_names[] = {"tex_diffuse", "tex_ambient", "tex_specular"}; + const char* textures_base_shader_names[] = {"tex_diffuse", "tex_ambient", "tex_specular", "tex_heights", "tex_normal"}; gShader.bindTextures(textures_base_shader_names, sizeof(textures_base_shader_names)/sizeof(const char*)); // Загрузка сцены из obj файла