[3Dゲーム]3Dモデルの大きさの利点

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

[3Dゲーム]3Dモデルの大きさの利点

#1

投稿記事 by ptolemy » 9年前

こんにちは。今回は、少し不安な点があったので質問させていただきました。
環境は、DXライブラリ,VS2013,C言語です。製作しているゲームはFPSです。

さっそく本題ですが
配布されている3Dモデルは、それぞれ製作者によってサイズが違いますよね。
とするとどれか一つのモデルを基準にして全てそろえる必要があります。

しかし、私は、最初に基準としたモデルが少し大きかったため、今になると
ステージのモデルが莫大な大きさになってしまいました。

そこで質問ですが

恐ろしく小さいセットで動かした場合と
莫大な大きさのセットで動かした場合では、それぞれメリットデメリットはあるのでしょうか?

ゲームの規模が大きくなる前に手を打っておきたいのでご回答宜しくお願いします。

ちなみに大きさですが、
小さい→配布されているモデルを縮小して大きさを合わせる
大きい→配布されているモデルを拡大して大きさを合わせる
というような位置づけでお願いします。

アバター
h2so5
副管理人
記事: 2212
登録日時: 13年前
住所: 東京
連絡を取る:

Re: [3Dゲーム]3Dモデルの大きさの利点

#2

投稿記事 by h2so5 » 9年前

極端にスケールを大きくしたり、小さくしたりすると浮動小数点数の精度の問題が発生します。

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#3

投稿記事 by ptolemy » 9年前

h2so5 さんが書きました:極端にスケールを大きくしたり、小さくしたりすると浮動小数点数の精度の問題が発生します。
ご回答ありがとうございます。
少し調べたのですが、浮動小数点数型と誤差こちらのサイトで記載されている値を超えたら、精度の問題が発生してしまうという理解でよろしいですか?


現在、私の状態だと、ステージとキャラクターの比率が10000:1くらいになっています。
よって、ステージの端から端まで座標が7桁超えます。(float型を使用してます。)

プレイに障害が出る気がするので、改善したいんですが、
10000:1と1:0.0001
ではは変わらないものですか?
できるだけ座標の値が小さい方がいいので...

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

Re: [3Dゲーム]3Dモデルの大きさの利点

#4

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

最小単位と最大単位の比率の問題なので、比率が6桁を超えた場合は誤差を生じます。
あとキャラクターが1のサイズと例えられてますが、キャラクタの関節とかはもっと小サイズのはずですよ。
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#5

投稿記事 by ptolemy » 9年前

ステージ:キャラクター=10000:1というのは倍率の比率のつもりで書かせていただきました。
大きさというより、倍率です。すみません説明を入れてませんでした。
配布されているものを10000倍と1倍にしているという意味あいです。

よって、移動すると座標が莫大な数になります。
端まで移動すると、「-1980000.0f....」などのような座標の値になります。
この場合、10000倍:1倍の比率のまま実際の倍率を小さくすればいい問題なのでしょうか?
softya(ソフト屋) さんが書きました:最小単位と最大単位の比率の問題なので、比率が6桁を超えた場合は誤差を生じます。
例えば、float型の座標の変数があったとする、その値が一定の桁数を超えたら異常がおきるというわけではないのですか?

少し、説明不足でした。すみませんでした。

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

Re: [3Dゲーム]3Dモデルの大きさの利点

#6

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

サンプルを書いてみました。
カメラから見て同じ位置にボールが見えてます(ライティングは未調整)。
カーソルの上下でZ座標だけ変わります。
さて、Z座標が誤差範囲に到達すると何が起こるでしょうか?
確かめてみてください。
【補足】 まぁ、それ以前でも誤差で揺れてますけどね。あとおかしくなり始めても止めないでください。その先に行くともっと面白くなります。

コード:

#include <math.h>
#include <DxLib.h>
int Key[256]; // キーが押されているフレーム数を格納する

// キーの入力状態を更新する
int gpUpdateKey(){
	char tmpKey[256]; // 現在のキーの入力状態を格納する
	GetHitKeyStateAll( tmpKey ); // 全てのキーの入力状態を得る
	for( int i=0; i<256; i++ ){ 
		if( tmpKey[i] != 0 ){ // i番のキーコードに対応するキーが押されていたら
			Key[i]++;     // 加算
		} else {              // 押されていなければ
			Key[i] = 0;   // 0にする
		}
	}
	return 0;
}

