キャラクターのジャンプ処理

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
kerotan0820
記事: 91
登録日時: 14年前

キャラクターのジャンプ処理

#1

投稿記事 by kerotan0820 » 14年前

キャラクターをジャンプさせる処理を物理計算を用いずに再現してみようと思いました

ゲームプログラミングの館の各単元を読んで理解はしているものの、自身で考えたものをプログラムに治すことはまだ慣れていないので、まずキャラクターを上昇させ、一定の座標に達したら降下し元の位置に戻る、速度の変化などはナシで挑戦してみることにしました。

そこで書いたプログラムがこちらです。

コード:

#include "DxLib.h"

int WINAPI WinMain(HINSTANCE,HINSTANCE,LPSTR,int){
  if( ChangeWindowMode(TRUE) != DX_CHANGESCREEN_OK || DxLib_Init() == -1 ) return -1; //ウィンドウ化と初期化処理
  



  int x=320,y=448,flag=0,image[16];
  char Key[256];

  LoadDivGraph("char.png",16,4,4,32,32,image) ; //画像を分割してimage配列に保存


while(!ProcessMessage() && !ClearDrawScreen() && !GetHitKeyStateAll( Key ) && !Key[KEY_INPUT_ESCAPE]){
            //↑メッセージ処理        ↑画面をクリア         ↑キーボード入力状態取得       ↑ESCが押されると終了
 
                if( Key[ KEY_INPUT_RETURN ]  == 1 ) //エンターキーが押された
					flag=1;
					while(1){        //ジャンプ上昇処理
						if(flag=1){//flagが1なら上昇
							if(y>=240){
								DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画
								y-=20;
							}else{
								flag=0; //flagを0に初期化 
								break;
							}
						}
					}
					while(1){        //ジャンプ下降処理
						if(flag=0){
							if(y<=448){
								DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画
								y+=20;
							}else{
								break;
							}
						}
					}
					
					
					ScreenFlip();//裏画面を表画面に反映

}
  WaitKey();
  DxLib_End();
  return 0 ;
}

  


エンターを押すことでジャンプ処理が実行され、まず上昇処理のwhileに入ります。
一定の座標に達したらbreakし、下降処理のwhileに入ります。
下降しきったところで一連の流れが終了します。

大雑把になりますが、上記のような動作をさせたいのですが、実行すると 応答なしのまま動作しません。

エラーはでないのですが、プログラム上に問題があるのでしょうか?
ご教示いただけると幸いです。

□追記□
プログラムを添付していたのですが、短いプログラムなので質問に直接のせました。
最後に編集したユーザー kerotan0820 on 2011年4月01日(金) 13:31 [ 編集 1 回目 ]
けろけろにゃー (」・ω・)」うー!

アバター
みけCAT
記事: 6734
登録日時: 14年前
住所: 千葉県
連絡を取る:

Re: キャラクターのジャンプ処理

#2

投稿記事 by みけCAT » 14年前

コード:

                    while(1){        //ジャンプ下降処理
                        if(flag=0){
                            if(y<=448){
                                DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画
                                y+=20;
                            }else{
                                break;
                            }
                        }
                    }
この部分で、if(flag=0)は永遠に偽なので、いつまで経ってもbreakせず、無限ループになってしまいます。
flagが0と等しいことを判定する式はflag==0です。
同様に、その上のif(flag=1)も修正する必要があると思います。
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

アバター
softya(ソフト屋)
副管理人
記事: 11677
登録日時: 14年前
住所: 東海地方
連絡を取る:

Re: キャラクターのジャンプ処理

#3

投稿記事 by softya(ソフト屋) » 14年前

大問題としては、DrawGraph()してもScreenFlip()しないと画面が更新されないのでwhileループが有ること自体が問題です。
ProcessMessage()→ClearDrawScreen()→DrawGraph()→ScreenFlip()で1回の画面描画ですので、whileが無くても動くようにしてください。
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

kerotan0820
記事: 91
登録日時: 14年前

Re: キャラクターのジャンプ処理

#4

投稿記事 by kerotan0820 » 14年前

皆様回答ありがとうございます。

以下のとおりにプログラムを修正しました

コード:

#include "DxLib.h"

