#include "game_match.h" GameMatch::GameMatch() { GenerateBoard(); _txt = g_factory->CreateTextDefault(); _txt->SetFontSize(24); _txt->SetPositionAlign(toPosition(400, 50), Align::CT); _txt->SetString("Score: 0"); } GameMatch::~GameMatch() { } void GameMatch::Init() { } void GameMatch::Update() { if (g_input->KeyDown(MouseCode::LEFT)) { Point mousePos = g_input->GetCursorPosition(); int x = (mousePos.x - 100) / 60; int y = (mousePos.y - 100) / 60; if (x >= 0 && x < BOARD_SIZE && y >= 0 && y < BOARD_SIZE) { if (_selectedPos.x == -1) { _selectedPos = toPosition(static_cast(x), static_cast(y)); } else { if ((abs(static_cast(_selectedPos.x) - x) == 1 && static_cast(_selectedPos.y) == y) || (abs(static_cast(_selectedPos.y) - y) == 1 && static_cast(_selectedPos.x) == x)) { if (CanSwap(static_cast(_selectedPos.x), static_cast(_selectedPos.y), x, y)) { SwapItems(static_cast(_selectedPos.x), static_cast(_selectedPos.y), x, y); CheckMatches(); RemoveMatches(); DropItems(); RefillBoard(); CheckMatches(); RemoveMatches(); } } _selectedPos = toPosition(-1.0f, -1.0f); } } } } void GameMatch::Render() { for (int y = 0; y < BOARD_SIZE; y++) { for (int x = 0; x < BOARD_SIZE; x++) { int type = _board[y][x].type; if (type > 0) { g_gfx->SetCoor(nullptr); g_gfx->SetColor(createColorHSV((type - 1) * 60.0f, 1.0f, 1.0f)); g_gfx->RectangleSolid2D(toPosition(100 + x * 60, 100 + y * 60), toPosition(100 + x * 60 + 50, 100 + y * 60 + 50)); } } } if (_selectedPos.x != -1) { g_gfx->SetCoor(nullptr); g_gfx->SetColor(ColorDef::WHITE); g_gfx->Rectangle2D(toPosition(100 + _selectedPos.x * 60, 100 + _selectedPos.y * 60), toPosition(100 + _selectedPos.x * 60 + 50, 100 + _selectedPos.y * 60 + 50)); } if(_txt) _txt->Render(); } void GameMatch::GenerateBoard() { for (int y = 0; y < BOARD_SIZE; y++) { for (int x = 0; x < BOARD_SIZE; x++) { _board[y][x].type = rand() % 5 + 1; } } } void GameMatch::CheckMatches() { for (int y = 0; y < BOARD_SIZE; y++) { for (int x = 0; x < BOARD_SIZE; x++) { _board[y][x].matched = false; } } for (int y = 0; y < BOARD_SIZE; y++) { int count = 1; int type = _board[y][0].type; for (int x = 1; x < BOARD_SIZE; x++) { if (_board[y][x].type == type) { count++; } else { if (count >= 3) { for (int i = x - count; i < x; i++) { _board[y][i].matched = true; } } count = 1; type = _board[y][x].type; } } if (count >= 3) { for (int i = BOARD_SIZE - count; i < BOARD_SIZE; i++) { _board[y][i].matched = true; } } } for (int x = 0; x < BOARD_SIZE; x++) { int count = 1; int type = _board[0][x].type; for (int y = 1; y < BOARD_SIZE; y++) { if (_board[y][x].type == type) { count++; } else { if (count >= 3) { for (int i = y - count; i < y; i++) { _board[i][x].matched = true; } } count = 1; type = _board[y][x].type; } } if (count >= 3) { for (int i = BOARD_SIZE - count; i < BOARD_SIZE; i++) { _board[i][x].matched = true; } } } } void GameMatch::RemoveMatches() { for (int y = 0; y < BOARD_SIZE; y++) { for (int x = 0; x < BOARD_SIZE; x++) { if (_board[y][x].matched) { _board[y][x].type = 0; _score += 10; } } } _txt->SetString("Score: " + to_string(_score)); } void GameMatch::DropItems() { for (int x = 0; x < BOARD_SIZE; x++) { int emptyCount = 0; for (int y = BOARD_SIZE - 1; y >= 0; y--) { if (_board[y][x].type == 0) { emptyCount++; } else if (emptyCount > 0) { _board[y + emptyCount][x].type = _board[y][x].type; _board[y][x].type = 0; } } } } void GameMatch::RefillBoard() { for (int x = 0; x < BOARD_SIZE; x++) { for (int y = 0; y < BOARD_SIZE; y++) { if (_board[y][x].type == 0) { _board[y][x].type = rand() % 5 + 1; } } } } bool GameMatch::CanSwap(int x1, int y1, int x2, int y2) { SwapItems(x1, y1, x2, y2); CheckMatches(); bool hasMatch = false; for (int y = 0; y < BOARD_SIZE; y++) { for (int x = 0; x < BOARD_SIZE; x++) { if (_board[y][x].matched) { hasMatch = true; break; } } if (hasMatch) { break; } } SwapItems(x1, y1, x2, y2); return hasMatch; } void GameMatch::SwapItems(int x1, int y1, int x2, int y2) { std::swap(_board[y1][x1].type, _board[y2][x2].type); std::swap(_board[y1][x1].matched, _board[y2][x2].matched); }