DQ6 AI処理の解析7

だいぶ間が空きましたが、続きを見ていきます。前回は回復行動を見たので、今回は攻撃行動です。

攻撃系の行動はほとんど共通です。AIの行動区分の「攻撃系」にはニフラム・ザキなどの一発離脱系も含まれます(バシルーラはAIの選択対象外)。

  • SR: $02D675 AI判断用_SR_001A(直接攻撃)
02D675LDX #$0004X=#$0004
02D678LDA $25DDA=$25DD単体・グループ・全体かの情報
02D67BBMI #$07if(n==on) goto $02D684
02D67DDEXX–
02D67EDEXX–
02D67FASLA< <1
02D680BCS #$02if(c==on) goto $02D684
02D682DEXX–
02D683DEXX–
02D684JSR $D688SR: $($02D688+X)
02D687RTSreturn

DQ6では単体・グループ・全体攻撃は戦闘行動IDは同じなので別の情報で判断して振り分けています。基本的にやってることはどれも同じなので、単体の直接攻撃をみてみます。

  • SR: $02D478 AI判断用_SR_0001(単体対象行動)
02D478STZ $14DP($14)=#$00
02D47ALDA #$0017A=#$0017最大インデックスからデクリメントしていく
02D47DSTA $258B$258B=A
02D480LDY #$04ACY=#$04AC最大インデックスの開始アドレス
02D483LDA #$0001A=#$0001
02D486STA $254B$254B=A
02D489STZ $2549$2549=#$00
02D48CLDA $203E,YA=$203E+Y
02D48FBEQ #$14if(z==on) goto $02D4A5
02D491JSR $D4B1SR: $02D4B1対象のステータスを調べる(無効c=on 反射v=on)
02D494BCS #$0Fif(c==on) goto $02D4A5
02D496JSR $D4EBSR: $02D4EB対象の戦闘行動の効果値取得(ダメージ系)
02D499CMP $14A>=DP($14)?
02D49BBCC #$08if(c==off) goto $02D4A5
02D49DSTA $14DP($14)=A効果値が最大なら差し替え
02D49FLDA $258BA=$258B
02D4A2STA $2591$2591=A対象情報も更新
02D4A5TYAA=Y
02D4A6SECc=on
02D4A7SBC #$0034A-=(#$0034+!c)
02D4AATAYY=A
02D4ABDEC $258B$258B–
02D4AEBPL #$DCif(n==off) goto $02D48C
02D4B0RTSreturn

単体の行動なので、対象全てに対して効果値の算出を行い、効果値が最大の相手に対して行動するといういつものパターンです。

  • SR: $02D4EB 対象の戦闘行動の効果値取得
02D4EBJSL $C2E065SR: $02E065効果値算出(ダメージ系)
02D4EFSTA $00DP($00)=A
02D4F1JSR $D52ASR: $02D52A効果値の補正
02D4F4LDA $0CA=DP($0C)
02D4F6CMP #$8020A==#$8020?
02D4F9BNE #$02if(z==off) goto $02D4FD
02D4FBASL $00DP($00)< <1山彦の帽子装備でダメージが倍加するなら倍にする
02D4FDLDA $00A=DP($00)
02D4FFSECc=on
02D500SBC $2030,YA-=($2030+Y+!c)対象の現HPと比較する
02D503BCC #$22if(c==off) goto $02D527この行動で対象が倒せる場合
02D505STA $00DP($00)=A
02D507LDA $0EA=DP($0E)作戦がガンガン行こうぜか
02D509CMP #$0000A==#$0000?
02D50CBEQ #$02if(z==on) goto $02D510
02D50ESTZ $00DP($00)=#$00ガンガン行こうぜ以外は効果値は加算しない
02D510LDA $00A=DP($00)
02D512CLCc=off
02D513ADC $203E,YA+=($203E+Y+c)脅威値合計を加算する
02D516BCC #$04if(c==off) goto $02D51C
02D518LDA #$FFFFA=#$FFFF
02D51BCLCc=off
02D51CADC $203C,YA+=($203C+Y+c)
02D51FBCC #$03if(c==off) goto $02D524
02D521LDA #$FFFFA=#$FFFFオーバーフロー対策
02D524STA $00DP($00)=A
02D526RTSreturn
02D527LDA $00A=DP($00)
02D529RTSreturn

ダメージ予想値が対象のHP以下であれば倒せないのでそのままダメージ予想値が効果値となりますが、倒せる場合は脅威値合計を加算します(脅威値合計のほうがダメージ値より大きくなるので優先的に選ばれやすくなる)。

  • SR: $02E065 効果値算出
02E065PHPPush P Flag
02E066PHBPush DB
02E067REP #$30m=off(A/M:16b) x=off(X/Y:16b)
02E069PEA #$7E7EPush #$7E7E
02E06CPLBPull DB
02E06DPLBPull DB
02E06EPHXPush X
02E06FPHYPush Y
02E070LDA $255FA=$255F
02E073ASLA< <1
02E074TAXX=A
02E075LDA $C8EE67,XA=$08EE67+X
02E079TAXX=A
02E07ALDA $C8C666,XA=$08C666+X
02E07EAND #$003FA&=#$003F評価対象の戦闘行動の属性ID取得
02E081CMP #$0021A>=#$0021?
02E084BCS #$FEif(c==on) goto $02E084
02E086ASLA< <1
02E087TAXX=A
02E088JSR $E0D6SR: $($02E0D6+X)AI効果値算出用SRのインデックス
02E08BLDA $2517A=$2517
02E08EORA #$0020Aor=#$0020
02E091STA $2517$2517=A
02E094LDA $258BA=$258B
02E097STA $2559$2559=A
02E09AJSL $C2852FSR: $02852Fダメージ補正処理
02E09ELDA $2559A=$2559
02E0A1STA $258B$258B=A
02E0A4LDA $00A=DP($00)
02E0A6PLYPull Y
02E0A7PLXPull X
02E0A8PLBPull DB
02E0A9PLPPull P Flag
02E0AARTLreturn

