神代クロ のすべての投稿

ゲーム開発31:XAudio2でWaveを再生する1

前にXACT3Waveを再生する処理を書きましたが、いちいちWaveファイルを固めるのはメンドくさい。

てな訳で、改めてXAudio2でWaveを再生することにしました。まぁサンプルにそのものずばりな物があるので(XAudio2BasicSound)、それを元にゲームで使える様な物に作り替えます。

基本的な処理の流れは、COMを初期化してXAudio2を使えるようにする。マスターボイスを作ってその中にWaveから取り出したソースボイスを入れる。再生。といった感じです。

今回はXAudio2の部分CAudioBaseクラスだけ記述しました。Waveファイルからデータを取り出す処理は次回。

//--------------------------------------------------------------------------------------
// 生成
CAudioBase::CAudioBase()
{
 for (int i=0; i<MAX_SOUND; i++) {
  pSourceVoice[i]=NULL;
  pXAudioBuffer[i]=NULL;
  pbWaveData[i]=NULL;
 }

 pXAudio2=NULL;
 pMasteringVoice=NULL;
}
//-----------------------------------------------------------------------------
// 解放
CAudioBase::~CAudioBase()
{
 Release();

 // マスターボイス解放
 if (pMasteringVoice!=NULL) {
  pMasteringVoice->DestroyVoice();
  pMasteringVoice=NULL;
 }

 // XAudio解放
 SAFE_RELEASE(pXAudio2);

 // COM解放
 CoUninitialize();
}
//--------------------------------------------------------------------------------------
// 初期化
BOOL CAudioBase::Init()
{
 // COM初期化
 CoInitializeEx(NULL, COINIT_MULTITHREADED);

 // デバッグモードの場合
 UINT32 flags=0;
#ifdef _DEBUG
 flags|=XAUDIO2_DEBUG_ENGINE;
#endif

 // XAudio2生成
 if (FAILED(XAudio2Create(&pXAudio2, flags))) {
  CoUninitialize();
  return E_FAIL;
 }

 // マスターボイス生成
 if (FAILED(pXAudio2->CreateMasteringVoice(&pMasteringVoice))) {
  SAFE_RELEASE(pXAudio2);
  CoUninitialize();
  return E_FAIL;
 }

 return S_OK;
}
//-----------------------------------------------------------------------------
// 解放
void CAudioBase::Release()
{
 // ソースボイス解放
 for (int i=0; i<MAX_SOUND; i++) {
  ReleaseSound(i);
 }
}
//-----------------------------------------------------------------------------
// サウンド解放
void CAudioBase::ReleaseSound(int no)
{
 if (pbWaveData[no]!=NULL) {
  SAFE_DELETE(pbWaveData[no]);
 }
 if (pXAudioBuffer[no]!=NULL) {
  SAFE_DELETE(pXAudioBuffer[no]);
 }
 if (pSourceVoice[no]!=NULL) {
  pSourceVoice[no]->DestroyVoice();
  pSourceVoice[no]=NULL;
 }
}
//--------------------------------------------------------------------------------------
// ファイル読み込み
int CAudioBase::LoadSound(LPSTR szFilename, int loop_flag)
{
 int  i;

 // 空いているWaveがあるか検索
 for (i=0; i<MAX_SOUND; i++) {
  if (pSourceVoice[i]==NULL) {
   break;
  }
 }
 if (i>=MAX_SOUND) {
  return -1;
 }

 // Waveファイル読み込み
 CAudioWave wav;
 if (FAILED(wav.Open(szFilename, NULL))) {
  return -1;
 }

 // Waveファイルのフォーマット取得
 WAVEFORMATEX* pwfx=wav.GetFormat();

 // サイズ計算
 DWORD cbWaveSize=wav.GetSize();

 // メモリにデータを乗せる
 pbWaveData[i]=new BYTE[cbWaveSize];
 if (FAILED(wav.Read(pbWaveData[i], cbWaveSize, &cbWaveSize))) {
  SAFE_DELETE_ARRAY(pbWaveData[i]);
  return -1;
 }

 // ソースボイス生成
 if (FAILED(pXAudio2->CreateSourceVoice(&pSourceVoice[i], pwfx))) {
  SAFE_DELETE_ARRAY(pbWaveData[i]);
  return -1;
 }

 if (loop_flag!=0) {
  loop_flag=XAUDIO2_LOOP_INFINITE;
 }

 // オーディオバッファ設定
 pXAudioBuffer[i]=new XAUDIO2_BUFFER;
 pXAudioBuffer[i]->Flags=XAUDIO2_END_OF_STREAM;
 pXAudioBuffer[i]->AudioBytes=cbWaveSize;
 pXAudioBuffer[i]->pAudioData=pbWaveData[i];
 pXAudioBuffer[i]->PlayBegin=0;
 pXAudioBuffer[i]->PlayLength=0;
 pXAudioBuffer[i]->LoopBegin=0;
 pXAudioBuffer[i]->LoopLength=0;
 pXAudioBuffer[i]->LoopCount=loop_flag;
 if (FAILED(pSourceVoice[i]->SubmitSourceBuffer(pXAudioBuffer[i]))) {
  pSourceVoice[i]->DestroyVoice();
  SAFE_DELETE_ARRAY(pbWaveData[i]);
  return -1;
 }

 return i;
}
//--------------------------------------------------------------------------------------
// サウンド再生
void CAudioBase::PlaySound(int no)
{
 if (no==-1 || pSourceVoice[no]==NULL) {
  return;
 }
 StopSound(no);
 pSourceVoice[no]->FlushSourceBuffers();
 pSourceVoice[no]->SubmitSourceBuffer(pXAudioBuffer[no]);
 HRESULT hr=pSourceVoice[no]->Start(0);
}
//--------------------------------------------------------------------------------------
// サウンド停止
void CAudioBase::StopSound(int no)
{
 if (no==-1 || pSourceVoice[no]==NULL) {
  return;
 }

 pSourceVoice[no]->Stop(0);
}

