先ほどまでは、しっかり敵の方向を向いて撃っていたのですが
敵が一定の範囲内に迫ってきたら元々の行動パターンで攻撃し、
範囲外にいた場合プレイヤーについてくる、ということをしたくてコードを変えていたら
動かなくなりました。。
しかし、自分の頭の中でルーチンをたどっていくと正常に動かないとおかしいです。
もしよかったら悪い部分を指摘してもらえないでしょうか?
void com_move_up(int i){
if(player[i].speed_max > player[i].speed_inertia){//最高速度の設定
player[i].speed_inertia += player[i].axel;
}
}
void com_move_nup(int i){//Wキーを押していないときの処理と同等
if(player[i].axel < player[i].speed_inertia){//-防止、orで0以上、にするのもアリ
player[i].speed_inertia -= player[i].axel;//摩擦、加速度減少
}
if(player[i].speed_inertia<=player[i].axel){
player[i].speed_inertia=0;
}//減速度より慣性速度が低い場合とまる
}
void com_moveing(double *l_tmpx,double *l_tmpy,int i,double l_x){//移動先をテンプレートに代入。加速度が微塵もついてなかったらもちろん進行先座標に0を代入
if(player[i].speed_inertia>0){
*l_tmpx = cos(player[i].angle_inertia + l_x) * (player[i].speed + player[i].speed_inertia);//構造体にすべし。(多人数対策)
*l_tmpy = sin(player[i].angle_inertia + l_x) * (player[i].speed + player[i].speed_inertia);//と思ったけどtmpに入れてるのがすでに構造体なわけでいいんだった
}else{
*l_tmpx=0;
*l_tmpy=0;
}
}
void com_check_move(double *l_tmpx,double *l_tmpy,int i){//先に判定して可能なら移動する。l_p_x,yはcharacterの座標のtmp、そこにmove関数から来る数値を足して可能かどうか判断する。
if(1<=field_check((int)(player[i].x + *l_tmpx),(int)(player[i].y),0,i)){//x座標、y座標、敵1か味方0か、その番号
player[i].x+=*l_tmpx;
}
if(1<=field_check((int)(player[i].x),(int)(player[i].y + *l_tmpy),0,i)){//x座標、y座標、敵1か味方0か、その番号
player[i].y+=*l_tmpy;
}
if(2==field_check((int)(player[i].x + *l_tmpx),(int)(player[i].y),0,i)){//敵にぶつかってたら
player[i].life-=0.1; //ダメージ計算は別にすべき
}
if(2==field_check((int)(player[i].x),(int)(player[i].y + *l_tmpy),0,i)){
player[i].life-=0.1;//ダメージ計算は別にすべき
}
}
void com_compact_angles(int i){
if(player[i].angle>1*PI){
player[i].angle -= 2*PI;
}
if(player[i].angle<-1*PI){
player[i].angle += 2*PI;
}
if(player[i].angle_inertia>1*PI){
player[i].angle_inertia -= 2*PI;
}
if(player[i].angle_inertia<-1*PI){
player[i].angle_inertia += 2*PI;
}
}
double com_range_target(int i,int z){//敵zとの距離を測る。
double com_range;
double com_target_x;
double com_target_y;
com_target_x = player[i].x - enemy[z].x; //代入するお//準備
com_target_y = player[i].y - enemy[z].y; //
com_range = com_target_x*com_target_x+com_target_y*com_target_y;
return com_range;
}
void com_ai_base_main(){
for(int i=1;i<PLAYER_NUMBER_MAX;i++){//仲間を全員動かすためのループ
if(player[i].life>0){//仲間が死んでたり居なかったりしたときの分岐
double l_tmpx=0,l_tmpy=0;
double enemy_com_angle;
double player0_com_angle;
double enemy_com_angle_inertia;
double l_x = 0;
int z =player[i].target; //代入しないと利用できない・・・
player0_com_angle = atan2(player[0].y-player[i].y,player[0].x-player[i].x)-player[i].angle;//playerへの角度
enemy_com_angle = atan2(enemy[z].y-player[i].y,enemy[z].x-player[i].x)-player[i].angle;//敵への角度-機体の角度,正面にくれば来るほど絶対値は小さくなる。
enemy_com_angle_inertia = atan2(enemy[z].y-player[i].y,enemy[z].x-player[i].x)-player[i].angle_inertia;//敵への角度-機体の慣性方向
switch (player[i].ai_number){
case 0:
if(player[i].targeting_flag==1){//誰かをtargetしてたら
if(sin(-player[i].angle_rps)>sin(enemy_com_angle)){
com_angle_left(i); //関数部分
if(0>cos(enemy_com_angle)){//後方180度内にいる場合(cosの関数は↑1,↓-1,←→0になってる)
com_move_left(i,&l_x);
}
}
if(sin(player[i].angle_rps)<sin(enemy_com_angle)){ //このangle_rpsは誤差修正//1フレームで曲がれる数より高い角度にいたら
com_angle_right(i); //関数部分
if(0>cos(enemy_com_angle)){
com_move_right(i, &l_x);
}
}
if(enemy[z].life>0){ //敵の通し番号iをtargetしている時、ライフがあるならば
if(0.5<cos(enemy_com_angle)){//前方180度内にいるなら
com_move_up(i); //関数部分
com_angle_change(i);
}else{ //後ろに居る時
if(100<com_range_target(i,z)){
com_move_nup(i);
com_angle_change(i);
}else{
com_move_up(i);
}
}
}else{ //ターゲット中の敵のライフが無いならば
player[i].targeting_flag=0;
}
if(sin(player[i].angle_rps)>sin(enemy_com_angle)&&sin(-player[i].angle_rps)<sin(enemy_com_angle)){//正面に敵が居るとき撃つ(sin(θ)でangle_rpsより小さければ撃つ)
shot_search_shot(i,player[i].gun_knd,0); //関数部分//第三引数は撃主
}
}else{//誰もターゲットしていない時
for(int t=0;t<ENEMY_NUMBER_MAX;t++){
if((10000>com_range_target(i,t))&&(enemy[t].life>0)){
player[i].target=t;
player[i].targeting_flag=1;
}
}
}
break;
default:
break;
}//switch終わり
com_moveing(&l_tmpx,&l_tmpy,i,l_x); //関数部分 //壁判定その他諸々のための一時保存
com_check_move(&l_tmpx,&l_tmpy,i); //関数部分 //壁判定
com_compact_angles(i); //角度最小化
}
}
}