Directx11如何管理多个顶点/索引缓冲区?

时间:2017-01-25 19:44:04

标签: c++ directx

我正在研究一个小型游戏框架,因为我正在学习DirectX11。 有一个BufferManager类(可能是静态的)来处理实时或之前创建的模型的所有顶点和索引数据的最佳方法是什么。该类应负责创建Buffers动态或静态,具体取决于模型信息,然后绘制它们。

  • 我是否应该有一个顶点和索引向量列表并将所有新模型附加到它...然后每当添加新数据时重新创建缓冲区并在绘制之前设置新缓冲区。
  • 我是否应该为模型分配顶点和索引缓冲区,访问相应模型的缓冲区并在每次绘制调用之前设置为IASetVertexBuffer(model[i].getVertBuff());
  • 另外一些模型可能是动态的,而另一些则是静态的,我该如何在这里进行批处理?

1 个答案:

答案 0 :(得分:1)

此处未显示任何代码,但您要求的构造如下:

  • 为纹理,模型网格,顶点数据,法线,音频等创建文件加载器
  • 拥有可重复使用的结构,可存储模型特定网格的所有数据。
  • 创建时,您还需要一个单独的纹理类来保存有关不同纹理的信息。这样,可以为不同的模型或网格引用相同的纹理,并且您不必每次都将它们加载到内存中。
  • 对于不同的网格也可以这样做;您可以引用可能是不同模型对象一部分的网格。
  • 要执行此操作,您需要一个资产存储类来管理您的所有资产。这样,如果资产已经在内存中,它将不再加载它;例如字体,纹理,模型,音频文件等。
  • 接下来的部分是您将需要Batch类和Batch Manager类
    • 批次类将根据一些参数定义批处理的容器:原始类型,如果它们是否具有透明度(优先级队列)等。
    • Batch Manager类将执行组织并将批次发送到呈现阶段。此类还将用于说明批处理可以容纳多少个顶点以及您拥有多少个批处理(存储桶)。比率将取决于游戏内容。基本2D精灵类型应用程序的良好比率将是大约10个批次,其中每个批次包含不少于10,000个顶点。接下来的步骤是根据原始类型及其优先级(alpha通道 - Z深度)填充相似类型的存储桶,如果存储桶无法保存数据,则它将寻找另一个要填充的存储桶。如果没有可用于保存数据的存储桶,则批处理管理器将查找最充满最高优先级队列的存储桶,它将该批处理发送到要呈现的视频卡,然后它将重用该存储桶。
    • 最后一部分是ShaderManager类,用于管理程序将使用的不同类型的着色器。因此,所有这些类或结构都将捆绑在一起。

如果你恰当地设计了这个,你可以从实际的游戏内容,属性和逻辑或规则集中抽象出所有的引擎行为和责任。这样您的游戏引擎就可以重复使用多个游戏。这样你的引擎对特定游戏没有任何依赖性,当你准备好重用它时,你所要做的就是创建一个继承自这个静态或动态库的所有引擎组件的主项目。被纳入下一场比赛。这种代码分离是通用可重用代码的一种很好的方法。

为了更好地展示这种方法,我建议您查看此网站www.MarekKnows.com并按照Shader Engine系列视频教程进行操作。虽然这个特定的网站专注于使用C ++的Win32,但使用的是OpenGL而不是DirectX。然而,整体设计模式具有相同的概念。唯一的区别是剥离OpenGL部件并用DirectX API替换它们。

编辑 - 其他参考资料:

我还发现这是由Marek Krzeminski撰写的批量渲染过程,这是来自他的视频教程,但在Batch Rendering by Marek at Gamedev