我是OpenGL的新手,在熟悉基本形状的渲染后,我决定学习如何添加纹理,快速谷歌搜索给了我SOIL库。我决定通过将一个纹理应用到填充窗口的四边形来开始简单。这是我的代码:
#include <stdlib.h>
#include <stdio.h>
#include <GL/gl.h>
#include <GL/glu.h>
#include <GL/glut.h>
#include <SOIL/SOIL.h>
#define WIDTH 0x320
#define HEIGHT 0x258
#define INIT_X 0
#define INIT_Y 0
GLuint texture;
GLuint glInitTexture(char* filename)
{
FILE* f = NULL;
f = fopen(filename, "r");
if(f == NULL)
{
fprintf(stderr, "cannot load file %s!", filename);
exit(1);
}
GLuint t = SOIL_load_OGL_texture(filename, SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, SOIL_FLAG_MIPMAPS);
glBindTexture(GL_TEXTURE_2D, t);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
return t;
}
void init()
{
glClearColor(1.0f, 1.0f, 1.0f, 1.0f);
glEnable(GL_DEPTH_TEST);
glEnable(GL_TEXTURE_2D);
texture = glInitTexture("image.png");
}
void drawImage(GLuint file,
float x,
float y,
float w,
float h,
float angle)
{
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
glPushMatrix();
glTranslatef(x, y, 0.0);
glRotatef(angle, 0.0, 0.0, 1.0);
glBindTexture(GL_TEXTURE_2D, file);
glBegin(GL_QUADS);
glTexCoord2f(0.0, 0.0); glVertex3f(x, y, 0.0f);
glTexCoord2f(0.0, 1.0); glVertex3f(x, y + h, 0.0f);
glTexCoord2f(1.0, 1.0); glVertex3f(x + w, y + h, 0.0f);
glTexCoord2f(1.0, 0.0); glVertex3f(x + w, y, 0.0f);
glEnd();
glFlush();
glPopMatrix();
}
void reshape(int w, int h)//courtesy of http://www.lighthouse3d.com/tutorials/glut-tutorial/preparing-the-window-for-a-reshape/
{
if(h == 0) h = 1;
float ratio = w * 1.0 / h;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glViewport(0, 0, w, h);
gluPerspective(45.0, ratio, 0.1, 1000.0);
glMatrixMode(GL_MODELVIEW);
}
void render()
{
glLoadIdentity();
drawImage(texture, 0.0f, 0.0f, 4.0f, 4.0f, 0.0);
glutSwapBuffers();
}
int main(int argc, char* argv[])
{
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);
glutInitWindowSize(WIDTH, HEIGHT);
glutInitWindowPosition(INIT_X, INIT_Y);
glutCreateWindow("Applying Textures");
glutDisplayFunc(render);
glutIdleFunc(render);
glutReshapeFunc(reshape);
glutIgnoreKeyRepeat(1);
init();
glutMainLoop();
return 0;
}
然而,当我加载编译并运行程序时,我唯一得到的是一个带有白色背景的窗口。我还应该注意文件&#34; image.png&#34;确实存在并填充红色以与白色背景形成对比以用于测试目的。我想知道我做错了什么和/或我错过了什么。
答案 0 :(得分:1)
身份模型视图矩阵导致原点朝向-Z轴的“相机”。
你的drawImage()
正在向下与一个与Z = 0平面共面的四边形。这是在后面的身份矩阵的近剪裁平面。
将相机向后滑动一点,这样就不会嵌入Z = 0平面:
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glTranslatef( 0, 0, -15 ); // this is where the magic happens
所有在一起:
#include <GL/glut.h>
GLuint glInitTexture(char* filename)
{
GLuint t = 0;
glGenTextures( 1, &t );
glBindTexture(GL_TEXTURE_2D, t);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
unsigned char data[] = { 255, 0, 0, 255 };
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 1, 1, 0, GL_RGBA, GL_UNSIGNED_BYTE, data );
return t;
}
void drawImage(GLuint file,
float x,
float y,
float w,
float h,
float angle)
{
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
glPushMatrix();
glTranslatef(x, y, 0.0);
glRotatef(angle, 0.0, 0.0, 1.0);
glBindTexture(GL_TEXTURE_2D, file);
glEnable(GL_TEXTURE_2D);
glBegin(GL_QUADS);
glTexCoord2f(0.0, 0.0); glVertex3f(x, y, 0.0f);
glTexCoord2f(0.0, 2.0); glVertex3f(x, y + h, 0.0f);
glTexCoord2f(2.0, 2.0); glVertex3f(x + w, y + h, 0.0f);
glTexCoord2f(2.0, 0.0); glVertex3f(x + w, y, 0.0f);
glEnd();
glPopMatrix();
}
GLuint texture;
void render()
{
glClearColor(1.0f, 1.0f, 1.0f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glEnable(GL_DEPTH_TEST);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
const double w = glutGet( GLUT_WINDOW_WIDTH );
const double h = glutGet( GLUT_WINDOW_HEIGHT );
gluPerspective(45.0, w / h, 0.1, 1000.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glTranslatef( 0, 0, -15 );
drawImage(texture, 0.0f, 0.0f, 4.0f, 4.0f, 0.0);
glutSwapBuffers();
}
int main(int argc, char* argv[])
{
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);
glutInitWindowSize(600, 600);
glutCreateWindow("Applying Textures");
glutDisplayFunc(render);
texture = glInitTexture("image.png");
glutMainLoop();
return 0;
}