비공개2012. 8. 17. 17:45


 

 생각나는데로 막짬 2시간 30분 ㅠ

역시 난 C 스타일

 

 OTL

 

 

 

#include <iostream>
using namespace std;

// 벽으로 이동하려고 하면 어떻게 되는가?
// 첫 번째 목표 지점에 둔 상자를 다시움직이려고 하면 어떻게 되는가?
// 상자를 두개 이상 밀면 어떻게 되는가?
// 상자를 벽 쪽으로 밀면 어떻게 되는가?

const int MAX_SPACE = 30;
const char g_Stage1[][MAX_SPACE] =	{
										{"########"},
										{"# .. p #"},
										{"# OO   #"},
										{"#      #"},
										{"########"}
									};

enum eObject {
	OBJ_NONE = 0,
	OBJ_SPACE,
	OBJ_WALL,
	OBJ_GOAL,
	OBJ_BLOCK,
	OBJ_BLOCK_ON_GOAL,
	OBJ_MAN,	
	OBJ_MAN_ON_GOAL
};

enum eDirection
{
	DIR_LEFT = 0,
	DIR_RIGHT,
	DIR_UP,
	DIR_DOWN
};

void MoveObject( int* _pBoard, int _pos, eDirection _eDir );

int main()
{
	/// 초기화
	int line = sizeof( g_Stage1 ) / MAX_SPACE ;

	int* pStage = new int[line * MAX_SPACE];
	memset(pStage, 0, line * MAX_SPACE );

	// 컨트롤 하기위한 배열 재구성
	for( int i = 0; i < line; i++ )
	{
		for( int j = 0; j < MAX_SPACE; j++ )
		{
			switch( g_Stage1[i][j] )
			{
			case ' ' : pStage[i * MAX_SPACE + j] = OBJ_SPACE;	break;
			case '#' : pStage[i * MAX_SPACE + j] = OBJ_WALL;	break;
			case '.' : pStage[i * MAX_SPACE + j] = OBJ_GOAL;	break;
			case 'O' : pStage[i * MAX_SPACE + j] = OBJ_BLOCK;	break;
			case 'p' : pStage[i * MAX_SPACE + j] = OBJ_MAN;		break;
			default  : pStage[i * MAX_SPACE + j] = OBJ_NONE;	break;
			}
		}
	}

	while(1)
	{	
		system("cls");

		// 배열 그리기
		for( int i = 0; i < line; i++ )
		{
			for( int j = 0; j < MAX_SPACE; j++ )
			{
				eObject objNum = (eObject)pStage[i * MAX_SPACE + j];
				if( objNum == 0 )
				{
					cout << endl;
					break;
				}

				char ch;
				switch( objNum )
				{
				case OBJ_NONE		:					break;
				case OBJ_SPACE		:		ch = ' ';	break;
				case OBJ_WALL		:		ch = '#';	break;
				case OBJ_GOAL		:		ch = '.';	break;
				case OBJ_BLOCK		:		ch = 'o';	break;
				case OBJ_BLOCK_ON_GOAL :	ch = 'O';	break;
				case OBJ_MAN		:		ch = 'p';	break;
				case OBJ_MAN_ON_GOAL :		ch = 'P';	break;
				}

				cout << ch;
			}
		}

		int nGoalTotalCount = 0;
		for( int i = 0; i < line; i++ )
		{
			for( int j = 0; j < MAX_SPACE; j++ )
			{
				// 골인 총 개수 파악( 클리어 체크용 )
				if( (eObject)pStage[i * MAX_SPACE + j] == OBJ_GOAL )
					nGoalTotalCount++;
			}
		}


		// 게임 클리어 판단
		int nBlockOnGoalCount = 0;
		for( int i = 0; i < line; i++ )
		{
			for( int j = 0; j < MAX_SPACE; j++ )
			{
				if( (eObject)pStage[ i * MAX_SPACE + j ] == OBJ_BLOCK_ON_GOAL )
				{
					if( nBlockOnGoalCount == nGoalTotalCount )
					{
						cout << endl << "Congraturation!!!" << endl;
						system("pause");
						return 1;
					}
				}
			}
		}

		// 설명
		cout << endl << "[a:left] / [d:right] / [w:up] / [s:down]" << endl;
		
		// 키 입력
		char ch;
		cin >> ch;

		// 입력받은 키 값에 대한 데이터 처리 및 갱신
		int manPos = -1;
		for( int i = 0; i < line; i++ )
		{
			for( int j = 0; j < MAX_SPACE; j++ )
			{
				// 플레이어 위치
				if( (eObject)pStage[i * MAX_SPACE + j] == OBJ_MAN || (eObject)pStage[i * MAX_SPACE + j] == OBJ_MAN_ON_GOAL )
					manPos = i * MAX_SPACE + j;
			}
		}

		switch( ch )
		{
						
		case 'a' : MoveObject( pStage, manPos, DIR_LEFT );
			break;
		case 'd' : MoveObject( pStage, manPos, DIR_RIGHT );
			break;
		case 'w' : MoveObject( pStage, manPos, DIR_UP );
			break;
		case 's' : MoveObject( pStage, manPos, DIR_DOWN );
			break;
		}


	}
	
	return 0;
}

