zoukankan      html  css  js  c++  java
  • 纹理窗口Qt+OpenGL之纹理贴图

    上班之余抽点时间出来写写博文,希望对新接触的朋友有帮助。今天在这里和大家一起学习一下纹理窗口

        NeNe的代码中是加载到了一个正方体当中,代码很长。其实单纯的想要纹理贴图是很便利的。具体的纹理贴图技巧在NeNe的书中的有很具体的分析。

        

        .h文件:

    #ifndef PICGLWIDGET_H
    #define PICGLWIDGET_H
    
    #include <QtGui/QWidget>
    #include <QWidget>
    #include <QtOpenGL>
    #include <GL/GLU.h>
    #include <gl/gl.h>
    
    class PicGLWidget : public QGLWidget
    {
        Q_OBJECT
        
    public:
        explicit PicGLWidget(QWidget *parent = 0);
        ~PicGLWidget();
    
    protected:
        void loadGLTextures ();
    
        void initializeGL();  //初始化OpenGL窗口部件
        void paintGL();  //绘制整个OpenGL窗口,只要有更新发生,这个函数就会被调用
        void resizeGL(int width, int height); //处置窗口巨细变更事件的,参数是新状态下的宽和高
        void keyPressEvent(QKeyEvent *e);  //鼠标处置函数
    
    protected:
        bool fullscreen;  //判断是不是全屏的变量
        float Zyot;
        GLuint texture[1];
    };
    
    #endif // PICGLWIDGET_H

        .cpp文件:

        每日一道理
    人生是洁白的画纸,我们每个人就是手握各色笔的画师;人生也是一条看不到尽头的长路,我们每个人则是人生道路的远足者;人生还像是一块神奇的土地,我们每个人则是手握农具的耕耘者;但人生更像一本难懂的书,我们每个人则是孜孜不倦的读书郎。
    #include "picglwidget.h"
    
    PicGLWidget::PicGLWidget(QWidget *parent)
        : QGLWidget(parent)
    {
        fullscreen = false;
        Zyot = -10.0f;
    }
    
    void PicGLWidget::initializeGL()
    {
        setGeometry(300, 150, 500, 500);//设置窗口初始位置和巨细
        loadGLTextures();
        glEnable(GL_TEXTURE_2D);//启用纹理
        glShadeModel(GL_SMOOTH);//设置阴影平滑模式
        glClearColor(0.0, 0.0, 0.0, 0.5);//转变窗口的背景颜色
        glClearDepth(1.0);//设置深度缓存
        glEnable(GL_DEPTH_TEST);//答应深度测试
        glDepthFunc(GL_LEQUAL);//设置深度测试类型
        glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);//停止透视校正
    
        glBlendFunc(GL_SRC_ALPHA, GL_ONE);//源像素因子采取alpha通道值,目标像素因子采取1.0
        glEnable(GL_BLEND);
    }
    
    void PicGLWidget::paintGL()
    {
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
        glLoadIdentity();
        glTranslatef(0.0, 0.0, Zyot);
        glBindTexture(GL_TEXTURE_2D, texture[0]);//绑定纹理目标
        glBegin(GL_QUADS);
            glTexCoord2f( 0.0, 0.0 ); glVertex3f( -1.0, -1.0,  1.0 );
            glTexCoord2f( 1.0, 0.0 ); glVertex3f(  1.0, -1.0,  1.0 );
            glTexCoord2f( 1.0, 1.0 ); glVertex3f(  1.0,  1.0,  1.0 );
            glTexCoord2f( 0.0, 1.0 ); glVertex3f( -1.0,  1.0,  1.0 );
        glEnd();
    }
    
    void PicGLWidget::resizeGL(int width, int height)
    {
        if(0 == height)
              height = 1;//防止一条边为0
          glViewport(0, 0, (GLint)width, (GLint)height);//重置当前视口,本身不是重置窗口的,只不过是这里被Qt给封装好了
          glMatrixMode(GL_PROJECTION);//选择投影矩阵
          glLoadIdentity();//重置选择好的投影矩阵
          gluPerspective(45.0, (GLfloat)width/(GLfloat)height, 0.1, 100.0);//建立透视投影矩阵
          glColor4f(1.0f, 1.0f, 1.0f, 0.5f);
          glBlendFunc(GL_SRC_ALPHA, GL_ONE);
          glMatrixMode(GL_MODELVIEW);//以下2句和下面出现的解释一样
          glLoadIdentity();
    }
    
    void PicGLWidget::keyPressEvent(QKeyEvent *e)
    {
        switch(e->key())
            {
                /*F1键为全屏和普通屏显示切换键*/
                case Qt::Key_F1:
                    fullscreen = !fullscreen;
                    if(fullscreen)
                        showFullScreen();
                    else
                    {
                        setGeometry(300, 150, 500, 500);
                        showNormal();
                    }
                    updateGL();
                    break;
                /*Ese为退出程序键*/
                case Qt::Key_Escape:
                    close();
            }
    }
    
    void PicGLWidget::loadGLTextures()
    {
        QImage tex, buf;
            if(!buf.load("./images/2.bmp"))//这个时候因为debug没有在外面,所以图片文件夹就是本目录了
            {
                qWarning("Cannot open the image...");
                QImage dummy(128, 128, QImage::Format_RGB32);//当没找到所需打开的图片时,创建一副128*128巨细,深度为32位的位图
                dummy.fill(Qt::green);
                buf = dummy;
            }
            tex = convertToGLFormat(buf);//将Qt图片的格式buf转换成opengl的图片格式tex
            glGenTextures(1, &texture[0]);//开拓3个纹理内存,索引指向texture[0]
    
            /*建立第一个纹理*/
            glBindTexture(GL_TEXTURE_2D, texture[0]);//将创建的纹理内存指向的内容绑定到纹理对象GL_TEXTURE_2D上,经过这句代码后,以后对
                                                    //GL_TEXTURE_2D的操作的任何操作都同时对应与它所绑定的纹理对象
            glTexImage2D(GL_TEXTURE_2D, 0, 3, tex.width(), tex.height(), 0, GL_RGBA, GL_UNSIGNED_BYTE, tex.bits());//开始真正创建纹理数据
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);//当所显示的纹理比加载进来的纹理小时,采取GL_NEAREST的方法来处置
                                                                              //GL_NEAREST方式速度非常快,因为它不是真正的滤波,所以占用内存非常
                                                                              // 小,速度就快了
            glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);//当所显示的纹理比加载进来的纹理大时,采取GL_NEAREST的方法来处置
    }
    
    PicGLWidget::~PicGLWidget()
    {
        
    }

        当然,你需要在pro文件中添加opengl。

        纹理和窗口

    文章结束给大家分享下程序员的一些笑话语录: 神灯新篇
    一个程序员在海滩上发现了一盏神灯。他在灯上擦了几下,一个妖怪就从灯里跳出来说:“我是世界上法术最强的妖怪。我可以实现你的任何梦想,但现在,我只能满足你一个愿望。”程序员摊开了一幅中东地图说:“我想让中东得到永久的和平。”妖怪答道:“哦,我没办法。自打创世纪以来,那里的战火就没有停息过。这世上几乎没有我办不到的事,但这件事除外。”程序员于是说:“好吧,我是一个程序员,为许多用户编写过程序。你能让他们把需求表述得更清楚些,并且让我们的软件项目有那么一两次按进度按成本完成吗?”妖怪说:“唔,我们还是来看中东地图吧。”

  • 相关阅读:
    [zz]libvirt中CPU和内存的细粒度管理机制
    SAP 模块中文解释
    邪恶的Php一句话木马 assert函数制作简单木马
    PHP开发中三维数组的应用
    返回本机时间或服务器时间
    向SQL中插入数据
    Word的字体
    人生如锅
    打开指定的文件
    计算最大序号
  • 原文地址:https://www.cnblogs.com/jiangu66/p/3076839.html
Copyright © 2011-2022 走看看