Thunderbird3のIMAPでGmailを使ってみる

Thunderbird3Thunderbirdがバージョン3.0になりました。見たらIMAPの高速化とかGmailとの連携強化とか書かれてたので、利用してみる事にしました。

ちなみにIMAPが何なのかはよくわかってませんw POPと違い、サーバー上のメールを直接操作出来るって事でいいのかな?

ThunderbirdでGmailのアカウントを設定すると、自動でIMAPのサーバに接続します。しかしGmailには16000通くらいメールがあったので、ダウンロード完了するまで30分くらいかかったよ。

で、未読既読がごちゃごちゃしてたので、全部既読にしようと全選択してから既読を選んだら…なんか完了するまで2時間くらいかかったよ(汗)

これは最初だけなのかな。その後は受信トレイとかクリックすると微妙に固まるけど、まぁ問題ないレベルでした。

Thunderbirdでメール送信したらGmailの送信済みメールに入るし、既読やアーカイブを指定したらそれも反映されるし、良いね。今まではいちいちGmailサイトに行ってやってたからなぁ。

複数のPCで全く同じ環境になるのは良いです。二重ダウンロードとか未読のまま忘れてしまうなんて事がなくなるし。

ただ、いちいちサーバに見に行ってるため、やっぱり重いのは気になるかな。

とにかくしばらく使ってみよう。

※機能を見直してたら「○日分のメッセージをローカルに同期する」って設定があるね。これで最近のだけ受け取れば良かったのか。

※これも後から知ったけど、Shift+Cで一括で既読にできます。ちゃんとマニュアル読まないとダメだね。

エコポイントをEdyで受け取る

9月に地デジテレビを買った際に付いてたエコポイントが、ようやく交換できました。

