■迎春


30 Janvier MMVIII
 なんだか慌しく一月も終わりつつあります。早い。しかも二月は短いのだ。今年は29日まであるけど。

 ハルコを久しぶりに描いてみたら意外と細部覚えてなくて、うん、あれだ、アレンジということで。


DEV フレームワーク
 色々管理機能を強化してたらどんどんシェルっぽくなるのは必然なんだろうか。なんだかすごく無駄なことをしているんじゃないかという疑念が。まあそれはそれでまたヘンなこと出来るのでまるっきり無駄ではないんですが…問題はそのヘンなことを具現化する時間が確保しづらいということなのです。
 一日48時間ぐらいあればいいのに。きっと32時間ぐらい寝れるぞ。

MOVIE 不思議惑星キン・ザ・ザ
 前から観たかった怪作。丁度やってたので観てきた。
 チープなスラップスティック仕立ての社会風刺SF映画なんですが、なかなか面白かったのです。クー!

23 Janvier MMVIII
DEV リプレイ機能
 こちらから
 現状主流の方式がキー入力情報のみを記録するキーログリプレイ。同一の操作をするなら同一の結果が出てくるであろう、という数学的にも合理的な方式であり、1フレームにつき1キーログ(長さは格納方式によるがだいたい1ワード単位)とストレージにも優しいので、今後もこれが主流であり続けるだろう。
 反面、この方式はリプレイずれという不具合を発生しやすい。
 同一の操作にも関わらず、同一の結果が出てこない原因は以下のとおり。
[1]初期化が不完全性(乱数含む)
[2]初期化時及び初期化後に生成されるデータのみで内部自己完結していない
[3]表示スキップなどの再生ステップ操作による1ステップ内のシーケンス処理の不一致
[4]ハードウェア及びシステムレベルの不具合
 これでほぼ全てカバーされる。順に見ていこう。キーワードは「鎖国主義」だ。

[1]初期化の不完全性
 乱数シードが一番重要だが、システム変数なども全てこの時点で与えなければならない。
 また、ゲームの設定などもこの時点で「新たに生成したインスタンス」に全て与えなければならない。
 要するにこれは完全に初期化されたことが保証されているまっさらな状態のメモリ空間を用意しろということなので、プログラム的には厳密にインスタンスを毎回生成する必要はない。
 ゲーム中に設定ファイルを直接見にいったり、グローバルな変数を参照するなど言語道断である。
 全てのデータの入力をこの段階のみで行う出島を作る。但しデータの出力に関しては管理は不要。

[2]初期化時及び初期化後に生成されるデータのみで内部自己完結していない
 [1]とほぼ同義なのだが、初期化後についても外部へ固定(const)ではないデータを読みにいってはいけない。動的なデータは変化する可能性があるので、これがリプレイ再生時の差異を生む原因だ。
 動的なデータは全て初期化時に「新たに生成したインスタンス」に与えられたデータのみを使用する。全て新たに生成し均一のタイミングでデータの初期化を行えば出力結果に差異は出ない。
 つまり鎖国しろということである。

