移動判定について

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

移動判定について

#1

投稿記事 by pupil、 » 16年前

皆様、始めまして。
今、キャラクターをスタート地点からゴール地点まで移動させると言う
ゲームを作ろうと考えているのですが、どう考えても解決できない部分
があるのでお力を貸して下さい。

MAPの壁の判定なのですが、1マスに上下左右の壁の情報を入れたいと思
っています。

ゲームプログラミングの館24を応用したいと考えているのですが;

int hantei[15][20] = {
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 },
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,1,0,0,0,1,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,1,1,1,0,0,0,1,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,1,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 },
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 },
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 },
};

int can_or_cannot(int x,int y,int muki){//進めるかを判定する
if(muki==0)//上向きなら
if(hantei[y/32-1][x/32]==1)//進めるか判定
return 1;//エラー
if(muki==1)//左向きなら
if(hantei[y/32][x/32-1]==1)
return 1;
if(muki==2)//下向きなら
if(hantei[y/32+1][x/32]==1)
return 1;
if(muki==3)//右向きなら
if(hantei[y/32][x/32+1]==1)
return 1;
return 0;//正常
}

コレを工夫して1マスに壁の上下左右の情報を入れるにはどうすればいいでしょうか?
1ならx+側とx-側が壁 2ならy-側とy+側が壁 と言うような感じです。

kazuoni

Re:移動判定について

#2

投稿記事 by kazuoni » 16年前

もしマップチップを使用するなら
int hantei[15][20] = { 
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 }, 
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,1,1,1,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,1,0,1,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,1,0,1,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,1,1,0,1,0,1,0,1,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,0,0,1,0,1,0,1,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,1,1,1,1,0,1,0,1,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1 }, 
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 }, 
{ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1 }, 
};
ですかね。
まあマップが狭くなっちゃいますが。。
でも障害のチップにキャラがめり込んでしまったら元も子もないと思いますし^^;

もし線で道を書くつもりならちょっと工夫が必要ですね。
まず2^4=16パターンの数字を用意します。
0=全部通れる
1=全部通れない
2=上だけ通れない
3=右だけ通れない
...
次に
can_or_cannot(int x,int y,int muki)
でif文条件にそれぞれの数字の時に通行不可の条件を加えればよいです。

理論上はこんな感じですけど、結構大変そうですね。。

lbfuvab

Re:移動判定について

#3

投稿記事 by lbfuvab » 16年前

進む事のできる方向を

#define UP   0x1
#define DOWN  0x2
#define RIGHT  0x4
#define LEFT  0x8

と定義し判定時は

if(hantei[x][y] & UP){
  //処理
}

などとする方法はどうでしょうか?

non

Re:移動判定について

#4

投稿記事 by non » 16年前

>コレを工夫して1マスに壁の上下左右の情報を入れるにはどうすればいいでしょうか?
>1ならx+側とx-側が壁 2ならy-側とy+側が壁 と言うような感じです。

質問です。
添付は、自分がいる場所の上下左右の座標のデータが1なら壁(進めない)という情報ですが、
pupilさんが目指しているのは、薄い壁といういうイメージだと考えていいのでしょうか?
例えばマイクロマウスの壁のように隣のブロックも通れる通路ではあるけど、間に壁があるような。

だとすれば、
方法1、ビットをうまく使う。
上 右 下 左
b3 b2 b1 b0 を上下左右の状態として入れる。
0 0 0 0 (10進0)なら上下左右とも進める
0 1 1 0 (10進6)なら右と下は壁

方法2 構造体を使う
static KABE{
int up;
int right;
int down;
int left;
}

などの方法があります。

non

Re:移動判定について

#5

投稿記事 by non » 16年前

方法1はlbfuvabさんと同じですね。

pupil、

Re:移動判定について

#6

投稿記事 by pupil、 » 16年前

>kazuoniさん

なるほど~確かに0~順にif分で分岐すれば何とかなりそうですが^^;
数が多くてわかりにくくなりますよね~


>lbfuvabさん
なるほど~定義と言う数学的な方法も使えるのですね~
えと、1が上で2が下なら、3が上下壁って事なのでしょうか?

いやはや、C言語の奥の深さには驚かされてばかりです;


>nonさん

>質問です。
>添付は、自分がいる場所の上下左右の座標のデータが1なら壁(進めない)という情報ですが、
>pupilさんが目指しているのは、薄い壁といういうイメージだと考えていいのでしょうか?
ですです。すみません、テンプはゲーム館からコピペした物なので;

確か2年ほど前に情報Aの授業でbitの話が出てきましたが、
何でそんなややこしいもん使うねん!とスルーした記憶が
あります。あぁ、今から思えばもう少し理解を深めておけ
ばよかったですね。でも、何とか理解しました。

方法2の構造体の話なのですが、イマイチイメージが沸きません;
もう少し詳しく書いてはいただけ無いでしょうか?



すみません、環境書くの忘れてました;
OS     WindowsVista
コンパイラ Visual C++ 9.0
C暦    1ヶ月

ツクール買ってゲーム作るのももったい無いかな~とおもっていろいろ
探していたらこのサイトに出会いました。この掲示板は解答が早いんですね~
ものすごくびっくりしました。今回は丁寧な解答ありがとうございました。
また困ったら助けてください。よろしくお願いします。

non

Re:移動判定について

#7

投稿記事 by non » 16年前

添付プログラムと同じように書けばこうなります。
static KABE{ 
	int up; 
	int right; 
	int down; 
	int left; 
};
static KABE hantei[15][20]={{1,1,1,1},{1,1,0,1}・・・以下略

int can_or_cannot(int x,int y,int muki){//進めるかを判定する 
	if(muki==0)//上向きなら 
		if(hantei[y][x].up==1)//進めるか判定 
			return 1;//エラー 
	if(muki==1)//左向きなら 
		if(hantei[y][x].left==1) 
			return 1; 
   以下略
初期値を与えるのが、やや面倒ですね。一つの座標につき、4つ入力が必要です。

non

Re:移動判定について

#8

投稿記事 by non » 16年前

データを与えるのが面倒そうなので、共有体を使ってみました。
union KABE{
	unsigned char BYTE;
	struct {
		unsigned char up:1;
		unsigned char right:1;
		unsigned char down:1;
		unsigned char left:1;
		unsigned char work:4;
	}BIT;
};
union KABE hantei[15][20]={15,11,・・・以下略

int can_or_cannot(int x,int y,int muki){//進めるかを判定する 
	if(muki==0)//上向きなら 
		if(hantei[y][x].BIT.up==1)//進めるか判定 
			return 1;//エラー 
	if(muki==1)//左向きなら 
		if(hantei[y][x].BIT.left==1) 
			return 1; 
   以下略
ただし、この方法の場合、どちらが上位ビットになるかは環境に依存しますので、
よく確認することが必要です。
共有体とは、同じ箱に2つの名前がつくようなものです。
ですから8ビットまとめて値を代入するときは
hantei[y][x].BYTE=0x06; //16進数で入力する場合
のようにすれば良く、
1ビット単位で参照するときは
hantei[y][x].BIT.left のように使います。
このときleftがBit0(最下位ビット)になるかは環境に依存しますので注意が必要です。
環境によってはBit7(最上位ビット)になることもあります。
unsigned char work:4;は8ビットになるように調整するためのものです。

閉鎖

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