エコポイント登録サイトでEdyを選択。数週間後にメールが来たので、Edyに投げる用の携帯メールアドレス等の登録をしました。

それから数週間後、EdyギフトIDが届きました。しかしよく考えてみたら、Edyを持っていない事に気づきw 知人のアドバイスを元にANAマイレージクラブのEdy付きを申し込む。

それからさらに数週間後、ANAからカードが送られてきたので、それを使っておサイフケータイのEdyを登録、ようやくエコポイントをゲットできました。

長かった。Edyはコンビニで使えるから、たぶん効率が良いね。

…あれ? EdyはJCBのクレジットカードが登録できないぞorz

ゲーム開発30:坂道との当たり判定

坂道との当たり判定だいぶ間があいたけど、いくつかの処理を追加しました。

マップチップをシンプルに
ドット絵をあれこれいじくり回してたけど、結局シンプルな形にしてしまいました。地味だけど仕方ない。そのうちマップチップを増やして、奥行きを表現したいです。

縦スクロール対応
今までは横スクロールしかしませんでしたが、マップエディタ導入を機にマップサイズを可変にし、縦にもスクロール出来るようにしました。横と違い、staticな変数を持って、ゆっくりスクロールするようにしてます。縦が激しいと酔う。

坂道に対応
坂道を上り降り出来るようになりました。方法は線分の交差判定を使ってます。キャラクタの足元を横一直線の線分とし、坂道の線分との重なりで当たり判定を取っています。この方法なら複雑な地形も簡単に作れるなぁ。実装はネット上にあったコードを参考に組んでます。

処理落ち(汗)
大した事してないはずなのに処理落ち(フレームスキップ)が起きてました。ちなみに50fpsだと大丈夫なのに、60fpsだと処理落ち。もしかしたら単にフレームレートの計算ミスの可能性もあるけど、何にしても原因を特定しなきゃなぁ。

引き続き坂道の処理を作ります。実はまだちょっと挙動がおかしい。

//-----------------------------------------------------------------------------
// 交差判定
BOOL CField::CrossLine(POINT p1, POINT p2, POINT q1, POINT q2)
{
 float A, B, C, D;
 BOOL ret=TRUE;

 A=(float)(p2.y-p1.y);
 B=(float)(p1.x-p2.x);
 C=-(A*p1.x+B*p1.y);
 D=(A*q1.x+B*q1.y+C)*(A*q2.x+B*q2.y+C);

 if (D>0) {
  ret=FALSE;
 }
 else {
  A=(float)(q2.y-q1.y);
  B=(float)(q1.x-q2.x);
  C=-(A*q1.x+B*q1.y);
  D=(A*p1.x+B*p1.y+C)*(A*p2.x+B*p2.y+C);

  if (D>0) {
   ret=FALSE;
  }
 }
 return ret;
}

Google日本語入力を導入する

Google日本語入力Google日本語入力が公開されたので、早速インストールしてみました。

これまでIMEはずっとマイクロソフトのを使ってました。ずっとってのはWindows95の初代の時からで、実質13年くらいかなぁ。そんなに困ってなかったしね。でもなんか妙にネット上で話題になってたから試しにw

インストールしたら、最初日本語入力が出来なくなってしまい、焦ったり。どうも「詳細なテキストサービスをオフにする」にチェックを入れてるとダメっぽい。なのでチェックを外して再起動。問題なく入力出来るようになりました。

普通に使う分には全く問題ないね。まぁMS-IMEで学習してたのは、また学習し直しだけど。このIMEのキモは固有名詞です。ネットからデータを引っ張ってくるお陰で、常に最新の変換をしてくれます。

せいけん→聖剣の刀鍛冶
のぎざ→乃木坂春香の秘密
こいひ→恋姫無双
とある→とある科学の
ちょうで→超電磁砲

素晴らしいw

もうこのまま使い続けても良いかな。

