ocraで画像や音その他のファイルをexeに入れる方法

ocra による Ruby の EXE 化を見てもらえば終わる話なのだが。
ちょっと具体的にDXRubyで扱うリソースをまとめてみたのでそのレポートをば。

サンプル

ここに置いておいた。解凍するとexeファイルが1個出てくる。これを実行するとサンプルゲームが動く。exeの中に画像や音、その他データファイルが格納されているのである。
http://dxruby.sourceforge.jp/files/samplestg.zip
サンプルゲームのソースはSourceForgeから普通にダウンロードできるが、大変古いものなのでコードそのものに期待してはいけない。ていうか今のRubyでは動かない。

詳細

ゲームの開発中はソースを直接実行する形で動かすことになるのだが、これをそのままOcraでexe化するとrequireで読み込んだライブラリと、require_relativeで読み込んだソースがexeに取り込まれることになる。他の画像や音などは基本的にメインのソースからの相対パス指定で読むことになるので、exeファイルからの相対位置が同じ場所に配置した状態でzip圧縮することになる。
requireで取り込んだライブラリはexe内のRuby処理系が持っていて、require_relativeで読むものはメインのソースからの相対位置が同じ場所に展開されるので読めるし、画像などはexeファイルの場所がカレントディレクトリになるから読める、という話である。

Ocraではexe化するときのocraコマンドの引数でファイル名を指定してやることで、exe内に取り込むことができる。例えばサンプルSTGはメインのソースの位置の下にimage、sound、tekidata、stagedataというディレクトリを掘ってそこにデータを配置しているので、

D:\usr\samplestg>ocra --windows main.rb sound image tekidata stagedata

などという感じでディレクトリを指定してやれば、その中身がすべてexeに取り込まれる。

また、カレントディレクトリがexeの位置なので、カレントからの相対位置の指定で画像を読むことはできなくなる。この解消方法として、メインのソースの位置を初っ端で

$dirpath = File.dirname(__FILE__)

などとして保存しておいて、
画像を読むときは

IMAGE_saruhead = load_stgimage($dirpath + "/image/stg_さるあたま.png")

とかそういう感じに指定してやれば、展開されたフルパスでの指定となるので読めるようになる。この指定方法ならソースから実行しても同じように読めるので、コードの書き方はともかくパス指定方法としてはこのようにするのがよいだろう。

思ったことなど

Ocraでは実行時にテンポラリのディレクトリに展開されるので、ゲーム実行中にそこを覗けばソースも画像も丸見えということになってしまうわけで、ソースや画像の隠蔽にはこの手法は使えない。隠したい場合は前に書いたような方法で強引にどうにかして隠すか、もっと強引な方法を使うかのどちらかである。
ただ、ゲームをダウンロードして展開したときにいろんなディレクトリやファイルがごろごろと展開されないという意味ではイメージは良いかもしれない。起動は遅くなるが。
あと、Ayameなどを使う場合はソースの場所に置くのではなく、Rubyのbinの中にdllを突っ込んでおくとか、拡張ライブラリの場所にsoを置いておくとか、そういう感じのことをしておかないとダメかもしれない。インストーラをきちんと作れという話に行き着くのだが、そのへんは0.0.3とかいうしょぼいバージョンなので大目に見てほしい。そのうちDXRuby本体に満足いくサウンドライブラリを作り込む気ではいるので、まあ、年単位で待っていただければと。
ちなみにOcraによるExe化についてはきちんとまとめてリファレンスに追加する予定である。