[3]表示スキップなどの再生ステップ操作で1ステップ内のシーケンス処理の不一致
 リプレイ処理で一番原因の多い部分であり地道に潰していかなければならない部分である。
 といっても原因となる要素の種類そのものは約3種類。
 ■乱数などのシーケンス管理
 乱数のように前回の計算結果をリレーしていくシーケンス管理は処理回数が変わってしまうことで出力結果の不一致が発生する。これは厳密に処理回数を管理し一致させることで解決する。
 なお、表示処理のスキップ処理などに対応する場合は、表示処理専用のものを用意するか、シーケンス管理を必要とするものを使用せず、完全に独立した処理を行わせる。表示負荷を軽減したりするパーティクル処理などはこの不具合の温床であり、それを回避するには負荷軽減処理を切り捨てるか、或いは完全に不干渉で独立した処理を行なうようにする。尚、物理エンジンのように干渉が不可欠なものは省略してはいけないので、必ず処理しなければならない。
 ■表示などのスキップ管理
 厳密には上のシーケンス管理と被る内容だが、重要なポイントがあるので別記。
 まず前提条件として描画部分の管理は内部処理から完全に独立させなければならない。オブジェクト内部で直接描画命令を実行するとか、パーティクルが処理関数をぶらさげてるとか言語道断である。
 どちらかというと[2]寄りの管理なのだが、使いまわしが難しい部分でもあるので[3]に分類した。
 ■オブジェクトオーダー管理
 オブジェクト生成のタイミングや表示負荷軽減などによってオブジェクトがメモリ空間に存在する順番は維持されねばならない。例えば当たり判定などの処理で2つ以上が重なった場合、どちらを先に処理するか?処理しているのか?という問題である。
 順不一致でも動作するように処理することは可能だが、全てのケースでそのようにコードを書かなければならないので非常に負担が大きい他、ルール的にそれが成り立たない可能性(完全に均一な条件をもつ複数の対象に対して1回しか処理できない、など)もあるのであまりおすすめしない。
 ルールを変えればいいではないか、と思うかもしれないが、コーディングがルールに制限を及ぼすことは本末転倒であり、大変よろしくない。まあ宇宙麻雀とか作りたいならそれでも構わないだろう。

