Page 97 ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 通常モードに戻る ┃ INDEX ┃ ≪前へ │ 次へ≫ ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ ▼Nes.cpp内のザッパーの処理についての質問 リチャード堀井 03/9/12(金) 16:41 ┣Re(1):Nes.cpp内のザッパーの処理についての質問 リチャード堀井 03/9/12(金) 18:24 ┣同じ所で別件 リチャード堀井 03/9/12(金) 20:02 ┗Re(1):Nes.cpp内のザッパーの処理についての質問 Norix 03/9/12(金) 20:11 ┗Re(2):Nes.cpp内のザッパーの処理についての質問 リチャード堀井 03/9/17(水) 14:51 ─────────────────────────────────────── ■題名 : Nes.cpp内のザッパーの処理についての質問 ■名前 : リチャード堀井 <dragonquaver@yahoo.com> ■日付 : 03/9/12(金) 16:41 -------------------------------------------------------------------------
VirtuaNES のソースを読ませていただいているリチャード堀井と申します。 (以前Norix様にCloneGamePartyの掲示板でご意見頂いたのですが覚えていらっしゃいますでしょうか?) 最新のソースの virtuanessrc082\NES\Nes.cpp 内の関数 void NES::EmulateFrame( BOOL bDraw ) において、ザッパーの処理について疑問があるので質問させて下さい。 現在のソースではループの一番最後で ザッパーのチェック → スキャンライン用変数の更新 というふうになっているのですが、それより上の部分で if( pad->IsZapperMode() && scanline == ZapperY ) というような行を複数行見つけることができます。 現在だとメンバ変数 bZapper の値はスキャンライン0の処理中は常に FALSE であり、 スキャンライン0の処理の最後にザッパーのチェック、スキャンライン用変数の更新 という流れになっているのですが 以下のようにしてはダメでしょうか? 1.関数のはじめに INT scanline = -1; としてスキャンライン用の変数を -1 からはじめる。 2.現在無限ループになっているwhile文を while (scanline == nescfg->TotalScanlines - 1) とする(下のほうの break が要らなくなります) 3.ループの頭で scanline++; NES_scanline = scanline; とし、スキャンライン用変数を更新する 4.ザッパーのチェックをして bZapper を更新する。 5.ループ内の if( pad->IsZapperMode() && scanline == ZapperY ) の行を if (bZapper) に置き換える 6.ループ最後の break する if ブロックとスキャンライン変数の更新を取り除く これでいいような気がするのですが、唯一 スキャンライン0の処理中、いままで常に FALSE だった bZapper が ZapperY の値によって TRUE になってしまう可能性がある。 という挙動の変更があると思われます。 これはマズいでしょうか? 本来ならば動かして検証したいのですが、私は光線銃関係のROMを所有していないし、 VirtuaNESの動作についてよくわかっていないのでこちらで質問させて頂きました。 |
自己レスです。 ループ条件は while (scanline == nescfg->TotalScanlines - 1) ではなくて while (!(scanline == nescfg->TotalScanlines - 1)) ですね。スミマセン。 |
条件式もっと簡単になるような気がする所を発見したのでご報告しておきます。 void NES::EmulateFrame( BOOL bDraw )内 スキャンライン 1〜239 の間に実行される部分に if( bDraw ) { ... } else { if( pad->IsZapperMode() && scanline == ZapperY ) { ... } else { if( !ppu->IsSprite0( scanline ) ) { ... } else { ... } } } という部分がありますが(コメントで「これの位置でラスター系は画面が違う」のちょっと上) ここ if ((bDraw == FALSE) && (( pad->IsZapperMode() && scanline == ZapperY )) && (!ppu->IsSprite0(scanline))) { ppu->DummyScanline( scanline ); } else { ppu->Scanline( scanline, Config.graphics.bAllSprite, Config.graphics.bLeftClip ); } でよさそうな気がします。 これより上部の RenderMethod が TILE_RENDER の場合の該当部分も 同じように削れそうです。 もしかしたらメンテナンス性等を考慮されてわざとなのかとも思いましたが 条件分岐減るのでもっと速くてコンパクトになると思ったので一応ご報告です。 |
▼リチャード堀井さん: >VirtuaNES のソースを読ませていただいているリチャード堀井と申します。 >(以前Norix様にCloneGamePartyの掲示板でご意見頂いたのですが覚えていらっしゃいますでしょうか?) 何となく記憶にはあるような無いような; >において、ザッパーの処理について疑問があるので質問させて下さい。 > >現在のソースではループの一番最後で 略 >これはマズいでしょうか? 質問の部分については,「描画しない場合にZapperの当たり判定を取る為に 1ラインだけレンダリングするかどうか」と言う部分です。 で,bZapperは拡張Padで当たり判定をチェックする時にも使っています。 ZapperのY座標の部分をレンダリングした後で無いと,Zapperの当たり判定が 前フレームのデータになって当たらなくなるのでこのようになっていたんじゃ なかったかなぁ。 まぁ,改良すべき余地は多々あると思いますが; |
▼Norixさん: >質問の部分については,「描画しない場合にZapperの当たり判定を取る為に >1ラインだけレンダリングするかどうか」と言う部分です。 > >で,bZapperは拡張Padで当たり判定をチェックする時にも使っています。 > >ZapperのY座標の部分をレンダリングした後で無いと,Zapperの当たり判定が >前フレームのデータになって当たらなくなるのでこのようになっていたんじゃ >なかったかなぁ。 ご説明ありがとうございます。 うぅ、せっかく説明して頂いたのによくわからなかったです。 スミマセン。 |