文 / Benedikt S. Vogler

过去今年里我一直在开发一款名为Wurfel Engine的游戏引擎。以下大部分内容是对于我在学校中的最后一次考试所发现的一些算式与解决方法的解释并在过去2年里得到完善的论文摘录。

你们可以在Wurfel Engine SDK,即我基于Java所编写的开放源游戏引擎中找到以下的大多数算式。现在的我正使用该引擎创造名《Caveland》的商业游戏。

储存地图数据块

储存砖块的一种简单的方式便是使用钻石地图。钻石地图就是一个旋转的固定网格(如图1)。

fig1(from gamasutra)

如果整款游戏都是发生在一张小小的地图上的话这便很适合。然而如果你需要执行一个更大的(开放)游戏世界或生成地图内容,你便需要“流出”数据。为此你需要加载数据块。使用钻石地图是否能够完成流传播?如果你使用钻石地图格式,你的数据块只会如下无缝地进行排列:

fig2(from gamasutra)

灰色矩形代表的是屏幕。你可以发现你需要更多组块去覆盖屏幕。然而你希望组块能够像这样组合在一起:

fig3(from gamasutra)

因此Wurfel Engine使用了一排移动的网格,通常被叫做“错列地图”,这非常适合地图流传播。在错列地图中每个第二排都会移动半个砖块。

fig4(from gamasutra)

拥有数据组块的RAM将遭遇只能模仿接近摄像机的实体的问题。这适合于大多数游戏。如果该区域外部的某些内容(游戏邦注:对于游戏玩法来说可能很重要)出现,你就需要在RAM中添加更多数据块。

访问并储存数据块

存在多种储存数据的方式,在这种情况下数据块总是包含组块。我们想要更快速地访问数据,这意味着基于0(1)进行访问。做到这点的一种简单方式便是使用一个3D数组。很长一段时间我都在使用一个巨大的3D数组,它将被插入一个巨大的地图模型中,如果它们被移除可视区域,那么剩下的数据将被移出内存。

这一解决方法也带有自身的缺陷,因为它允许一个视窗的存在。如果你想要在一个开放世界中执行分屏的话会怎样?摄像机可以设置在完全不同的地方,但只有你处于同一个场所时地图才会运行。我通过将各自带有一个3D模型的数据块储存在一起而解决了这一问题(现在我正在使用一个简单的列表)。为了找到并获得归属于游戏坐标的单元格内容,二手手机买卖平台你需要为每个数据块和维度储存一个固定点。之后你可以在列表上反复进行迭代并判断哪个数据块覆盖了这一坐标。如果是这种情况的话,你便可以通过在角落减去固定点而估算指标的位置。

自定义迭代器是贯穿这张地图的一种有效工具。

fig5(from gamasutra)

基于不为了海量储存减少RAM的使用同游戏,你需要在内存中储存许多数据块或组块。如果你在每个数据块中都包含数千个组块,那么储存每个伴随着多个字段的组块将快速消耗内存容量。现在我正在尝试一个版本,即我只会储存3个字节去代表一个组块。如果它们处于摄像机视窗中,它们便会被转换成带有更多字段且能够用于渲染方法中的对象。这一方法能够帮助我们节省不少空间,即我们可以使用200兆的空间去储存一个1800平方千米的区域。

执行屏幕的一种更好的方法

如果你正在使用一张钻石地图,你的行数将不会发生改变,你也不需要如下的方法,因为你可以通过旋转并改变屏幕空间坐标获得备选单元,然后再离散化数值。

使用错列地图离散化屏幕空间的x和y坐标将会呈现出两个砖块间模糊的结果。

存在两种用于识别正确砖块的常见方法。一种方法便是使用一些颜色编码图像(图6)去识别你的鼠标所点击的角落。这更像是一个难以执行的黑客,有可能改变砖块的维度,并且会创造出错误的结果。还有一种方法是估算砖块中心位置间的距离并使用最接近的那个。我发现这一方法拥有一些意外的结果。这是一种动态的方法,能够通过使用一些不等式去检测侧面而支持不同的砖块大小。