[4]ハードウェア及びシステムレベルの不具合
 コンシューマのように全てほぼ同一の動作をするハード(PS系を除く)ならば発生しない問題。
 大きいところではSSEや3Dnowなどの数学処理機能、DirectXの設定による浮動小数点の桁数、端数処理など。環境によって出力結果に差異が発生するもの。これらの問題は様々な対処方法があるのでこれらを踏まえていけばよい。ただ、対処できるから環境の不具合ではないわけではなく、本来なら同じコードなら同じ動作をすべきところなのです。まあ結局は同じように動くように書くしかないんですが。
 また、中にはHTなどのCPU割り当て問題のようにプログラムレベルでは対応が難しいものもある。
 これは経験を積むことと情報収集しておくしかない。なによりユーザーからの正確なフィードバックが必要だ。正確な、というのがポイントで、必要な情報はその時に応じて様々なので、直接連絡をもらえないと困るんですが、最近はとんでもないところに書き捨てられてたりするのが本当に困る。嫌がらせか(笑
 まあ直接連絡してこないということは直す必要なし、ということで放っておいていいような気もします。

 それはともかく。
 上記のうち[1][2]は一度うまく構成しておけば再利用可能である。一応[4]もそうなのだが、現在のPC環境は刻々と変化してゆく(Vistaを見よ)ので残念ながらメンテナンスフリーにはなりえない。
 そして[1][2]の鎖国処理をきちんと行えば中の処理に変動を与える要素はない。リプレイの不具合を解消とは変動する要素をひとつずつ取り除いていく処理に他ならない。鎖国が完成し外堀が埋まって、尚も問題が発生するなら、それは中に原因があるわけである。つまり[3]だ。
 ただ[3]に関しては毎回しっかりと管理しながらコードを書いていくしかないので、最終的にはこれがリプレイ不具合フリーの阻害となる。完全にフリーにすることは事実上不可能であるが、原因は上記のように限られてはいるので、何らかの支援処理を行うことは可能かもしれない。

・おまけ
 これらだけでは実現できない機能もいくつかある。例えばステージごとに再生ポイントを設定したりすることである。これを解決するにはリプレイそのものをステージ毎に分割するという方法があるが、シームレスに進行するようなゲームを作る場合、それだけでは足りないのでゲームで使用するメモリ全ての記録をとる処理(つまりステートセーブ)を行う必要がある。この処理は記録を取るタイミング、再生を開始するタイミングが連続するように慎重に設定する必要がある。
 シームレス処理はリプレイ処理とは非常に相性の悪いものなので、やるなら相当覚悟が必要だ。
 ポーズ処理もなかなか難しい。リプレイ再生時にはポーズ処理をそのものを飛ばさなければならないしポーズ中のキーログはちゃんと捨てておかねばならない。ここら辺の介入処理は上記のステートセーブ処理に似たタイミングでの処理を行うので一緒に作っておくと後で楽。

 キーログ以外の方式を使うとなると次に挙がってくるのが全てのオブジェクトの情報を記録するという手もある。あることにはあるのだが…1フレーム毎に数MBもの情報を記録するのか?無www理wwww
 そんなことするならリアルタイムでムービーでも撮っといたほうがまだマシです。

 色々簡単に省略してさらっと触れるつもりがやっぱり長くなってしまった(笑
 本当はキーコンフィグの取り扱いとか確保するバッファの大きさと書き出しタイミングなど、他にも注意すべき点や面倒な問題もまだまだあります。なによりリプレイ機能はデバッグに時間がかかるのが厄介。
 うちの場合はキーコンフィグはキーログに記録する前に標準キーに変換しているので、リプレイ機能には直接関係しなかったりします(ゲーム中にキーコンフィグ設定変更できるのもこれの恩恵)。

19 Janvier MMVIII
 とりあえず年始でいきなりすっこけた分取り戻したので、次はこっちだー。
 今年の風邪は本当にしぶとくて困ります。

DEV スペース大納言(仮
 というわけでver1.01アップデートパッチをリリース。
 これまでにご連絡頂いた不具合の修正と、記録部分の機能追加などを。
 他に不具合があったりご要望などがあればメールにてご連絡お願いいたしますです。

11 Janvier MMVIII
 ダーイダーイ。
 年明けて早々に風邪をひいてしまい、すっかり寝正月になってしまいなんだこれ。
 …と寝込んでる間ロクにゲームもできなくてげんにょりだったわけですが。去年後半はほとんどゲーム遊べてなかったんで、やっと遊べるーと思った矢先にこの仕打ち。どうしてくれましょうぞ。

 というわけで、さて次はなに作ろうかなーと考えつつ、溜めこんでたゲームをぼちぼちと開封中。
 と書くと参考にするネタ探しのように聞こえますが、僕の場合作るゲームと遊ぶゲームは全然違うので(飽きるから)、そんなことはあんまりないです。似たようなものばかりやってるとすぐ袋小路に陥るので良くないのです。インターフェイスの作り方とか、ゲームに直接関係ないとこは参考にしたりしますね。
 あまりにゲームやってなかったもんで、XBOX360もWiiも電源入れるの数ヶ月ぶりという(笑

MOVIE AVP2
 あと、とりあえずエイリアンズvsプレデター観てきたのです。
 確か前回は人間も共闘とかしてたよーな気がしたんですが…今回はなんか人間の扱いが酷いというか…両者の殺し合いにただ巻き込まれてガンガン死んでいくだけの人間の儚さに吹く。人類ヨワス。

Le jour de l'An MMVIII
 あけましておめでとうございます。
 今年は去年よりはマシな年だといいですなあ(ぉ

EVENT 年末のアレ
 ちょっと吃驚するようなこともありましたが、概ね滞りなく今回も無事に終わりました。
 大晦日なんて超アレな日程にも関わらず足を運んで頂いた方々、ありがとうございました。

 いつものように挨拶し損ねたとこに年明けてからポロポロ気付くわけでして。
 やっぱり挨拶リストみたいなのを作っておかないと駄目ですのう。とほほ。睡眠不足よくない。

 今回も本とか色々頂きました。ありがたく初笑いの刑に(笑
 あと、以前書いていたバニーさんの立体の原形の人が完成品くれたのでワーイ。と掲載。
 ジェットストリームリーフ(違
 実はこのバニーさん台がなくても自立するようなんですが、後ろからみると結構すさまじいバランスになってて面白い。リーフ星人は鉢植えにしようか悩み中。バニーさんのキットも持ってるんですが、そっちは磨いたところで止まってたりします…せっかくだからそっちはダイナマイトバディにしようかしら。

MISC 大復活?
 うーむ。
 復活ってタイトルでコケて10年間立ち直れなかった某シリーズもあるので、あまり縁起がいい名前とは思えんのです。せっかく大往生したのですから、次はそうですね、大霊界とかのほうがいいと思います。


■ 2007 [01] [02] [03] [04] [05] [06] [07] [08] [09] [10] [11] [12]