QT openglwidget实现简单的3D绘制显示和纹理贴图

UI如图`

头文件

#ifndef OPENWIDGET_H
#define OPENWIDGET_H

#include <QWidget>
#include"qopenglwidget.h"
#include<qopenglfunctions.h>
#include<qopenglshaderprogram.h>
#include<QOpenGLBuffer>
class QOpenGLShaderProgram;
class QOpenGLTexture;
class OpenWidget : public QOpenGLWidget, protected QOpenGLFunctions
{
    Q_OBJECT
public:
    explicit OpenWidget(QWidget *parent = nullptr);

//signals:

//public slots:
public:
    void initializeGL();
    void resizeGL(int w, int h);
    void paintGL();
    void keyPressEvent(QKeyEvent*event);
private:
  QOpenGLShaderProgram *program;
  QOpenGLBuffer vbo;
  QOpenGLTexture* texture[2];
  GLfloat translate,xRot,yRot,zRot;
};

#endif // OPENWIDGET_H`

cpp

#include "openwidget.h"
#include<qopenglshaderprogram.h>
#include<QOpenGLTexture>
#include<qimage.h>
#include<QKeyEvent>
OpenWidget::OpenWidget(QWidget *parent) : QOpenGLWidget(parent)
{
translate=-6.0;
xRot=zRot=0.0;
yRot=-30.0;
}

void OpenWidget::initializeGL()
{
	initializeOpenGLFunctions();
    glEnable(GL_DEPTH_TEST);
     texture[0]=new QOpenGLTexture(QImage(QString(":/myopengl/side%1.bmp")));
     texture[1]=new QOpenGLTexture(QImage(QString(":/myopengl/side%2.bmp")));
   QOpenGLShader *vshader=new QOpenGLShader(QOpenGLShader::Vertex,this);
   const char *vsrc=
           "#version 150                               \n"
           "in vec4 vPosition;                         \n"
           "in vec4 vTexCoord;                         \n"
           "out vec4 texCoord;                         \n"
           "uniform mat4 matrix;                       \n"
           "void main(){                               \n"
           "texCoord=vTexCoord;                        \n"
           "gl_Position=matrix*vPosition;              \n"
           "}                                          \n";
   if (!vshader->compileSourceCode(vsrc))
   {
	   return;
   }
   QOpenGLShader *fshader=new QOpenGLShader(QOpenGLShader::Fragment,this);
   const char *fsrc=
           "#version 150                              \n"
           "uniform sampler2D tex;                    \n"
           "in vec4 texCoord;                         \n"
           "out vec4 fColor;                          \n"
           "void main(){                              \n"
           "fColor=texture(tex,vec2(texCoord));       \n"
           "}                                         \n";
   if (!fshader->compileSourceCode(fsrc))
  {
  return;
  }
  program=new QOpenGLShaderProgram(this);
  if (!program->addShader(vshader))
  {
	  return;
  }
  if (!program->addShader(fshader))
  {
	  return;
  }
  if (!program->link())
  {
	  return;
  }
  if (!program->bind())
  {
	  return;
  }

}

void OpenWidget::resizeGL(int w, int h)
{

}

void OpenWidget::paintGL()
{
        int w=width();
        int h=height();
        int side=qMin(w,h);
        glViewport((w-side)/2,(h-side)/2,side,side);
        glClear(GL_COLOR_BUFFER_BIT|GL_ACCUM_BUFFER_BIT);
    GLfloat vertices[2][4][3]=
    {
        {{-0.8f,0.8f,0.8f},
        {-0.8f,-0.8f,0.8f},
        {0.8f,-0.8f,0.8f},
        {0.8f,0.8f,0.8f}},
        {{0.8f,0.8f,0.8f},
        {0.8f,-0.8f,0.8f},
        {0.8f,-0.8f,-0.8f},
        {0.8f,0.8f,-0.8f}},
    };
    vbo.create();
    vbo.bind();
    vbo.allocate(vertices,48*sizeof(GLfloat));
   GLuint vPosition =program->attributeLocation("vPosition");
   //glVertexAttribPointer(vPosition, 2, GL_FLOAT, GL_FALSE, 0, vertices);
   glEnableVertexAttribArray(vPosition);
   program->setAttributeBuffer(vPosition,GL_FLOAT,0,3,0);
  GLfloat coords[2][4][2]=
  {
      {{0.0f,1.0f},
      {0.0f,0.0f},
      {1.0f,0.0f},
      {1.0f,1.0f}},
      {{0.0f,1.0f},
      {0.0f,0.0f},
      {1.0f,0.0f},
      {1.0f,1.0f}}
  };
  vbo.write(24*sizeof (GLfloat),coords,16*sizeof(GLfloat));
  GLuint vTexCoord=program->attributeLocation("vTexCoord");
  program->setAttributeBuffer(vTexCoord,GL_FLOAT,24*sizeof (GLfloat),2,0);
  glEnableVertexAttribArray(vTexCoord);
  program->setUniformValue("tex",0);
  //透视投影效果
  QMatrix4x4 matrix;
  matrix.perspective(45.0f,(GLfloat)w/(GLfloat)h,0.1f,100.0f);
  matrix.translate(0,0,translate);
  matrix.rotate(xRot,1.0,0.0,0.0);
  matrix.rotate(yRot,0.0,1.0,0.0);
  matrix.rotate(zRot,0.0,0.0,1.0);
  program->setUniformValue("matrix",matrix);
  for(int i=0;i<2;i++)
 { texture[i]->bind();
  glDrawArrays(GL_TRIANGLE_FAN, i*4, 4);
 }
  //    glDrawArrays(GL_POINTS,0,1);
}

