12/26(土)


例の「当たり判定エディター」のプレビュー版を1BAくんに見せました。
したら、「一枚の画像に複数のスプライトデータが乗ってるのでそれに対応しないとダメだ」って言われたです。
「先に言えよなぁ・・・」って言ったら、「言ったぞ先に!」って言われたです。

まあ、言った言ってないって言い合っても水掛け論なので、「とりあえず、入力の仕様を書面で送れ」と言うことに落ちついたです。

で、その書面はまだ来ないです。
よって、「当たり判定エディター」の方はお休みしてます。

実際、一枚の画像に複数のスプライトデータが乗ってる状態に変更しないとだめなんだろうけど、えむっちは現在TListにTBitmapをぶら下げて管理しているのを止めないとダメになるでしょう。

で、多分、TBitmapのListを別に持って、複数のBitmapを読み込めるようにし、さらにAnimationさせる側では、Bitmapへのポインタ、X、Y、W、Hをひとまとめにした構造体のListを持つのが妥当な改造案だなぁと考えたよ。

ま、後は例の書面が来てから考えるとしましょう。


で、「当たり判定エディター」とは別に、Soundまわりを組んでくれって頼まれたよ。
サウンドまわりねぇ・・・曲はMIDIなのか?
とかいろいろ話し合ったんだけど、曲はCDって手もあるので先に効果音をやるのだってことに落ちついたです。
だから、今日からDirectSoundをやってたです。(スプライトのクラスはいつになることやら・・・)

DirectSoundは意外に簡単でした。とりあえず、鳴るようになりました。
DirectDrawと違ってデバッガーも使えるし・・・ねぇ?

それでも、いくつか気になった点があったので書いておくです。

DirectSoundには、プライマリバッファってのとセカンダリバッファってのあります。

で、セカンダリの方にWaveデータを読み込んで、再生する時にプライマリバッファに書き込んで鳴らすってしくみらしい・・・
なんで、こんなメンドクサイことになってるかって言うと、複数の音を同時に鳴らす時にセカンダリバッファを複数作って、プライマリの方にミキシング済みのデータを書き込むって寸法なのだ。

しかし実は、「ミキシングしてプライマリに書き込む」って部分はDirectSoundが勝手にやってくれるので、我々(プログラマ)の作業としては、「セカンダリバッファを作成し、Waveデータを読み込む」って部分だけなのだ。(プライマリバッファはDirectSoundオブジェクトをCreateすると同時に勝手に作成される)

で、後はPlayメソッドを呼び出すと再生してくれるのだ。


例によって、「I/O別冊DirectX実践プログラミング」を見ながらBuilderに書きかえるんですが、DirectSoundはほとんどそのままで行けます。(DirectDrawはいろいろ苦労したけどねぇ)

まずは、CreateDirectSound。
第一引数は、GUIDだけど、デフォルトのサウンドカードを使う場合はNULLでOKなのでNULLにしておこう。
第二引数に、DirectSoundオブジェクトへのポインタのアドレス。ようは、CreateしたDirectSoundのアドレスが帰ってくるのね。
第三引数は、NULLにするらしい。

次は協調レベルの設定。
SetCooperativeLevelメソッド。
第一引数がハンドルかぁ・・・何のハンドルだろ?
DirectXのHelpを見るとアプリケーションのハンドルとなってる・・・
じゃ、Application->Handleか?
ま、これを渡しておこう。(注)
第二引数が協調レベルのフラグ。ま、NORMALでいいだろう・・・

ここまでで、コンパイルして実行してみた。
を、動くじゃん。(と言っても、Errが帰ってないだけで、何にも鳴らんけど・・・)

じゃ、次はセカンダリバッファを作成して、Waveデータを読み込んでみるか・・・

CreateSoundBufferメソッドかぁ・・・
第一引数の、DSBDESCはサイズとかフラグとかセットする。
で、DSBDESC.lpxfxFormatにFORMATEX構造体のアドレスを格納するのか・・・
で、FORMATEX構造体にはWaveデータのフォーマット情報を格納するのか・・・
じゃ、Read(&formatex, sizeof(FORMATEX))でいいか・・・
第二引数がDirectSoundBufferへのポインタのアドレスか・・・例によってCreateしたDirectSoundBufferのアドレスが格納されるのだね。
第三引数は、NULLらしい。

じゃ、ここまでをコンパイルして実行してみるか・・・
ありゃ?動かん・・・って言うか、無限ループに落ちてる・・・何故?
sizeofがまずいのか・・・?
値見てみるか・・・18!?
16じゃないのか?
うーん、Help見てみるか・・・
あ、やっぱり18Byteだ。
なんじゃ、この最後のcbSizeってのは?
Help見ても英語じゃけえよくわからんなぁ・・・
何々、どうやら、PCMじゃない場合になんか設定してPCMの時は0にするって読めるぞ。(えむっちは英語が苦手なのでここに書いてあることを信用しないように!)
じゃとりあえず、sizeof(FORMATEX)-2にして、cbSizeには0を入れておくか・・・

を、無限ループしなくなったよ、OK、OK。

じゃ、次は再生か・・・
Playメソッドね。
第一引数と第二引数は0にするのか。
で、第三引数にループ再生する場合はDSBPLAY_LOOPINGフラグね。

で、コンパイル&ゴー
ん、鳴らんぞ?
何故・・・
別にエラーも帰ってないよ・・・
ボリュームが小さいのかしら・・・?
スピーカのボリュームをMAXにして・・・やっぱり鳴らん。
SoundBufferのボリュームが小さいのかしら・・・?
いや、ちゃんとあってるぞ。
う〜ん、こまった・・・

あ、そう言えばハンドルがあったなぁ・・・
こいつをForm->Handleに変えてみるか・・・

ををっ、鳴った。
しかも、ウルサイ。
ってさっきスピーカのボリューム最大にしてたよ。

いやーよかったよかった、OK、OKですよぉ。
どうやら、渡したハンドルのウィンドウがActiveじゃない時は音が出ないみたいだ。
なるほどねぇ・・・

と、言うところで、時間が無くなったのでまた明日。


戻る