Java LWJGL中的Tile引擎

Java LWJGL中的Tile引擎,java,opengl,sprite,lwjgl,tiles,Java,Opengl,Sprite,Lwjgl,Tiles,我正在用LWJGL重写一个游戏(最初的引擎是纯java的),我想知道将地图渲染到屏幕上的最有效方法。我将制作一个平铺贴图,并为每个可行走平铺、碰撞平铺和静止对象创建一个图层。我将通过解析一个XML文件来阅读游戏中的所有内容 我的问题是,我是否应该这样做,并将每个磁贴分别读取到游戏中,并将值存储到2d数组中,将它们分配给精灵,并将每个精灵渲染到其各自位置的屏幕上?或者,让这些层成为自己的单个图片文件并渲染层而不是平铺,会不会对CPU/GPU造成更少的负担?我想第二个会让人更痛苦,但它值得吗?最好将

我正在用LWJGL重写一个游戏(最初的引擎是纯java的),我想知道将地图渲染到屏幕上的最有效方法。我将制作一个平铺贴图,并为每个可行走平铺、碰撞平铺和静止对象创建一个图层。我将通过解析一个XML文件来阅读游戏中的所有内容


我的问题是,我是否应该这样做,并将每个磁贴分别读取到游戏中,并将值存储到2d数组中,将它们分配给精灵,并将每个精灵渲染到其各自位置的屏幕上?或者,让这些层成为自己的单个图片文件并渲染层而不是平铺,会不会对CPU/GPU造成更少的负担?我想第二个会让人更痛苦,但它值得吗?

最好将瓷砖组合在一起,形成一个大的纹理图谱。假设您使用32x32像素的瓷砖,2k纹理最多可以容纳4096个不同的瓷砖,对于一个游戏来说可能已经足够了。原因是您可以绑定此纹理一次,然后(几乎)使用它进行所有渲染,从而避免昂贵的纹理切换操作。不要对每个磁贴使用单独的图片。所有纹理和其他渲染资源都应该提前上传,最好在游戏负载或级别负载时上传

对于实际的平铺和对象,您应该构建一个顶点缓冲区,该缓冲区包含所有对象的顶点属性,并在级别加载期间上载它。此缓冲区将包含顶点位置、颜色、纹理坐标。。。绘制平铺所需的一切,如果一个缓冲区不够,可以将其拆分为多个缓冲区。对于每个帧,使用摄影机坐标找出哪些平铺可见,哪些不可见,然后发出绘制调用,调用第一个可见平铺的起始索引和可见平铺的计数。简单的AABB检查在这里非常好。当然,为了实现这一点,顶点缓冲区的布局必须使其只朝一个方向移动,例如从左到右和从上到下

或者,您可以进行更多更具攻击性的顶点计数修剪,但代价是进行更多的绘制调用:将世界分割成块,使每个块足够大,可以覆盖整个屏幕。如上所述,为每个块创建顶点缓冲区。然后做同样的摄像机检查,找出哪一块是可见的,然后画出来。在这种情况下,在任何给定时间至少有1个块可见,最多有4个块可见,这意味着1到4个draw调用。这种方法比前一种方法更有优势,因为不必在每个分块上循环,您可以在分块上循环,这意味着所需的检查要少得多


如果操作正确,您可能只需要几个绘制调用就可以渲染世界,并且仍然能够绘制大量的瓷砖。显然,这只意味着对于静态对象,您需要以不同的方式绘制动态对象。请记住,draw调用可以进行上下文切换,这非常昂贵,应该尽可能避免。

现代GPU每秒可以渲染数千万个三角形。第二种方法可能会稍微快一点,但当您仅使用0.01%的容量开始时,这并不重要。Ohhh。我之前读过一篇文章,有人在屏幕上渲染了大约700个精灵,他有明显的延迟,但我猜他没有具体说明这些精灵的分辨率是多少。但是,我将使用16x16或32x32,所以我认为你是对的。他可能是以一种愚蠢的方式渲染他的精灵,比如每帧都重新上传。我怎么能不这样做呢?上传纹理是调用
glTexImage2D
或类似函数。所以,不要每帧都打电话?或者在你真正遇到问题之前不要担心性能。谢谢你的回复。我对OpenGL还很陌生,所以我很难理解所有这些东西。我也没有找到真正展示这些openGL对象的功能以及如何使用它们的资源。你能给我指一个资源来解释你提到的那些主题吗?这是一个很好的开始使用openGL的资源。它使用C++,但所有的东西都应该与java相同。关于优化,这是一个相当广泛和复杂的话题,所以现在我们不要太担心;我目前正在制作2D游戏,所以我真的怀疑渲染是否需要太多的优化才能工作。谢谢你,伙计!