fig6(from gamasutra)

如果你使用如下方程式,你便能够获得与一些图形计算器中的图像方法一样的结果:

fig7(from gamasutra)

当然了,你也可以通过将x或y乘以一个系数而扭曲砖块。

如果你着眼于图表,你将会看到一些重叠的区域。通过检查两个完整的方程式,你便可以识别每个区域并检测一些点是否位于一些邻近的位置上。

一旦你执行了这一方法,你便可以使用该方法去获得游戏中任何点数的单元坐标,该功效也使这一方法变成了一个更加强大的工具。

巧妙地裁剪等距世界

等距游戏世界通常都是扁平的。有时候砖块也是扁平的,但它们更常使用3维砖块,因为这样便可以在高度上移动它们。渲染一个扁平的世界并不会受限于性能。然而Wurfel Engine使用了一个立方体地图。你可以在彼此上方堆积许多组块,这将导致许多重叠组块的出现。因为执行碎片/像素着色器而出现的许多看不见的像素导致执行非定义隐藏界面检测(HSD)会非常致命。

提高性能的一种简单方式便是基于带有三个不同精灵的三面分割每个组块。如果没有组块在前方而遮住其它组块,你便可以只渲染上方和前方。这一算法将执行每个组块的循环并检查其直接邻近对象,从而确定最终的裁剪对象。

为了让设计高度等于设计深度(图8)而使用扭曲的四边形组块时,我们便能够执行一些有效的裁剪。

fig8(from gamasutra)

我通过面向每个组块发送三条射线而做到了这点(图9),每一面一条射线,贯穿地图并检测它们何时遇到可视的那一面。每一条射线会为了每一个半面而分裂成两条以上的射线。在有些情况中一些组块将覆盖一半的面,而有些加深了另一半面的图层将被隐藏于其它组块中(图10)。每个撞击到的面都将获得一个标志。然后渲染器将只会渲染没有标志的面。

fig9(from gamasutra)

fig10(from gamasutra)

后面组块的左边被隐藏起来了,并且没有直接的邻近组块

然而为了艺术,维度将被转换成真正的等距组块。它们是存在问题的,即当你在堆积时它们并不能排成一行,因为设计高度大于设计深度。你可以在图11中看到这点:并不是每一个角落都能够与网格对齐。射线将通过假设组块是否匀称地将其覆盖住而追踪裁剪是否有效。所以基于光线投射的裁剪算法将被更简单的算法所取代。这一算法的问题在于它并不能判断组块是否被隐藏起来以及组块之间是否存在一定的空间,如当组块被一堵墙或屋顶所覆盖住时。

fig11(from gamasutra)

当地图内容改变时,两种裁剪算法都应该被执行。

总结

基于使用案例和要求,我们知道存在更多不同方式去创造一个类似且有效的游戏引擎。每个设计选择都应该始于组块的维度。在体素引擎领域中,我们可以找到许多更快捷的内存节省方式,并且能够将其用于之后的研究中。

