Qt实现 QOpenGL绘制彩色三角形

1、QOpenGL介绍

QOpenGLWidget类封装了opengl,比起原生的opengl,使用起来很方便。只需要让子类继承QOpenGLWidget。

OpenGL(英语:Open Graphics Library,译名:开放图形库或者“开放式图形库”)是用于渲染2D、3D矢量图形的跨语言、跨平台的应用程序编程接口(API)。这个接口由近350个不同的函数调用组成,用来从简单的图形比特绘制复杂的三维景象。而另一种程序接口系统是仅用于Microsoft Windows上的Direct3D。OpenGL常用于CAD、虚拟现实、科学可视化程序和电子游戏开发。(摘自维基百科)

其实OpenGL是把图像数据和几何数据发送给电脑显卡,进行一系列处理后,把图形显示到屏幕上进行展示。

QOpenGLWidget允许在平台支持的情况下使用不同的OpenGL版本和配置文件,只需通过setFormat()设置请求的格式即可。

可以根据自己电脑所支持的opengl版本进行兼容性设置。

QSurfaceFormat format;format.setDepthBufferSize(24);format.setStencilBufferSize(8);format.setVersion(3, 2);format.setProfile(QSurfaceFormat::CoreProfile);this->setFormat(format);

QOpenGLWidget还提供了三个函数来方便我们处理业务。分别是
paintGL():绘制渲染opengl场景,update的时候会自动调用
resizeGL() :设置opengl的大小,resize的时候调用
initializeGL() :提供初始化opengl需要的环境的接口,在resizeGL或者paintGL之前会被调用一次。

2、效果

3、主要代码介绍:

1、着色器装载