void OpenWidget::keyPressEvent(QKeyEvent *event)
{
    switch (event->key())
    {case Qt::Key_Up:
        xRot+=10;
        break;
    case Qt::Key_Left:
            yRot+=10;
            break;
    case Qt::Key_Right:
            zRot+=10;
            break;
    case Qt::Key_Down:
            translate-=1;
            break;
    case Qt::Key_Space:
            translate+=1;
            break;
    default:
        break;

    }
    update();
    QOpenGLWidget::keyPressEvent(event);
}

版本环境QT 5.13.2 msvc2015-64

下面是一个使用QtOpenGL Widget进行简单建模的示例: 1. 创建一个Qt项目,选择OpenGL Widget作为主窗口。 2. 打开mainwindow.cpp文件,在initializeGL()函数中添以下代码,用于设置OpenGL的各种参数: ```cpp void MainWindow::initializeGL() { // 设置清屏颜色为黑色 glClearColor(0, 0, 0, 1); // 启用深度测试 glEnable(GL_DEPTH_TEST); // 启用颜色材质,以光照效果为主 glEnable(GL_COLOR_MATERIAL); // 启用光照 glEnable(GL_LIGHTING); // 启用0号光源 glEnable(GL_LIGHT0); // 设置光源位置 GLfloat lightPos[] = { 0.5, 0.5, 0.5, 0.5 }; glLightfv(GL_LIGHT0, GL_POSITION, lightPos); // 设置光源颜色为白色 GLfloat lightColor[] = { 1, 1, 1, 1 }; glLightfv(GL_LIGHT0, GL_DIFFUSE, lightColor); } ``` 3. 在paintGL()函数中添以下代码,用于绘制一个简单的立方体: ```cpp void MainWindow::paintGL() { // 清除颜色和深度缓冲区 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // 绘制立方体 glBegin(GL_QUADS); // 绘制前面 glColor3f(1, 0, 0); glVertex3f(-0.5, -0.5, 0.5); glVertex3f(0.5, -0.5, 0.5); glVertex3f(0.5, 0.5, 0.5); glVertex3f(-0.5, 0.5, 0.5); // 绘制后面 glColor3f(0, 1, 0); glVertex3f(-0.5, -0.5, -0.5); glVertex3f(-0.5, 0.5, -0.5); glVertex3f(0.5, 0.5, -0.5); glVertex3f(0.5, -0.5, -0.5); // 绘制左边 glColor3f(0, 0, 1); glVertex3f(-0.5, -0.5, 0.5); glVertex3f(-0.5, 0.5, 0.5); glVertex3f(-0.5, 0.5, -0.5); glVertex3f(-0.5, -0.5, -0.5); // 绘制右边 glColor3f(1, 1, 0); glVertex3f(0.5, -0.5, 0.5); glVertex3f(0.5, -0.5, -0.5); glVertex3f(0.5, 0.5, -0.5); glVertex3f(0.5, 0.5, 0.5); // 绘制顶部 glColor3f(0, 1, 1); glVertex3f(-0.5, 0.5, 0.5); glVertex3f(0.5, 0.5, 0.5); glVertex3f(0.5, 0.5, -0.5); glVertex3f(-0.5, 0.5, -0.5); // 绘制底部 glColor3f(1, 0, 1); glVertex3f(-0.5, -0.5, 0.5); glVertex3f(-0.5, -0.5, -0.5); glVertex3f(0.5, -0.5, -0.5); glVertex3f(0.5, -0.5, 0.5); glEnd(); } ``` 4. 编译运行程序,即可看到一个简单的立方体。 以上示例只是一个简单的例子,QtOpenGL Widget可以用于更复杂的建模和渲染任务。需要注意的是,在进行复杂的建模时,需要使用更高级的OpenGL技术和算法。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值