CCAO v0.992のゲームロード毎のキー設定初期化をやめる
武器毎に待機モーション・攻撃モーションを変更するという凄いMOD、CCAO ですが、スクリプトによりゲームをロードする度に設定が初期化されてしまいます。特にキーボード設定が戻ってしまうのは大変不便です。
この記事では、CSを使ってこれを防ぎ、キー設定を維持するやり方を解説します。無許可での変更や再配布は禁止されているので、修正したespをアップはしません。
なお、これは v0.992時点でのものです。
v0.993で、MOD導入時のみにキーを初期化するように修正されたようです。
どうやってゲームロードする度に設定を初期化しているのか
スクリプトで GetGameLoaded を使ってセーブデータのロード and ニューゲームを検出して、そこで初期化用のユーザー定義関数を呼び出しています。その関数内でキー設定を含め、色々なものが初期化されます。
それでは、設定初期化に関係ある部分だけに絞ってスクリプトを見てみます。「zzCCAO.esp」をCSで開いてみてください。
↓初期化用の関数のキー設定のところだけ抜き出したもの。これが呼び出されることで初期化が行われる。
Scriptname zzCCAOFuncInit Begin Function {} set zzCCAO.cbKey to 47 set zzCCAO.cbAttackKey to GetControl 4 ;関係なし set zzCCAO.cbLeftKey to GetControl 2 ;関係なし set zzCCAO.cbRightKey to GetControl 3 ;関係なし set zzCCAO.cbBackKey to GetControl 1 ;関係なし set zzCCAO.cbForwardKey to GetControl 0 ;関係なし set zzCCAO.cbReadyKey to GetControl 8 ;関係なし set zzCCAO.cbCycleUp to 201 set zzCCAO.cbCycleDown to 209 set zzCCAO.cbcycleCurkey to 0 End
関係なし、とコメントが入っている行は考慮する必要のないものです。GetControl を使っていることからわかるようにOblivionのキー設定を参照していて、キーを変更するものではないからです。その上下4行が問題の箇所となります。
↓常時動いているスクリプトで GetGameLoaded を使って検出、zzCCAOFuncGameLoadSequence を呼び出す。
Scriptname zzCCAOMainScript Begin gamemode if ( GetGameLoaded || zzCCAO.isLoaded == 99 ) Call zzCCAOFuncGameLoadSequence endif End
↓この関数が初期化用の関数、zzCCAOFuncInit を呼び出す。
Scriptname zzCCAOFuncGameLoadSequence Begin Function{} Call zzCCAOFuncInit End
流れとしては、「監視用のスクリプトが関数を呼び出す→その関数が初期化用の関数を呼び出す」となっています。
DoOnce変数で一度だけ実行させる
キー設定の初期化を、MOD導入後の初プレイの時だけにすれば解決します。
↓よくあるやり方。
short DoOnce Begin GameMode If (DoOnce == 0) set DoOnce to 1 ;行う処理をここに EndIf End
通常はこれでいいのですが、このMODの場合は初期化をユーザー定義関数で行っているので少し複雑です。私はユーザー定義関数を使ったことがないのですが、関数というだけあって変数の値を保存できないようです。上の例で言うと、実行される毎にDoOnce変数が0になってしまうので、毎回実行されることに。
ということで、初期化用の関数内でフラグを使って一度だけ実行、はできません。そこで、これを呼び出すスクリプト側(関数でない普通のスクリプト)でフラグを使うことにします。
Scriptname zzCCAOMainScript short initkey ;追加 Begin gamemode if ( GetGameLoaded || zzCCAO.isLoaded == 99 ) Call zzCCAOFuncGameLoadSequence if ( initkey == 0 ) ;ここから追加 set initkey to 1 set zzCCAO.cbKey to 47 set zzCCAO.cbCycleUp to 201 set zzCCAO.cbCycleDown to 209 set zzCCAO.cbcycleCurkey to 0 endif ;ここまで追加 endif End
凄い単純です。初期化用の関数から抜き出してきただけです。initkey変数により、一度だけしか実行されません。
そうしたら、初期化用の関数のほうのキー設定を消します。
Scriptname zzCCAOFuncInit Begin Function {} ;set zzCCAO.cbKey to 47 set zzCCAO.cbAttackKey to GetControl 4 set zzCCAO.cbLeftKey to GetControl 2 set zzCCAO.cbRightKey to GetControl 3 set zzCCAO.cbBackKey to GetControl 1 set zzCCAO.cbForwardKey to GetControl 0 set zzCCAO.cbReadyKey to GetControl 8 ;set zzCCAO.cbCycleUp to 201 ;set zzCCAO.cbCycleDown to 209 ;set zzCCAO.cbcycleCurkey to 0 End
コメントアウトしている部分が、先ほど抜き出したものです。あちらに書いてあるので毎回実行されるこちらからは消しておきます。コメントアウトでなく消してしまっても大丈夫です。
これで「zzCCAO.esp」を保存すれば、毎回キー設定が初期化されることはなくなります。