Moai SDK を使う
 All Files Functions Variables Pages
シーン(状態遷移)の実現

概要

状態遷移の利用方法

状態遷移について簡単に説明します。
イメージしやすくするために「歩く」「休む」という2つの状態を考えます。これらの状態は、適当な時間で遷移するとします。文章で表現すると、

「歩いたり、休んだりする」

とも書けます。
これを状態遷移で表現すると、

dot_inline_dotgraph_2.png

という風に表現できます。
ここでは、「状態に入ってきたとき」「状態を処理しているとき」「状態から抜けるとき」の関数を定義することで表現する方法を紹介します。

例えば、上記の「歩く」という条件は以下のように定義することができます。

local walk = {}
local rest = {}
-- 「歩く」の定義
walk["Enter"] = function(state)
print("enter walk")
end
walk["Execute"] = function(state)
print(".")
if math.random() < 0.1 then
state:change_to(rest)
end
end
walk["Exit"] = function(state)
print("exit walk")
end

これを State_machine クラスを利用した実際のコードが、以下になります。

--! \example
--! 「歩く」と「休む」の状態を遷移するサンプル
package.path = "../lib/?.lua"
_G.Path_to_lib = "../lib"
require("Gui")
require("State_machine")
require("Coroutine")
Gui:open_window("state_machine", Gui.landscape)
local walk = {}
local rest = {}
-- 「歩く」の定義
walk["Enter"] = function(state)
print("enter walk")
end
walk["Execute"] = function(state)
print(".")
if math.random() < 0.1 then
state:change_to(rest)
end
end
walk["Exit"] = function(state)
print("exit walk")
end
-- 「休む」の定義
rest["Enter"] = function(state)
print("enter rest")
end
rest["Execute"] = function(state)
print("z")
if math.random() < 0.1 then
state:change_to(walk)
end
end
rest["Exit"] = function(state)
print("exit rest")
end
local state_machine = State_machine:new()
state_machine:set_current_state(walk)
local update = function()
while true do
state_machine:update()
coroutine.yield()
end
end
Coroutine:new(update)

このような考え方は、キャラクターの行動だけでなく、ゲームの起動画面からプロローグ画面に移るといったシーン管理などにも利用できます。
状態に分けることによって、各状態毎の実装に分割できるのがメリットです。

State_machine についての詳細は State_machine.lua から確認できます。

この概念については、「ゲーム AI プログラミング」の書籍などで詳しく説明されています。