【发布时间】:2017-01-15 19:23:10
【问题描述】:
主题
我的问题是关于在结合 Apple 框架时更新周期的划分,以尊重该主题的典型模式和良好实践,因为大多数文档和示例代码尚未适应 Swift(或至少我在任何地方都找不到它)。
在 GameplayKit 中有很多方法可以管理更新周期,我不太确定什么是组合所有内容的好方法。
元素
首先:实体/组件中的每个类(GKComponent 和GKEntity(子)类)都有一个update() 方法,您可以覆盖该方法以执行每帧更新。那必须来自当前GKScene/SKScene的更新周期。
然后您就有了GKComponentSystem,您可以使用它来启动已添加到其中的给定类型的每个组件的update() 方法。我明白了,这很方便。
但我也想使用状态机系统,它也有自己的更新周期......结合所有这些让我感到困惑。
我的情况
如果我有一个 GKEntity 的子类,并在初始化时创建了一个 GKStateMachine 的实例。状态机有几个状态(目前:“Spawn”、“Normal”、“Stunned”和“Death”。
现在,我正在用我的GKEntity 子类创建一个大的“千篇一律”,并创建它将在初始化期间使用的所有组件。但它变得非常不切实际。例如,我有一个MovementComponent,它是GKAgent2D 的子类。我创建了一个管理实体创建的单例,所以在创建实例后,if 循环遍历所有实体的组件并将它们添加到相关的GKComponentSystems。单例有一个它自己的 update() 方法,更新将调用传递给GKComponentSystems。我使用的一些组件不需要逐帧更新,因此没有为它们创建GKComponentSystem,我根据需要手动更新它们。
如果我回到我的实体,因为我一次创建所有内容并使用GKComponentSystems 更新组件,我的组件的更新方法加载了guard 和if-let 语句,因为我需要访问实体的状态机器,检查它是否是实体可以移动的状态(正常状态)并做它的事情或逃避功能。这在我看来效率不高:移动组件在生成、眩晕或死亡时不需要更新。
最重要的是,它使我对GKStateMachine 的使用完全过度,因为我的更新方法是空的:无论如何,组件都会由GKComponentSystem 更新。
我的想法
完全删除
GKComponentSystems并简单地循环遍历我的所有实体(如果需要,可能在某些时候将它们分类到不同的集合中)并调用它们的update()方法。将更新发送到状态机,然后状态机将更新该状态中涉及的组件。-
保留
李>GKComponentSystems并使用状态机来处理组件,例如在进入和退出正常状态时从组件系统中添加和删除MovementComponent。
选项 1 很简单,但从长远来看,当我的结构变得更复杂时可能会导致问题,因为某些组件可能需要先于其他组件更新。让每个实体更新自己的组件会分散更新过程。
选项 2 在某种程度上也会让人感到困惑,但我最担心的是组件的创建/删除。我是只将它们从GKComponentSystems 中取出还是完全从实体中取出?最有效的方法是什么?
实际问题
我的哪个选项是最好的?有没有更好的办法。
【问题讨论】:
-
这被 5 个对 SpriteKit 和 GameplayKit 没有表现出兴趣的人关闭,真是太不可思议了。这个问题是任何考虑使用 SpriteKit 的固有问题,即使没有 GameplayKit。结合起来,这是在整个使用过程中运行的第一个和随后的设计/架构问题。还有像 MarkBrownsword 和其他一些人,他们拥有丰富的经验和细致入微的理解,不仅可以提供客观的概述,还可以提供具体、准确和有针对性的建议。那不是意见。他们是专家。没有人能回答这个问题。
-
因此,带着对这些投票结束本次投票的人的直接恼怒,为自己辩护。除非另有证明,否则您不是专家。您能否展示对 ECS、游戏循环和状态机的深刻理解?使用 SpriteKit 和 GameplayKit 时,您的“在棋盘上运行”在哪里?就因为你们五个不了解这个问题的针对性和针对性,并不意味着其他人不了解。我没有洞察力和智慧来回答这个问题,但至少了解它的内在目的以及回答它需要什么......专家。忽略你的关闭推理。
-
@Confused :非常感谢。我很感激。
-
我现在有同样类型的难题,除了 GKEntity/GKComponent 类之外,我一直在尝试使用协议、结构和扩展......我不确定会起作用,但我和你一样在寻找最佳实践。
标签: sprite-kit swift3 gameplay-kit