使用 SDL_Renderer 绘制 2D 内容和使用 SDL_GLContext 绘制 OpenGL 内容

2021-12-19 00:00:00 opengl sdl rendering sdl-2 c++

我学习 SDL 2D 编程已有一段时间了,现在我想创建一个结合使用 SDL 和 OpenGL 的程序.我是这样设置的:

I have been learning about SDL 2D programming for a while and now I wanted to create a program using SDL and OpenGL combined. I set it up like this:

SDL_Init(SDL_INIT_VIDEO);

window = SDL_CreateWindow("SDL and OpenGL", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, width, height, SDL_WINDOW_OPENGL);

context = SDL_GL_CreateContext(window);

该程序现在只是一个使用 OpenGl 显示的带有白线的黑色窗口.这是渲染的代码:

The program is for now just a black window with a white line displayed using OpenGl. Here is the code for the rendering:

glClearColor(0, 0, 0, 0);
glClear(GL_COLOR_BUFFER_BIT);         

glBegin(GL_LINES);     
glVertex2d(1, 0);
glVertex2d(-1, 0);
glEnd();

SDL_GL_SwapWindow(window);  

所以问题是,我想额外使用纯 SDL 和 SDL_Renderer 对象渲染纹理,就像我以前在没有 OpenGL 的情况下所做的那样.我试过了,但没有用.甚至有可能做到这一点以及如何做到这一点?我所做的是创建一个 SDL_Renderer,然后在绘制 OpenGL 的东西之后这样做:

So the thing is, I would like to render textures additionally using pure SDL and a SDL_Renderer object, as I did before without OpenGL. I tried that out but it didn't work. Is it even possible to do that and how? What I did is creating a SDL_Renderer and then after drawing OpenGL stuff doing this:

SDL_Rect fillRect;
fillRect.w = 50;
fillRect.h = 50;
fillRect.x = 0;
fillRect.y = 0; 

SDL_SetRenderDrawColor(renderer, 100, 200, 100, 0);
SDL_RenderFillRect(renderer, &fillRect);

SDL_RenderPresent(renderer);    

但这行不通.矩形没有显示,虽然在几毫秒内它会稍微出现.我觉得 OpenGL 渲染正在覆盖它.

But this does not work. The rectangle is not shown, although for some milliseconds it appears slightly. I feel like the OpenGL rendering is overwriting it.

推荐答案

SDL 使用 OpenGL(或在某些情况下是 Direct3D)并且 OpenGL 具有影响程序中 GL 调用的内部状态.当前版本的 SDL 没有明确指出它更改或依赖于任何调用的状态,并且它不包括重置为已知状态的函数.这意味着您不应将 SDL_Renderer 与 OpenGL 混合使用.

SDL uses OpenGL (or in some cases Direct3D) and OpenGL has internal state which affects the GL calls in your program. The current version of SDL does not clearly indicate which states it changes or depends upon for any call and it does not include functions to reset to a known state. That means you should not mix SDL_Renderer with OpenGL yet.

不过,如果你现在真的想要这个功能,你可以试试 SDL_gpu(注意:我是作者).它确实支持与 OpenGL 调用和自定义着色器的混合.您可能想要指定您需要的 OpenGL API 版本(例如,使用 GPU_InitRenderer(GPU_RENDERER_OPENGL_1, ...))并重置 SDL_gpu 使用每帧的 GL 状态 (GPU_ResetRendererState()).查看 SDL_gpu 源代码库中的 3d 演示了解更多信息.

However, if you really want this functionality now, you can try SDL_gpu (note: I'm the author). It does support mixing with OpenGL calls and custom shaders. You would want to specify which version of the OpenGL API you need (e.g. with GPU_InitRenderer(GPU_RENDERER_OPENGL_1, ...)) and reset the GL state that SDL_gpu uses each frame (GPU_ResetRendererState()). Check out the 3d demo in the SDL_gpu source repository for more.

https://github.com/grimfang4/sdl-gpu/blob/master/demos/3d/main.c

相关文章