こんにちはゲストさん。会員登録(無料)して質問・回答してみよう!

解決済みの質問

シューティングゲームのタスクシステム

ゲームを作っているプログラミング初心者です。
C言語とDXライブラリを使ってシューティングゲームを作っているのですが、敵の消滅でバグがおきています。

どこがおかしいのかが全く分からないのですが、どこがおかしいのでしょうか・・・?
↓ソースだけアップしてあります。
http://kaede.zzkt.com/shootsouece/index.html

↓は圧縮ファイルのパスです。画像などの素材も入ってます。
http://kaede.zzkt.com/program/shootinggame.lzh

どなたかよろしくお願いします。

投稿日時 - 2008-08-23 18:58:52

QNo.4272807

すぐに回答ほしいです

質問者が選んだベストアンサー

 まず、直さなければいけないのは、配列周りです。
 配列は int t[100]と宣言したら、t[0]~t[99]までが有効になります。

 コードを拝見すると、1~100のようにアクセスしているようです。
 例えば、bulletは 200の要素数ですが、for文で 1~200まででアクセスしています。

 これを全箇所修正して下さい(タスクの next/prev周りが指すインデックスも)。

 まずこれらを正常にしないと他に問題があっても気付きにくいかと思います。

>なぜか、enemy構造体のthistcb変数の中に何故か200が代入される現象も発見しました。
>変数名変えたほうがいいでしょうか・・・?
 変数名を変えても問題は解決しないと思いますが、
thistcbは自分のインデックス番号かなにかでしょうか?
 使われている形跡がないのでthistcbの役割がよくわからず、
何が正しいのかちょっとわからないです。

 見た限り「敵弾のタスクリストの初期化」のコメントの下の
for文の中で、200を代入しているようです。
 これを上の修正を行うと、多分 200だったところが
199になるかと思います。

投稿日時 - 2008-08-24 19:25:14

補足

宣言の数を10から11に変更して直しました。

結局、thistcbはタスクのエラーを発見するときに使おうとしていただけなので消しました。

今まで動いてたのが逆に不思議ですね

敵のタスクは直ってません。
敵を消したときに複数同時に消える現象をみて気づいたのですが、
これは削除していようとしているタスクがeactiveの先頭と誤認されているから、他のタスクが隔離されている、ということなのでしょうか?

投稿日時 - 2008-08-24 19:34:50

お礼

解決しました。

if(enemy[e].next==0 && enemy[e].prev==0){
enemy[e].next = efree.next;
enemy[e].prev = 0;
enemy[efree.next].prev = e;
efree.next = e;
eactive.next=0;
eactive.prev=0;
}
else{
ichihoa = enemy[e].next;
ichihob = enemy[e].prev;
enemy[efree.next].prev = e;
enemy[e].next = efree.next;
efree.next = e;
enemy[e].prev = 0;
enemy[ichihob].next = ichihoa;
enemy[ichihoa].prev = ichihob;
}

これではenemy[e].nextもしくはenemy[e].prevのみが0のとき、efree.nextやefree.prevにアクセスしないようになっていました。
↓以下が新しいソースです。efreeがenemyfree、eactiveがenemyactiveに変わっています。
if((enemy[e].next==0)&&(enemy[e].prev==0)){
enemy[e].next = enemyfree.next;
enemy[e].prev = 0;
enemy[enemyfree.next].prev = e;
enemyfree.next = e;
enemyactive.next=0;
enemyactive.prev=0;
}
else{
if((enemy[e].next!=0)&&(enemy[e].prev==0)){
ichihoa=enemyfree.next;
enemy[enemy[e].next].prev=0;
enemy[enemyfree.next].prev=e;
enemyfree.next=e;
enemyactive.next=enemy[e].next;
enemy[e].next=enemyfree.next;
enemy[e].prev=0;
enemy[e].next=ichihoa;
}
else{
if((enemy[e].next==0)&&(enemy[e].prev!=0)){
enemy[enemy[e].prev].next=0;
enemyactive.prev=enemy[e].prev;
enemy[e].next=enemyfree.next;
enemy[e].prev=0;
enemy[enemyfree.next].prev=e;
enemyfree.next=e;
}
else{
ichihoa = enemy[e].next;
ichihob = enemy[e].prev;
enemy[enemyfree.next].prev = e;
enemy[e].next = enemyfree.next;
enemyfree.next = e;
enemy[e].prev = 0;
enemy[ichihob].next = ichihoa;
enemy[ichihoa].prev = ichihob;
}
}
}

文化祭に間に合いそうです。
本当にありがとうございました。

できれば他にミスがあれば教えていただけませんか?

投稿日時 - 2008-08-24 20:13:31

このQ&Aは役に立ちましたか?

0人が「このQ&Aが役に立った」と投票しています

回答(4)

ANo.3

No.2です。
>それなので削除した後の描写処理でハングアップしているようです
 なるほど。

 私のほうで確認した現象は敵が何匹か出てきたところで、
敵の移動ループの中で eが 50という配列の外を指してしまい
enemy[e].typeの switch-caseでERROR_EXIT()が実行される、
というものでした。

 現象が少し違うようですが、根は同じなのかもしれませんね。


#正直このタスク(?)は結構厳しいですね。
 使いづらくないですか?

投稿日時 - 2008-08-24 17:43:32

補足

>タスク(?)
私もそう思います。本当にタスクなのか微妙です。

C言語でやるのを自分ひとりで考えた結果こんな使いづらいものに。
まぁ一度作ってしまえば呼び出せばいいだけなのでそこは・・・
あまり作り直す時間も無いのでそこは御勘弁を。

なぜか、enemy構造体のthistcb変数の中に何故か200が代入される現象も発見しました。
変数名変えたほうがいいでしょうか・・・?

そして指摘してくださったエラーの原因はどこなのでしょう・・・?

投稿日時 - 2008-08-24 18:12:03

ANo.2

>敵の消滅でバグがおきています
 具体的にはどういうバグですか?
 症状がわからないのでは、答えようがありません。

投稿日時 - 2008-08-24 16:07:48

補足

バグというよりか、エラーでした。

さっき変数を表示させてわかったのですが、
自機のショットで敵の体力を0以下にした時に、タスクをアクティブタスクからフリータスクに戻すようにしているのですが、削除したときにアクティブタスクが永久ループに陥るようになっているようです。
それなので削除した後の描写処理でハングアップしているようです。

投稿日時 - 2008-08-24 16:43:58

ANo.1

Wr5

DirectXSDK、まだ入れていないのでビルドしてはいませんが…
Visual Studioのデバッガなどでおおよその位置の絞り込みとかできませんか?

投稿日時 - 2008-08-24 01:07:35

補足

回答ありがとうございます。
VisualStudio2005でビルドしてみましたがさっぱりです。
Borlandしかまともに使ったことがないのでVisualStudioは・・・

あと、DxLibraryを使ってるのでDirectXSDKは必要ありません。
以下からライブラリをダウンロードするだけでいけるはずです。
http://homepage2.nifty.com/natupaji/DxLib/

自分は学生なのですが、文化祭で出展したいのでどうかおねがいします・・・

投稿日時 - 2008-08-24 14:03:05

あなたにオススメの質問