我处理了大量的体系结构设计模式和指南,以供选择,并遵循作为一个android客户端服务器应用程序开发人员。
最受欢迎的是:
由于模式的严格规则,开发人员不得不承认模式本身只是推荐的,根本不需要Android。
LibGDX也是如此。LibGDX库没有提供严格的规则或要求,因此开发人员可以自由决定如何编写游戏。
所以问题是:
是否有一些建议,设计指南,甚至LibGDX游戏开发人员遵循的标准?我应该如何以其他开发人员很容易理解的方式编写代码(使用LibGDX)?
发布于 2021-09-10 11:49:12
三年过去了,我可以自己回答这个问题了。
我发现使用ECS (实体组件-系统)是创建游戏的最佳方法。
使用这种方法,您将有3个不同的目的对象。顾名思义,它们是:
Entity --只是一个通用对象,它只包含一组component对象,通常是一个ID。Component -是一袋数据。没有逻辑只是普通的POJO。它包含的数据将定义包含组件的Entity的行为。System -是你把逻辑放进去的地方。每个系统都应该处理一个entity当且仅当它包含一组非常特定的components。Engine --是一个场景的表示,所有的entities都在其中生活,并由systems处理。实现这种方法的简单方法是使用阿什利库。它是ECS的一个轻量级实现。虽然我的经验表明,这是最好的情况下,真正的游戏。如果你想有非常具体的动画(甚至游戏对象),那么使用scene2d。
Scene2d代表了一种更熟悉的方法(对绝大多数开发人员来说)。它是放置在层次结构中的UI元素的图表。有非常有用的Action,可以用来实现您的动画。它也最适合任何你想在游戏中显示的UI。
因此,总而言之,我已经计算出,每个屏幕应该有几个类,才能有明确的分工。
Screen --我把它看作是运行代码的分支。它包含一个Engine (如果我们需要一个ECS)和一个Stage (如果我们需要一个UI)。处理所有游戏事件,用户输入和路由。Engine容器,它知道如何管理它的系统、实体和组件.Stage - UI容器,它知道什么UI元素应该存在,它们应该如何外观和行为。kotlin中的简单示例(请注意,在我的实际项目中,我使用柯恩 DI将所有内容绑定在一起):
class MyGameScreen : Screen, MyGameEngine.Callback, MyGameStage.Callback {
val engine = MyGameEngine(callback = this)
val stage = MyGameStage(callback = this)
override fun create() {
engine.create()
stage.create()
}
override fun render(delta: Float) {
enigne.update(delta)
stage.act(delta)
stage.draw()
}
override fun dispose() {
enigne.dispose()
stage.dispose()
}
override fun buttonPress() {
//handle button press
}
override fun onGameEvent(event: MyGameEngine.Event) {
//handle some game event
}
}
class MyGameEngine(
private val callback: Callback
) : com.badlogic.ashley.core.PooledEngine() {
fun create() {
// create and add all your systems and entities
}
sealed class Event {
// ...
}
interface Callback {
fun onGameEvent(event: Event)
}
}
class MyGameStage(
private val callback: Callback
) : com.badlogic.gdx.scenes.scene2d.Stage() {
val button1 = TextButton(...).apply {
addClickListener { callback.buttonPress() }
}
val label1 = Label(...)
// and so on
fun create() {
val root = Table().apply {
// add all your actors to the root table
}
val rootContainer = Container(root).apply {
setFillParent(true)
fill()
top()
}
addActor(rootContainer)
}
fun startSomeAnimation() {
val action = Actions.sequence(
// your animation
)
addAction(action)
}
interface Callback {
fun buttonPress()
}
}发布于 2018-11-05 10:24:48
根据我的经验,没有一个标准是每个人都遵循的。libGDX开发人员来自不同的背景。有些人是日常生活中的后端开发人员,有些人只是业余爱好者,学习他们的第一种开发技能。
我看到许多libGDX开源项目都有典型的静态SomeManager.getInstance()调用,而我更喜欢传递引用(作为后端开发人员,您将了解这些优点-可测试性等等)。
即使libGDX后端本身也不遵循一种方法。有一些部分通过反射获得对管理器的引用(这并不好,因为您必须从混淆中排除此类类),还有一些部分使用静态getInstances()。
如果您也是HTML5,您还必须遵守一些基于GWT的限制,因此有时您不得不在开发Spring应用程序时采取一种您永远不会做的方式。
https://stackoverflow.com/questions/53136080
复制相似问题