球の減速について

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
伊集院電一郎

球の減速について

#1

投稿記事 by 伊集院電一郎 » 13年前

ここ→http://dixq.net/g/32.htmlを参考に玉の動きについて学んでいるのですが
x方向の減速が簡単そうなんですが地味に分かりません。
除じょに減速して最後に止めたいのですがどのようにすればいいでしょうか。
基本的なことかもしれませんがよろしくお願いします

コード:

#include "DxLib.h"
#include <math.h>

#define e 0.800
#define g 9.807
#define y_max 2.000
#define PI 3.141593

int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance,LPSTR lpCmdLine, int nCmdShow ){
	ChangeWindowMode( TRUE ) ; // ウインドウモードに変更
	if( DxLib_Init() == -1 ) return -1; //DXライブラリ初期化 エラーが起きたら終了
	int y,image[16],time1,time2,flag=0,i,j; //時間を取得するtime1,time2。フラグ-flag
	double t,v0;
	char Key[256];
	int x=400;
	double ss=1;
	double s=1;double ooo=1;
	SetDrawScreen( DX_SCREEN_BACK ) ;//描画先を裏画面に設定
	while(1){
		ClearDrawScreen();//裏画面のデータを全て削除
		GetHitKeyStateAll( Key ) ; // すべてのキーの状態を得る
		if( ProcessMessage() == -1 ) break ; //異常がおきたら終了
		//右クリックで開始
		if( ( GetMouseInput() & MOUSE_INPUT_RIGHT ) != 0 ){
			time1 = GetNowCount();
			flag=1;
			j=0;
		}
		++x;
		++ss;
		s+=cos(PI*ss/40.0f)*5.0f;
		ooo=sqrt( ss)*4;

		if(flag==1){
			time2 = GetNowCount() ; // 現在経過時間を得る
			t = (double)(time2 - time1) / 1000.000;
			v0= sqrt ( 2.000 * g * y_max); //初速度を計算
			for(i=0;i<j;i++) //j回跳ね返った時の初速度
				v0*=e; //eは反発係数
			y = (int)((v0 * t - 0.500 * g * t * t ) * 480.000 / y_max);
			if(y>=0)
				DrawCircle( ss , 480-32-y , 10 , GetColor( 255 , 255 , 255 ) , TRUE) ;
			else{
				DrawCircle( ss , 480-32   , 10 , GetColor( 255 , 255 , 255 ) , TRUE) ;
				time1=GetNowCount();
				j++;
			}
		}

		if( Key[ KEY_INPUT_ESCAPE ] == 1 ) break;//Escボタンが押されたらブレイク

		DrawFormatString( 0,   0, GetColor( 255 , 255 , 255 ), "time1 : %f", time1 ) ;
		DrawFormatString( 0,  20, GetColor( 255 , 255 , 255 ), "t : %f", t ) ;
		DrawFormatString( 0,  40, GetColor( 255 , 255 , 255 ), "y:%d", y ) ;
		DrawFormatString( 0,  60, GetColor( 255 , 255 , 255 ), "x:%d", x ) ;
		DrawFormatString( 0,  80, GetColor( 255 , 255 , 255 ), "sin:%f", sin(s) ) ;
		DrawFormatString( 0, 100, GetColor( 255 , 255 , 255 ), "ooo:%f", ooo ) ;
		ScreenFlip() ;//裏画面データを表画面へ反映
	}
	DxLib_End() ;// DXライブラリ使用の終了処理
	return 0 ;// ソフトの終了
}
※ (管理人がソースコードの記載を修正しました)

アバター
Dixq (管理人)
管理人
記事: 1661
登録日時: 13年前
住所: 北海道札幌市
連絡を取る:

Re: 球の減速について

#2

投稿記事 by Dixq (管理人) » 13年前

上の赤で囲まれた注意書きにもある通り、ソースコードはコードタグで囲んで頂けると幸いです。
インデントなども綺麗に揃えたほうがわかりやすいと思います。
後、変数名を見ても何の役割をするのかパッとみて良くわからないので、コードを提示する時は、変数名を解りやすくするか、
コメントを付けて頂けると有難いです。

ところで、ssがx座標のようですが、徐々に止めたいなら、x方向の速度Vxを用意して、それを少なくしてはどうですか?
水平方向の速度Vxは最初何かの値にセットしておきます。

