Текстурирование текстур загрузки с синим цветом не является фактическим цветом
Метод загрузки:
bool TextureManager::LoadBMP(const char *path, unsigned int &texture)
{
std::fstream hFile(path, std::ios::in | std::ios::binary);
if (!hFile.is_open())
{
throw std::invalid_argument("Error: File Not Found.");
return false;
}
hFile.seekg(0, std::ios::end);
int Length = hFile.tellg();
hFile.seekg(0, std::ios::beg);
std::vector<uint8_t> FileInfo(Length);
hFile.read(reinterpret_cast<char*>(FileInfo.data()), 54);
if (FileInfo[0] != 'B' && FileInfo[1] != 'M')
{
hFile.close();
throw std::invalid_argument("Error: Invalid File Format. Bitmap Required.");
return false;
}
if (FileInfo[28] != 24 && FileInfo[28] != 32)
{
hFile.close();
throw std::invalid_argument("Error: Invalid File Format. 24 or 32 bit Image Required.");
return false;
}
short BitsPerPixel = FileInfo[28];
int width = FileInfo[18] + (FileInfo[19] << 8);
int height = FileInfo[22] + (FileInfo[23] << 8);
uint32_t PixelsOffset = FileInfo[10] + (FileInfo[11] << 8);
uint32_t size = ((width * BitsPerPixel + 31) / 32) * 4 * height;
std::vector<unsigned char> Pixels(size);
hFile.seekg(PixelsOffset, std::ios::beg);
hFile.read(reinterpret_cast<char*>(Pixels.data()), size);
hFile.close();
/*******************GENERATING TEXTURES*******************/
glGenTextures(1, &texture); // Generate a texture
glBindTexture(GL_TEXTURE_2D, texture); // Bind that texture temporarily
GLint mode = GL_RGB; // Set the mode
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
// Create the texture. We get the offsets from the image, then we use it with the image's
// pixel data to create it.
glTexImage2D(GL_TEXTURE_2D, 0, mode, width, height, 0, mode, GL_UNSIGNED_BYTE, Pixels.data());
// Unbind the texture
glBindTexture(GL_TEXTURE_2D, NULL);
// Output a successful message
std::cout << "Texture \"" << path << "\" successfully loaded.\n";
return true; // Return success code
}
Метод рендеринга:
void Game::Render()
{
glLoadIdentity();
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, TextureID);
glUniform1i(glGetUniformLocation(program->Id, "img"), 0);
glBegin(GL_QUADS);
glTexCoord2f(1, 0); //gl_MultiTexCoord0
glVertex3f(-1, 1, -4); //gl_Vertex
glTexCoord2f(0, 0);
glVertex3f(-1, -1, -4);
glTexCoord2f(0, 1);
glVertex3f(1, -1, -4);
glTexCoord2f(1, 1);
glVertex3f(1, 1, -4);
glEnd();
}
вершинный шейдер:
#version 120
uniform vec3 color;
varying vec2 texcoord;
void main()
{
gl_Position=gl_ModelViewProjectionMatrix*gl_Vertex;
texcoord=gl_MultiTexCoord0.xy;
}
фрагментарный шейдер:
#version 120
uniform sampler2D img;
varying vec2 texcoord;
void main()
{
vec4 texcolor=texture2D(img,texcoord);
gl_FragColor=texcolor;
}
фактическая текстура:
мой результат вывода:
Ваши красные и синие каналы обмениваются файлом изображения.
GLint pixel_mode = GL_BGR; // Image File
GLint internal_mode = GL_RGB; // OpenGL
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
// Create the texture. We get the offsets from the image, then we use it with the image's
// pixel data to create it.
glTexImage2D(GL_TEXTURE_2D, 0, internal_mode, width, height, 0, pixel_mode, GL_UNSIGNED_BYTE, Pixels.data());
.bmp
(DIB). Формат файла хранит 24-битные данные RGB следующим образом: 0xRRGGBB
. Это означает, что синий является наименее значимым байтом, а красный - наиболее значимым, что фактически противоположно тому, что ожидает OpenGL ( 0xBBGGRR
) при использовании GL_RGB
. Если вы скажете GL, что данные изображения, которые вы предоставляете, хранятся в порядке BGR (как я показал), то это не имеет большого значения.
height
. Отрицательный означает порядок сканирования снизу вверх.