你没有提到你使用的是什么语言,所以我将用中产阶级提供的面向对象的 Lua 编写这个 - https://github.com/kikito/middleclass(免责声明:我是中产阶级的创造者)
另一种选择是将过场动画拆分为“动作列表”。如果您已经有一个在对象列表上调用“更新”方法的游戏循环,这可能会更好地与您的代码融合。
像这样:
helloJane = CutScene:new(
WalkAction:new(bob, jane),
LookAction:new(bob, jane),
SayAction:new(bob, "How are you?"),
WaitAction:new(2),
SayAction:new(jane, "Fine")
)
Actions 将有一个 status 属性和三个可能的值:'new'、'running'、'finished'。所有的“动作类”都是Action 的子类,它将定义start 和stop 方法,并且默认将状态初始化为'new'。还有一个默认的update 方法会引发错误
Action = class('Action')
function Action:initialize() self.status = 'new' end
function Action:stop() self.status = 'finished' end
function Action:start() self.status = 'running' end
function Action:update(dt)
error('You must re-define update on the subclasses of Action')
end
Action 的子类可以改进这些方法,并实现update。例如,这里是WaitAction:
WaitAction = class('WaitAction', Action) -- subclass of Action
function WaitAction:start()
Action.start(self) -- invoke the superclass implementation of start
self.startTime = os.getTime() -- or whatever you use to get the time
end
function WaitAction:update(dt)
if os.getTime() - self.startTime >= 2 then
self:stop() -- use the superclass implementation of stop
end
end
唯一缺少的实现部分是 CutScene。一个 CutScene 主要有三样东西:
* 要执行的操作列表
* 对当前动作的引用,或动作列表中该动作的索引
* 更新方法如下:
function CutScene:update(dt)
local currentAction = self:getCurrentAction()
if currentAction then
currentAction:update(dt)
if currentAction.status == 'finished' then
self:moveToNextAction()
-- more refinements can be added here, for example detecting the end of actions
end
end
end
使用这种结构,您唯一需要的就是游戏循环在每次循环迭代时调用helloJane:update(dt)。并且您消除了对协程的需求。