int WINAPI WinMain( HINSTANCE, HINSTANCE, LPSTR, int ) {
	ChangeWindowMode( TRUE ), DxLib_Init(), SetDrawScreen( DX_SCREEN_BACK );

	float cameraX = 0, cameraZ = -20; //カメラの座標
	float targetX = 0, targetZ = 0; //カメラの視線の先ターゲットの座標


	//奥行0.1~1000までをカメラの描画範囲とする
	SetCameraNearFar( 0.1f, 1000.0f ) ;

	// while(裏画面を表画面に反映, メッセージ処理, 画面クリア, キーの更新)
    while( ScreenFlip()==0 && ProcessMessage()==0 && ClearDrawScreen()==0 && gpUpdateKey()==0 ){
		DrawFormatString( 0,0, GetColor(255,255,255), "Z座標=%f", targetZ);
		
		if( Key[ KEY_INPUT_DOWN  ] >= 1 ){ // 下キーが押されていたら
			targetZ+=10000;
		}
		if( Key[ KEY_INPUT_UP    ] >= 1 ){ // 上キーが押されていたら
			targetZ-=10000;
		}
		
		//第一引数の視点から第二引数のターゲットを見る角度にカメラを設置
		SetCameraPositionAndTarget_UpVecY( VGet( targetX+cameraX, 20, targetZ+cameraZ ), VGet( targetX, 10.0f, targetZ ) ) ;

		// 3Dモデルの描画
		DrawSphere3D( VGet( targetX, 10.0f, targetZ ), 5.0f, 32, GetColor( 255, 0, 0 ), GetColor( 255, 255, 255 ), TRUE ) ;

	}

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

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#7

投稿記事 by ptolemy » 9年前

softya(ソフト屋) さんが書きました:サンプルを書いてみました。カメラから見て同じ位置にボールが見えてます(ライティングは未調整)。カーソルの上下でZ座標だけ変わります。さて、Z座標が誤差範囲に到達すると何が起こるでしょうか?確かめてみてください。【補足】 まぁ、それ以前でも誤差で揺れてますけどね。あとおかしくなり始めても止めないでください。その先に行くともっと面白くなります。
実行させていただきました。
どんどん球体からつぼ型に変化しました。
これが誤差によるズレということですか。
驚きました。
私のゲームのでも試してみたら、初期段階の崩れで止まっていました。ということは同じく変形に至るということですね。

ゲームでは、大きさの比率は同じくして、倍率を変更して、できるだけ値が小さい範囲で行ってみます。

もう一つお聞きしたいのですが、見えるモデルや位置などの状態は同じで
1・全体的にモデルが大きい 莫大な移動量
2・全体的にモデルが小さい 少ない移動量
だとしたら「負荷・変形」の度合い以外に「見栄えや繊細さ」などの違いはありますか?

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

Re: [3Dゲーム]3Dモデルの大きさの利点

#8

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

そうですね。扱う数値の比率で変わるので例をお見せしましょう。
先ほどとほぼ同じですが、球のサイズとカメラの相対位置が1/100になっています。カーソルで移動できるZの単位は1/10です。
で、同じように動かすと変形は違いますが誤差が生じますね。
顕著な誤差が発生する時に、先ほどと距離の数値が違いませんか?

コード:

#include <math.h>
#include <DxLib.h>
int Key[256]; // キーが押されているフレーム数を格納する

// キーの入力状態を更新する
int gpUpdateKey(){
	char tmpKey[256]; // 現在のキーの入力状態を格納する
	GetHitKeyStateAll( tmpKey ); // 全てのキーの入力状態を得る
	for( int i=0; i<256; i++ ){ 
		if( tmpKey[i] != 0 ){ // i番のキーコードに対応するキーが押されていたら
			Key[i]++;     // 加算
		} else {              // 押されていなければ
			Key[i] = 0;   // 0にする
		}
	}
	return 0;
}

int WINAPI WinMain( HINSTANCE, HINSTANCE, LPSTR, int ) {
	ChangeWindowMode( TRUE ), DxLib_Init(), SetDrawScreen( DX_SCREEN_BACK );

	float cameraX = 0, cameraZ = -0.2f; //カメラの座標
	float targetX = 0, targetZ = 0; //カメラの視線の先ターゲットの座標


	//奥行0.1~1000までをカメラの描画範囲とする
	SetCameraNearFar( 0.001f, 100.0f ) ;

	// while(裏画面を表画面に反映, メッセージ処理, 画面クリア, キーの更新)
    while( ScreenFlip()==0 && ProcessMessage()==0 && ClearDrawScreen()==0 && gpUpdateKey()==0 ){
		DrawFormatString( 0,0, GetColor(255,255,255), "Z座標=%f", targetZ);
		
		if( Key[ KEY_INPUT_DOWN  ] >= 1 ){ // 下キーが押されていたら
			targetZ+=1000;
		}
		if( Key[ KEY_INPUT_UP    ] >= 1 ){ // 上キーが押されていたら
			targetZ-=1000;
		}
		
		//第一引数の視点から第二引数のターゲットを見る角度にカメラを設置
		SetCameraPositionAndTarget_UpVecY( VGet( targetX+cameraX, 0, targetZ+cameraZ ), VGet( targetX, 0, targetZ ) ) ;

		// 3Dモデルの描画
		DrawSphere3D( VGet( targetX, 0, targetZ ), 0.05f, 32, GetColor( 255, 0, 0 ), GetColor( 255, 255, 255 ), TRUE ) ;

	}

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

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#9

投稿記事 by ptolemy » 9年前

softya(ソフト屋) さんが書きました:そうですね。扱う数値の比率で変わるので例をお見せしましょう。先ほどとほぼ同じですが、球のサイズとカメラの相対位置が1/100になっています。カーソルで移動できるZの単位は1/10です。で、同じように動かすと変形は違いますが誤差が生じますね。顕著な誤差が発生する時に、先ほどと距離の数値が違いませんか?
そうですね。ということは、この変形は、型の範囲によっておこるものではないのですか?

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

Re: [3Dゲーム]3Dモデルの大きさの利点

#10

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

計算時に現れる一番大きな数値と一番小さな数値が6桁を超えた比率差がある場合に誤差が生じるのです。
例えば、距離が10000でも大きさが0.001なら誤差に巻き込まれますが、大きさが0.01なら大丈夫です。
キャラの指先とか、そう言う小さな部分での誤差が発生しやすいのです。

大きさによって受ける影響度の違いです。同じ距離にある大きさの違う球で表示しています。

コード:

#include <math.h>
#include <DxLib.h>
int Key[256]; // キーが押されているフレーム数を格納する
 
// キーの入力状態を更新する
int gpUpdateKey(){
    char tmpKey[256]; // 現在のキーの入力状態を格納する
    GetHitKeyStateAll( tmpKey ); // 全てのキーの入力状態を得る
    for( int i=0; i<256; i++ ){ 
        if( tmpKey[i] != 0 ){ // i番のキーコードに対応するキーが押されていたら
            Key[i]++;     // 加算
        } else {              // 押されていなければ
            Key[i] = 0;   // 0にする
        }
    }
    return 0;
}
 
int WINAPI WinMain( HINSTANCE, HINSTANCE, LPSTR, int ) {
    ChangeWindowMode( TRUE ), DxLib_Init(), SetDrawScreen( DX_SCREEN_BACK );
 
    float cameraX = 0, cameraZ = -0.4f; //カメラの座標
    float targetX = 0, targetZ = 0; //カメラの視線の先ターゲットの座標
 
 
    //奥行0.1~1000までをカメラの描画範囲とする
    SetCameraNearFar( 0.1f, 1000.0f ) ;
 
    // while(裏画面を表画面に反映, メッセージ処理, 画面クリア, キーの更新)
    while( ScreenFlip()==0 && ProcessMessage()==0 && ClearDrawScreen()==0 && gpUpdateKey()==0 ){
        DrawFormatString( 0,0, GetColor(255,255,255), "Z座標=%f", targetZ);
        
        if( Key[ KEY_INPUT_DOWN  ] >= 1 ){ // 下キーが押されていたら
            targetZ+=1000;
        }
        if( Key[ KEY_INPUT_UP    ] >= 1 ){ // 上キーが押されていたら
            targetZ-=1000;
        }
        
        //第一引数の視点から第二引数のターゲットを見る角度にカメラを設置
        SetCameraPositionAndTarget_UpVecY( VGet( targetX+cameraX, 0, targetZ+cameraZ ), VGet( targetX, 0, targetZ ) ) ;
 
        // 3Dモデルの描画
        DrawSphere3D( VGet( targetX-0.5f, 0, targetZ+0.7f ), 0.05f, 32, GetColor( 255, 0, 0 ), GetColor( 255, 255, 255 ), TRUE ) ;
        
        // 3Dモデルの描画
        DrawSphere3D( VGet( targetX+0.5f, 0, targetZ+0.7f ), 0.5f, 32, GetColor( 0, 255, 0 ), GetColor( 255, 255, 255 ), TRUE ) ;
 
    }
 
    DxLib_End();
    return 0;
}
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#11

投稿記事 by ptolemy » 9年前

softya(ソフト屋) さんが書きました:計算時に現れる一番大きな数値と一番小さな数値が6桁を超えた比率差がある場合に誤差が生じるのです。例えば、距離が10000でも大きさが0.001なら誤差に巻き込まれますが、大きさが0.01なら大丈夫です。キャラの指先とか、そう言う小さな部分での誤差が発生しやすいのです。
データ型こちらでは7桁とあるのですが、有効桁数とはまた違うのですか?

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

Re: [3Dゲーム]3Dモデルの大きさの利点

#12

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

スレイヴ さんが書きました:
softya(ソフト屋) さんが書きました:計算時に現れる一番大きな数値と一番小さな数値が6桁を超えた比率差がある場合に誤差が生じるのです。例えば、距離が10000でも大きさが0.001なら誤差に巻き込まれますが、大きさが0.01なら大丈夫です。キャラの指先とか、そう言う小さな部分での誤差が発生しやすいのです。
データ型こちらでは7桁とあるのですが、有効桁数とはまた違うのですか?
正確には約7桁だったはずですが記憶違いかもしれません。良い機会ですのでプログラムで色々テストしてみてください。整数の場合と少数の場合でも変わったはずです。
私は誤差近辺は怖いので使いません。
まず、2進法で浮動小数点データが計算されいているので10進数に置き換えると正確ではないのです。2進数で23bitが有効桁です。
更に浮動小数点データとして保持されているときは、少数のない整数でも少数に正規化が行われるため話はややこしいです。
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#13

投稿記事 by ptolemy » 9年前

softya(ソフト屋) さんが書きました:正確には約7桁だったはずですが記憶違いかもしれません。良い機会ですのでプログラムで色々テストしてみてください。整数の場合と少数の場合でも変わったはずです。私は誤差近辺は怖いので使いません。まず、2進法で浮動小数点データが計算されいているので10進数に置き換えると正確ではないのです。2進数で23bitが有効桁です。更に浮動小数点データとして保持されているときは、少数のない整数でも少数に正規化が行われるため話はややこしいです。
なるほど。あくまで約なんですね。進む速度(ゲームなどのキャラの移動)を固定した場合、倍率を変えたら、速度も同じくサイズと等倍され、
0.01のサイズ10000の速度

0.001のサイズ1000の速度
としたら同じ体感速度になるということですか?

softya(ソフト屋) さんが書きました:計算時に現れる一番大きな数値と一番小さな数値が6桁を超えた比率差がある場合に誤差が生じるのです。例えば、距離が10000でも大きさが0.001なら誤差に巻き込まれますが、大きさが0.01なら大丈夫です。キャラの指先とか、そう言う小さな部分での誤差が発生しやすいのです。
計算方法として、
10000:0.001=10000000:1=8桁:1桁 差が7 ×
10000:0.01=1000000:1=7桁:1桁 差が6 ○
ということでよろしいですか?

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

Re: [3Dゲーム]3Dモデルの大きさの利点

#14

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

実感しないと体感的に理解できないと思うので、ぜひ実験してみてください。
私の考えは伝わった気もしますが、実験して失敗してみるのが一番身につくんです。

私の作ったような短時間で作れる適当なプログラムでも問題点は確認できるので、疑問の思ったら自分でプログラムを書いてみましょう。
短いプログラムのほうが、こちらも動作確認しやすいので答えやすいです。
どう実験して良いか分からないとか、実験結果が意味不明の時に質問して貰うとより理解できると思います。

>0.01のサイズ10000の速度
>↓
>0.001のサイズ1000の速度
> としたら同じ体感速度になるということですか?

これは現実世界でも映画でも同じですよ。
スケールと体感速度ってプログラムに限った話ではありません。
「借りぐらしのアリエッティ」でもそう感じませんか?

>10000:0.001=10000000:1=8桁:1桁 差が7 ×
>10000:0.01=1000000:1=7桁:1桁 差が6 ○
>ということでよろしいですか?

1000000:1ぐらいなら大丈夫かなと言う体験的なものなので数学的には怪しいです。
5000000:1だと多分ダメかな(未検証なので無条件に信じないように)。
気になるら前にも書いた通りプログラムで検証してください。
逆にギリギリな領域は使わななら、細かいところは気にしないで良いんじゃないでしょうか?
どうするかはスレイブさんが決めてください。
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#15

投稿記事 by ptolemy » 9年前

受験でバタバタしてて返信遅れました。
softya(ソフト屋) さんが書きました:実感しないと体感的に理解できないと思うので、ぜひ実験してみてください。私の考えは伝わった気もしますが、実験して失敗してみるのが一番身につくんです。私の作ったような短時間で作れる適当なプログラムでも問題点は確認できるので、疑問の思ったら自分でプログラムを書いてみましょう。短いプログラムのほうが、こちらも動作確認しやすいので答えやすいです。どう実験して良いか分からないとか、実験結果が意味不明の時に質問して貰うとより理解できると思います。
いつもすみません。「自分でテストしてから質問してください」というのを実行せず。短いプログラムとはどのくらいシンプルなのかというのが少しわからなかった点もあったので、イメージがわきました。これからはしっかり実験できそうです。
softya(ソフト屋) さんが書きました:これは現実世界でも映画でも同じですよ。スケールと体感速度ってプログラムに限った話ではありません。「借りぐらしのアリエッティ」でもそう感じませんか?
なるほど。今考えてみると大きさによる世界観が違った場合でもそう感じます。
いろいろなところで大きさの比というものが揃えられているからこそ等しく感じることができるのですね。
softya(ソフト屋) さんが書きました:逆にギリギリな領域は使わななら、細かいところは気にしないで良いんじゃないでしょうか?どうするかはスレイブさんが決めてください。
大きさの比をそろえて、小さすぎず大きすぎない地点を見つけたいと思います。

今回は本当にありがとうございました。
サンプルプログラムまで書いてくださり理解しやすかったです。
この掲示板に頼ってばかりではなく、自分でも問題を解決できるように努力します。

アバター
ptolemy
記事: 258
登録日時: 10年前

Re: [3Dゲーム]3Dモデルの大きさの利点

#16

投稿記事 by ptolemy » 9年前

早速、スケールにかかわる値を書き出して、1/100まで縮小した値にしました。
比を変えずに値を変えたため、しっかりと全体的にスケールが変わらないまま値の幅が小さくなりました。
よってステージのモデルの端から端まで移動しても、10000くらいで丸く収まりました。

値は以下の通りです。
カメラの高さ=340
視線先の高さ=512
y地面からの高さ= 2000
ステージ倍率=1000
プレイヤー倍率=0.5
歩く速度=200
走る速度=400
カメラのプレイヤーからの距離=500
視線先座標のプレイヤーからの距離=-1600
↓変更
カメラの高さ=3.4
視線先の高さ=5.12
y地面からの高さ=20
ステージ倍率=10
プレイヤー倍率=0.005
歩く速度=2
走る速度=4
カメラのプレイヤーからの距離=5
視線先座標のプレイヤーからの距離=-16

閉鎖

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