実際、自分も作ったはいいけれども保守以外で使ったことはまともになかったりします。
が、ちょっとルーチン的に気になったので前バージョンを公開してから複数のADVシステムでテストをしていました。
WindowModePatchは「お行儀のいいシステム」で使用することを前提として作っている
「汎用性」を求めるためにかなりいろいろと変な細工をしています。特にシステムDLLの乗っ取りで処理を行っているため、一般的と私が思っているシステムの流れから外れると
とたんに大失敗を見る目になってしまいます。その条件とは、プログラムの内部的には
- 登録されるウィンドウクラスは対象のプロセスではただ一つである
- はじめに作成されるウィンドウは描画対象となるメインウィンドウであり、そのサイズはゲーム画面の解像度と同じ大きさである
- ゲームの描画はメインウィンドウのみで行われ、それ以外のウィンドウはダイアログなどゲーム描画とは関係ないものである
- GDIやDirectXを使う描画では「典型的な使用方法」を使用するものとする (たとえば、GDIならGetDC~ReleaseDCを毎フレーム行い、その間に描画を行う)
- DirectX系の初期化は複数のバージョンにまたいで行われない (Direct3D9を使うときにDirectDrawも初期化してみる、といったことがない)
という仮定の下で動くように設計されていますが、このいずれかだけでも外れるとひどいことになってしまうのがおちなのです。
ちなみに、ゲームのインストール時にDirectXのインストールを強制されるからと言って、「描画にDirectXを使っている」とは限らないのも失敗しやすい原因だったりします。
そのため、システムの中でも「汎用性」を重んじるシステムで不具合確率が大きい
典型的な例が吉里吉里です。上記にあげた条件がすべて外れているために「絶対に検出に失敗する」という例となっています。
なので、WindowModePatchで動かそうとしても全く動きません。こればかりはいろいろな方法を試していますが、今のところすべて失敗しています。
吉里吉里の場合は、各バージョンごとにそれを仕込んだコードを書き出してシステムを作り直した方が早いような気もしないでもないです。
なお、2番目の「ウィンドウが作られたときに指定解像度で初期化されない」パターンについてだけ解除法があり、
設定ファイルに解像度を直接指定することで何とかなる「場合もあり」ます。(とあるシステムでこれで動くことを確認しています)
微妙に組み替えてVer 0.18 Alphaを出そうかとも思いましたが
ウィンドウの検出方法とウィンドウメッセージの修正方法を変更したものですが、実際、0.17 Alphaと変化したとはあまり思えないのでリリースしていません。
方法としては、
0.17以前:クラス登録時にWindowModePatch側のウィンドウプロシージャを呼び出すようにして、その中でメッセージを加工した上でシステム側から指定されたプロシージャを再度呼び出す
0.18以降:システムのメッセージ処理API呼び出しの部分でメッセージの変更を行い、プロシージャに渡す値を加工する
というものです。どちらかというと現在組んでいる0.18側の方が機構としてはよくなるような気がするのですが、どうなのでしょうか・・・?
一応情報があれば改良はしたいと思っていますが・・・