【发布时间】:2017-08-22 06:15:47
【问题描述】:
我正在尝试为 SceneKit iOS 游戏设计架构。我在下面展示了我当前首选想法的两个粗略 高级对象图/图表。
我目前只关注高级架构,即管理 Menu/GameLevel/Config/Paused 应用程序状态之间的转换,并使应用程序数据驱动,以便它可以处理多个级别等。一旦我得到这个工作,然后我将解决较低级别的架构,例如对于 GameLevel 状态,我将有一个 GameLevelModel 对象来表示实际的游戏关卡逻辑。
很高兴听到哪个看起来更有希望,有什么明显的陷阱或要避免的事情吗?
A 版)基于 MVC,带有自定义容器和嵌套 VC
我试图在这个版本中保持接近 MVC 范式。
应用程序的行为在其不同状态(菜单/游戏级别/配置/等)之间发生显着变化,因此我将使用永久容器视图控制器,以父子关系管理/转换多个嵌套 VC根据 Apple 的“iOS 视图控制器编程指南”。这些实际上是整个 MVC。
因为 Apple 的容器控制器(UINavigation-、UISplitScreen-、UITabBar-)都不适合(我需要整个屏幕),所以我将拥有一个自定义容器 VC (RootViewController),它始终有一个嵌套的子 VC。每个子 VC 的视图将始终完全覆盖容器的视图。子 VC 之间的转换将由 RootVC 管理并由其 StateMachine 驱动。
每个子 VC(实际上是整个 MVC)在其对应状态变为当前状态时创建,然后在被下一个状态替换且不再需要时释放。类似于 UINavigationController 如何处理它包含的 VC。
我对这种架构的唯一担心是它看起来有点沉重。 SceneKit 看起来像是设计用于单个 SCNView 并在我们需要更改 3D 内容时在多个 SCNScene 之间转换。这也提供了更多的过渡选项。
--------------------------
| RootViewController |
--------------------------
| | | | |
------------------ | | | | | ------------------
| GameLevelsData |----- | | | -------| SCNView |
------------------ | | | ------------------
------------------ | | |
| PlayerData |-------- | |
------------------ | |
| |
---------------- |
| StateMachine | |
---------------- |
| |
|-(*MenuState) |
|-(LevelState) |
|-(ConfigState) |
|
|
------------------------
| MenuViewController |
------------------------
----------------- | | ------------------
| MenuData |------ -------| MenuSCNView |
----------------- ------------------
(child VCs for other States, Level-/Config-/etc are created as needed)
|
------------------------
| LevelViewController |
------------------------
------------------ | | ------------------
| GameLevelModel |------ -------| LevelSCNView |
------------------ ------------------
版本 B) 基于场景(一个 VC,多个场景)
我将只有一个视图控制器 (GameViewController) 及其视图 (SCNView),它们将持续整个应用程序生命周期。 (我将不在这里有容器和嵌套的 VC。)
应用状态(Menu/GameLevel/Config/etc)之间的行为和内容的变化是通过场景和不同 TouchHandler(每个状态的 UIResponder 子类)之间的唯一视图转换来实现的,在相关时给予 First Responder 状态。
(Menu-、GameLevel- 等)TouchHandler 类只会覆盖touchesBegan/Moved/Ended 和canBecomeFirstResponder,这样我就可以拦截触摸事件而不会使单个控制器和视图膨胀。我的其他对象都不是 UIResponder。我还没有完全测试过这部分。
对于每个应用程序状态,将创建该状态所需的对象,例如相应的 Scene、TouchHandler、(在 GameLevelState 中具有游戏关卡逻辑的 GameLevelModel)等,并在进入下一个状态时释放。
我目前的问题是,当使用 SKTransition 在单个 SCNView 上的多个 SCNScene 之间转换时,在 5-20 次转换后会出现内存泄漏。我尝试通过简化场景、在解除分配之前删除所有动作、节点来解决,但没有任何帮助。避免泄漏的唯一方法是避免 SKTransition 并直接将场景分配给 View 的场景属性scnView.scene = scnScene。所以这需要我自己制作过渡动画。
--------------------------
| GameViewController |
--------------------------
| | | |
------------------ | | | | ------------------
| GameLevelsData |----- | | -------| SCNView |
------------------ | | ------------------
------------------ | | |
| PlayerData |-------- | |
------------------ | |
| |
---------------- |
| StateMachine | |
---------------- |
| ------------------
|-(*MenuState)--------- | MenuSCNScene |
|-(LevelState) | | ------------------
|-(ConfigState) | |
| |
-------------------- | |
| MenuTouchHandler |---| |
-------------------- |
----------------- |
| MenuData |---------
-----------------
(When entering, each state creates objects of corresponding
dedicated subclasses for its Model, TouchHandler and Scene)
| | |
-------------------- | | -------------------
| LevelTouchHandler |---| | | LevelSCNScene |
-------------------- | -------------------
------------------ |
| GameLevelModel |---------
------------------
提前致谢。
【问题讨论】:
-
我会在gamedev.stackexchange.com问这个问题
-
谢谢大卫,我也是这么想的,首先在那里搜索答案和解决方案,但发现很少,然后在这里查看,stackoverflow 上还有更多内容。例如,在 GameDev 搜索“SceneKit”会得到 27 次点击,而在这里我得到 3400 次 :)
标签: architecture game-engine scenekit