ダメージ補正処理は実際の戦闘行動でも使用しているダメージ補正処理と同じです(バイキルトなら2倍、防御なら半減、フバーハなら半減などの補正)。DQ3に移植する際にも同じようにしたかったのですが、関連するメモリがそのまま流用できるのかわからなかったため、補正用のSRを新規定義しています。バイキルト・防御状態はチェックしていますが、簡易版にしています(特に種族特攻の計算はすっ飛ばしています)。

  • SR: $02E11B AI判断用効果値算出_SR_0001(直接攻撃)
02E11BLDA $2555A=$2555
02E11EASLA< <1
02E11FTAXX=A
02E120LDA $C2F092,XA=$02F092+X
02E124TAXX=A
02E125LDA $205A,XA=$205A+X行動主体の攻撃力取得
02E128AND #$03FFA&=#$03FF
02E12BSTA $00DP($00)=A
02E12DLDA $258BA=$258B
02E130ASLA< <1
02E131TAXX=A
02E132LDA $C2F092,XA=$02F092+X
02E136TAXX=A
02E137LDA $2058,XA=$2058+X対象の守備力取得
02E13AAND #$03FFA&=#$03FF
02E13DSTA $02DP($02)=A
02E13FJSR $E143SR: $02E143直接攻撃推定ダメージ値取得
02E142RTSreturn
  • SR: $02E143 直接攻撃推定ダメージ値取得
02E143LDA $02A=DP($02)
02E145LSRA>>1
02E146STA $04DP($04)=A
02E148LDA $00A=DP($00)
02E14ASECc=on
02E14BSBC $04A-=(DP($04)+!c)
02E14DBCC #$22if(c==off) goto $02E171
02E14FLSRA>>1
02E150BEQ #$1Fif(z==on) goto $02E171
02E152STA $08DP($08)=A
02E154LDA $00A=DP($00)
02E156LSRA>>1
02E157LSRA>>1
02E158LSRA>>1
02E159LSRA>>1
02E15ASTA $06DP($06)=A
02E15CCMP $08A>=DP($08)?
02E15EBCS #$0Bif(c==on) goto $02E16B
02E160LDA $04A=DP($04)
02E162CMP $00A>=DP($00)?
02E164BCS #$05if(c==on) goto $02E16B
02E166LDA $08A=DP($08)
02E168STA $00DP($00)=A
02E16ARTSreturn
02E16BLDA $06A=DP($06)
02E16DLSRA>>1
02E16ESTA $00DP($00)=A
02E170RTSreturn
02E171STZ $00DP($00)=#$00
02E173RTSreturn

ここは直接攻撃によるダメージ値を乱数による変動なしで算出しています。いろいろやっていますが

  • 攻撃力-守備力1/2< =1なら0
  • 攻撃力1/16>(攻撃力-守備力1/2)1/2なら攻撃力1/32
  • 攻撃力=守備力1/2なら攻撃力1/32
  • 上記以外なら(攻撃力-守備力1/2)1/2

ということのようです。ちなみにダメージ呪文系はどうなっているかというと、

  • SR: $02E236 AI判断用効果値算出_SR_0009(メラ系)
02E236JSL $C9291ASR: $09291A戦闘行動の最小値を取得する
02E23ARTSreturn

で、単純に数値設定の最小値を取ってくるだけです(この後対象の耐性による補正などが入りますが)。最後に一発離脱系を見てみます。

  • SR: $02E23B AI判断用効果値算出_SR_000A(ザキ系)
02E23BLDA $258BA=$258B
02E23EASLA< <1
02E23FTAXX=A
02E240LDA $C2F092,XA=$02F092+X
02E244TAXX=A
02E245LDA $2030,XA=$2030+X現HPを効果値のベースとする
02E248STA $04DP($04)=A
02E24ALDA $255FA=$255F
02E24DSTA $258D$258D=A
02E250JSL $C2A665SR: $02A665耐性を考慮した閾値取得?
02E254CMP #$0081A>=#$0081?成功率が50%以下なら効果値を半減
02E257BCS #$01if(c==on) goto $02E25A
02E259LSRA>>1
02E25ALDX #$0004X=#$0004
02E25DJSL $C00D0CSR: $000D0CDP($00+X)=A(1Byte)*DP($00+X)
02E261LDA $05A=DP($05)
02E263BEQ #$01if(z==on) goto $02E266
02E265DECA–
02E266STA $00DP($00)=A
02E268RTSreturn

ザキ系はダメージ系よりも効果値は低くなるようになっているようです(このへんはFC版DQ4のクリフトの反省があるのかもしれませんが)。省略しますが、ニフラム系は脅威値合計に成功率をかけてさらに1/32しているので、普通にプレイしていたらまず選択されることはありません(AIの区分がダメージ系と同じ区分なので)。DQ3に移植する際には一発離脱系の行動はダメージ系と別区分にしたので(効果値の計算式も若干変えた)、AIをONにしているとそこそこ目にする機会が多いと思います。マニュアルではまずやらないゾンビ系にもザキを撃ったりしてされ効いたりするのにはちょっとびっくりしましたが、AIがイメージと違う弱点を突くから耐性を変えるというのもどうかと思うのでそのままにしています。

結構長くなったので今回はこのへんで。次回は補助系行動を見てみます。

コメント

タイトルとURLをコピーしました