想要一个 OpenGL 2D 示例(VC++,画一个矩形) [英] Want an OpenGL 2D example (VC++, draw a rectangle)

查看:37
本文介绍了想要一个 OpenGL 2D 示例(VC++,画一个矩形)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想创建一个高性能的 2D 程序.

我使用的是 VC++2008.假设我已经创建了主窗口.我想要的是在主窗口的客户区绘制一个红色矩形(左上角:10,20,右下角:200, 300),就像 FillRect() API 所做的那样,但使​​用 OpenGL.

void InitOpenGL(HWND hwnd){....//我该怎么办?//仅用于 2D 绘图,且 (0,0) 应为左上角.}//下面的函数将在 WM_PAINT 处理程序中调用void DrawRectWithOpenGL(RECT* pRect){....//我该怎么办?}

OpenGL 是否有像 Direct2D/DirectWrite 这样的 2D 绘图 API 或库?

解决方案

我强烈建议你看看一些 OpenGL 教程 (http://nehe.gamedev.net/ 是一个不错的网站,它会告诉您您需要知道的一切),但是假设您在代码中正确设置了 OpenGL,您会做一些事情在你的 DrawRectWithOpenGL 函数中是这样的(我不是 C++ 程序员,但我认为我的代码看起来适合 C++):

void DrawRectWithOpenGL(RECT* pRect){glPushMatrix();//确保我们的转换不会影响其他代码中的任何其他转换glTranslatef(pRect->x, pRect->y, 0.0f);//将矩形平移到其指定的 x 和 y 位置//这里放其他变换glBegin(GL_QUADS);//我们要画一个四边形,即有四个边的形状glColor3f(1, 0, 0);//设置颜色为红色glVertex2f(0, 0);//绘制矩形的四个角glVertex2f(0, pRect->h);glVertex2f(pRect->w, pRect->h);glVertex2f(pRect->w, 0);glEnd();glPopMatrix();}

OpenGL 没有 2D 绘图 API,但只需忽略 Z 轴(或仅使用 Z 轴确保以正确的深度绘制精灵,即这样您就可以绘制背景在前景之后,因为背景的深度被设置所以它位于前景之后).希望这可以帮助.一定要花时间看一些教程,一切都会变得清晰.

编辑:要为 2D 绘图设置 OpenGL,您需要设置正交投影(我链接到的教程使用透视投影,抱歉没有提到这一点).这是我执行此操作的一些代码的示例(在创建窗口后,它应该位于 InitOpenGL 函数中的某个位置):

glClearColor(0.0, 0.0, 0.0, 0.0);//设置清除的屏幕颜色为黑色glViewport(0, 0, 屏幕宽度, 屏幕高度);//这会设置视口,以便坐标 (0, 0) 位于窗口的左上角//设置正交投影,使坐标(0, 0)在左上角//最小和最大深度是-10和10.要启用深度只需输入//glEnable(GL_DEPTH_TEST)glMatrixMode(GL_PROJECTION);glLoadIdentity();glOrtho(0, 屏幕宽度, 屏幕高度, 0, -10, 10);//回到模型视图,这样我们就可以画东西了glMatrixMode(GL_MODELVIEW);glLoadIdentity();glClear(GL_COLOR_BUFFER_BIT 或 GL_DEPTH_BUFFER_BIT);//清除屏幕和深度缓冲区

这就是初始化排序.您应该能够使用 100 和 200 之类的值并让它们正确显示在屏幕上,即坐标以像素为单位.

为了处理窗口大小的变化,你要做的是找到窗口的大小(使用外部库.我不确定你可以在 OpenGL 中做到这一点,尽管来自 GLUT 的 glutGet(GLUT_WINDOW_WIDTH) 和 glutGet(GLUT_WINDOW_HEIGHT)可能有用,但我还没有测试过),然后使用更新的窗口大小再次调用 glViewport 和 glOrtho .

同样,您必须使用外部库来准确查明何时窗口大小发生变化.我不确定你可以使用什么,但如果你碰巧使用 SDL,那么它可能会有一些事件处理(并且可能能够返回屏幕宽度和高度,如果 glutGet 不起作用).

我希望这会有所帮助!

I want to create a high performace 2D program.

I'm using VC++2008. Suppose I have created the main window. What I want is to draw a red rectangle (top left: 10,20, bottom right: 200, 300) in the main window's client area like what FillRect() API does but using OpenGL.

void InitOpenGL(HWND hwnd)
{
.... // What should I do?
     // Only for 2D drawing, and the (0,0) should be the top left point.
}

// the function below will be called in the WM_PAINT handler
void DrawRectWithOpenGL(RECT* pRect)
{
.... // What should I do?
}

EDIT1: Does OpenGL have a 2D drawing API or lib like Direct2D/DirectWrite?

解决方案

I strongly suggest you take a look at some OpenGL tutorials (http://nehe.gamedev.net/ is a good site, it'll tell you everything you need to know), but assuming you have OpenGL set up correctly in your code, you'd do something like this in your DrawRectWithOpenGL function (I'm not a C++ programmer but I think my code looks right for C++):

void DrawRectWithOpenGL(RECT* pRect)
{
  glPushMatrix();  //Make sure our transformations don't affect any other transformations in other code
    glTranslatef(pRect->x, pRect->y, 0.0f);  //Translate rectangle to its assigned x and y position
    //Put other transformations here
    glBegin(GL_QUADS);   //We want to draw a quad, i.e. shape with four sides
      glColor3f(1, 0, 0); //Set the colour to red 
      glVertex2f(0, 0);            //Draw the four corners of the rectangle
      glVertex2f(0, pRect->h);
      glVertex2f(pRect->w, pRect->h);
      glVertex2f(pRect->w, 0);       
    glEnd();
  glPopMatrix();
}

OpenGL doesn't have a 2D drawing API but its easy to do 2D things by just ignoring the Z axis (or just using the Z axis for making sure that sprites are drawn at the correct depth, i.e. so you can draw the background after the foreground because the background's depth is set so it lies behind the foreground). Hope this helps. Definitely take the time to look at some tutorials and it will all become clear.

EDIT: For setting up OpenGL for 2D drawing, you need to set up an orthographic projection (the tutorials that I linked to uses perspecive projection, sorry for not mentioning that). Here's an example of some of my code that does this (which should be somewhere in your InitOpenGL function, after you have created your window):

glClearColor(0.0, 0.0, 0.0, 0.0);  //Set the cleared screen colour to black
glViewport(0, 0, screenwidth, screenheight);   //This sets up the viewport so that the coordinates (0, 0) are at the top left of the window

//Set up the orthographic projection so that coordinates (0, 0) are in the top left
//and the minimum and maximum depth is -10 and 10. To enable depth just put in
//glEnable(GL_DEPTH_TEST)
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0, screenwidth, screenheight, 0, -10, 10);

//Back to the modelview so we can draw stuff 
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glClear(GL_COLOR_BUFFER_BIT or GL_DEPTH_BUFFER_BIT); //Clear the screen and depth buffer

So that's the initialisation sorted. You should be able to use values like 100 and 200 and have them appear correctly on the screen, i.e. the coordinates are in pixels.

To handle window size changes, what you would do is find the size of the window (using an external library. I'm not sure you can do it in OpenGL, although glutGet(GLUT_WINDOW_WIDTH) and glutGet(GLUT_WINDOW_HEIGHT) from GLUT might work, but I haven't tested it), and then call glViewport and glOrtho again with the updated window size.

Again, you'd have to use an external library to find out exactly when the window size changes. I'm not sure what you could use, although if you happen to be using SDL then that might have some event handling for it (and may be able to return the screen width and height, if glutGet doesn't work).

I hope this helps!

这篇关于想要一个 OpenGL 2D 示例(VC++,画一个矩形)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