summaryrefslogtreecommitdiffstats
path: root/src/Generating/GridStructGen.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/Generating/GridStructGen.cpp')
-rw-r--r--src/Generating/GridStructGen.cpp138
1 files changed, 138 insertions, 0 deletions
diff --git a/src/Generating/GridStructGen.cpp b/src/Generating/GridStructGen.cpp
new file mode 100644
index 000000000..975fd3fdc
--- /dev/null
+++ b/src/Generating/GridStructGen.cpp
@@ -0,0 +1,138 @@
+
+// GridStructGen.cpp
+
+// Implements the cGridStructGen class representing a common base class for structure generators that place structures in a semi-random grid
+
+#include "Globals.h"
+#include "GridStructGen.h"
+
+
+
+
+cGridStructGen::cGridStructGen(
+ int a_Seed,
+ int a_GridSizeX, int a_GridSizeZ,
+ int a_MaxStructureSizeX, int a_MaxStructureSizeZ,
+ size_t a_MaxCacheSize
+) :
+ m_Seed(a_Seed),
+ m_GridSizeX(a_GridSizeX),
+ m_GridSizeZ(a_GridSizeZ),
+ m_MaxStructureSizeX(a_MaxStructureSizeX),
+ m_MaxStructureSizeZ(a_MaxStructureSizeZ),
+ m_MaxCacheSize(a_MaxCacheSize)
+{
+}
+
+
+
+
+
+void cGridStructGen::GetStructuresForChunk(int a_ChunkX, int a_ChunkZ, cStructurePtrs & a_Structures)
+{
+ // Calculate the min and max grid coords of the structures to be returned:
+ int MinBlockX = a_ChunkX * cChunkDef::Width - m_MaxStructureSizeX;
+ int MinBlockZ = a_ChunkZ * cChunkDef::Width - m_MaxStructureSizeZ;
+ int MaxBlockX = a_ChunkX * cChunkDef::Width + m_MaxStructureSizeX + cChunkDef::Width - 1;
+ int MaxBlockZ = a_ChunkZ * cChunkDef::Width + m_MaxStructureSizeZ + cChunkDef::Width - 1;
+ int MinGridX = MinBlockX / m_GridSizeX;
+ int MinGridZ = MinBlockZ / m_GridSizeZ;
+ int MaxGridX = MaxBlockX / m_GridSizeX;
+ int MaxGridZ = MaxBlockX / m_GridSizeZ;
+ if (MinGridX < 0)
+ {
+ --MinGridX;
+ }
+ if (MinGridZ < 0)
+ {
+ --MinGridZ;
+ }
+ if (MaxGridX < 0)
+ {
+ --MaxGridX;
+ }
+ if (MaxGridZ < 0)
+ {
+ --MaxGridZ;
+ }
+
+ // Walk the cache, move each structure that we want into a_Structures:
+ for (cStructurePtrs::iterator itr = m_Cache.begin(), end = m_Cache.end(); itr != end;)
+ {
+ if (
+ ((*itr)->m_OriginX >= MinBlockX) && ((*itr)->m_OriginX < MaxBlockX) &&
+ ((*itr)->m_OriginZ >= MinBlockZ) && ((*itr)->m_OriginZ < MaxBlockZ)
+ )
+ {
+ // want
+ a_Structures.push_back(*itr);
+ itr = m_Cache.erase(itr);
+ }
+ else
+ {
+ // don't want
+ ++itr;
+ }
+ } // for itr - m_Cache[]
+
+ // Create those structures that haven't been in the cache:
+ for (int x = MinGridX; x < MaxGridX; x++)
+ {
+ int OriginX = x * m_GridSizeX;
+ for (int z = MinGridZ; z < MaxGridZ; z++)
+ {
+ int OriginZ = z * m_GridSizeZ;
+ bool Found = false;
+ for (cStructurePtrs::const_iterator itr = a_Structures.begin(), end = a_Structures.end(); itr != end; ++itr)
+ {
+ if (((*itr)->m_OriginX == OriginX) && ((*itr)->m_OriginZ == OriginZ))
+ {
+ Found = true;
+ break;
+ }
+ } // for itr - a_Structures[]
+ if (!Found)
+ {
+ a_Structures.push_back(CreateStructure(OriginX, OriginZ));
+ }
+ } // for z
+ } // for x
+
+ // Copy a_Forts into m_Cache to the beginning:
+ cStructurePtrs StructuresCopy (a_Structures);
+ m_Cache.splice(m_Cache.begin(), StructuresCopy, StructuresCopy.begin(), StructuresCopy.end());
+
+ // Trim the cache if it's too long:
+ size_t CacheSize = 0;
+ for (cStructurePtrs::iterator itr = m_Cache.begin(), end = m_Cache.end(); itr != end; ++itr)
+ {
+ CacheSize += (*itr)->GetCacheCost();
+ if (CacheSize > m_MaxCacheSize)
+ {
+ // Erase all items from this one till the cache end
+ m_Cache.erase(itr, m_Cache.end());
+ break;
+ }
+ }
+}
+
+
+
+
+
+void cGridStructGen::GenFinish(cChunkDesc & a_ChunkDesc)
+{
+ int ChunkX = a_ChunkDesc.GetChunkX();
+ int ChunkZ = a_ChunkDesc.GetChunkZ();
+ cStructurePtrs Structures;
+ GetStructuresForChunk(ChunkX, ChunkZ, Structures);
+ for (cStructurePtrs::const_iterator itr = Structures.begin(); itr != Structures.end(); ++itr)
+ {
+ (*itr)->DrawIntoChunk(a_ChunkDesc);
+ } // for itr - Structures[]
+}
+
+
+
+
+