x += Vx;

をループの度に計算します。
Vxはループの度に

Vx -= 0.1;

とでもして、0にすれば、xの移動量は次第に少なくなり、0になります。
もっと移動量全体を含め、時間との関係を持った計算式にしたければ、
y方向で計算している力学の方程式を水平方向にも使えばよいでしょう。

徐々に止めたいということなので行いたい事の詳細はわかりませんが・・。

伊集院電一郎

Re: 球の減速について

#3

投稿記事 by 伊集院電一郎 » 13年前

こんな感じでしょうか。

コード:

#include "DxLib.h"
#include <math.h>
 
#define e 0.800
#define g 9.807
#define y_max 2.000
 #define PI 3.141593


int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance,LPSTR lpCmdLine, int nCmdShow ){
        ChangeWindowMode( TRUE ) ;          // ウインドウモードに変更
        if( DxLib_Init() == -1 ) return -1; //DXライブラリ初期化 エラーが起きたら終了 

	

	int y,image[16],time1,time2,flag=0,i,j; //時間を取得するtime1,time2。フラグ-flag
        double t,v0;
        char Key[256];
 int x=400;
 double ss=1;
 double s=1;double ooo=1;
        SetDrawScreen( DX_SCREEN_BACK ) ;//描画先を裏画面に設定
 double Vx = 5;
                                   
        while(1){
                ClearDrawScreen();//裏画面のデータを全て削除
                GetHitKeyStateAll( Key ) ;           // すべてのキーの状態を得る
                if( ProcessMessage() == -1 ) break ; //異常がおきたら終了
 //右クリックで開始
                if( ( GetMouseInput() & MOUSE_INPUT_RIGHT ) != 0  ){
                        time1 = GetNowCount();
                        flag=1;
                        j=0;
                }++x;
			

ss += Vx;

                if(flag==1){ 
                        time2 = GetNowCount() ;                  // 現在経過時間を得る
                        t = (double)(time2 - time1) / 1000.000;
                        v0= sqrt ( 2.000 * g * y_max);           //初速度を計算
                        for(i=0;i<j;i++) 
							Vx -= 0.3;                        //j回跳ね返った時の初速度
                                v0*=e;                           //eは反発係数
                        y = (int)((v0 * t - 0.500 * g * t * t ) * 480.000 / y_max);
                        if(y>=0)
                           DrawCircle( ss , 480-32-y , 10 , GetColor( 255 , 255 , 255 ) , TRUE) ;
                        else{
                           DrawCircle( ss , 480-32 , 10 , GetColor( 255 , 255 , 255 ) , TRUE) ;
                                time1=GetNowCount();
                                j++;
                        }
                }
        
                if( Key[ KEY_INPUT_ESCAPE ]  == 1 ) break;//Escボタンが押されたらブレイク

DrawFormatString( 0, 0,  GetColor( 255 , 255 , 255 ), "time1 : %f", time1 ) ;
 DrawFormatString( 0, 20,  GetColor( 255 , 255 , 255 ), "t : %f", t ) ;
DrawFormatString( 0, 40,  GetColor( 255 , 255 , 255 ), "y:%d", y ) ;
DrawFormatString( 0, 60,  GetColor( 255 , 255 , 255 ), "x:%d", x ) ;
DrawFormatString( 0, 80,  GetColor( 255 , 255 , 255 ), "sin:%f", sin(s) ) ;
DrawFormatString( 0, 100,  GetColor( 255 , 255 , 255 ), "ss:%f", ss ) ;
                ScreenFlip() ;//裏画面データを表画面へ反映
        }
        DxLib_End() ;// DXライブラリ使用の終了処理
        return 0 ;// ソフトの終了
}

できればもっとゆるやかに止めたいのですが・・・

アバター
kimuchi
記事: 163
登録日時: 13年前
住所: 東京

Re: 球の減速について

#4

投稿記事 by kimuchi » 13年前

推測の域を出ませんが一応。

43、44行目で
for(i=0;i<j;i++)
Vx -= 0.3;
とありますが、この場合跳ね返ったときにそのときの跳ね返った回数だけVxから0.3引くことになります。
跳ね返るごとにVxから0.3引くのであればfor文は必要ないように思えます。

閉鎖

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