void MyQOpengl::InitShader(){    //顶点着色器    QOpenGLShader *vShader = new QOpenGLShader(QOpenGLShader::Vertex, this);    const char *vSrc =            "in vec4 vPosition;                        \n"            "in vec4 vColor;                           \n"            "out vec4 color;                           \n"            "void main() {                             \n"            "   color = vColor;                        \n"            "   gl_Position = vPosition;               \n"            "}                                         \n";    vShader->compileSourceCode(vSrc);     //片段着色器    QOpenGLShader *fShader = new QOpenGLShader(QOpenGLShader::Fragment, this);    const char *fSrc =            "in vec4 color;                             \n"            "out vec4 fColor;                           \n"            "void main() {                              \n"            "   fColor = color;                         \n"            "}                                          \n";    fShader->compileSourceCode(fSrc);     //着色器程序    _pShaderProgram = new QOpenGLShaderProgram;    _pShaderProgram->addShader(vShader);    _pShaderProgram->addShader(fShader);     _pShaderProgram->link();    _pShaderProgram->bind();}

这里我们需要创建一个顶点着色器和片段着色器,然后通过addShader装载它们,所谓着色器就是像素被渲染时执行的程序,在GPU中执行的程序。const char *vSrc字符串是opengl着色器语言(OpenGL Shading Language)即GLSL。通过这些语言来描述给GPU。

而顶点就是我们图形的几个顶角,片段就是几个顶点包围起来的全部像素点,通过对以上进行渲染,就能得到我们需要的图形和颜色。

2、顶点描述

下面描述的是三角形的三个顶点

//顶点位置GLfloat vertices[] = {   -0.5f, -0.5f,   //left   0.0f, 0.5f,     //top   0.5f, -0.5f,    //right};

如下图所示:

3、顶点颜色

对三个顶点进行颜色的描述,分别表示r、g、b,我们知道,通过r、g、b的组合可以组合出任何我们想要的颜色

GLfloat colors[] = {   1.0f, 0.5f, 0.2f,   //r g b   1.0f, 0.5f, 0.2f,   1.0f, 0.5f, 0.2f,};

4、QOpenGLBuffer _vbo用于管理OpenGL的缓存对象,流程是create()创建缓存对象--bind()绑定对象关联的缓存到OpenGL环境--allocate()分配缓存空间--setAttributeBuffer()填充数据。

_vbo.create();_vbo.bind();_vbo.allocate(vertices, 18*sizeof(GLfloat)); GLuint vPosition = _pShaderProgram->attributeLocation("vPosition");_pShaderProgram->setAttributeBuffer(vPosition, GL_FLOAT, 0, 2, 0);glEnableVertexAttribArray(vPosition);

4、全部代码:

头文件:

#ifndef MYQOPENGL_H#define MYQOPENGL_H #include <QOpenGLWidget>#include <QOpenGLFunctions>#include <QOpenGLBuffer>#include <QOpenGLShaderProgram> class MyQOpengl : public QOpenGLWidget, protected QOpenGLFunctions{    Q_OBJECT public:    explicit MyQOpengl(QWidget *parent = 0);     void InitShader(); protected:    void initializeGL() override;    void paintGL() override;    void resizeGL(int w, int h) override; private:    QOpenGLShaderProgram *_pShaderProgram;    QOpenGLBuffer _vbo;}; #endif // MYQOPENGL_H

cpp

#include "myqopengl.h"#include <QDebug> MyQOpengl::MyQOpengl(QWidget *parent)    : QOpenGLWidget(parent){} void MyQOpengl::initializeGL(){    // 为当前环境初始化OpenGL函数    initializeOpenGLFunctions();     InitShader();} void MyQOpengl::InitShader(){    //顶点着色器    QOpenGLShader *vShader = new QOpenGLShader(QOpenGLShader::Vertex, this);    const char *vSrc =            "in vec4 vPosition;                        \n"            "in vec4 vColor;                           \n"            "out vec4 color;                           \n"            "void main() {                             \n"            "   color = vColor;                        \n"            "   gl_Position = vPosition;               \n"            "}                                         \n";    vShader->compileSourceCode(vSrc);     //片段着色器    QOpenGLShader *fShader = new QOpenGLShader(QOpenGLShader::Fragment, this);    const char *fSrc =            "in vec4 color;                             \n"            "out vec4 fColor;                           \n"            "void main() {                              \n"            "   fColor = color;                         \n"            "}                                          \n";    fShader->compileSourceCode(fSrc);     //着色器程序    _pShaderProgram = new QOpenGLShaderProgram;    _pShaderProgram->addShader(vShader);    _pShaderProgram->addShader(fShader);     _pShaderProgram->link();    _pShaderProgram->bind();}void MyQOpengl::resizeGL(int w, int h){    glViewport(0,0,w,h);} void MyQOpengl::paintGL(){    glClear(GL_COLOR_BUFFER_BIT);    glClearColor(0.2f, 0.3f, 0.3f,1.0f);     //顶点位置    GLfloat vertices[] = {        -0.5f, -0.5f,   //left        0.0f, 0.5f,     //top        0.5f, -0.5f,    //right    };     _vbo.create();    _vbo.bind();    _vbo.allocate(vertices, 18*sizeof(GLfloat));     GLuint vPosition = _pShaderProgram->attributeLocation("vPosition");    _pShaderProgram->setAttributeBuffer(vPosition, GL_FLOAT, 0, 2, 0);    glEnableVertexAttribArray(vPosition);      // 顶点颜色    GLfloat colors[] = {        1.0f, 0.5f, 0.2f,   //r g b        1.0f, 0.5f, 0.2f,        1.0f, 0.5f, 0.2f,    };     _vbo.write(6*sizeof(GLfloat), colors, 12*sizeof(GLfloat));    GLuint vColor = _pShaderProgram->attributeLocation("vColor");    _pShaderProgram->setAttributeBuffer(vColor, GL_FLOAT, 6*sizeof(GLfloat), 3, 0);    glEnableVertexAttribArray(vColor);     // 绘制    glDrawArrays(GL_TRIANGLES, 0, 3);}通过以上代码实现QOPenGL绘制了一个橘色的三角形[object Object]
(0)

相关推荐