MMORPG开发和服务器端逻辑,更新所有游戏对象?

时间:2013-04-28 14:49:48

标签: c# .net

我之前设计过多人游戏,但现在我想创建一个MMORPG架构用于学习/挑战目的。我想在一台服务器上模拟数百(或几千)个并发播放器。

到目前为止一直很好,除了现在我正面临一个问题,即找出一种更好的方法来尽可能快地更新服务器上的所有游戏对象。

游戏对象我指的是所有玩家,暴徒,子弹。

问题在于所有Players,Mobs,Bullets都存储在服务器端内存的集合中,以便更快地处理,并迭代所有这些以检查冲突,更新运行状况,更新运动等等......太长了。

让我们说我有1000名玩家,全世界有10000名小怪,所有玩家和生物都有责任创造5个其他游戏对象(不多也不少),如子弹。

这将在集合中提供(1000 + 10000)* 5 = 55000个游戏对象。

迭代所有对象,更新它们,在具有4GB RAM的双核HT i5上永远(几分钟)。这是错误的。

迭代时,代码看起来像这样(伪):

for(int i = 0; i < gameobjects.Count; i++) {
  for(int j = 0; j < gameobjects.Count; j++) {
      // logic to verify if gameobjects[i] is in range of
      // gameobjects[j]
  }
}

作为优化,我正在考虑将我的游戏对象划分到不同的区域和集合中,但这不能解决我需要每秒多次更新所有对象的问题。

我应该如何继续更新服务器端的所有游戏对象?我做了大量的搜索来找到有趣的游戏设计模式但到目前为止没有结果。 :(

提前致谢!

3 个答案:

答案 0 :(得分:4)

我会完全改变设计并实现事件库设计。这有许多优点,显而易见的是,您只需要更新实际与之交互的对象。因为在MMO游戏中你总是会有大部分游戏对象闲置,或者根本没有看到。

没有理由计算在任何播放器屏幕上看不到的对象。这将是疯狂的,需要一个你很可能负担不起的服务器场。相反,你可以尝试预测运动。或者存储当前未与之交互的所有对象的列表,并更频繁地更新这些对象。

如果玩家无法看到物体,您可以远距离传送该装置而不是让它平稳地移动。基本上在允许物体移动的受限区域内移动单元很长的距离。即使对象对玩家不可见,使对象看起来像是自由移动。通常这会在新玩家进入或离开区域时作为事件触发。

您可以通过简单地计算自上次更新以来的时间来预测,并预测对象将走多远,就好像它对玩家可见一样。这对于具有设置路径的对象或NPC特别有用,因为它使计算更加简单。

答案 1 :(得分:2)

你的代码运行速度很慢,不仅因为它检查了所有N个对象,而且因为它检查了对象的所有可能的交互,并且在你的样本中需要N ^ 2个计算= 3 025 000 000。

减少这种检查次数的一种方法是将游戏世界中的对象放入网格中,这样不在相同或对齐单元格中的对象就无法相互交互。

此外,您当前的代码会检查每次交互两次,您可以通过在内部循环中从i开始循环来轻松解决此问题:

for(int i = 0; i < gameobjects.Count; i++) 
  for(int j = i; j < gameobjects.Count; j++) 

答案 2 :(得分:0)

循环超过55,000个对象不应该太慢。显然,你经常在这些对象上做太多的事情,并且可能做一些不应该总是这样做的事情。

例如,如果暴徒周围没有玩家,是否真的要计算? (如果一棵树落在森林里,周围没有人,它真的会发出声音吗?)

此外,许多对象可能不需要在每个循环中更新。例如,玩家可以留给客户进行计算,并且每1-2秒只进行一次“验证”。将所有玩家的碰撞倾倒到客户端会使您的服务器工作负载更容易处理。玩家的子弹或光线投射也是如此。作为回报,它也让游戏更加流畅。

跟踪路径时的怪物是否需要进行碰撞测试,或路径的节点是否足够?

针对每个其他对象测试每个对象非常糟糕。是否必须对所有其他怪物进行测试,或者只需要测试特定类型或派系?你能否将你的世界分成更小的区域,只能测试其中的怪物对抗其中的物体?

在MMO服务器的代码中做了大量的工作,使其正常工作。完成的优化有时是疯狂的,但只要它有效。