QGLWidget绘制矩形使用实例精讲

2 篇文章 0 订阅

目录

1.概述 

2.代码实例-顶点绘制方式

main.cpp

myglwidget.h 

myglwidget.cpp

代码执行接结果

3.代码实例-线形绘制方式

4.坐标系讲解


1.概述 

QGLWidget类是一个用于渲染OpenGL图形的小部件。

QGLWidget提供了显示集成到Qt应用程序中的OpenGL图形的功能。它使用起来非常简单。您可以继承它并像使用其他QWidget一样使用它的子类,除了您可以在使用QPainter和标准OpenGL呈现命令之间进行选择之外。

注意:QGLWidget这个类是遗留Qt OpenGL模块的一部分,和其他QGL类一样,应该在新的应用程序中避免使用。从Qt 5.4开始,推荐使用QOpenGLWidget和QOpenGL类

QGLWidget提供了三个方便的虚拟函数,你可以在子类中重新实现它们来执行典型的OpenGL任务:

paintGL() -渲染OpenGL场景。在小部件需要更新时调用。
resizeGL() -设置OpenGL视图,投影等。在小部件调整大小时调用(以及在它第一次显示时调用,因为所有新创建的小部件都会自动获取一个调整大小事件)。
initializeGL() -设置OpenGL渲染上下文,定义显示列表等。在第一次调用resizeGL()或paintGL()之前调用一次。


以下是QGLWidget子类的大致轮廓:

class MyGLDrawer : public QGLWidget
{
    Q_OBJECT        // must include this if you use Qt signals/slots

public:
    MyGLDrawer(QWidget *parent)
        : QGLWidget(parent) {}

protected:

    void initializeGL()
    {
        // Set up the rendering context, define display lists etc.:
        ...
        glClearColor(0.0, 0.0, 0.0, 0.0);
        glEnable(GL_DEPTH_TEST);
        ...
    }

    void resizeGL(int w, int h)
    {
        // setup viewport, projection etc.:
        glViewport(0, 0, (GLint)w, (GLint)h);
        ...
        glFrustum(...);
        ...
    }

    void paintGL()
    {
        // draw the scene:
        ...
        glRotatef(...);
        glMaterialfv(...);
        glBegin(GL_QUADS);
        glVertex3f(...);
        glVertex3f(...);
        ...
        glEnd();
        ...
    }

};

综上所述,一般我们要做的事情就是重新实现一下initializeGL()、resizeGL(int w, int h)、paintGL()这3个函数

2.代码实例-顶点绘制方式

main.cpp

#include "opengltest.h"
#include <QtWidgets/QApplication>
#include "myglwidget.h"

int main(int argc, char *argv[])
{
	QApplication a(argc, argv);
	MyGLWidget *widget = new MyGLWidget(NULL);
	widget->show();
	return a.exec();
}

myglwidget.h 

#ifndef MYGLWIDGET_H
#define MYGLWIDGET_H

#include <QGLWidget>

class MyGLWidget : public QGLWidget
{
	Q_OBJECT

public:
	MyGLWidget(QWidget *parent);
	~MyGLWidget();

protected:
	void initializeGL();
	void resizeGL(int w, int h);
	void paintGL();

private:
	
};

#endif // MYGLWIDGET_H

myglwidget.cpp

#include "myglwidget.h"
#include "qapplication.h"
#include "qrect.h"
#include "QDesktopWidget"

MyGLWidget::MyGLWidget(QWidget *parent)
	: QGLWidget(parent)
{

}

MyGLWidget::~MyGLWidget()
{

}

void MyGLWidget::initializeGL()
{
	//获取屏幕大小
	QRect deskRect = QApplication::desktop()->availableGeometry();

	//设置窗口的坐标和尺寸,让窗口居中显示  
	setGeometry(deskRect.width()/2 - 500/2, deskRect.height()/2 - 300/2, 500, 300);

	//清除颜色  
	glClearColor(0.0, 0.0, 0.0, 0);

}

void MyGLWidget::resizeGL(int w, int h)
{
	glViewport(0, 0, (GLsizei)w, (GLsizei)h);
}

void MyGLWidget::paintGL()
{
	//清屏  
	glClear(GL_COLOR_BUFFER_BIT);

	// 设置两面均为顶点绘制方式
	glPolygonMode(GL_FRONT_AND_BACK, GL_POINT); 

	// 设置CCW方向为“正面”,CCW即CounterClockWise,逆时针 
	glFrontFace(GL_CCW);  

	//逆时针绘制一个矩形,每个for循环对应一条边
	glBegin(GL_POLYGON);
	for (int i = 0;i < 125;i++)
	{
		glVertex2f(-0.5f + (0.5/125)*i, -0.5f);//绘制125个点,连成1条线段
	}
	
	for (int i = 0;i < 75;i++)
	{
		glVertex2f(0.0f, -0.5f + (0.5/75)*i);
	}	
	
	for (int i = 0;i < 125;i++)
	{
		glVertex2f(0.0f - (0.5/125)*i, 0.0f);
	}
	
	for (int i = 0;i < 75;i++)
	{
		glVertex2f(-0.5f, 0.0f - (0.5/75)*i);
	}

	glEnd();
}

代码执行接结果

3.代码实例-线形绘制方式

线形绘制方式,只需要指定四个顶点的位置即可,系统会自动帮我们连成线。代码如下:

void MyGLWidget::paintGL()
{
	//清屏  
	glClear(GL_COLOR_BUFFER_BIT);

	// 设置反面为线形模式
	glPolygonMode(GL_FRONT, GL_LINE);
	glPolygonMode(GL_BACK, GL_LINE);

	// 设置CCW方向为“正面”,CCW即CounterClockWise,逆时针 
	glFrontFace(GL_CCW);  

	glBegin(GL_POLYGON);
	glVertex2f(-0.5f, -0.5f);
	glVertex2f(0.0f, -0.5f);
	glVertex2f(0.0f, 0.0f);
	glVertex2f(-0.5f, 0.0f);
	glEnd();
	
	glBegin(GL_POLYGON);
	glVertex2f(0.0f, 0.0f);
	glVertex2f(0.0f, 0.5f);
	glVertex2f(0.5f, 0.5f);
	glVertex2f(0.5f, 0.0f);
	glEnd();

}

4.坐标系讲解

一般我们将程序界面的中心点作为原点, 左边为X正半轴,上面为Y轴正半轴。然后我们在用代码画点时,用的不是绝对坐标,而是一个比例值。例如上图中(-0.5, -0.5)这个点是X轴负半轴的一半和Y轴负半轴的一半所表示的点,而程序左下角的点是X轴负半轴整个半轴长度和Y轴负半轴整个半轴长度所对应的点。文字描述比较抽象,最好直接看图吧。

  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Allen Roson

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值