30

我正在 Windows 中构建物理模拟引擎和编辑器。我想使用 Qt 构建编辑器部分,并且我想使用 SDL 和 OpenGL 运行引擎。

我的第一个想法是仅使用 Qt 构建编辑器,并与引擎(资源管理器、渲染器、数学)共享尽可能多的代码。但是,我也希望能够在编辑器中运行模拟。这意味着我还必须共享使用 SDL 线程的模拟代码。

所以,我的问题是:有没有办法通过使用 SDL 将 OpenGL 渲染到 Qt 窗口?

我在网上读到有可能为 SDL 提供一个用于渲染的窗口句柄。有人有经验吗?

此外,模拟器的线程部分可能会出现问题,因为它使用 SDL 线程。

4

3 回答 3

24

这是我在项目中所做的简化。您可以像使用普通小部件一样使用它,但根据需要,您可以使用它的 m_Screen 对象绘制到 SDL 表面,它会显示在小部件中:)

#include "SDL.h"
#include <QWidget>

class SDLVideo : public QWidget {
    Q_OBJECT

public:
    SDLVideo(QWidget *parent = 0, Qt::WindowFlags f = 0) : QWidget(parent, f), m_Screen(0){
        setAttribute(Qt::WA_PaintOnScreen);
        setUpdatesEnabled(false);

        // Set the new video mode with the new window size
        char variable[64];
        snprintf(variable, sizeof(variable), "SDL_WINDOWID=0x%lx", winId());
        putenv(variable);

        SDL_InitSubSystem(SDL_INIT_VIDEO | SDL_INIT_NOPARACHUTE);

        // initialize default Video
        if((SDL_Init(SDL_INIT_VIDEO) == -1)) {
            std:cerr << "Could not initialize SDL: " << SDL_GetError() << std::endl;
        }

        m_Screen = SDL_SetVideoMode(640, 480, 8, SDL_HWSURFACE | SDL_DOUBLEBUF);
        if (m_Screen == 0) {
            std::cerr << "Couldn't set video mode: " << SDL_GetError() << std::endl;
        }
    }

    virtual ~SDLVideo() {
        if(SDL_WasInit(SDL_INIT_VIDEO) != 0) {
            SDL_QuitSubSystem(SDL_INIT_VIDEO);
            m_Screen = 0;
        }
    }
private:
    SDL_Surface *m_Screen;
};

希望这可以帮助

注意:将此小部件的最小和最大尺寸设置为 SDL 表面尺寸通常是有意义的。

于 2008-09-28T01:35:28.987 回答
15

虽然您可能会像第一个答案一样让它工作,但建议您可能会因为线程而遇到问题。在线程方面没有简单的解决方案,在这里您可以让 SDL Qt 和 OpenGL 主循环交互。不好玩。

最简单和最明智的解决方案是将这两个部分解耦。这样 SDL 和 Qt 在单独的进程中运行,并让它们使用某种消息进行通信(我在这里推荐 d-bus)。您可以让 SDL 呈现到无边框窗口中,并且您的编辑器通过消息发送命令。

于 2008-10-06T16:37:13.837 回答
3

从 QT 渲染到 opengl 很简单(并且效果很好) 没有 SDL 的直接经验,但这里有一个关于混合它们的示例应用程序。 http://www.devolution.com/pipermail/sdl/2003-January/051805.html

有一篇关于将 QT widgewts 直接与 opengl 混合的好文章 http://doc.trolltech.com/qq/qq26-openglcanvas.html有点超出您的严格需要,但相当聪明!

于 2008-09-23T02:00:29.553 回答