diff options
| author | fschildt <florian.schildt@protonmail.com> | 2025-10-18 11:33:30 +0200 | 
|---|---|---|
| committer | fschildt <florian.schildt@protonmail.com> | 2025-10-18 11:38:45 +0200 | 
| commit | 935f1971bee684c6c9baded2564a550351cc5582 (patch) | |
| tree | e4650d9b39b108be52638f6b45681b42dfc72b15 /src/games/minesweeper | |
| parent | 7935895480b74fb9fe02e5f26a82265a72604d77 (diff) | |
Diffstat (limited to 'src/games/minesweeper')
| -rw-r--r-- | src/games/minesweeper/Minesweeper.cpp | 126 | ||||
| -rw-r--r-- | src/games/minesweeper/Minesweeper.hpp | 21 | 
2 files changed, 91 insertions, 56 deletions
diff --git a/src/games/minesweeper/Minesweeper.cpp b/src/games/minesweeper/Minesweeper.cpp index a091491..5a37a04 100644 --- a/src/games/minesweeper/Minesweeper.cpp +++ b/src/games/minesweeper/Minesweeper.cpp @@ -12,7 +12,6 @@  // - Show current time spent  // - Show current flags/mines left  // - Permit uncovering of flagged cell -// - Game Over: Winning Condition (maybe: total_cells - uncovered_cells == mine_count)  // - Game Over: Show Highscore for selected difficulty @@ -31,62 +30,60 @@ static constexpr Color s_mine_count_colors[8] = {  Minesweeper::Minesweeper()      : m_font{s_dejavu_sans_filepath, 22}  { +    float cell_size = 1.2f * std::min(m_world_height / s_max_grid_height, m_world_width / s_max_grid_width); +    float cell_size_without_border = 0.8f * cell_size; + +    m_cell_outer_size = {cell_size, cell_size}; +    m_cell_inner_size = {cell_size_without_border, cell_size_without_border};  }  void  Minesweeper::Reset(Difficulty difficulty)  { -    int32_t mine_count; +    m_cells_uncovered = 0;      if (difficulty == beginner) {          m_grid_width = 8;          m_grid_height = 8; -        mine_count = 10; +        m_mine_count = 10;      }      else if(difficulty == intermediate) {          m_grid_width = 16;          m_grid_height = 16; -        mine_count = 40; +        m_mine_count = 40;      }      else {          m_grid_width = 30;          m_grid_height = 16; -        mine_count = 99; +        m_mine_count = 99;      } +    assert(m_grid_width <= s_max_grid_width); +    assert(m_grid_height <= s_max_grid_height); -    float cell_size = 1.2f * std::min(m_world_height / max_map_height, m_world_width / max_map_width); -    float cell_size_without_border = 0.8f * cell_size; - -    V2F32 grid_size = { -        (float)m_grid_width * cell_size, -        (float)m_grid_height * cell_size -    }; +    float grid_draw_width = (float)m_grid_width * m_cell_outer_size.x; +    float grid_draw_height = (float)m_grid_height * m_cell_outer_size.y;      m_grid_pos = { -        (m_world_width - grid_size.x) / 2, -        (m_world_height - grid_size.y) / 2, +        (m_world_width - grid_draw_width) / 2, +        (m_world_height - grid_draw_height) / 2,      }; -    m_cell_outer_size = {cell_size, cell_size}; -    m_cell_inner_size = {cell_size_without_border, cell_size_without_border}; -      memset(m_is_covered_bitmap, 0xff, sizeof(m_is_covered_bitmap));      memset(m_is_flagged_bitmap, 0 , sizeof(m_is_flagged_bitmap)); -    InitIsMineBitmap(mine_count); +    InitIsMineBitmap();      InitAdjacentMineCounters();  }  void -Minesweeper::InitIsMineBitmap(int32_t mine_count) +Minesweeper::InitIsMineBitmap()  { -    assert(mine_count < m_grid_width * m_grid_height); - +    assert(m_mine_count < m_grid_width * m_grid_height);      memset(m_is_mine_bitmap, 0 , sizeof(m_is_mine_bitmap));      std::mt19937 rng((std::random_device()()));      std::uniform_int_distribution<int32_t> dist(0, m_grid_width * m_grid_height - 1); - +    int32_t mine_count = m_mine_count;      while (mine_count) {          int32_t random_pos = dist(rng);          int32_t y = random_pos / m_grid_width; @@ -127,6 +124,13 @@ Minesweeper::InitAdjacentMineCounters()  }  bool +Minesweeper::IsWon() +{ +    bool is_won = m_grid_width*m_grid_height - m_cells_uncovered == m_mine_count; +    return is_won; +} + +bool  Minesweeper::Update(std::vector<SDL_Event>& events)  {      g_renderer.SetCameraSize(4.0f, 3.0f); @@ -159,7 +163,7 @@ Minesweeper::Update(std::vector<SDL_Event>& events)      }      else if (m_game_status == game_over) {          DrawBoard(); -        DrawDefaultGameOverMenu(); +        DrawGameOverMenu();      }      return true; @@ -211,7 +215,9 @@ Minesweeper::ProcessEventDuringResume(SDL_Event &event)              break;          } -        if (event.button.button == 1) { +        uint8_t left_click = 1; +        uint8_t right_click = 3; +        if (event.button.button == left_click) {              if (IsCovered(x, y)) {                  if (IsMine(x, y)) {                      m_is_covered_bitmap[y] &= ~(1 << x); @@ -220,10 +226,13 @@ Minesweeper::ProcessEventDuringResume(SDL_Event &event)                  }                  else {                      Uncover(x, y); +                    if (IsWon()) { +                        m_game_status = game_over; +                    }                  }              }          } -        else if (event.button.button == 3) { +        else if (event.button.button == right_click) {              if (IsCovered(x, y)) {                  ToggleFlag(x ,y);              } @@ -245,6 +254,8 @@ Minesweeper::Uncover(int32_t x, int32_t y)      if (!IsCovered(x, y))   return;      m_is_covered_bitmap[y] &= ~(1 << x); +    m_cells_uncovered += 1; +      if (IsFlagged(x, y)) {          ToggleFlag(x, y);      } @@ -318,29 +329,6 @@ Minesweeper::ScreenPosToViewPos(V2F32 screen_pos)  }  void -Minesweeper::DrawStartMenu() -{ -    ImGui::Begin("MinesweeperStart"); -    if (ImGui::RadioButton("beginner", m_difficulty == beginner ? true : false)) { -        m_difficulty = beginner; -    } -    if (ImGui::RadioButton("intermediate", m_difficulty == intermediate ? true : false)) { -        m_difficulty = intermediate; -    } -    if (ImGui::RadioButton("expert", m_difficulty == expert ? true : false)) { -        m_difficulty = expert; -    } -    if (ImGui::Button("Start")) { -        Reset(m_difficulty); -        m_game_status = game_resuming; -    } -    if (ImGui::Button("Exit")) { -        m_game_status = game_exit; -    } -    ImGui::End(); -} - -void  Minesweeper::DrawBoard()  {      Color covered_cell_color {0.6f, 0.6f, 0.6f}; @@ -424,3 +412,45 @@ Minesweeper::DrawBoard()      }  } +void +Minesweeper::DrawStartMenu() +{ +    ImGui::Begin("MinesweeperStart"); +    if (ImGui::RadioButton("beginner", m_difficulty == beginner ? true : false)) { +        m_difficulty = beginner; +    } +    if (ImGui::RadioButton("intermediate", m_difficulty == intermediate ? true : false)) { +        m_difficulty = intermediate; +    } +    if (ImGui::RadioButton("expert", m_difficulty == expert ? true : false)) { +        m_difficulty = expert; +    } +    if (ImGui::Button("Start")) { +        Reset(m_difficulty); +        m_game_status = game_resuming; +    } +    if (ImGui::Button("Exit")) { +        m_game_status = game_exit; +    } +    ImGui::End(); +} + +void +Minesweeper::DrawGameOverMenu() +{ +    ImGui::Begin("MinesweeperGameOverMenu", nullptr, s_imgui_window_flags_menu); +    if (IsWon()) { +        ImGui::Text("You won!"); +    } +    else { +        ImGui::Text("You Lost."); +    } +    if (ImGui::Button("Play Again")) { +        m_game_status = game_starting; +    } +    if (ImGui::Button("Exit")) { +        m_game_status = game_exit; +    } +    ImGui::End(); +} + diff --git a/src/games/minesweeper/Minesweeper.hpp b/src/games/minesweeper/Minesweeper.hpp index fbdcb30..1db77ff 100644 --- a/src/games/minesweeper/Minesweeper.hpp +++ b/src/games/minesweeper/Minesweeper.hpp @@ -25,8 +25,9 @@ private:      void ProcessEventDuringResume(SDL_Event& event);      void Reset(Difficulty Difficulty); -    void InitIsMineBitmap(int32_t mine_count); +    void InitIsMineBitmap();      void InitAdjacentMineCounters(); +    bool IsWon();      void UncoverMines();      void Uncover(int32_t x, int32_t y); @@ -43,28 +44,32 @@ private:  private:      void DrawBoard();      void DrawStartMenu(); +    void DrawGameOverMenu();  private: -    static constexpr int32_t max_map_height = 32; -    static constexpr int32_t max_map_width = 32; +    static constexpr int32_t s_max_grid_height = 32; +    static constexpr int32_t s_max_grid_width = 32;  private:      Difficulty m_difficulty = beginner; +    int32_t m_cells_uncovered; +    int32_t m_mine_count;      float m_world_width = 4.0f;      float m_world_height = 3.0f;      int32_t m_grid_width; -    int32_t m_grid_height; V2F32 m_grid_pos; +    int32_t m_grid_height; +    V2F32 m_grid_pos;      V2F32 m_cell_outer_size;      V2F32 m_cell_inner_size; -    uint32_t m_is_covered_bitmap[max_map_height] {}; -    uint32_t m_is_flagged_bitmap[max_map_height] {}; -    uint32_t m_is_mine_bitmap[max_map_height] {}; -    int32_t m_adjacent_mine_counts[max_map_width * max_map_height] {}; +    uint32_t m_is_covered_bitmap[s_max_grid_height] {}; +    uint32_t m_is_flagged_bitmap[s_max_grid_height] {}; +    uint32_t m_is_mine_bitmap[s_max_grid_height] {}; +    int32_t m_adjacent_mine_counts[s_max_grid_width * s_max_grid_height] {};      Font m_font;  };  | 
