diff --git a/Source/levels/gendung.cpp b/Source/levels/gendung.cpp index 4946ea30a..036c86643 100644 --- a/Source/levels/gendung.cpp +++ b/Source/levels/gendung.cpp @@ -351,6 +351,13 @@ void InitGlobals() } // namespace +#ifdef BUILD_TESTING +std::optional GetSizeForThemeRoom() +{ + return GetSizeForThemeRoom(0, { 0, 0 }, 5, 10); +} +#endif + dungeon_type GetLevelType(int level) { if (level == 0) diff --git a/Source/levels/gendung.h b/Source/levels/gendung.h index 85cca8e18..e2253c286 100644 --- a/Source/levels/gendung.h +++ b/Source/levels/gendung.h @@ -215,6 +215,10 @@ extern char dSpecial[MAXDUNX][MAXDUNY]; extern int themeCount; extern THEME_LOC themeLoc[MAXTHEMES]; +#ifdef BUILD_TESTING +std::optional GetSizeForThemeRoom(); +#endif + dungeon_type GetLevelType(int level); void CreateDungeon(uint32_t rseed, lvl_entry entry); diff --git a/test/drlg_common_test.cpp b/test/drlg_common_test.cpp index 171dc87a6..e564c22ba 100644 --- a/test/drlg_common_test.cpp +++ b/test/drlg_common_test.cpp @@ -4,6 +4,7 @@ #include #include "engine/points_in_rectangle_range.hpp" +#include "levels/gendung.h" namespace devilution { @@ -70,4 +71,38 @@ TEST(DrlgTest, RectangleRangeIterator) EXPECT_EQ(region[2][2], 9) << "Reverse iterators are required"; } +TEST(DrlgTest, ThemeRoomSize) +{ + memset(dungeon, 0, sizeof(dungeon)); + + EXPECT_EQ(GetSizeForThemeRoom(), Size(8, 8)) << "All floor theme area should be 8x8"; + + dungeon[9][9] = 1; + EXPECT_EQ(GetSizeForThemeRoom(), Size(7, 7)) << "Corners shrink the chosen dimensions"; + dungeon[9][5] = 1; + EXPECT_EQ(GetSizeForThemeRoom(), Size(7, 3)) << "Minimum dimensions are determined by corners outside the min area"; + dungeon[9][4] = 1; + EXPECT_EQ(GetSizeForThemeRoom(), Size(7, 8)) << "Walls below the min size let larger opposing dimensions get picked"; + dungeon[9][5] = 0; + dungeon[9][4] = 0; + dungeon[9][9] = 0; + + // Time for some unusual cases + dungeon[7][2] = 1; + dungeon[5][9] = 1; + EXPECT_EQ(GetSizeForThemeRoom(), Size(5, 7)) << "Search space terminates at width 8 due to the wall being in the first three rows"; + + dungeon[6][4] = 1; + EXPECT_EQ(GetSizeForThemeRoom(), Size(4, 7)) << "Smallest width now defined by row 5, height still extends due to minSize"; + dungeon[6][4] = 0; + + dungeon[5][9] = 0; + dungeon[7][2] = 0; + + dungeon[7][0] = 1; + dungeon[6][6] = 1; + dungeon[8][5] = 1; + EXPECT_EQ(GetSizeForThemeRoom(), Size(4, 4)) << "Search is terminated by the 0 width row 7, inset corner gives a larger height than otherwise expected"; +} + } // namespace devilution