2008年12月30日火曜日

スクリプトの話(最終回)〜シーンを切り替える「ステート」

今年も残すところあとわずかとなり、
今年中に片付けておかなければならないことを
バタバタと片付ける毎日ですが、
そう言えば、そう、
この連載も最終回を残すのみで止まっておりました。
というわけで、駆け足で幕を引きたいと思います。w

     *   *   *

さて、ダイアログを表示してボタンで選択させるなど、
処理を分岐する時に一番お世話になるのは「if文」ですね。
ただ、この「if文」が適しているのは、
「もし〜の時」の「〜」の部分がそれぞれ対応関係にある場合ですね。
例えば「1」と「1より大きい数の時」とか、
ステータスが「open」と「close」の時、
色が <1.0, 1.0, 1.0> と <0.0, 0.0, 0.0> の時、というように
比較対照が可能な場合です。

それでは、私の「世界時計HUD」のような場合はどうでしょう。
タッチするとダイアログが開き、
「Colors」と「Calculate」というボタンがあります。
「Colors」を選ぶと今度は色名のボタンが出て来て
どれかを選ぶと文字色が選んだ色に設定されます。
一方、「Calculate」を選ぶと、今度は都市の名前のボタンが現れ、
都市を選ぶと更に時刻を選ぶボタンが、
それも3ページにわたって表示され、
都市と時刻の選択の結果として、
その都市でその時間の時の世界の各都市の時刻の一覧が表示されます。





おわかりでしょうか?
「Colors」と「Calculate」は同じような選択ボタンでありながら、
その後の動きは全く違うのです。
これをもし「if文」を使って書いたとしたら
それはややこしいことになりますし、
予期しない変数の動きに翻弄されることになるかもしれません。
いっそのこと、「Colors」と「Calculate」それぞれを押した時、
全く別の処理の流れにするようにしてしまえば……。

こんな時便利なのが、「ステート」です。
ステートとは文字通りには「状態」ということです。
が、ここでは、この連載のはじめの方で
スクリプト=「台本」、
リンデンのスクリプトもアバターやオブジェクトを主人公とした
ドラマや劇だと考えればいいと書きましたが、
そういう意味では「ステート」は「シーン」、
「幕」とか「場面」に当たるものだと考えればいいでしょう。

ステートで一番有名なのが「default」というステートです。
defaultしかないスクリプトは
1場面だけでできた劇のようなものです。
しかし、多くの劇ではいくつかのシーンから構成され、
シーンが異なると主人公の行動も心の動きも変わったりします。
同じロミオも人生を憂う弱々青年ロミオだったり、
ジュリエットの心に光を点す王子様のような存在であったり、
ティボルトと剣で戦う時には勇敢な男であったりします。
同じように、リンデンのスクリプトも
「ステート」をいくつか設定することで、
複雑な動きをコントロールすることができるようになります。

例えば、上の「世界時計HUD」の例では、
「Colors」ボタンを押すと「色設定用のステート」に映り、
色の設定をし終わると、default ステートに戻って来ます。
同じように「Calculate」ボタンを押すと
「時刻計算用のステート」に移り、
都市と時刻を指定して世界各地の一覧を表示し、
ここで「OK」ボタンを押すと default に戻って来るのです。
実際の処理は複雑なので、イメージだけ書いておくと
こんな感じです。

(グローバル変数定義)

(時刻表示用の関数定義)

default {
  state_entry(){
    (初期設定の処理)
  )

  timer(){
    (時刻更新の処理)
  }


  touch_start(integer total_number) {
    (時計がタッチされた時の処理)
  }

  listen(integer channel, string name, key id, string message){
    if(message == "Colors") {
      state select_colors;
    }else if (message == "Calculate") {
      state select_calculate;
    }
  }
}

state select_colors {
  (「Colors」ボタンを選んだ時の処理)
}

state select_calculate {
  (「Calculate」ボタンを選んだ時の処理)
}

大体こんな感じです。
想像がおつきになるかと思いますが、
実際は select_colors のステートの中でも
select _calculate のステートの中でも
またダイアログを表示してボタンを選んで、という処理になりますので、
この中にもまた touch_start や listen があり、
ボタンの値によって「if文」で処理が分かれるので、
もっと複雑にはなります。
が、ステートを変えると便利なのは、
select_colors のステートにある時は、
select_calculate や default ステートの時のことを
全く考えずに、色設定のことに集中して考えられる点です。
これが「if文」だと、常に「そうでない場合はどうなるか」を
頭の片隅で考え続けながらプログラムを書いていかなければなりません。
これは、最初の頃に書いたように
プロでも間違いを犯しやすい状態と言えます。
ステートはリンデン・スクリプトの中でもとっつきにくい、
わかりにくいもののように思われていますが、
使いこなすと却って初心者のプログラミングを
楽にしてくれるものでもあるのです。
「if文」で条件分岐するのが難しい、と思ったら、
思い切って新しいステートを宣言して導入してみることを
ここではお薦めしておきたいと思います。

     *   *   *

というわけで、20回にわたって書いてきました「スクリプトの話」、
一応今回を以て終了とさせて戴きたいと思います。
スクリプトというものをプログラムと捉えるよりも、
アバターやオブジェクトが動き出すドラマ、物語の台本として考え、
そこで行き詰まった時にどうすればいいか、
そのコツのようなものを書いてきたつもりです。
これがスクリプトは難しい、どうもうまく動かないという方々の
ご参考に、少しでもなれば幸いです。
まだまだ本当はあれもこれも書いておいた方がいいのかな、
などと思うところはありますが、
とりあえずはここで止めておくことにしまして、
もし皆さんからのご意見、ご要望、ご質問などありましたら、
このSNSのメッセージ、またはIMでお寄せ頂ければ
またどこかで書かせて頂くこともあると思います。
その時はどうぞよろしくお願いします。

最後までお付き合い頂いた皆様、
本当にありがとうございました。
それでは、また!

No response to “スクリプトの話(最終回)〜シーンを切り替える「ステート」”

Leave a Reply