OpenGL新手 - 在场景中移动对象的最佳方法

时间:2010-06-27 08:49:44

标签: language-agnostic opengl graphics 3d

我是OpenGL和图形编程的新手,虽然我一直对这个主题很感兴趣,但理论上有一个基础。

我想要做的是创建一个场景,其中一组对象在其中移动。具体来说,他们是一个场上的机器人足球运动员。对象是:

  • 不改变的灯光,场地和目标
  • 球,是一个单个网格,将进行平移和旋转但不缩放
  • 每个都由身体部位组成的运动员,每个运动员都被翻译并旋转以产生连体的错觉

所以对我的GL新手来说,我想将这些对象加载到场景中然后只是移动它们。顶点的属性不会改变,无论是它们的定位还是纹理/法线/等。只是将他们的“父母”对象整体转变。

此外,球员都有相同的身体。我可以通过将模型加载到内存中一次,然后每次使用不同的转换矩阵多次绘制它来进行优化吗?

我目前正在使用OpenTK,这是​​一个基于OpenGL库的轻量级包装器。

这个问题的有用答案可能是:

  • OpenGL的哪些部分可以满足我的需求?我是否必须每帧重绘所有脸部?只是那些移动?我可以更新一些转换矩阵吗?使用OpenTK我能做到这么简单吗? psuedocode会是什么样子?或者,
  • 是否有更好的框架是免费的(理想情况下是开源的)并提供这种抽象级别?

请注意,我需要在.NET across multiple platforms中运行任何解决方案。

3 个答案:

答案 0 :(得分:5)

使用所谓的顶点数组可能是优化这种场景的最可靠方法。这是一个很好的教程:

http://www.songho.ca/opengl/gl_vertexarray.html

顶点数组或更一般地说,gl数据数组保存顶点位置,法线,颜色等数据。您还可以使用一个数组来保存这些缓冲区的索引,以指示绘制它们的顺序 然后你有一些密切相关的函数来管理这些数组,分配它们,设置数据并绘制它们。您只需使用一个OpenGL命令(如glDrawElements()

)即可执行复杂网格的渲染

这些数组通常驻留在主机内存中。进一步的优化是使用顶点缓冲区对象,这些对象与常规数组具有相同的概念,但驻留在GPU内存上并且速度稍快。以下是对此的反对意见:

http://www.songho.ca/opengl/gl_vbo.html

使用缓冲区而不是旧的glBegin() .. glEnd()具有与OpenGL ES兼容的优点。在OpenGL ES中,数组和缓冲区是绘制内容的唯一方法。

--- 编辑

使用“模型视图”矩阵移动,旋转它们并在场景中变换它们,并且不需要对网格数据进行任何更改。举例说明:

你有初始化:

void initGL() {
  // create set of arrays to draw a player
  // set data in them
  // create set of arrays for ball
  // set data in them
}

void drawScene {
  glMatrixMode(GL_MODEL_VIEW);
  glLoadIdentity();
  // set up view transformation
  gluLookAt(...);
  drawPlayingField();

  glPushMatrix();
  glTranslate( player 1 position );
  drawPlayer();
  glPopMatrix();

  glPushMatrix();
  glTranslate( player 2 position );
  drawPlayer();
  glPopMatrix();

  glPushMatix();
  glTranslate( ball position );
  glRotate( ball rotation );
  drawBall();
  glPopMatrix();
}

答案 1 :(得分:4)

由于你的开始,我建议坚持立即模式渲染并让它首先工作。如果您感觉更舒服,可以改进顶点数组。如果你觉得更舒服,那就是VBOs。最后,如果您获得超级舒适,实例化是您案例中最快的解决方案(没有变形,只有整个对象转换)。

除非你试图实现像Fifa 2009这样的东西,否则最好坚持使用简单的方法,直到你遇到明显的效率问题。不需要过早地让自己头疼。

对于整个对象转换,通常会转换模型视图矩阵。

glPushMatrix();
// do gl transforms here and render your object
glPopMatrix();

对于加载对象,你甚至需要提出一些格式或实现可以加载网格格式的东西(obj是最容易支持的格式之一)。有一些高级库可以简化这一过程,但我建议您使用OpenGL来获得您的体验和控制。

答案 2 :(得分:1)

我希望OpenGL API可以通过IDE支持(intellisense等)轻松导航。几个小时后,显然需要建立一些基本规则。所以我停止了输入和RTFM。

http://www.glprogramming.com/red/

在找到他们的OpenGL基础时,我可以给予发现此问题的任何其他人的最佳建议。长篇大论,但赋权。