在3D openGL世界中创建2D界面的问题

2024-06-28 20:23:03 发布

您现在位置:Python中文网/ 问答频道 /正文

我在一个项目,需要我创建一个二维界面渲染“在顶部”或三维世界。在其他一些论坛上,我读到你可以使用“gluOrthor2D()”来完成这项工作,并在完成后切换回GluPerspective()。唯一的问题是,我为它编写的测试代码只显示三维世界,而不是二维四元世界。但是,当我禁用3D渲染代码时,四元曲线会出现在它应该出现的地方。 我把代码删减为只使用openGL的语句,我写在下面。代码是用Pyglet库用Python编写的。在


场景初始化代码:

glViewport(0, 0, width, height)
glMatrixMode(GL_PROJECTION)
glLoadIdentity()
gluPerspective(60.0, float(width)/height, .1, 10000.)
glMatrixMode(GL_MODELVIEW)
glClearDepth(1.0)
glShadeModel(GL_FLAT)
glEnable(GL_DEPTH_TEST)
glDepthFunc(GL_LEQUAL) 
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST)

帧渲染代码。号召builder.buildMap()创建3D场景,glBegin glEnd对绘制二维四边形:

^{pr2}$

在阶段设置3模式功能:

glDisable(GL_DEPTH_TEST) 
glMatrixMode(GL_PROJECTION)
glLoadIdentity()
gluOrtho2D(0, width, 0, height)
glMatrixMode(GL_MODELVIEW)

以及阶段设置3模式功能:

glEnable(GL_DEPTH_TEST) 
glMatrixMode(GL_PROJECTION)
glLoadIdentity()
gluPerspective(60.0, float(width)/float(height), .1, 10000.)
glMatrixMode(GL_MODELVIEW)

我真的希望有人能指出我的错误!感谢您的帮助:)


Tags: 代码test场景世界floatwidthheightdepth
3条回答

我使用以下矩阵进行二维渲染:

glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(0, w, h, 0, 0, 1);
glViewport(0, 0, w, h);

glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glTranslatef(0.375f, 0.375f, 0);

很多人都搞错了如何使用glViewport等。他们总是把它放在整形回调中,这是完全错误的。在

在需要这些设置之前,您总是先在渲染功能中设置完整的设置。所以您的代码应该是(pesudocode):

render_scene():
    // first clear the whole window
    glViewport(0, 0, window.width, window.height)
    glClearDepth(1.0)
    glClearColor(1., 1., 1., 1.);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT)

    glViewport(3Dstuff.x, 3Dstuff.y, 3Dstuff.w, 3Dstuff.h)
    // maybe also set scissor to clip
    glMatrixMode(GL_PROJECTION)
    glLoadIdentity()
    gluPerspective(60.0, float(width)/height, .1, 10000.)
    glMatrixMode(GL_MODELVIEW)
    setup3DstuffModelview()
    glDepthFunc(...)
    glEnable(GL_DEPTH_TEST)
    // other state stuff
    render3Dstuff()

    // now the 2D stuff
    glViewport(2Dstuff.x, 2Dstuff.y, 2Dstuff.w, 2Dstuff.h)
    // clear depth and stencil   if you need parts of the 3D depth / stencil
    // for some algorithm retain it or save and restore by FBO renderbuffers or
    // glReadPixels, glDrawPixels
    glClearDepth(1.0)
    glClear(GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT)

    glMatrixMode(GL_PROJECTION)
    glLoadIdentity()
    glOrtho(...)
    glMatrixMode(GL_MODELVIEW)
    glLoadIdentity()
    setup2DstuffModelview()
    glDepthFunc(...)
    glDisable(GL_DEPTH_TEST)
    // other state stuff
    render2Dstuff()

    // repeat for all the layers you need

这一点非常重要:OpenGL是一种状态机。除非你能证明所有的状态都发生了改变。在

在切换到GL\umodelview之后,似乎没有调用glLoadIdentity()。最简单的记住方法是每次更改投影矩阵时都调用它,切换到GL\umodelview并调用glLoadIdentity()(除非您真的想保留旧的)。在

相关问题 更多 >