VirtualBoxでAndroidを動かしてみる

VirtualBoxでAndroidを動かしてみるノートPCにVirtualBoxを入れたので、今更ながらGoogle Androidを動かしてみた。

ここから2ファイルダウンロードして
COPY /B liveandroidv0.3.iso.001 +liveandroidv0.3.iso.002 liveandroidv0.3.iso
で結合。LiveCD版なので、後はそのままVirtualBoxに突っ込んだら動きました。

言語を日本語に変えてテキトーにいじってみる。操作系が携帯電話を想定したものなので、最初戸惑ったけど、軽快に動作するね。ただ日本語の入力自体は出来ないみたい。

あとアットマークが表示できなくて困ったり。これは単にキーボードの設定をしてないだけで、Shift+2キーで表示できた。

ブラウザは普通にYahoo!Japanとか見れるね。ただFlashが入ってないのと、GMailはじめ幾つかのサイトはモバイル仕様だった。Javacriptが完全じゃないのかな。

メーラーもアカウント設定したら普通に受信して読めたよ。ただメール内画像や添付ファイルが開けなかった。

レースゲームが入ってたんだけど、画面が結構グリングリン回転するね。あとスーパーマリオのエミュが入ってたんだけど、いいのかこれ(汗) アプリ名が中国語っぽかったけど。

ともかく、これなら色んなアプリが作れそうですね。Javaだから当たり前といえば当たり前か。

余裕が出来たらAndroidで何か組んでみようかな。まぁ実機が無いと虚しい気もするけどねw

スポーツクラブに行く(11日目)

久しぶりのスポーツクラブです。

前回行った際に爪が剥がれてしまい、痛いのでしばらく行く気が起きなくて…しかしこの2週間で1/3ほどの所で剥がれてた爪も、何とか復活したよ。まだ完全とはいえないけど、なかなかの回復力だね。

日曜の昼間なのでランニングマシンなどは予約待ち状態の混み具合でした。そんな訳でマシンが空いてすぐに使い始めたんだけど、なんかオッサン臭い…やっぱり人が使った直後はダメだわ。

平日の空いてる時間帯に行きたいけど、最近よく仕事電話がかかってくるから、昼間はPCの前にいないと困るかな。

マッチョダンディーへの道は遠い。

無線LANルータを買う

I-O DATA IEEE802.11g/b 無線LANルーター WN-G54/R4を買いました。これも今まで使ってたのが6年前に買ったやつで、いい加減古かったから。あと安かったし。

その古いのは暗号化方式がWEPなんだけど、これってザルみたいなセキュリティで1分あれば解析できてしまうらしい。よくもまぁ使い続けてたものだ。

今回のはルータではあるんだけど、既にルータはあるので、ハブアクセスポイントとして使います。普通にアクセスポイント単体で買うより安かったしね。

ちょいちょいと設定したら、問題なく動作しました。勿論ダブルワイヤレスなんていうセキュリティの穴は塞いであります。

ちゃんとPS3WPA2で接続できました。これでわざわざゲームのアップデートに有線を使わなくて済みます。

アニメ関連会社の社長と飲む

今日は数ヶ月ぶりにアニメ関連会社の社長さんと飲みました。

アニメ業界は不況の真っ只中だと思ってたら、その人の会社は堅調らしい。羨ましいね。最近は某パンツアニメにちょっとだけ関係してたとか。

色々話してるうちにiPhoneAndroidの話題が出ました。

思い起こせば2年前。「iPhoneでアプリ作らない?」という誘いがあったけど「Appleのケータイなんて流行るわけ無いだろ」と断ってしまったんだよね。その後日本でも発売され、大ヒットに。当時参入してれば今頃儲かってたかもなぁ…

iPhoneとAndroid。自分には関係ないやと思ってたけど、ビジネスとして考えたら面白そうではあるね。とりあえずそれぞれの技術書でも調べてみるか。