试图从整个应用程序访问QGLWidget

时间:2012-07-09 17:58:25

标签: c++ opengl qt4 qglwidget

我基本上要做的是创建QGLWidget的一个实例(或者更确切地说是QGLWidget的派生类),将其添加到QMainWindow,然后访问QGLWidget从我的QTCreator程序中的任何地方渲染上下文,以便能够在我选择的任何地方调用裸OpenGL。

我尝试过的事情:

1)创建一个名为QGLWidget的{​​{1}}的子类,并将其转换为单例,然后尝试子类化单例类“OGLWidget”。我认为这可以让我访问OGLWidget单例使用的相同渲染上下文,但它不起作用。

2)使用构造函数OGLWidget。对于这个,我尝试将单例对象转换为QGLWidget,然后在我将QGLWidget子类化为另一个名为“Display”的类中时将其粘贴在此构造函数中。我尝试在每个类openGl调用之前调用makeCurrent,但只绘制原始单例。我还检查了isSharing,并返回true。

2 个答案:

答案 0 :(得分:0)

为什么不使用Qt设计的用途:使用信号和插槽?也许你的问题比我第一眼看到的更复杂,但在我看来,如果你向你的QGLWidget添加插槽并将它们连接到应用程序中的任何位置的信号,你就可以完成你想要的。例如,可以在QMainWindow中完成连接。然后,此广告位可以调用paintGL()paintEvent()的实施内容来更新QGLWidget中的区域。像这样:

class MyQGLWidget : public QGLWidget {
// constructors and destructor...

protected:
    void paintGL();      // <-- implement this in any way you want if you use OpenGL
    void paintEvent();   // <-- or implement this one if you prefer using QPainter

public slots:
    void updateMyWindow();
}

void MyQGLWidget::updateMyWindow() {
    // Change some data here in any way you like
    // ...

    paintGL();
}

答案 1 :(得分:0)

首先,尽管signal \ slots是Qt强大且令人敬畏的功能,但由于增加了开销和渲染顺序问题,我永远不会在渲染例程中使用它们。特别是后者。此外,没有必要按照你提出的方式去做。 因此,在我看来,你在整个项目中分散渲染程序的想法是一个非常糟糕的主意。 我在自己的项目中做的是:

我的派生QGLWidget拥有一个Renderer类,它被实现为Singleton。它包含一些函数中的所有OpenGl调用。我已经创建了一个系统,其中所有可绘制的东西都来自同一个基类。当我想渲染时,我构建了一个渲染队列,我将其实现为具有自定义排序功能的priority_queue。当渲染帧时,我只需保持poppin'并渲染,直到队列为空。 使用事件驱动的渲染系统执行此操作,同时保持正确的渲染顺序可能会让您感到疯狂。

为了完整性,我的(简化的)QGLWidget定义:

#include <QtOpenGL/QGLWidget>

#include "global.h"
#include "renderer.h"

/**
 * Derivation of QGLWidget.
 */
class Engine : public QGLWidget
{
    Q_OBJECT
private:
    Renderer* renderer;
private slots:
    void renderTimeout(); // my render-loop is timer based
    void onTap(QMouseEvent* qme);
    void onMove(QMouseEvent* qme);
protected:
    void initializeGL();
    void resizeGL(int w, int h);
    /* for debugging I use QPainter for drawing overlays, 
     * so I can't use PaintGL */
    void paintEvent(QPaintEvent *event); 
    void mousePressEvent(QMouseEvent* qme);
    void mouseMoveEvent(QMouseEvent* qme);
public:
    Engine( QWidget* parent = 0 );
    ~Engine();
signals:
    void tapOccurred(QMouseEvent* qme);
    void moveOccurred(QMouseEvent* qme);
};