int WINAPI WinMain(HINSTANCE,HINSTANCE,LPSTR,int){
  if( ChangeWindowMode(TRUE) != DX_CHANGESCREEN_OK || DxLib_Init() == -1 ) return -1; //ウィンドウ化と初期化処理
  



  int x=320,y=448,flag=0,image[16];
  char Key[256];

  LoadDivGraph("char.png",16,4,4,32,32,image) ; //画像を分割してimage配列に保存


while(!ProcessMessage() && !GetHitKeyStateAll( Key ) && !Key[KEY_INPUT_ESCAPE]){
            //↑メッセージ処理        ↑画面をクリア         ↑キーボード入力状態取得       ↑ESCが押されると終了

	DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画 (一番最初の画像表示プログラム)
 
	if( Key[ KEY_INPUT_RETURN ]  == 1 ){
					flag=1; //上昇フラグ
					
				              /******ジャンプ上昇処理******/

						if(flag==1){//flagが1なら上昇
							for(y=448;y>=272;y-=16){
								ClearDrawScreen();
								DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画
								ScreenFlip();//裏画面を表画面に反映
							}
						}
						
					flag=0;//下降フラグ

					         /******ジャンプ下降処理******/

						if(flag==0){     //flagが0なら下降
							for(y=240;y<=448;y+=8){
								ClearDrawScreen();
								DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画
								ScreenFlip();//裏画面を表画面に反映
							}
						}
	} //Enterが押されたら実行する処理末

}

  WaitKey();
  DxLib_End();
  return 0 ;
}
なんとかキャラクターを動かすことは出来ましたが、上に移動し、下降した後に所定の位置に一体と、画面から少しはみ出た状態でもう一体表示されます。

forで座標の数値を増やしすぎているのが原因で、最初のセットポジションに表示するプログラムの一番最初のキャラクター表示プログラムがおかしな位置に表示されているのかな?とも思い
試行錯誤したのですがどうもうまくいきません。

ご教示いただけると幸いです
けろけろにゃー (」・ω・)」うー!

kerotan0820
記事: 91
登録日時: 14年前

Re: キャラクターのジャンプ処理

#5

投稿記事 by kerotan0820 » 14年前

すみません。

二つ目のfor文を外れたところに 

y-=8;
を追加したところ治りました ありがとうございました^^
けろけろにゃー (」・ω・)」うー!

アバター
softya(ソフト屋)
副管理人
記事: 11677
登録日時: 14年前
住所: 東海地方
連絡を取る:

Re: キャラクターのジャンプ処理

#6

投稿記事 by softya(ソフト屋) » 14年前

whileの代わりにforを書いても同じ問題があります。
while(!ProcessMessage() && !ClearDrawScreen() && !GetHitKeyStateAll( Key ) && !Key[KEY_INPUT_ESCAPE]){
のループの中に基本的に描画のためだけのwhileループもforループを書くと後で色々と困る事になります。このままだと応答しないプログラムと言われるとか、ClearDrawScreen()やScreenFlip();のタイミングが大きなプログラムになると管理しきれなくなる恐れが高いです。なので、むやみにclearDrawScreen();やScreenFlip();を入れるクセは今のうちに直しましょう。

元のままで少し修正してこんな形にすればお望みの物が作れます。何処が違うか良く考えてみてください。

コード:

#include "DxLib.h"

int WINAPI WinMain(HINSTANCE,HINSTANCE,LPSTR,int){
	if( ChangeWindowMode(TRUE) != DX_CHANGESCREEN_OK || DxLib_Init() == -1 ) return -1; //ウィンドウ化と初期化処理




	int x=320,y=448,flag=0,image[16];
	char Key[256];

	LoadDivGraph("char.png",16,4,4,32,32,image) ; //画像を分割してimage配列に保存


	while(!ProcessMessage() && !ClearDrawScreen() && !GetHitKeyStateAll( Key ) && !Key[KEY_INPUT_ESCAPE]){
		//↑メッセージ処理        ↑画面をクリア         ↑キーボード入力状態取得       ↑ESCが押されると終了

		if( Key[ KEY_INPUT_RETURN ]  == 1 ) //エンターキーが押された
			flag=1;
		//ジャンプ上昇処理
		if(flag==1){//flagが1なら上昇
			if(y>=240){
				y-=20;
			}else{
				flag=0; //flagを0に初期化 
			}
		}
		//ジャンプ下降処理
		if(flag==0){
			if(y<448){
				y+=20;
			}
		}

		DrawGraph(x,y, image[10] , TRUE ) ;//画像を描画

		ScreenFlip();//裏画面を表画面に反映

	}
	WaitKey();
	DxLib_End();
	return 0 ;
}
地面に食い込むのは、if(y<=448){としているからでif(y<448){とすれば直ります。
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

kerotan0820
記事: 91
登録日時: 14年前

Re: キャラクターのジャンプ処理

#7

投稿記事 by kerotan0820 » 14年前

softyさん>>

私のジャンプ処理の途中で左右への移動をさせようとしたりした時どう書けば良いのかと悩んでいました。
softyさんの書き方ならばエンターを押されたあとの処理としてジャンプ処理や移動処理などを加えることが容易にできることが分かりました。
これからはsoftyさんの教えてくださった記述の仕方にくむ癖をつけたいと思います。
けろけろにゃー (」・ω・)」うー!

閉鎖

“C言語何でも質問掲示板” へ戻る