Пример #1
0
void GameManager::NET_PlayGameFlow()
{
	Network network;
	PacketType type;
	ErrorType error;

	try
	{
		Network::Initialize();
	}
	catch (Network::Exception)
	{
		puts("초기화 도중 문제가 발생했습니다.");
		return;
	}

	try
	{
		network.Connect("10.73.42.117", 9000);
	}
	catch (Network::Exception ex)
	{
		switch (ex)
		{
		case Network::NETWORK_ERROR:
			puts("서버와 연결에 실패했습니다.");
			break;
		case Network::PARAMETER_ERROR:
			puts("함수의 인수가 잘못되었습니다.");
			break;
		}
		return;
	}
	puts("접속 성공!");

	try
	{
		const wchar_t name[MAX_NAME_LEN] = L"지면 F";
		const int studentID = 141055;

		error = network.SubmitName(name, studentID);
		if (error == ET_DUPLICATED_NAME)
		{
			puts("이미 존재하는 이름입니다.");
			return;
		}

		Network::GameStartData gameStartData;
		puts("게임 시작 대기중");
		network.WaitForStart(&gameStartData);
		wprintf_s(L"매칭되었습니다. 상대방 이름: %s, 학번: %d\n", gameStartData.oppositionName, gameStartData.oppositionStudentID);

		bool allOver = false;
		while (!allOver) //10판 종료
		{
			ShipData shipData;
			Network::Initialize();


			char mapData[MAP_SIZE];
			
			while (true)
			{
				ReadyToFight(m_Player1);
				ReadyToFight(m_Player2);
				m_GameRenderer->RenderPages(GAMEPLAY, NET_PLAY);
				for (int i = 0; i < DEFAULT_SHIP_COUNT; ++i)
				{
					Position netPosition;
					if (i != 4)
						netPosition = ConvertPosionForNET((ShipType)i, m_ShipPositions[i]);
					else if (i == 4)
						netPosition = ConvertPosionForNET((ShipType)(i - 1), m_ShipPositions[i]);
					shipData.SetShip((ShipData::ShipType)(i + 1), Coord(netPosition.m_X, netPosition.m_Y), netPosition.m_direction == 0 ? ShipData::DIR_VERTICAL : ShipData::DIR_HORIZONTAL);
				}
				shipData.ToMapData(mapData);
				error = network.SubmitMap(mapData);
				if (error == ET_INVALID_MAP)
					puts("유효하지 않은 맵 데이터입니다.");
				else
					break;
			}

			bool gameOver = false;

			while (!gameOver)
			{
				error = network.GetPacketType(&type);

				switch (type)
				{
				case PKT_SC_ERROR:
					if (error == ET_OPPOSITION_DISCONNECTED)
						puts("상대방의 접속이 끊어졌습니다.");
					else
						puts("알 수 없는 에러입니다.");
					return;

				case PKT_SC_MY_TURN: /* 공격 위치 전송 x, y는 0~7 사이의 정수이다.*/
				{
					Coordinate netShot;
					bool isAttacked;
					while (true)
					{
						do
						{
							netShot = m_Player1->RandomAttack(); //Make AI Attack T-T
							//netShot = m_GameInterface->AttackInterface(FIRST_MAP_GOTOX, FIRST_MAP_GOTOY); //Manual Mode
							isAttacked = m_Player2->CheckAttacked(netShot);
						} while (isAttacked);
						Coord myShot(netShot.m_X, netShot.m_Y);
						error = network.SubmitAttack(myShot);
						if (error == ET_INVALID_ATTACK)
							printf_s("유효하지 않은 공격");
						else
							break;
					}
					break;
				}

				case PKT_SC_ATTACK_RESULT:
				{
					Network::AttackResultData attackResult = network.GetAttackResult();
					Coordinate shot;
					shot.m_X = attackResult.pos.mX;
					shot.m_Y = attackResult.pos.mY;
					HitResult shotResult = (HitResult)attackResult.attackResult;
					if (attackResult.isMine) //내 에너미 맵에 내가 공격한 결과를 반영 마크
					{
						m_GameRenderer->PrintResult(shotResult);
						m_GameRenderer->PrintTurn(++m_Turn, DEFAULT_MAP_SIZE);
						m_Player1->MarkOnEnemyMap(shot, shotResult);
						m_Player2->MarkOnMyMap(shot, shotResult);
						m_Player1->RenderUpdateEnemyMapStatus(FIRST_MAP_GOTOX, FIRST_MAP_GOTOY);
					}
					else //내가 어택당하는 함수
					{
						m_Player1->MarkOnMyMap(shot, shotResult);
						m_Player1->RenderUpdateMyMapStatus((m_MapSize + 3) * 4 + 30, FIRST_MAP_GOTOY);
					}
					break;
				}

				case PKT_SC_GAME_OVER:
				{
					Network::GameResultData gameResult = network.GetGameResult();
					ResetGame();
					if (gameResult.isWinner)
						puts("승리!!!");
					else
						puts("패배...");
					printf_s("턴 수: %d\n", gameResult.turns);
					gameOver = true;
					break;
				}
				default:
					throw Network::UNEXPECTED_PACKET;
					break;
				}
			}
			network.GetPacketType(&type);


			if (type == PKT_SC_NEXT_GAME)
			{
				puts("다음 게임을 준비해주세요.");
			}
			else if (type == PKT_SC_ALL_OVER)
			{
				Network::FinalResultData finalResult = network.GetFinalResult();
				allOver = true;
			}
			else
				throw Network::UNEXPECTED_PACKET;
		}
	}
	catch (Network::Exception ex)
	{
		switch (ex)
		{
		case Network::NETWORK_ERROR:
			puts("네트워크에 문제가 발생했습니다.");
			break;
		case Network::SERVER_CLOSED:
			puts("서버와의 연결이 끊어졌습니다.");
			break;
		case Network::PARAMETER_ERROR:
			puts("함수의 인수가 잘못되었습니다.");
			break;
		case Network::UNEXPECTED_PACKET:
			puts("서버에서 잘못된 정보가 전송되었습니다.");
			break;
		default:
			break;
		}
	}
	network.Disconnect();
	m_GameStatus = WIN;
}
Пример #2
0
// ShipData 구조체를 사용해서 맵 데이터 생성하는 방법
void MakeMapData2(char* const mapData)
{
	ShipData shipData;

	char map[MAP_SIZE] = { 0, };

	int size, sx, sy, dir, listIdx = 0;
	bool placeable;
	Coord posArr[MAX_SHIP_LEN];	// ShipData에 넣을 배의 위치 배열

	for (int type = MD_NONE + 1; type < MD_END; ++type)
	{
		while (true)
		{
			size = ShipData::SHIP_LEN[type];
			placeable = true;
			dir = rand() % 2;
			if (dir == 0) // hori
			{
				sx = rand() % (MAP_WIDTH - size);
				sy = rand() % MAP_HEIGHT;
			}
			else // vert
			{
				sx = rand() % MAP_WIDTH;
				sy = rand() % (MAP_HEIGHT - size);
			}

			for (int i = 0; i < size && placeable; ++i)
			{
				if (dir == 0 && map[sx + i + sy * MAP_WIDTH])
					placeable = false;
				else if (dir == 1 && map[sx + (sy + i) * MAP_WIDTH])
					placeable = false;
			}

			if (placeable)
				break;
		}

		// 1.2 배의 좌표 배열을 가져와서...
		 Coord* shipPosArr = shipData.GetShipCoordArray((ShipType)type);

		for (int i = 0; i < size && placeable; ++i)
		{
			int x, y;
			Coord coord;
			if (dir == 0) { x = sx + i; y = sy; }
			else  { x = sx; y = sy + i; }
			map[x + y * MAP_WIDTH] = type;

			coord = Coord(x, y);
			// 1. 배의 좌표를 하나씩 넣는 방법
			// 1.1. 함수 사용
			shipData.SetShipCoord((ShipType)type, i, coord);
			// 1.2. 배열을 가져와서 넣기
			// shipPosArr[i] = coord;

			// 2. Coord 배열을 만들어서...
			// posArr[i] = coord;
		}

		// 2. 배의 좌표를 배열로 한 번에 넣는 방법
		// shipData.SetShip((ShipType)type, posArr);

		// 3. 배의 시작지점과 방향만 넣는 방법
		// shipData.SetShip((ShipType)type, Coord(sx, sy), dir==0 ? DIR_HORIZONTAL:DIR_VERTICAL);
	}

	// 배의 배치를 맵 데이터로 변환
	shipData.ToMapData(mapData);
}