基于组块设计执行开放世界等距游戏引擎相关推荐

  1. 《原神》——开放世界二次元游戏的一些见解和建议

    一.原神在海外的布局 原神商业化的成功绝对离不开其海外的布局,截止目前的数据来看,原神在海外的市场带来的商业化价值已经和国内相近甚至更高.原神不仅在多国拿到付费榜榜首的好成绩,并且在12月1日,谷歌公 ...

  2. 从零到设计、建模和实现游戏引擎的3D游戏角色模型制作

    从零到设计.建模和实现游戏引擎的游戏角色创建方法的分步指南. 1.. 概念艺术 首先,我们根据描述和风格参考创建粗略的概念艺术.在这个阶段,主要目标是创建角色的总体形状和感觉.所以它可以是黑白的. 如 ...

  3. 【SIGGRAPH 2015】【巫师3 狂猎 The Witcher 3: Wild Hunt 】顶级的开放世界游戏的实现技术。...

    [SIGGRAPH 2015][巫师3 狂猎 The Witcher 3: Wild Hunt ]顶级的开放世界游戏的实现技术 作者:西川善司 日文链接  http://www.4gamer.net/ ...

  4. 线上幽灵:世界头号黑客_开放世界设计的经验教训:幽灵行动的故事

    线上幽灵:世界头号黑客 游戏设计案例研究 (GAME DESIGN CASE STUDY) Video games convey the exquisite sense of escapism lik ...

  5. 从《旷野之息》马匹系统的设计看任天堂对开放世界的把控

    托大量开放世界的福,如今全世界玩家都知道了开放世界要保证内容密度,大而空的开放世界是不好玩的.<旷野之息>被作为模范生经常会被拿出来举例,比如这张图. 旷野之息的地图互动点密度非常高 但内 ...

  6. Unity游戏开发:开放世界地形关卡

    荒野大镖客.赛博朋克2077.上古卷轴系列等等这些主机游戏又被称之为游戏中的好莱坞大片!数亿美元的巨大研发投入,使得这样量级的游戏,不仅要有高质的互动体验.具有特色的玩法.还需要具有及其炫目的画面视觉 ...

  7. 开发2年半,「纪念碑谷」的团队做了一款开放世界“观鸟”游戏

    如果你随便抓一个路人问他/她在手机上玩过最有艺术感的游戏是什么,相信大概率会得到的答案是「纪念碑谷」. 这款由英国Ustwo Games在2014年公布的作品极具个性和创意,在当时一众良莠不齐的移动游 ...

  8. 腾讯开放世界游戏《王者荣耀·世界》获登记批准,对标《原神》

    据 Tech 星球,开放世界游戏<王者荣耀・世界>于今年 8 月开始申请软件著作权登记,并于近日成功登记该游戏产品. 消息人士透露,虽然软件著作权已成功登记,但目前产品尚处于研发阶段. 在 ...

  9. 基于Python实现的吃豆人游戏设计

    资源下载地址:https://download.csdn.net/download/sheziqiong/86817091 资源下载地址:https://download.csdn.net/downl ...

最新文章

  1. 非阻塞模式与阻塞模式
  2. csu 1757(贪心或者树状数组)
  3. QQ、MSN、skype的网页临时会话代码
  4. fseek获取大于4G的文件大小的问题
  5. IBM押注沃森人工智能技术 未来6年或达170亿美元
  6. 搭建IIS并配置网站之旅
  7. 从原理上搞定编码-- Base64编码
  8. ASIHTTPRequest详解
  9. Kotlin — 适用于移动端跨平台
  10. java多个收银台收银_Java策略模式设计(简易收银台SpringBoot)
  11. 如何写php大马,带你走进php大马的结构模块编写之路
  12. 圆形led屏幕_一种简单的圆形LED显示屏的制作方法
  13. 前端偶数行有底纹怎么写_如何在Excel中的替代行上应用底纹
  14. PowerPoint.Application win32 操作ppt 复制 新建 插入图片
  15. 积分(Integral)
  16. 百度地图商家标注,查询附近3000米内的商家并标到地图上
  17. 【人工智能】1.问题求解:启发式搜索算法
  18. 【C语言】N 阶矩阵的转置
  19. 使用FFMPEG制作gif图片
  20. 免费营销:四大营销心理效应

热门文章

  1. 又到 6 月底,想来和你聊一聊毕业季,愿你前程似锦!
  2. mysql服务器多线程模型_mysql-线程模型
  3. devexpress内置图片的位置_向微思WGIS中叠加位图图片
  4. [视频教程] ubuntu系统下安装最新版的MySQL
  5. 【share】PHP站点用Squid再次疯狂加速你的WEB
  6. Python学习【day02】-str类型方法记录
  7. 关于IOS中safari下的select下拉菜单,文字过长不换行的问题
  8. Android Studio开发第二篇创建新项目
  9. bootstrap轮播,播放到最后一张图片的时候,就不正确了。
  10. 通过css将多个图标或图片用同一张图片通过定位背景位置调用到页面