百度:
可以看到一位前辈的讲解。参考它弄的。
刚开始搞了3天,里面可能会有很多错误。
专门定义了一个类
.h
#include <QGLWidget>
#include <GL/glut.h>
//glut.h包含了gl.h
//#include <GL/gl.h>
class SilderBar:public QGLWidget
{
public:
SilderBar(const QGLFormat & format, QWidget *parent = 0);
~SilderBar();
}
.cpp
在构造函数中加入
setAutoFillBackground(false);
不然图元不会显示
#define BMP_Header_Length 54
void drawSomething()
{
//此类继承QGLWidget类,此函数具体啥作用没调查
makeCurrent();
glClear(GL_COLOR_BUFFER_BIT);
//设置GL_TEXTURE_2D
glEnable(GL_TEXTURE_2D);
GLuint texWall;
//这里读取了一个24位BMP图片
texWall = load_texture(FileNameBmp);
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
// 这里就是把那个位图跟这个二维图形勾搭上
glBindTexture(GL_TEXTURE_2D, texWall);
//画了一个多边形,贴图的时候一一对应,不然肯定画歪
//glVertex3f可以控制图片的显示范围,例如在这里,图片的白边就不会显示,变相实现BMP透明?
glBegin(GL_POLYGON);
glTexCoord2f(0.0f, 0.0f); glVertex3f(0.0f, 0.0f, 0.0f);
glTexCoord2f(0.0f, 1.0f); glVertex3f(0.0f, 0.3f, 0.0f);
glTexCoord2f(0.5f, 1.0f); glVertex3f(0.15f, 0.3f, 0.0f);
glTexCoord2f(1.0f, 0.5f); glVertex3f(0.3f, 0.15f,0.0f);
glTexCoord2f(0.5f, 0.0f); glVertex3f(0.15f, 0.0f, 0.0f);
glEnd();
//取消GL_TEXTURE_2D
//glDisable(GL_TEXTURE_2D);
doneCurrent
}
GLuint load_texture(const char* file_name)
{
GLint width, height, total_bytes;
GLubyte* pixels = 0;
GLuint last_texture_ID, texture_ID = 0;
// 打开文件,如果失败,返回
FILE* pFile = fopen(file_name, "rb");
if( pFile == 0 )
return 0;
// 读取文件中图象的宽度和高度
fseek(pFile, 0x0012, SEEK_SET);
fread(&width, 4, 1, pFile);
fread(&height, 4, 1, pFile);
fseek(pFile, BMP_Header_Length, SEEK_SET);
// 计算每行像素所占字节数,并根据此数据计算总像素字节数
{
GLint line_bytes = width * 3;
while( line_bytes % 4 != 0 )
++line_bytes;
total_bytes = line_bytes * height;
}
// 根据总像素字节数分配内存
pixels = (GLubyte*)malloc(total_bytes);
if( pixels == 0 )
{
fclose(pFile);
return 0;
}
// 读取像素数据
if( fread(pixels, total_bytes, 1, pFile) <= 0 )
{
free(pixels);
fclose(pFile);
return 0;
}
// 分配一个新的纹理编号
glGenTextures(1, &texture_ID);
if( texture_ID == 0 )
{
free(pixels);
fclose(pFile);
return 0;
}
// 绑定新的纹理,载入纹理并设置纹理参数
// 在绑定前,先获得原来绑定的纹理编号,以便在最后进行恢复
glGetIntegerv(GL_TEXTURE_BINDING_2D,(GLint*)&last_texture_ID);
glBindTexture(GL_TEXTURE_2D, texture_ID);
//纹理过滤设定
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
//颜色混合模式
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0,
GL_BGR_EXT, GL_UNSIGNED_BYTE, pixels);
glBindTexture(GL_TEXTURE_2D, last_texture_ID);
// 之前为pixels分配的内存可在使用glTexImage2D以后释放
// 因为此时像素数据已经被OpenGL另行保存了一份(可能被保存到专门的图形硬件中)
free(pixels);
return texture_ID;
}
以上就是读取24位BMP并贴在一个二维多边形上了
.ui文件上的显示
//设定大小
QRect rectSB(508, 99, 282, 275);
//定义一个scene
QGraphicsScene *m_scene= new QGraphicsScene();
m_scene->setSceneRect(rectSB);
//没啥说的就是搞了那个要显示的对象
m_Sb = new SilderBar(QGLFormat(QGL::SampleBuffers), this);
m_Sb->setGeometry(rectSB);
// 在ui文件上拉了一个graphicsView来显示
ui->graphicsView->setViewport(m_Sb);
ui->graphicsView->setScene(m_scene);