void MoveObject( int* _pStage, int _pos, eDirection _eDir )
{
	int manMovePos = -1;

		 if( _eDir == DIR_LEFT )	manMovePos = _pos - 1;
	else if( _eDir == DIR_RIGHT )	manMovePos = _pos + 1;
	else if( _eDir == DIR_UP )		manMovePos = _pos - MAX_SPACE;
	else if( _eDir == DIR_DOWN )	manMovePos = _pos + MAX_SPACE;

	if( manMovePos < 0 ) return;

	// 이동가능한가?
	bool bMove = true;
	if( (eObject)_pStage[manMovePos] == OBJ_NONE			|| 
		(eObject)_pStage[manMovePos] == OBJ_BLOCK			||
		(eObject)_pStage[manMovePos] == OBJ_MAN				|| 
		(eObject)_pStage[manMovePos] == OBJ_WALL			|| 
		(eObject)_pStage[manMovePos] == OBJ_BLOCK_ON_GOAL )
	{
		bMove = false;
	}

	// 이동 하려는 지점이 블럭 일 경우 밀자!
	int objIndex = -1;
	if( (eObject)_pStage[manMovePos] == OBJ_BLOCK )
	{
		// 밀려는 방향으로 블럭 앞 체크
			 if( _eDir == DIR_LEFT )	objIndex = manMovePos - 1;
		else if( _eDir == DIR_RIGHT )	objIndex = manMovePos + 1;
		else if( _eDir == DIR_UP )		objIndex = manMovePos - MAX_SPACE;
		else if( _eDir == DIR_DOWN )	objIndex = manMovePos + MAX_SPACE;

		if( objIndex == -1 || objIndex < 0 ) return;

		if( (eObject)_pStage[objIndex] == OBJ_SPACE || (eObject)_pStage[objIndex] == OBJ_GOAL )
			bMove = true;
	}

	if( bMove )
	{
		// 기존 지점 상태 변경
		if( (eObject)_pStage[_pos] == OBJ_MAN_ON_GOAL ) _pStage[_pos] = OBJ_GOAL;
		else										    _pStage[_pos] = OBJ_SPACE;

		// 이동 지점 상태 변경
			 if( (eObject)_pStage[manMovePos] == OBJ_GOAL )		_pStage[manMovePos] = OBJ_MAN_ON_GOAL;
		else if( (eObject)_pStage[manMovePos] == OBJ_BLOCK )
		{
			_pStage[manMovePos]	= OBJ_MAN;	
			if( (eObject)_pStage[objIndex] == OBJ_GOAL ) _pStage[objIndex] = OBJ_BLOCK_ON_GOAL;
			else										 _pStage[objIndex] = OBJ_BLOCK;
		}
		else _pStage[manMovePos] = OBJ_MAN;		
	}
}
Posted by 닭꽝