summaryrefslogtreecommitdiffstats
path: root/source/Generating
diff options
context:
space:
mode:
authorTiger Wang <ziwei.tiger@hotmail.co.uk>2013-11-27 22:35:13 +0100
committerTiger Wang <ziwei.tiger@hotmail.co.uk>2013-11-27 22:35:13 +0100
commita6630d32394120a78af56bc612fa3c3449283248 (patch)
tree2c791266b0f213cd56961299da8d2258b8f85d8e /source/Generating
parentFixed spawn point being generally in an ocean (diff)
parentVoronoi-related biomegens use the new cVoronoiMap class. (diff)
downloadcuberite-a6630d32394120a78af56bc612fa3c3449283248.tar
cuberite-a6630d32394120a78af56bc612fa3c3449283248.tar.gz
cuberite-a6630d32394120a78af56bc612fa3c3449283248.tar.bz2
cuberite-a6630d32394120a78af56bc612fa3c3449283248.tar.lz
cuberite-a6630d32394120a78af56bc612fa3c3449283248.tar.xz
cuberite-a6630d32394120a78af56bc612fa3c3449283248.tar.zst
cuberite-a6630d32394120a78af56bc612fa3c3449283248.zip
Diffstat (limited to '')
-rw-r--r--source/Generating/BioGen.cpp707
-rw-r--r--source/Generating/BioGen.h230
-rw-r--r--source/Generating/ChunkGenerator.cpp329
-rw-r--r--source/Generating/CompoGen.cpp634
-rw-r--r--source/Generating/ComposableGenerator.cpp501
-rw-r--r--source/Generating/DistortedHeightmap.cpp444
-rw-r--r--source/Generating/EndGen.cpp217
-rw-r--r--source/Generating/HeiGen.cpp390
-rw-r--r--source/Generating/Noise3DGenerator.cpp576
-rw-r--r--src/Generating/Caves.cpp (renamed from source/Generating/Caves.cpp)0
-rw-r--r--src/Generating/Caves.h (renamed from source/Generating/Caves.h)0
-rw-r--r--src/Generating/ChunkDesc.cpp (renamed from source/Generating/ChunkDesc.cpp)0
-rw-r--r--src/Generating/ChunkDesc.h (renamed from source/Generating/ChunkDesc.h)0
-rw-r--r--src/Generating/ChunkGenerator.h (renamed from source/Generating/ChunkGenerator.h)0
-rw-r--r--src/Generating/CompoGen.h (renamed from source/Generating/CompoGen.h)0
-rw-r--r--src/Generating/ComposableGenerator.h (renamed from source/Generating/ComposableGenerator.h)0
-rw-r--r--src/Generating/DistortedHeightmap.h (renamed from source/Generating/DistortedHeightmap.h)0
-rw-r--r--src/Generating/EndGen.h (renamed from source/Generating/EndGen.h)0
-rw-r--r--src/Generating/FinishGen.cpp (renamed from source/Generating/FinishGen.cpp)0
-rw-r--r--src/Generating/FinishGen.h (renamed from source/Generating/FinishGen.h)0
-rw-r--r--src/Generating/HeiGen.h (renamed from source/Generating/HeiGen.h)0
-rw-r--r--src/Generating/MineShafts.cpp (renamed from source/Generating/MineShafts.cpp)0
-rw-r--r--src/Generating/MineShafts.h (renamed from source/Generating/MineShafts.h)0
-rw-r--r--src/Generating/Noise3DGenerator.h (renamed from source/Generating/Noise3DGenerator.h)0
-rw-r--r--src/Generating/Ravines.cpp (renamed from source/Generating/Ravines.cpp)0
-rw-r--r--src/Generating/Ravines.h (renamed from source/Generating/Ravines.h)0
-rw-r--r--src/Generating/StructGen.cpp (renamed from source/Generating/StructGen.cpp)0
-rw-r--r--src/Generating/StructGen.h (renamed from source/Generating/StructGen.h)0
-rw-r--r--src/Generating/Trees.cpp (renamed from source/Generating/Trees.cpp)0
-rw-r--r--src/Generating/Trees.h (renamed from source/Generating/Trees.h)0
30 files changed, 0 insertions, 4028 deletions
diff --git a/source/Generating/BioGen.cpp b/source/Generating/BioGen.cpp
deleted file mode 100644
index 926120afc..000000000
--- a/source/Generating/BioGen.cpp
+++ /dev/null
@@ -1,707 +0,0 @@
-
-// BioGen.cpp
-
-// Implements the various biome generators
-
-#include "Globals.h"
-#include "BioGen.h"
-#include "../../iniFile/iniFile.h"
-#include "../LinearUpscale.h"
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBioGenConstant:
-
-void cBioGenConstant::GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- for (int i = 0; i < ARRAYCOUNT(a_BiomeMap); i++)
- {
- a_BiomeMap[i] = m_Biome;
- }
-}
-
-
-
-
-
-void cBioGenConstant::InitializeBiomeGen(cIniFile & a_IniFile)
-{
- AString Biome = a_IniFile.GetValueSet("Generator", "ConstantBiome", "Plains");
- m_Biome = StringToBiome(Biome);
- if (m_Biome == -1)
- {
- LOGWARN("[Generator]::ConstantBiome value \"%s\" not recognized, using \"Plains\".", Biome.c_str());
- m_Biome = biPlains;
- }
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBioGenCache:
-
-cBioGenCache::cBioGenCache(cBiomeGen * a_BioGenToCache, int a_CacheSize) :
- m_BioGenToCache(a_BioGenToCache),
- m_CacheSize(a_CacheSize),
- m_CacheOrder(new int[a_CacheSize]),
- m_CacheData(new sCacheData[a_CacheSize]),
- m_NumHits(0),
- m_NumMisses(0),
- m_TotalChain(0)
-{
- for (int i = 0; i < m_CacheSize; i++)
- {
- m_CacheOrder[i] = i;
- m_CacheData[i].m_ChunkX = 0x7fffffff;
- m_CacheData[i].m_ChunkZ = 0x7fffffff;
- }
-}
-
-
-
-
-
-cBioGenCache::~cBioGenCache()
-{
- delete[] m_CacheData;
- delete[] m_CacheOrder;
-}
-
-
-
-
-
-void cBioGenCache::GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- if (((m_NumHits + m_NumMisses) % 1024) == 10)
- {
- LOGD("BioGenCache: %d hits, %d misses, saved %.2f %%", m_NumHits, m_NumMisses, 100.0 * m_NumHits / (m_NumHits + m_NumMisses));
- LOGD("BioGenCache: Avg cache chain length: %.2f", (float)m_TotalChain / m_NumHits);
- }
-
- for (int i = 0; i < m_CacheSize; i++)
- {
- if (
- (m_CacheData[m_CacheOrder[i]].m_ChunkX != a_ChunkX) ||
- (m_CacheData[m_CacheOrder[i]].m_ChunkZ != a_ChunkZ)
- )
- {
- continue;
- }
- // Found it in the cache
- int Idx = m_CacheOrder[i];
-
- // Move to front:
- for (int j = i; j > 0; j--)
- {
- m_CacheOrder[j] = m_CacheOrder[j - 1];
- }
- m_CacheOrder[0] = Idx;
-
- // Use the cached data:
- memcpy(a_BiomeMap, m_CacheData[Idx].m_BiomeMap, sizeof(a_BiomeMap));
-
- m_NumHits++;
- m_TotalChain += i;
- return;
- } // for i - cache
-
- // Not in the cache:
- m_NumMisses++;
- m_BioGenToCache->GenBiomes(a_ChunkX, a_ChunkZ, a_BiomeMap);
-
- // Insert it as the first item in the MRU order:
- int Idx = m_CacheOrder[m_CacheSize - 1];
- for (int i = m_CacheSize - 1; i > 0; i--)
- {
- m_CacheOrder[i] = m_CacheOrder[i - 1];
- } // for i - m_CacheOrder[]
- m_CacheOrder[0] = Idx;
- memcpy(m_CacheData[Idx].m_BiomeMap, a_BiomeMap, sizeof(a_BiomeMap));
- m_CacheData[Idx].m_ChunkX = a_ChunkX;
- m_CacheData[Idx].m_ChunkZ = a_ChunkZ;
-}
-
-
-
-
-
-void cBioGenCache::InitializeBiomeGen(cIniFile & a_IniFile)
-{
- super::InitializeBiomeGen(a_IniFile);
- m_BioGenToCache->InitializeBiomeGen(a_IniFile);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBiomeGenList:
-
-void cBiomeGenList::InitializeBiomes(const AString & a_Biomes)
-{
- AStringVector Split = StringSplit(a_Biomes, ",");
-
- // Convert each string in the list into biome:
- for (AStringVector::const_iterator itr = Split.begin(); itr != Split.end(); ++itr)
- {
- AStringVector Split2 = StringSplit(*itr, ":");
- if (Split2.size() < 1)
- {
- continue;
- }
- int Count = 1;
- if (Split2.size() >= 2)
- {
- Count = atol(Split2[1].c_str());
- if (Count <= 0)
- {
- LOGWARNING("Cannot decode biome count: \"%s\"; using 1.", Split2[1].c_str());
- Count = 1;
- }
- }
- EMCSBiome Biome = StringToBiome(Split2[0]);
- if (Biome != -1)
- {
- for (int i = 0; i < Count; i++)
- {
- m_Biomes.push_back(Biome);
- }
- }
- else
- {
- LOGWARNING("Cannot decode biome name: \"%s\"; skipping", Split2[0].c_str());
- }
- } // for itr - Split[]
- if (!m_Biomes.empty())
- {
- m_BiomesCount = (int)m_Biomes.size();
- return;
- }
-
- // There were no biomes, add default biomes:
- static EMCSBiome Biomes[] =
- {
- biOcean,
- biPlains,
- biDesert,
- biExtremeHills,
- biForest,
- biTaiga,
- biSwampland,
- biRiver,
- biFrozenOcean,
- biFrozenRiver,
- biIcePlains,
- biIceMountains,
- biMushroomIsland,
- biMushroomShore,
- biBeach,
- biDesertHills,
- biForestHills,
- biTaigaHills,
- biExtremeHillsEdge,
- biJungle,
- biJungleHills,
- } ;
- m_Biomes.reserve(ARRAYCOUNT(Biomes));
- for (int i = 0; i < ARRAYCOUNT(Biomes); i++)
- {
- m_Biomes.push_back(Biomes[i]);
- }
- m_BiomesCount = (int)m_Biomes.size();
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBioGenCheckerboard:
-
-void cBioGenCheckerboard::GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- int Base = cChunkDef::Width * a_ChunkZ + z;
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int Add = cChunkDef::Width * a_ChunkX + x;
- a_BiomeMap[x + cChunkDef::Width * z] = m_Biomes[(Base / m_BiomeSize + Add / m_BiomeSize) % m_BiomesCount];
- }
- }
-}
-
-
-
-
-
-void cBioGenCheckerboard::InitializeBiomeGen(cIniFile & a_IniFile)
-{
- super::InitializeBiomeGen(a_IniFile);
- AString Biomes = a_IniFile.GetValueSet ("Generator", "CheckerBoardBiomes", "");
- m_BiomeSize = a_IniFile.GetValueSetI("Generator", "CheckerboardBiomeSize", 64);
- m_BiomeSize = (m_BiomeSize < 8) ? 8 : m_BiomeSize;
- InitializeBiomes(Biomes);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBioGenVoronoi :
-
-void cBioGenVoronoi::GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- int BaseZ = cChunkDef::Width * a_ChunkZ;
- int BaseX = cChunkDef::Width * a_ChunkX;
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- int AbsoluteZ = BaseZ + z;
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- cChunkDef::SetBiome(a_BiomeMap, x, z, VoronoiBiome(BaseX + x, AbsoluteZ));
- } // for x
- } // for z
-}
-
-
-
-
-
-void cBioGenVoronoi::InitializeBiomeGen(cIniFile & a_IniFile)
-{
- super::InitializeBiomeGen(a_IniFile);
- m_CellSize = a_IniFile.GetValueSetI("Generator", "VoronoiCellSize", 64);
- AString Biomes = a_IniFile.GetValueSet ("Generator", "VoronoiBiomes", "");
- InitializeBiomes(Biomes);
-}
-
-
-
-
-
-EMCSBiome cBioGenVoronoi::VoronoiBiome(int a_BlockX, int a_BlockZ)
-{
- int CellX = a_BlockX / m_CellSize;
- int CellZ = a_BlockZ / m_CellSize;
-
- // Note that Noise values need to be divided by 8 to gain a uniform modulo-2^n distribution
-
- // Get 5x5 neighboring cell seeds, compare distance to each. Return the biome in the minumim-distance cell
- int MinDist = m_CellSize * m_CellSize * 16; // There has to be a cell closer than this
- EMCSBiome res = biPlains; // Will be overriden
- for (int x = CellX - 2; x <= CellX + 2; x++)
- {
- int BaseX = x * m_CellSize;
- for (int z = CellZ - 2; z < CellZ + 2; z++)
- {
- int OffsetX = (m_Noise.IntNoise3DInt(x, 16 * x + 32 * z, z) / 8) % m_CellSize;
- int OffsetZ = (m_Noise.IntNoise3DInt(x, 32 * x - 16 * z, z) / 8) % m_CellSize;
- int SeedX = BaseX + OffsetX;
- int SeedZ = z * m_CellSize + OffsetZ;
-
- int Dist = (SeedX - a_BlockX) * (SeedX - a_BlockX) + (SeedZ - a_BlockZ) * (SeedZ - a_BlockZ);
- if (Dist < MinDist)
- {
- MinDist = Dist;
- res = m_Biomes[(m_Noise.IntNoise3DInt(x, x - z + 1000, z) / 8) % m_BiomesCount];
- }
- } // for z
- } // for x
-
- return res;
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBioGenDistortedVoronoi:
-
-void cBioGenDistortedVoronoi::GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- int BaseZ = cChunkDef::Width * a_ChunkZ;
- int BaseX = cChunkDef::Width * a_ChunkX;
-
- // Distortions for linear interpolation:
- int DistortX[cChunkDef::Width + 1][cChunkDef::Width + 1];
- int DistortZ[cChunkDef::Width + 1][cChunkDef::Width + 1];
- for (int x = 0; x <= 4; x++) for (int z = 0; z <= 4; z++)
- {
- Distort(BaseX + x * 4, BaseZ + z * 4, DistortX[4 * x][4 * z], DistortZ[4 * x][4 * z]);
- }
-
- LinearUpscale2DArrayInPlace(&DistortX[0][0], cChunkDef::Width + 1, cChunkDef::Width + 1, 4, 4);
- LinearUpscale2DArrayInPlace(&DistortZ[0][0], cChunkDef::Width + 1, cChunkDef::Width + 1, 4, 4);
-
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- int AbsoluteZ = BaseZ + z;
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- // Distort(BaseX + x, AbsoluteZ, DistX, DistZ);
- cChunkDef::SetBiome(a_BiomeMap, x, z, VoronoiBiome(DistortX[x][z], DistortZ[x][z]));
- } // for x
- } // for z
-}
-
-
-
-
-
-void cBioGenDistortedVoronoi::InitializeBiomeGen(cIniFile & a_IniFile)
-{
- // Do NOT call super::InitializeBiomeGen(), as it would try to read Voronoi params instead of DistortedVoronoi params
- m_CellSize = a_IniFile.GetValueSetI("Generator", "DistortedVoronoiCellSize", 96);
- AString Biomes = a_IniFile.GetValueSet ("Generator", "DistortedVoronoiBiomes", "");
- InitializeBiomes(Biomes);
-}
-
-
-
-
-void cBioGenDistortedVoronoi::Distort(int a_BlockX, int a_BlockZ, int & a_DistortedX, int & a_DistortedZ)
-{
- double NoiseX = m_Noise.CubicNoise3D((float)a_BlockX / m_CellSize, (float)a_BlockZ / m_CellSize, 1000);
- NoiseX += 0.5 * m_Noise.CubicNoise3D(2 * (float)a_BlockX / m_CellSize, 2 * (float)a_BlockZ / m_CellSize, 2000);
- NoiseX += 0.08 * m_Noise.CubicNoise3D(16 * (float)a_BlockX / m_CellSize, 16 * (float)a_BlockZ / m_CellSize, 3000);
- double NoiseZ = m_Noise.CubicNoise3D((float)a_BlockX / m_CellSize, (float)a_BlockZ / m_CellSize, 4000);
- NoiseZ += 0.5 * m_Noise.CubicNoise3D(2 * (float)a_BlockX / m_CellSize, 2 * (float)a_BlockZ / m_CellSize, 5000);
- NoiseZ += 0.08 * m_Noise.CubicNoise3D(16 * (float)a_BlockX / m_CellSize, 16 * (float)a_BlockZ / m_CellSize, 6000);
-
- a_DistortedX = a_BlockX + (int)(m_CellSize * 0.5 * NoiseX);
- a_DistortedZ = a_BlockZ + (int)(m_CellSize * 0.5 * NoiseZ);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cBioGenMultiStepMap :
-
-cBioGenMultiStepMap::cBioGenMultiStepMap(int a_Seed) :
- m_Noise1(a_Seed + 1000),
- m_Noise2(a_Seed + 2000),
- m_Noise3(a_Seed + 3000),
- m_Noise4(a_Seed + 4000),
- m_Noise5(a_Seed + 5000),
- m_Noise6(a_Seed + 6000),
- m_Seed(a_Seed),
- m_OceanCellSize(384),
- m_MushroomIslandSize(64),
- m_RiverCellSize(384),
- m_RiverWidthThreshold(0.125),
- m_LandBiomesSize(1024)
-{
-}
-
-
-
-
-
-void cBioGenMultiStepMap::InitializeBiomeGen(cIniFile & a_IniFile)
-{
- m_OceanCellSize = a_IniFile.GetValueSetI("Generator", "MultiStepMapOceanCellSize", m_OceanCellSize);
- m_MushroomIslandSize = a_IniFile.GetValueSetI("Generator", "MultiStepMapMushroomIslandSize", m_MushroomIslandSize);
- m_RiverCellSize = a_IniFile.GetValueSetI("Generator", "MultiStepMapRiverCellSize", m_RiverCellSize);
- m_RiverWidthThreshold = a_IniFile.GetValueSetF("Generator", "MultiStepMapRiverWidth", m_RiverWidthThreshold);
- m_LandBiomesSize = (float)a_IniFile.GetValueSetI("Generator", "MultiStepMapLandBiomeSize", (int)m_LandBiomesSize);
-}
-
-
-
-
-
-void cBioGenMultiStepMap::GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- DecideOceanLandMushroom(a_ChunkX, a_ChunkZ, a_BiomeMap);
- AddRivers(a_ChunkX, a_ChunkZ, a_BiomeMap);
- ApplyTemperatureHumidity(a_ChunkX, a_ChunkZ, a_BiomeMap);
-}
-
-
-
-
-
-void cBioGenMultiStepMap::DecideOceanLandMushroom(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- // Distorted Voronoi over 3 biomes, with mushroom having only a special occurence.
-
- // Prepare a distortion lookup table, by distorting a 5x5 area and using that as 1:4 zoom (linear interpolate):
- int BaseZ = cChunkDef::Width * a_ChunkZ;
- int BaseX = cChunkDef::Width * a_ChunkX;
- int DistortX[cChunkDef::Width + 1][cChunkDef::Width + 1];
- int DistortZ[cChunkDef::Width + 1][cChunkDef::Width + 1];
- int DistortSize = m_OceanCellSize / 2;
- for (int x = 0; x <= 4; x++) for (int z = 0; z <= 4; z++)
- {
- Distort(BaseX + x * 4, BaseZ + z * 4, DistortX[4 * x][4 * z], DistortZ[4 * x][4 * z], DistortSize);
- }
- LinearUpscale2DArrayInPlace(&DistortX[0][0], cChunkDef::Width + 1, cChunkDef::Width + 1, 4, 4);
- LinearUpscale2DArrayInPlace(&DistortZ[0][0], cChunkDef::Width + 1, cChunkDef::Width + 1, 4, 4);
-
- // Prepare a 9x9 area of neighboring cell seeds
- // (assuming that 7x7 cell area is larger than a chunk being generated)
- const int NEIGHBORHOOD_SIZE = 4; // How many seeds in each direction to check
- int CellX = BaseX / m_OceanCellSize;
- int CellZ = BaseZ / m_OceanCellSize;
- int SeedX[2 * NEIGHBORHOOD_SIZE + 1][2 * NEIGHBORHOOD_SIZE + 1];
- int SeedZ[2 * NEIGHBORHOOD_SIZE + 1][2 * NEIGHBORHOOD_SIZE + 1];
- EMCSBiome SeedV[2 * NEIGHBORHOOD_SIZE + 1][2 * NEIGHBORHOOD_SIZE + 1];
- for (int xc = 0; xc < 2 * NEIGHBORHOOD_SIZE + 1; xc++)
- {
- int RealCellX = xc + CellX - NEIGHBORHOOD_SIZE;
- int CellBlockX = RealCellX * m_OceanCellSize;
- for (int zc = 0; zc < 2 * NEIGHBORHOOD_SIZE + 1; zc++)
- {
- int RealCellZ = zc + CellZ - NEIGHBORHOOD_SIZE;
- int CellBlockZ = RealCellZ * m_OceanCellSize;
- int OffsetX = (m_Noise2.IntNoise3DInt(RealCellX, 16 * RealCellX + 32 * RealCellZ, RealCellZ) / 8) % m_OceanCellSize;
- int OffsetZ = (m_Noise4.IntNoise3DInt(RealCellX, 32 * RealCellX - 16 * RealCellZ, RealCellZ) / 8) % m_OceanCellSize;
- SeedX[xc][zc] = CellBlockX + OffsetX;
- SeedZ[xc][zc] = CellBlockZ + OffsetZ;
- SeedV[xc][zc] = (((m_Noise6.IntNoise3DInt(RealCellX, RealCellX - RealCellZ + 1000, RealCellZ) / 11) % 256) > 90) ? biOcean : ((EMCSBiome)(-1));
- } // for z
- } // for x
-
- for (int xc = 1; xc < 2 * NEIGHBORHOOD_SIZE; xc++) for (int zc = 1; zc < 2 * NEIGHBORHOOD_SIZE; zc++)
- {
- if (
- (SeedV[xc ][zc] == biOcean) &&
- (SeedV[xc - 1][zc] == biOcean) &&
- (SeedV[xc + 1][zc] == biOcean) &&
- (SeedV[xc ][zc - 1] == biOcean) &&
- (SeedV[xc ][zc + 1] == biOcean) &&
- (SeedV[xc - 1][zc - 1] == biOcean) &&
- (SeedV[xc + 1][zc - 1] == biOcean) &&
- (SeedV[xc - 1][zc + 1] == biOcean) &&
- (SeedV[xc + 1][zc + 1] == biOcean)
- )
- {
- SeedV[xc][zc] = biMushroomIsland;
- }
- }
-
- // For each column find the nearest distorted cell and use its value as the biome:
- int MushroomOceanThreshold = m_OceanCellSize * m_OceanCellSize * m_MushroomIslandSize / 1024;
- int MushroomShoreThreshold = m_OceanCellSize * m_OceanCellSize * m_MushroomIslandSize / 2048;
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int AbsoluteZ = DistortZ[x][z];
- int AbsoluteX = DistortX[x][z];
- int MinDist = m_OceanCellSize * m_OceanCellSize * 16; // There has to be a cell closer than this
- EMCSBiome Biome = biPlains;
- // Find the nearest cell seed:
- for (int xs = 1; xs < 2 * NEIGHBORHOOD_SIZE; xs++) for (int zs = 1; zs < 2 * NEIGHBORHOOD_SIZE; zs++)
- {
- int Dist = (SeedX[xs][zs] - AbsoluteX) * (SeedX[xs][zs] - AbsoluteX) + (SeedZ[xs][zs] - AbsoluteZ) * (SeedZ[xs][zs] - AbsoluteZ);
- if (Dist >= MinDist)
- {
- continue;
- }
- MinDist = Dist;
- Biome = SeedV[xs][zs];
- // Shrink mushroom biome and add a shore:
- if (Biome == biMushroomIsland)
- {
- if (Dist > MushroomOceanThreshold)
- {
- Biome = biOcean;
- }
- else if (Dist > MushroomShoreThreshold)
- {
- Biome = biMushroomShore;
- }
- }
- } // for zs, xs
-
- cChunkDef::SetBiome(a_BiomeMap, x, z, Biome);
- } // for x
- } // for z
-}
-
-
-
-
-
-void cBioGenMultiStepMap::AddRivers(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- float NoiseCoordZ = (float)(a_ChunkZ * cChunkDef::Width + z) / m_RiverCellSize;
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- if (cChunkDef::GetBiome(a_BiomeMap, x, z) != -1)
- {
- // Biome already set, skip this column
- continue;
- }
-
- float NoiseCoordX = (float)(a_ChunkX * cChunkDef::Width + x) / m_RiverCellSize;
-
- double Noise = m_Noise1.CubicNoise2D( NoiseCoordX, NoiseCoordZ);
- Noise += 0.5 * m_Noise3.CubicNoise2D(2 * NoiseCoordX, 2 * NoiseCoordZ);
- Noise += 0.1 * m_Noise5.CubicNoise2D(8 * NoiseCoordX, 8 * NoiseCoordZ);
-
- if ((Noise > 0) && (Noise < m_RiverWidthThreshold))
- {
- cChunkDef::SetBiome(a_BiomeMap, x, z, biRiver);
- }
- } // for x
- } // for z
-}
-
-
-
-
-
-void cBioGenMultiStepMap::ApplyTemperatureHumidity(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- IntMap TemperatureMap;
- IntMap HumidityMap;
- BuildTemperatureHumidityMaps(a_ChunkX, a_ChunkZ, TemperatureMap, HumidityMap);
-
- FreezeWaterBiomes(a_BiomeMap, TemperatureMap);
- DecideLandBiomes(a_BiomeMap, TemperatureMap, HumidityMap);
-}
-
-
-
-
-
-void cBioGenMultiStepMap::Distort(int a_BlockX, int a_BlockZ, int & a_DistortedX, int & a_DistortedZ, int a_CellSize)
-{
- double NoiseX = m_Noise3.CubicNoise2D( (float)a_BlockX / a_CellSize, (float)a_BlockZ / a_CellSize);
- NoiseX += 0.5 * m_Noise2.CubicNoise2D(2 * (float)a_BlockX / a_CellSize, 2 * (float)a_BlockZ / a_CellSize);
- NoiseX += 0.1 * m_Noise1.CubicNoise2D(16 * (float)a_BlockX / a_CellSize, 16 * (float)a_BlockZ / a_CellSize);
- double NoiseZ = m_Noise6.CubicNoise2D( (float)a_BlockX / a_CellSize, (float)a_BlockZ / a_CellSize);
- NoiseZ += 0.5 * m_Noise5.CubicNoise2D(2 * (float)a_BlockX / a_CellSize, 2 * (float)a_BlockZ / a_CellSize);
- NoiseZ += 0.1 * m_Noise4.CubicNoise2D(16 * (float)a_BlockX / a_CellSize, 16 * (float)a_BlockZ / a_CellSize);
-
- a_DistortedX = a_BlockX + (int)(a_CellSize * 0.5 * NoiseX);
- a_DistortedZ = a_BlockZ + (int)(a_CellSize * 0.5 * NoiseZ);
-}
-
-
-
-
-
-void cBioGenMultiStepMap::BuildTemperatureHumidityMaps(int a_ChunkX, int a_ChunkZ, IntMap & a_TemperatureMap, IntMap & a_HumidityMap)
-{
- // Linear interpolation over 8x8 blocks; use double for better precision:
- DblMap TemperatureMap;
- DblMap HumidityMap;
- for (int z = 0; z < 17; z += 8)
- {
- float NoiseCoordZ = (float)(a_ChunkZ * cChunkDef::Width + z) / m_LandBiomesSize;
- for (int x = 0; x < 17; x += 8)
- {
- float NoiseCoordX = (float)(a_ChunkX * cChunkDef::Width + x) / m_LandBiomesSize;
-
- double NoiseT = m_Noise1.CubicNoise2D( NoiseCoordX, NoiseCoordZ);
- NoiseT += 0.5 * m_Noise2.CubicNoise2D(2 * NoiseCoordX, 2 * NoiseCoordZ);
- NoiseT += 0.1 * m_Noise3.CubicNoise2D(8 * NoiseCoordX, 8 * NoiseCoordZ);
- TemperatureMap[x + 17 * z] = NoiseT;
-
- double NoiseH = m_Noise4.CubicNoise2D( NoiseCoordX, NoiseCoordZ);
- NoiseH += 0.5 * m_Noise5.CubicNoise2D(2 * NoiseCoordX, 2 * NoiseCoordZ);
- NoiseH += 0.1 * m_Noise6.CubicNoise2D(8 * NoiseCoordX, 8 * NoiseCoordZ);
- HumidityMap[x + 17 * z] = NoiseH;
- } // for x
- } // for z
- LinearUpscale2DArrayInPlace(TemperatureMap, 17, 17, 8, 8);
- LinearUpscale2DArrayInPlace(HumidityMap, 17, 17, 8, 8);
-
- // Re-map into integral values in [0 .. 255] range:
- for (int idx = 0; idx < ARRAYCOUNT(a_TemperatureMap); idx++)
- {
- a_TemperatureMap[idx] = std::max(0, std::min(255, (int)(128 + TemperatureMap[idx] * 128)));
- a_HumidityMap[idx] = std::max(0, std::min(255, (int)(128 + HumidityMap[idx] * 128)));
- }
-}
-
-
-
-
-
-void cBioGenMultiStepMap::DecideLandBiomes(cChunkDef::BiomeMap & a_BiomeMap, const IntMap & a_TemperatureMap, const IntMap & a_HumidityMap)
-{
- static const EMCSBiome BiomeMap[] =
- {
- // 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
- /* 0 */ biTundra, biTundra, biTundra, biTundra, biPlains, biPlains, biPlains, biPlains, biPlains, biPlains, biDesert, biDesert, biDesert, biDesert, biDesert, biDesert,
- /* 1 */ biTundra, biTundra, biTundra, biTundra, biPlains, biPlains, biPlains, biPlains, biPlains, biPlains, biDesert, biDesert, biDesert, biDesert, biDesert, biDesert,
- /* 2 */ biTundra, biTundra, biTundra, biTundra, biPlains, biExtremeHills, biPlains, biPlains, biPlains, biPlains, biDesert, biDesert, biDesertHills, biDesertHills, biDesert, biDesert,
- /* 3 */ biTundra, biTundra, biTundra, biTundra, biExtremeHills, biExtremeHills, biPlains, biPlains, biPlains, biPlains, biDesert, biDesert, biDesertHills, biDesertHills, biDesert, biDesert,
- /* 4 */ biTundra, biTundra, biIceMountains, biIceMountains, biExtremeHills, biExtremeHills, biPlains, biPlains, biPlains, biPlains, biForestHills, biForestHills, biExtremeHills, biExtremeHills, biDesertHills, biDesert,
- /* 5 */ biTundra, biTundra, biIceMountains, biIceMountains, biExtremeHills, biExtremeHills, biPlains, biPlains, biPlains, biPlains, biForestHills, biForestHills, biExtremeHills, biExtremeHills, biDesertHills, biDesert,
- /* 6 */ biTundra, biTundra, biIceMountains, biIceMountains, biForestHills, biForestHills, biForest, biForest, biForest, biForest, biForest, biForestHills, biExtremeHills, biExtremeHills, biPlains, biPlains,
- /* 7 */ biTundra, biTundra, biIceMountains, biIceMountains, biForestHills, biForestHills, biForest, biForest, biForest, biForest, biForest, biForestHills, biExtremeHills, biExtremeHills, biPlains, biPlains,
- /* 8 */ biTundra, biTundra, biTaiga, biTaiga, biForest, biForest, biForest, biForest, biForest, biForest, biForest, biForestHills, biExtremeHills, biExtremeHills, biPlains, biPlains,
- /* 9 */ biTundra, biTundra, biTaiga, biTaiga, biForest, biForest, biForest, biForest, biForest, biForest, biForest, biForestHills, biExtremeHills, biExtremeHills, biPlains, biPlains,
- /* 10 */ biTaiga, biTaiga, biTaiga, biIceMountains, biForestHills, biForestHills, biForest, biForest, biForest, biForest, biJungle, biJungle, biSwampland, biSwampland, biSwampland, biSwampland,
- /* 11 */ biTaiga, biTaiga, biIceMountains, biIceMountains, biExtremeHills, biForestHills, biForest, biForest, biForest, biForest, biJungle, biJungle, biSwampland, biSwampland, biSwampland, biSwampland,
- /* 12 */ biTaiga, biTaiga, biIceMountains, biIceMountains, biExtremeHills, biJungleHills, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biSwampland, biSwampland, biSwampland, biSwampland,
- /* 13 */ biTaiga, biTaiga, biTaiga, biIceMountains, biJungleHills, biJungleHills, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biSwampland, biSwampland, biSwampland, biSwampland,
- /* 14 */ biTaiga, biTaiga, biTaiga, biTaiga, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biSwampland, biSwampland, biSwampland, biSwampland,
- /* 15 */ biTaiga, biTaiga, biTaiga, biTaiga, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biJungle, biSwampland, biSwampland, biSwampland, biSwampland,
- } ;
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- int idxZ = 17 * z;
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- if (cChunkDef::GetBiome(a_BiomeMap, x, z) != -1)
- {
- // Already set before
- continue;
- }
- int idx = idxZ + x;
- int Temperature = a_TemperatureMap[idx] / 16; // -> [0..15] range
- int Humidity = a_HumidityMap[idx] / 16; // -> [0..15] range
- cChunkDef::SetBiome(a_BiomeMap, x, z, BiomeMap[Temperature + 16 * Humidity]);
- } // for x
- } // for z
-}
-
-
-
-
-
-void cBioGenMultiStepMap::FreezeWaterBiomes(cChunkDef::BiomeMap & a_BiomeMap, const IntMap & a_TemperatureMap)
-{
- int idx = 0;
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++, idx++)
- {
- if (a_TemperatureMap[idx] > 4 * 16)
- {
- // Not frozen
- continue;
- }
- switch (cChunkDef::GetBiome(a_BiomeMap, x, z))
- {
- case biRiver: cChunkDef::SetBiome(a_BiomeMap, x, z, biFrozenRiver); break;
- case biOcean: cChunkDef::SetBiome(a_BiomeMap, x, z, biFrozenOcean); break;
- }
- } // for x
- idx += 1;
- } // for z
-}
-
-
-
-
diff --git a/source/Generating/BioGen.h b/source/Generating/BioGen.h
deleted file mode 100644
index bc70bfab2..000000000
--- a/source/Generating/BioGen.h
+++ /dev/null
@@ -1,230 +0,0 @@
-
-// BioGen.h
-
-/*
-Interfaces to the various biome generators:
- - cBioGenConstant
- - cBioGenCheckerboard
- - cBioGenDistortedVoronoi
-*/
-
-
-
-
-
-#pragma once
-
-#include "ComposableGenerator.h"
-#include "../Noise.h"
-
-
-
-
-
-class cBioGenConstant :
- public cBiomeGen
-{
-public:
- cBioGenConstant(void) : m_Biome(biPlains) {}
-
-protected:
-
- EMCSBiome m_Biome;
-
- // cBiomeGen overrides:
- virtual void GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap) override;
- virtual void InitializeBiomeGen(cIniFile & a_IniFile) override;
-} ;
-
-
-
-
-
-/// A simple cache that stores N most recently generated chunks' biomes; N being settable upon creation
-class cBioGenCache :
- public cBiomeGen
-{
- typedef cBiomeGen super;
-
-public:
- cBioGenCache(cBiomeGen * a_BioGenToCache, int a_CacheSize); // Doesn't take ownership of a_BioGenToCache
- ~cBioGenCache();
-
-protected:
-
- cBiomeGen * m_BioGenToCache;
-
- struct sCacheData
- {
- int m_ChunkX;
- int m_ChunkZ;
- cChunkDef::BiomeMap m_BiomeMap;
- } ;
-
- // To avoid moving large amounts of data for the MRU behavior, we MRU-ize indices to an array of the actual data
- int m_CacheSize;
- int * m_CacheOrder; // MRU-ized order, indices into m_CacheData array
- sCacheData * m_CacheData; // m_CacheData[m_CacheOrder[0]] is the most recently used
-
- // Cache statistics
- int m_NumHits;
- int m_NumMisses;
- int m_TotalChain; // Number of cache items walked to get to a hit (only added for hits)
-
- virtual void GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap) override;
- virtual void InitializeBiomeGen(cIniFile & a_IniFile) override;
-} ;
-
-
-
-
-
-/// Base class for generators that use a list of available biomes. This class takes care of the list.
-class cBiomeGenList :
- public cBiomeGen
-{
- typedef cBiomeGen super;
-
-protected:
- // List of biomes that the generator is allowed to generate:
- typedef std::vector<EMCSBiome> EMCSBiomes;
- EMCSBiomes m_Biomes;
- int m_BiomesCount; // Pulled out of m_Biomes for faster access
-
- /// Parses the INI file setting string into m_Biomes.
- void InitializeBiomes(const AString & a_Biomes);
-} ;
-
-
-
-
-
-class cBioGenCheckerboard :
- public cBiomeGenList
-{
- typedef cBiomeGenList super;
-
-protected:
- int m_BiomeSize;
-
- // cBiomeGen overrides:
- virtual void GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap) override;
- virtual void InitializeBiomeGen(cIniFile & a_IniFile) override;
-} ;
-
-
-
-
-
-class cBioGenVoronoi :
- public cBiomeGenList
-{
- typedef cBiomeGenList super;
-
-public:
- cBioGenVoronoi(int a_Seed) :
- m_Noise(a_Seed)
- {
- }
-
-protected:
- int m_CellSize;
-
- cNoise m_Noise;
-
- // cBiomeGen overrides:
- virtual void GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap) override;
- virtual void InitializeBiomeGen(cIniFile & a_IniFile) override;
-
- EMCSBiome VoronoiBiome(int a_BlockX, int a_BlockZ);
-} ;
-
-
-
-
-
-class cBioGenDistortedVoronoi :
- public cBioGenVoronoi
-{
- typedef cBioGenVoronoi super;
-public:
- cBioGenDistortedVoronoi(int a_Seed) :
- cBioGenVoronoi(a_Seed)
- {
- }
-
-protected:
- // cBiomeGen overrides:
- virtual void GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap) override;
- virtual void InitializeBiomeGen(cIniFile & a_IniFile) override;
-
- /// Distorts the coords using a Perlin-like noise
- void Distort(int a_BlockX, int a_BlockZ, int & a_DistortedX, int & a_DistortedZ);
-} ;
-
-
-
-
-
-class cBioGenMultiStepMap :
- public cBiomeGen
-{
- typedef cBiomeGen super;
-
-public:
- cBioGenMultiStepMap(int a_Seed);
-
-protected:
- // Noises used for composing the perlin-noise:
- cNoise m_Noise1;
- cNoise m_Noise2;
- cNoise m_Noise3;
- cNoise m_Noise4;
- cNoise m_Noise5;
- cNoise m_Noise6;
-
- int m_Seed;
- int m_OceanCellSize;
- int m_MushroomIslandSize;
- int m_RiverCellSize;
- double m_RiverWidthThreshold;
- float m_LandBiomesSize;
-
- typedef int IntMap[17 * 17]; // x + 17 * z, expected trimmed into [0..255] range
- typedef double DblMap[17 * 17]; // x + 17 * z, expected trimmed into [0..1] range
-
- // cBiomeGen overrides:
- virtual void GenBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap) override;
- virtual void InitializeBiomeGen(cIniFile & a_IniFile) override;
-
- /** Step 1: Decides between ocean, land and mushroom, using a DistVoronoi with special conditions and post-processing for mushroom islands
- Sets biomes to biOcean, -1 (i.e. land), biMushroomIsland or biMushroomShore
- */
- void DecideOceanLandMushroom(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap);
-
- /** Step 2: Add rivers to the land
- Flips some "-1" biomes into biRiver
- */
- void AddRivers(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap);
-
- /** Step 3: Decide land biomes using a temperature / humidity map; freeze ocean / river in low temperatures.
- Flips all remaining "-1" biomes into land biomes. Also flips some biOcean and biRiver into biFrozenOcean, biFrozenRiver, based on temp map.
- */
- void ApplyTemperatureHumidity(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap);
-
- /// Distorts the coords using a Perlin-like noise, with a specified cell-size
- void Distort(int a_BlockX, int a_BlockZ, int & a_DistortedX, int & a_DistortedZ, int a_CellSize);
-
- /// Builds two Perlin-noise maps, one for temperature, the other for humidity. Trims both into [0..255] range
- void BuildTemperatureHumidityMaps(int a_ChunkX, int a_ChunkZ, IntMap & a_TemperatureMap, IntMap & a_HumidityMap);
-
- /// Flips all remaining "-1" biomes into land biomes using the two maps
- void DecideLandBiomes(cChunkDef::BiomeMap & a_BiomeMap, const IntMap & a_TemperatureMap, const IntMap & a_HumidityMap);
-
- /// Flips biOcean and biRiver into biFrozenOcean and biFrozenRiver if the temperature is too low
- void FreezeWaterBiomes(cChunkDef::BiomeMap & a_BiomeMap, const IntMap & a_TemperatureMap);
-} ;
-
-
-
-
diff --git a/source/Generating/ChunkGenerator.cpp b/source/Generating/ChunkGenerator.cpp
deleted file mode 100644
index 33c956eba..000000000
--- a/source/Generating/ChunkGenerator.cpp
+++ /dev/null
@@ -1,329 +0,0 @@
-
-#include "Globals.h"
-
-#include "ChunkGenerator.h"
-#include "../World.h"
-#include "../../iniFile/iniFile.h"
-#include "../Root.h"
-#include "../PluginManager.h"
-#include "ChunkDesc.h"
-#include "ComposableGenerator.h"
-#include "Noise3DGenerator.h"
-
-
-
-
-
-/// If the generation queue size exceeds this number, a warning will be output
-const unsigned int QUEUE_WARNING_LIMIT = 1000;
-
-/// If the generation queue size exceeds this number, chunks with no clients will be skipped
-const unsigned int QUEUE_SKIP_LIMIT = 500;
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cChunkGenerator:
-
-cChunkGenerator::cChunkGenerator(void) :
- super("cChunkGenerator"),
- m_World(NULL),
- m_Generator(NULL)
-{
-}
-
-
-
-
-
-cChunkGenerator::~cChunkGenerator()
-{
- Stop();
-}
-
-
-
-
-
-bool cChunkGenerator::Start(cWorld * a_World, cIniFile & a_IniFile)
-{
- MTRand rnd;
- m_World = a_World;
- m_Seed = a_IniFile.GetValueSetI("Seed", "Seed", rnd.randInt());
- AString GeneratorName = a_IniFile.GetValueSet("Generator", "Generator", "Composable");
-
- if (NoCaseCompare(GeneratorName, "Noise3D") == 0)
- {
- m_Generator = new cNoise3DGenerator(*this);
- }
- else
- {
- if (NoCaseCompare(GeneratorName, "composable") != 0)
- {
- LOGWARN("[Generator]::Generator value \"%s\" not recognized, using \"Composable\".", GeneratorName.c_str());
- }
- m_Generator = new cComposableGenerator(*this);
- }
-
- if (m_Generator == NULL)
- {
- LOGERROR("Generator could not start, aborting the server");
- return false;
- }
-
- m_Generator->Initialize(a_World, a_IniFile);
-
- return super::Start();
-}
-
-
-
-
-
-void cChunkGenerator::Stop(void)
-{
- m_ShouldTerminate = true;
- m_Event.Set();
- m_evtRemoved.Set(); // Wake up anybody waiting for empty queue
- Wait();
-
- delete m_Generator;
- m_Generator = NULL;
-}
-
-
-
-
-
-void cChunkGenerator::QueueGenerateChunk(int a_ChunkX, int a_ChunkY, int a_ChunkZ)
-{
- {
- cCSLock Lock(m_CS);
-
- // Check if it is already in the queue:
- for (cChunkCoordsList::iterator itr = m_Queue.begin(); itr != m_Queue.end(); ++itr)
- {
- if ((itr->m_ChunkX == a_ChunkX) && (itr->m_ChunkY == a_ChunkY) && (itr->m_ChunkZ == a_ChunkZ))
- {
- // Already in the queue, bail out
- return;
- }
- } // for itr - m_Queue[]
-
- // Add to queue, issue a warning if too many:
- if (m_Queue.size() >= QUEUE_WARNING_LIMIT)
- {
- LOGWARN("WARNING: Adding chunk [%i, %i] to generation queue; Queue is too big! (%i)", a_ChunkX, a_ChunkZ, m_Queue.size());
- }
- m_Queue.push_back(cChunkCoords(a_ChunkX, a_ChunkY, a_ChunkZ));
- }
-
- m_Event.Set();
-}
-
-
-
-
-
-void cChunkGenerator::GenerateBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- if (m_Generator != NULL)
- {
- m_Generator->GenerateBiomes(a_ChunkX, a_ChunkZ, a_BiomeMap);
- }
-}
-
-
-
-
-
-void cChunkGenerator::WaitForQueueEmpty(void)
-{
- cCSLock Lock(m_CS);
- while (!m_ShouldTerminate && !m_Queue.empty())
- {
- cCSUnlock Unlock(Lock);
- m_evtRemoved.Wait();
- }
-}
-
-
-
-
-
-int cChunkGenerator::GetQueueLength(void)
-{
- cCSLock Lock(m_CS);
- return (int)m_Queue.size();
-}
-
-
-
-
-
-EMCSBiome cChunkGenerator::GetBiomeAt(int a_BlockX, int a_BlockZ)
-{
- ASSERT(m_Generator != NULL);
- return m_Generator->GetBiomeAt(a_BlockX, a_BlockZ);
-}
-
-
-
-
-
-BLOCKTYPE cChunkGenerator::GetIniBlock(cIniFile & a_IniFile, const AString & a_SectionName, const AString & a_ValueName, const AString & a_Default)
-{
- AString BlockType = a_IniFile.GetValueSet(a_SectionName, a_ValueName, a_Default);
- BLOCKTYPE Block = BlockStringToType(BlockType);
- if (Block < 0)
- {
- LOGWARN("[&s].%s Could not parse block value \"%s\". Using default: \"%s\".", a_SectionName.c_str(), a_ValueName.c_str(), BlockType.c_str(),a_Default.c_str());
- return BlockStringToType(a_Default);
- }
- return Block;
-}
-
-
-
-
-
-void cChunkGenerator::Execute(void)
-{
- // To be able to display performance information, the generator counts the chunks generated.
- // When the queue gets empty, the count is reset, so that waiting for the queue is not counted into the total time.
- int NumChunksGenerated = 0; // Number of chunks generated since the queue was last empty
- clock_t GenerationStart = clock(); // Clock tick when the queue started to fill
- clock_t LastReportTick = clock(); // Clock tick of the last report made (so that performance isn't reported too often)
-
- while (!m_ShouldTerminate)
- {
- cCSLock Lock(m_CS);
- while (m_Queue.size() == 0)
- {
- if ((NumChunksGenerated > 16) && (clock() - LastReportTick > CLOCKS_PER_SEC))
- {
- LOG("Chunk generator performance: %.2f ch/s (%d ch total)",
- (double)NumChunksGenerated * CLOCKS_PER_SEC/ (clock() - GenerationStart),
- NumChunksGenerated
- );
- }
- cCSUnlock Unlock(Lock);
- m_Event.Wait();
- if (m_ShouldTerminate)
- {
- return;
- }
- NumChunksGenerated = 0;
- GenerationStart = clock();
- LastReportTick = clock();
- }
-
- cChunkCoords coords = m_Queue.front(); // Get next coord from queue
- m_Queue.erase( m_Queue.begin() ); // Remove coordinate from queue
- bool SkipEnabled = (m_Queue.size() > QUEUE_SKIP_LIMIT);
- Lock.Unlock(); // Unlock ASAP
- m_evtRemoved.Set();
-
- // Display perf info once in a while:
- if ((NumChunksGenerated > 16) && (clock() - LastReportTick > 2 * CLOCKS_PER_SEC))
- {
- LOG("Chunk generator performance: %.2f ch/s (%d ch total)",
- (double)NumChunksGenerated * CLOCKS_PER_SEC / (clock() - GenerationStart),
- NumChunksGenerated
- );
- LastReportTick = clock();
- }
-
- // Hack for regenerating chunks: if Y != 0, the chunk is considered invalid, even if it has its data set
- if ((coords.m_ChunkY == 0) && m_World->IsChunkValid(coords.m_ChunkX, coords.m_ChunkZ))
- {
- LOGD("Chunk [%d, %d] already generated, skipping generation", coords.m_ChunkX, coords.m_ChunkZ);
- // Already generated, ignore request
- continue;
- }
-
- if (SkipEnabled && !m_World->HasChunkAnyClients(coords.m_ChunkX, coords.m_ChunkZ))
- {
- LOGWARNING("Chunk generator overloaded, skipping chunk [%d, %d]", coords.m_ChunkX, coords.m_ChunkZ);
- continue;
- }
-
- LOGD("Generating chunk [%d, %d, %d]", coords.m_ChunkX, coords.m_ChunkY, coords.m_ChunkZ);
- DoGenerate(coords.m_ChunkX, coords.m_ChunkY, coords.m_ChunkZ);
-
- // Save the chunk right after generating, so that we don't have to generate it again on next run
- m_World->GetStorage().QueueSaveChunk(coords.m_ChunkX, coords.m_ChunkY, coords.m_ChunkZ);
-
- NumChunksGenerated++;
- } // while (!bStop)
-}
-
-
-
-
-void cChunkGenerator::DoGenerate(int a_ChunkX, int a_ChunkY, int a_ChunkZ)
-{
- cChunkDesc ChunkDesc(a_ChunkX, a_ChunkZ);
- cRoot::Get()->GetPluginManager()->CallHookChunkGenerating(m_World, a_ChunkX, a_ChunkZ, &ChunkDesc);
- m_Generator->DoGenerate(a_ChunkX, a_ChunkZ, ChunkDesc);
- cRoot::Get()->GetPluginManager()->CallHookChunkGenerated(m_World, a_ChunkX, a_ChunkZ, &ChunkDesc);
-
- #ifdef _DEBUG
- // Verify that the generator has produced valid data:
- ChunkDesc.VerifyHeightmap();
- #endif
-
- cChunkDef::BlockNibbles BlockMetas;
- ChunkDesc.CompressBlockMetas(BlockMetas);
-
- m_World->SetChunkData(
- a_ChunkX, a_ChunkZ,
- ChunkDesc.GetBlockTypes(), BlockMetas,
- NULL, NULL, // We don't have lighting, chunk will be lighted when needed
- &ChunkDesc.GetHeightMap(), &ChunkDesc.GetBiomeMap(),
- ChunkDesc.GetEntities(), ChunkDesc.GetBlockEntities(),
- true
- );
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cChunkGenerator::cGenerator:
-
-cChunkGenerator::cGenerator::cGenerator(cChunkGenerator & a_ChunkGenerator) :
- m_ChunkGenerator(a_ChunkGenerator)
-{
-}
-
-
-
-
-
-void cChunkGenerator::cGenerator::Initialize(cWorld * a_World, cIniFile & a_IniFile)
-{
- m_World = a_World;
- UNUSED(a_IniFile);
-}
-
-
-
-
-
-EMCSBiome cChunkGenerator::cGenerator::GetBiomeAt(int a_BlockX, int a_BlockZ)
-{
- cChunkDef::BiomeMap Biomes;
- int Y = 0;
- int ChunkX, ChunkZ;
- cWorld::AbsoluteToRelative(a_BlockX, Y, a_BlockZ, ChunkX, Y, ChunkZ);
- GenerateBiomes(ChunkX, ChunkZ, Biomes);
- return cChunkDef::GetBiome(Biomes, a_BlockX, a_BlockZ);
-}
-
-
-
-
diff --git a/source/Generating/CompoGen.cpp b/source/Generating/CompoGen.cpp
deleted file mode 100644
index cc2a203af..000000000
--- a/source/Generating/CompoGen.cpp
+++ /dev/null
@@ -1,634 +0,0 @@
-
-// CompoGen.cpp
-
-/* Implements the various terrain composition generators:
- - cCompoGenSameBlock
- - cCompoGenDebugBiomes
- - cCompoGenClassic
-*/
-
-#include "Globals.h"
-#include "CompoGen.h"
-#include "../BlockID.h"
-#include "../Item.h"
-#include "../LinearUpscale.h"
-#include "../../iniFile/iniFile.h"
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cCompoGenSameBlock:
-
-void cCompoGenSameBlock::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int Start;
- if (m_IsBedrocked)
- {
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- Start = 1;
- }
- else
- {
- Start = 0;
- }
- for (int y = a_ChunkDesc.GetHeight(x, z); y >= Start; y--)
- {
- a_ChunkDesc.SetBlockType(x, y, z, m_BlockType);
- } // for y
- } // for z
- } // for x
-}
-
-
-
-
-
-void cCompoGenSameBlock::InitializeCompoGen(cIniFile & a_IniFile)
-{
- m_BlockType = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "SameBlockType", "stone").m_ItemType);
- m_IsBedrocked = (a_IniFile.GetValueSetI("Generator", "SameBlockBedrocked", 1) != 0);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cCompoGenDebugBiomes:
-
-void cCompoGenDebugBiomes::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- static BLOCKTYPE Blocks[] =
- {
- E_BLOCK_STONE,
- E_BLOCK_COBBLESTONE,
- E_BLOCK_LOG,
- E_BLOCK_PLANKS,
- E_BLOCK_SANDSTONE,
- E_BLOCK_WOOL,
- E_BLOCK_COAL_ORE,
- E_BLOCK_IRON_ORE,
- E_BLOCK_GOLD_ORE,
- E_BLOCK_DIAMOND_ORE,
- E_BLOCK_LAPIS_ORE,
- E_BLOCK_REDSTONE_ORE,
- E_BLOCK_IRON_BLOCK,
- E_BLOCK_GOLD_BLOCK,
- E_BLOCK_DIAMOND_BLOCK,
- E_BLOCK_LAPIS_BLOCK,
- E_BLOCK_BRICK,
- E_BLOCK_MOSSY_COBBLESTONE,
- E_BLOCK_OBSIDIAN,
- E_BLOCK_NETHERRACK,
- E_BLOCK_SOULSAND,
- E_BLOCK_NETHER_BRICK,
- E_BLOCK_BEDROCK,
- } ;
-
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
-
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- BLOCKTYPE BlockType = Blocks[a_ChunkDesc.GetBiome(x, z)];
- for (int y = a_ChunkDesc.GetHeight(x, z); y >= 0; y--)
- {
- a_ChunkDesc.SetBlockType(x, y, z, BlockType);
- } // for y
- } // for z
- } // for x
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cCompoGenClassic:
-
-cCompoGenClassic::cCompoGenClassic(void) :
- m_SeaLevel(60),
- m_BeachHeight(2),
- m_BeachDepth(4),
- m_BlockTop(E_BLOCK_GRASS),
- m_BlockMiddle(E_BLOCK_DIRT),
- m_BlockBottom(E_BLOCK_STONE),
- m_BlockBeach(E_BLOCK_SAND),
- m_BlockBeachBottom(E_BLOCK_SANDSTONE),
- m_BlockSea(E_BLOCK_STATIONARY_WATER)
-{
-}
-
-
-
-
-
-void cCompoGenClassic::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- /* The classic composition means:
- - 1 layer of grass, 3 of dirt and the rest stone, if the height > sealevel + beachheight
- - 3 sand and a 1 sandstone, rest stone if between sealevel and sealevel + beachheight
- - water from waterlevel to height, then 3 sand, 1 sandstone, the rest stone, if water depth < beachdepth
- - water from waterlevel, then 3 dirt, the rest stone otherwise
- - bedrock at the bottom
- */
-
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
-
- // The patterns to use for different situations, must be same length!
- const BLOCKTYPE PatternGround[] = {m_BlockTop, m_BlockMiddle, m_BlockMiddle, m_BlockMiddle} ;
- const BLOCKTYPE PatternBeach[] = {m_BlockBeach, m_BlockBeach, m_BlockBeach, m_BlockBeachBottom} ;
- const BLOCKTYPE PatternOcean[] = {m_BlockMiddle, m_BlockMiddle, m_BlockMiddle, m_BlockBottom} ;
- static int PatternLength = ARRAYCOUNT(PatternGround);
- ASSERT(ARRAYCOUNT(PatternGround) == ARRAYCOUNT(PatternBeach));
- ASSERT(ARRAYCOUNT(PatternGround) == ARRAYCOUNT(PatternOcean));
-
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int Height = a_ChunkDesc.GetHeight(x, z);
- const BLOCKTYPE * Pattern;
- if (Height > m_SeaLevel + m_BeachHeight)
- {
- Pattern = PatternGround;
- }
- else if (Height > m_SeaLevel - m_BeachDepth)
- {
- Pattern = PatternBeach;
- }
- else
- {
- Pattern = PatternOcean;
- }
-
- // Fill water from sealevel down to height (if any):
- for (int y = m_SeaLevel; y >= Height; --y)
- {
- a_ChunkDesc.SetBlockType(x, y, z, m_BlockSea);
- }
-
- // Fill from height till the bottom:
- for (int y = Height; y >= 1; y--)
- {
- a_ChunkDesc.SetBlockType(x, y, z, (Height - y < PatternLength) ? Pattern[Height - y] : m_BlockBottom);
- }
-
- // The last layer is always bedrock:
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- } // for x
- } // for z
-}
-
-
-
-
-
-void cCompoGenClassic::InitializeCompoGen(cIniFile & a_IniFile)
-{
- m_SeaLevel = a_IniFile.GetValueSetI("Generator", "ClassicSeaLevel", m_SeaLevel);
- m_BeachHeight = a_IniFile.GetValueSetI("Generator", "ClassicBeachHeight", m_BeachHeight);
- m_BeachDepth = a_IniFile.GetValueSetI("Generator", "ClassicBeachDepth", m_BeachDepth);
- m_BlockTop = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "ClassicBlockTop", "grass").m_ItemType);
- m_BlockMiddle = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "ClassicBlockMiddle", "dirt").m_ItemType);
- m_BlockBottom = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "ClassicBlockBottom", "stone").m_ItemType);
- m_BlockBeach = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "ClassicBlockBeach", "sand").m_ItemType);
- m_BlockBeachBottom = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "ClassicBlockBeachBottom", "sandstone").m_ItemType);
- m_BlockSea = (BLOCKTYPE)(GetIniItemSet(a_IniFile, "Generator", "ClassicBlockSea", "stationarywater").m_ItemType);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cCompoGenBiomal:
-
-void cCompoGenBiomal::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
-
- int ChunkX = a_ChunkDesc.GetChunkX();
- int ChunkZ = a_ChunkDesc.GetChunkZ();
-
- /*
- _X 2013_04_22:
- There's no point in generating the whole cubic noise at once, because the noise values are used in
- only about 20 % of the cases, so the speed gained by precalculating is lost by precalculating too much data
- */
-
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int Height = a_ChunkDesc.GetHeight(x, z);
- if (Height > m_SeaLevel)
- {
- switch (a_ChunkDesc.GetBiome(x, z))
- {
- case biOcean:
- case biPlains:
- case biExtremeHills:
- case biForest:
- case biTaiga:
- case biSwampland:
- case biRiver:
- case biFrozenOcean:
- case biFrozenRiver:
- case biIcePlains:
- case biIceMountains:
- case biForestHills:
- case biTaigaHills:
- case biExtremeHillsEdge:
- case biJungle:
- case biJungleHills:
- {
- FillColumnGrass(x, z, Height, a_ChunkDesc.GetBlockTypes());
- break;
- }
- case biDesertHills:
- case biDesert:
- case biBeach:
- {
- FillColumnSand(x, z, Height, a_ChunkDesc.GetBlockTypes());
- break;
- }
- case biMushroomIsland:
- case biMushroomShore:
- {
- FillColumnMycelium(x, z, Height, a_ChunkDesc.GetBlockTypes());
- break;
- }
- default:
- {
- // TODO
- ASSERT(!"CompoGenBiomal: Biome not implemented yet!");
- break;
- }
- }
- }
- else
- {
- switch (a_ChunkDesc.GetBiome(x, z))
- {
- case biDesert:
- case biBeach:
- {
- // Fill with water, sand, sandstone and stone
- FillColumnWaterSand(x, z, Height, a_ChunkDesc.GetBlockTypes());
- break;
- }
- default:
- {
- // Fill with water, sand/dirt/clay mix and stone
- if (m_Noise.CubicNoise2D(0.3f * (cChunkDef::Width * ChunkX + x), 0.3f * (cChunkDef::Width * ChunkZ + z)) < 0)
- {
- FillColumnWaterSand(x, z, Height, a_ChunkDesc.GetBlockTypes());
- }
- else
- {
- FillColumnWaterDirt(x, z, Height, a_ChunkDesc.GetBlockTypes());
- }
- break;
- }
- } // switch (biome)
- a_ChunkDesc.SetHeight(x, z, m_SeaLevel + 1);
- } // else (under water)
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- } // for x
- } // for z
-}
-
-
-
-
-
-void cCompoGenBiomal::InitializeCompoGen(cIniFile & a_IniFile)
-{
- m_SeaLevel = a_IniFile.GetValueSetI("Generator", "BiomalSeaLevel", m_SeaLevel) - 1;
-}
-
-
-
-
-
-void cCompoGenBiomal::FillColumnGrass(int a_RelX, int a_RelZ, int a_Height, cChunkDef::BlockTypes & a_BlockTypes)
-{
- BLOCKTYPE Pattern[] =
- {
- E_BLOCK_GRASS,
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- } ;
- FillColumnPattern(a_RelX, a_RelZ, a_Height, a_BlockTypes, Pattern, ARRAYCOUNT(Pattern));
-
- for (int y = a_Height - ARRAYCOUNT(Pattern); y > 0; y--)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, E_BLOCK_STONE);
- }
-}
-
-
-
-
-
-void cCompoGenBiomal::FillColumnSand(int a_RelX, int a_RelZ, int a_Height, cChunkDef::BlockTypes & a_BlockTypes)
-{
- BLOCKTYPE Pattern[] =
- {
- E_BLOCK_SAND,
- E_BLOCK_SAND,
- E_BLOCK_SAND,
- E_BLOCK_SANDSTONE,
- } ;
- FillColumnPattern(a_RelX, a_RelZ, a_Height, a_BlockTypes, Pattern, ARRAYCOUNT(Pattern));
-
- for (int y = a_Height - ARRAYCOUNT(Pattern); y > 0; y--)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, E_BLOCK_STONE);
- }
-}
-
-
-
-
-
-
-void cCompoGenBiomal::FillColumnMycelium (int a_RelX, int a_RelZ, int a_Height, cChunkDef::BlockTypes & a_BlockTypes)
-{
- BLOCKTYPE Pattern[] =
- {
- E_BLOCK_MYCELIUM,
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- } ;
- FillColumnPattern(a_RelX, a_RelZ, a_Height, a_BlockTypes, Pattern, ARRAYCOUNT(Pattern));
-
- for (int y = a_Height - ARRAYCOUNT(Pattern); y > 0; y--)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, E_BLOCK_STONE);
- }
-}
-
-
-
-
-
-void cCompoGenBiomal::FillColumnWaterSand(int a_RelX, int a_RelZ, int a_Height, cChunkDef::BlockTypes & a_BlockTypes)
-{
- FillColumnSand(a_RelX, a_RelZ, a_Height, a_BlockTypes);
- for (int y = a_Height + 1; y <= m_SeaLevel + 1; y++)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, E_BLOCK_STATIONARY_WATER);
- }
-}
-
-
-
-
-
-void cCompoGenBiomal::FillColumnWaterDirt(int a_RelX, int a_RelZ, int a_Height, cChunkDef::BlockTypes & a_BlockTypes)
-{
- // Dirt
- BLOCKTYPE Pattern[] =
- {
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- E_BLOCK_DIRT,
- } ;
- FillColumnPattern(a_RelX, a_RelZ, a_Height, a_BlockTypes, Pattern, ARRAYCOUNT(Pattern));
-
- for (int y = a_Height - ARRAYCOUNT(Pattern); y > 0; y--)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, E_BLOCK_STONE);
- }
- for (int y = a_Height + 1; y <= m_SeaLevel + 1; y++)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, E_BLOCK_STATIONARY_WATER);
- }
-}
-
-
-
-
-
-
-void cCompoGenBiomal::FillColumnPattern(int a_RelX, int a_RelZ, int a_Height, cChunkDef::BlockTypes & a_BlockTypes, const BLOCKTYPE * a_Pattern, int a_PatternSize)
-{
- for (int y = a_Height, idx = 0; (y >= 0) && (idx < a_PatternSize); y--, idx++)
- {
- cChunkDef::SetBlock(a_BlockTypes, a_RelX, y, a_RelZ, a_Pattern[idx]);
- }
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cCompoGenNether:
-
-cCompoGenNether::cCompoGenNether(int a_Seed) :
- m_Noise1(a_Seed + 10),
- m_Noise2(a_Seed * a_Seed * 10 + a_Seed * 1000 + 6000),
- m_Threshold(0)
-{
-}
-
-
-
-
-
-void cCompoGenNether::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- HEIGHTTYPE MaxHeight = a_ChunkDesc.GetMaxHeight();
-
- const int SEGMENT_HEIGHT = 8;
- const int INTERPOL_X = 16; // Must be a divisor of 16
- const int INTERPOL_Z = 16; // Must be a divisor of 16
- // Interpolate the chunk in 16 * SEGMENT_HEIGHT * 16 "segments", each SEGMENT_HEIGHT blocks high and each linearly interpolated separately.
- // Have two buffers, one for the lowest floor and one for the highest floor, so that Y-interpolation can be done between them
- // Then swap the buffers and use the previously-top one as the current-bottom, without recalculating it.
-
- int FloorBuf1[17 * 17];
- int FloorBuf2[17 * 17];
- int * FloorHi = FloorBuf1;
- int * FloorLo = FloorBuf2;
- int BaseX = a_ChunkDesc.GetChunkX() * cChunkDef::Width;
- int BaseZ = a_ChunkDesc.GetChunkZ() * cChunkDef::Width;
-
- // Interpolate the lowest floor:
- for (int z = 0; z <= 16 / INTERPOL_Z; z++) for (int x = 0; x <= 16 / INTERPOL_X; x++)
- {
- FloorLo[INTERPOL_X * x + 17 * INTERPOL_Z * z] =
- m_Noise1.IntNoise3DInt(BaseX + INTERPOL_X * x, 0, BaseZ + INTERPOL_Z * z) *
- m_Noise2.IntNoise3DInt(BaseX + INTERPOL_X * x, 0, BaseZ + INTERPOL_Z * z) /
- 256;
- } // for x, z - FloorLo[]
- LinearUpscale2DArrayInPlace(FloorLo, 17, 17, INTERPOL_X, INTERPOL_Z);
-
- // Interpolate segments:
- for (int Segment = 0; Segment < MaxHeight; Segment += SEGMENT_HEIGHT)
- {
- // First update the high floor:
- for (int z = 0; z <= 16 / INTERPOL_Z; z++) for (int x = 0; x <= 16 / INTERPOL_X; x++)
- {
- FloorHi[INTERPOL_X * x + 17 * INTERPOL_Z * z] =
- m_Noise1.IntNoise3DInt(BaseX + INTERPOL_X * x, Segment + SEGMENT_HEIGHT, BaseZ + INTERPOL_Z * z) *
- m_Noise2.IntNoise3DInt(BaseX + INTERPOL_Z * x, Segment + SEGMENT_HEIGHT, BaseZ + INTERPOL_Z * z) /
- 256;
- } // for x, z - FloorLo[]
- LinearUpscale2DArrayInPlace(FloorHi, 17, 17, INTERPOL_X, INTERPOL_Z);
-
- // Interpolate between FloorLo and FloorHi:
- for (int z = 0; z < 16; z++) for (int x = 0; x < 16; x++)
- {
- int Lo = FloorLo[x + 17 * z] / 256;
- int Hi = FloorHi[x + 17 * z] / 256;
- for (int y = 0; y < SEGMENT_HEIGHT; y++)
- {
- int Val = Lo + (Hi - Lo) * y / SEGMENT_HEIGHT;
- a_ChunkDesc.SetBlockType(x, y + Segment, z, (Val < m_Threshold) ? E_BLOCK_NETHERRACK : E_BLOCK_AIR);
- }
- }
-
- // Swap the floors:
- std::swap(FloorLo, FloorHi);
- }
-
- // Bedrock at the bottom and at the top:
- for (int z = 0; z < 16; z++) for (int x = 0; x < 16; x++)
- {
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- a_ChunkDesc.SetBlockType(x, a_ChunkDesc.GetHeight(x, z), z, E_BLOCK_BEDROCK);
- }
-}
-
-
-
-
-
-void cCompoGenNether::InitializeCompoGen(cIniFile & a_IniFile)
-{
- m_Threshold = a_IniFile.GetValueSetI("Generator", "NetherThreshold", m_Threshold);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cCompoGenCache:
-
-cCompoGenCache::cCompoGenCache(cTerrainCompositionGen & a_Underlying, int a_CacheSize) :
- m_Underlying(a_Underlying),
- m_CacheSize(a_CacheSize),
- m_CacheOrder(new int[a_CacheSize]),
- m_CacheData(new sCacheData[a_CacheSize]),
- m_NumHits(0),
- m_NumMisses(0),
- m_TotalChain(0)
-{
- for (int i = 0; i < m_CacheSize; i++)
- {
- m_CacheOrder[i] = i;
- m_CacheData[i].m_ChunkX = 0x7fffffff;
- m_CacheData[i].m_ChunkZ = 0x7fffffff;
- }
-}
-
-
-
-
-
-cCompoGenCache::~cCompoGenCache()
-{
- delete[] m_CacheData;
- delete[] m_CacheOrder;
-}
-
-
-
-
-
-void cCompoGenCache::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- #ifdef _DEBUG
- if (((m_NumHits + m_NumMisses) % 1024) == 10)
- {
- LOGD("CompoGenCache: %d hits, %d misses, saved %.2f %%", m_NumHits, m_NumMisses, 100.0 * m_NumHits / (m_NumHits + m_NumMisses));
- LOGD("CompoGenCache: Avg cache chain length: %.2f", (float)m_TotalChain / m_NumHits);
- }
- #endif // _DEBUG
-
- int ChunkX = a_ChunkDesc.GetChunkX();
- int ChunkZ = a_ChunkDesc.GetChunkZ();
-
- for (int i = 0; i < m_CacheSize; i++)
- {
- if (
- (m_CacheData[m_CacheOrder[i]].m_ChunkX != ChunkX) ||
- (m_CacheData[m_CacheOrder[i]].m_ChunkZ != ChunkZ)
- )
- {
- continue;
- }
- // Found it in the cache
- int Idx = m_CacheOrder[i];
-
- // Move to front:
- for (int j = i; j > 0; j--)
- {
- m_CacheOrder[j] = m_CacheOrder[j - 1];
- }
- m_CacheOrder[0] = Idx;
-
- // Use the cached data:
- memcpy(a_ChunkDesc.GetBlockTypes(), m_CacheData[Idx].m_BlockTypes, sizeof(a_ChunkDesc.GetBlockTypes()));
- memcpy(a_ChunkDesc.GetBlockMetasUncompressed(), m_CacheData[Idx].m_BlockMetas, sizeof(a_ChunkDesc.GetBlockMetasUncompressed()));
-
- m_NumHits++;
- m_TotalChain += i;
- return;
- } // for i - cache
-
- // Not in the cache:
- m_NumMisses++;
- m_Underlying.ComposeTerrain(a_ChunkDesc);
-
- // Insert it as the first item in the MRU order:
- int Idx = m_CacheOrder[m_CacheSize - 1];
- for (int i = m_CacheSize - 1; i > 0; i--)
- {
- m_CacheOrder[i] = m_CacheOrder[i - 1];
- } // for i - m_CacheOrder[]
- m_CacheOrder[0] = Idx;
- memcpy(m_CacheData[Idx].m_BlockTypes, a_ChunkDesc.GetBlockTypes(), sizeof(a_ChunkDesc.GetBlockTypes()));
- memcpy(m_CacheData[Idx].m_BlockMetas, a_ChunkDesc.GetBlockMetasUncompressed(), sizeof(a_ChunkDesc.GetBlockMetasUncompressed()));
- m_CacheData[Idx].m_ChunkX = ChunkX;
- m_CacheData[Idx].m_ChunkZ = ChunkZ;
-}
-
-
-
-
-
-void cCompoGenCache::InitializeCompoGen(cIniFile & a_IniFile)
-{
- m_Underlying.InitializeCompoGen(a_IniFile);
-}
-
-
-
-
diff --git a/source/Generating/ComposableGenerator.cpp b/source/Generating/ComposableGenerator.cpp
deleted file mode 100644
index 2637b64e7..000000000
--- a/source/Generating/ComposableGenerator.cpp
+++ /dev/null
@@ -1,501 +0,0 @@
-
-// ComposableGenerator.cpp
-
-// Implements the cComposableGenerator class representing the chunk generator that takes the composition approach to generating chunks
-
-#include "Globals.h"
-
-#include "ComposableGenerator.h"
-#include "../World.h"
-#include "../../iniFile/iniFile.h"
-#include "../Root.h"
-
-// Individual composed algorithms:
-#include "BioGen.h"
-#include "HeiGen.h"
-#include "CompoGen.h"
-#include "StructGen.h"
-#include "FinishGen.h"
-
-#include "Caves.h"
-#include "DistortedHeightmap.h"
-#include "EndGen.h"
-#include "MineShafts.h"
-#include "Noise3DGenerator.h"
-#include "Ravines.h"
-
-
-
-
-
-
-
-
-
-
-cComposableGenerator::cComposableGenerator(cChunkGenerator & a_ChunkGenerator) :
- super(a_ChunkGenerator),
- m_BiomeGen(NULL),
- m_HeightGen(NULL),
- m_CompositionGen(NULL),
- m_UnderlyingBiomeGen(NULL),
- m_UnderlyingHeightGen(NULL),
- m_UnderlyingCompositionGen(NULL)
-{
-}
-
-
-
-
-
-cComposableGenerator::~cComposableGenerator()
-{
- // Delete the generating composition:
- for (cFinishGenList::const_iterator itr = m_FinishGens.begin(); itr != m_FinishGens.end(); ++itr)
- {
- delete *itr;
- }
- m_FinishGens.clear();
- for (cStructureGenList::const_iterator itr = m_StructureGens.begin(); itr != m_StructureGens.end(); ++itr)
- {
- delete *itr;
- }
- m_StructureGens.clear();
-
- delete m_CompositionGen;
- m_CompositionGen = NULL;
- delete m_HeightGen;
- m_HeightGen = NULL;
- delete m_BiomeGen;
- m_BiomeGen = NULL;
- delete m_UnderlyingCompositionGen;
- m_UnderlyingCompositionGen = NULL;
- delete m_UnderlyingHeightGen;
- m_UnderlyingHeightGen = NULL;
- delete m_UnderlyingBiomeGen;
- m_UnderlyingBiomeGen = NULL;
-}
-
-
-
-
-
-void cComposableGenerator::Initialize(cWorld * a_World, cIniFile & a_IniFile)
-{
- super::Initialize(a_World, a_IniFile);
-
- InitBiomeGen(a_IniFile);
- InitHeightGen(a_IniFile);
- InitCompositionGen(a_IniFile);
- InitStructureGens(a_IniFile);
- InitFinishGens(a_IniFile);
-}
-
-
-
-
-
-void cComposableGenerator::GenerateBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- if (m_BiomeGen != NULL) // Quick fix for generator deinitializing before the world storage finishes loading
- {
- m_BiomeGen->GenBiomes(a_ChunkX, a_ChunkZ, a_BiomeMap);
- }
-}
-
-
-
-
-
-void cComposableGenerator::DoGenerate(int a_ChunkX, int a_ChunkZ, cChunkDesc & a_ChunkDesc)
-{
- if (a_ChunkDesc.IsUsingDefaultBiomes())
- {
- m_BiomeGen->GenBiomes(a_ChunkX, a_ChunkZ, a_ChunkDesc.GetBiomeMap());
- }
-
- if (a_ChunkDesc.IsUsingDefaultHeight())
- {
- m_HeightGen->GenHeightMap(a_ChunkX, a_ChunkZ, a_ChunkDesc.GetHeightMap());
- }
-
- if (a_ChunkDesc.IsUsingDefaultComposition())
- {
- m_CompositionGen->ComposeTerrain(a_ChunkDesc);
- }
-
- if (a_ChunkDesc.IsUsingDefaultStructures())
- {
- for (cStructureGenList::iterator itr = m_StructureGens.begin(); itr != m_StructureGens.end(); ++itr)
- {
- (*itr)->GenStructures(a_ChunkDesc);
- } // for itr - m_StructureGens[]
- }
-
- if (a_ChunkDesc.IsUsingDefaultFinish())
- {
- for (cFinishGenList::iterator itr = m_FinishGens.begin(); itr != m_FinishGens.end(); ++itr)
- {
- (*itr)->GenFinish(a_ChunkDesc);
- } // for itr - m_FinishGens[]
- }
-}
-
-
-
-
-
-void cComposableGenerator::InitBiomeGen(cIniFile & a_IniFile)
-{
- AString BiomeGenName = a_IniFile.GetValueSet("Generator", "BiomeGen", "");
- if (BiomeGenName.empty())
- {
- LOGWARN("[Generator] BiomeGen value not set in world.ini, using \"MultiStepMap\".");
- BiomeGenName = "MultiStepMap";
- }
-
- int Seed = m_ChunkGenerator.GetSeed();
- bool CacheOffByDefault = false;
- if (NoCaseCompare(BiomeGenName, "constant") == 0)
- {
- m_BiomeGen = new cBioGenConstant;
- CacheOffByDefault = true; // we're generating faster than a cache would retrieve data :)
- }
- else if (NoCaseCompare(BiomeGenName, "checkerboard") == 0)
- {
- m_BiomeGen = new cBioGenCheckerboard;
- CacheOffByDefault = true; // we're (probably) generating faster than a cache would retrieve data
- }
- else if (NoCaseCompare(BiomeGenName, "voronoi") == 0)
- {
- m_BiomeGen = new cBioGenVoronoi(Seed);
- }
- else if (NoCaseCompare(BiomeGenName, "distortedvoronoi") == 0)
- {
- m_BiomeGen = new cBioGenDistortedVoronoi(Seed);
- }
- else
- {
- if (NoCaseCompare(BiomeGenName, "multistepmap") != 0)
- {
- LOGWARNING("Unknown BiomeGen \"%s\", using \"MultiStepMap\" instead.", BiomeGenName.c_str());
- }
- m_BiomeGen = new cBioGenMultiStepMap(Seed);
-
- /*
- // Performance-testing:
- LOGINFO("Measuring performance of cBioGenMultiStepMap...");
- clock_t BeginTick = clock();
- for (int x = 0; x < 5000; x++)
- {
- cChunkDef::BiomeMap Biomes;
- m_BiomeGen->GenBiomes(x * 5, x * 5, Biomes);
- }
- clock_t Duration = clock() - BeginTick;
- LOGINFO("cBioGenMultiStepMap for 5000 chunks took %d ticks (%.02f sec)", Duration, (double)Duration / CLOCKS_PER_SEC);
- //*/
- }
-
- // Add a cache, if requested:
- int CacheSize = a_IniFile.GetValueSetI("Generator", "BiomeGenCacheSize", CacheOffByDefault ? 0 : 64);
- if (CacheSize > 0)
- {
- if (CacheSize < 4)
- {
- LOGWARNING("Biomegen cache size set too low, would hurt performance instead of helping. Increasing from %d to %d",
- CacheSize, 4
- );
- CacheSize = 4;
- }
- LOGD("Using a cache for biomegen of size %d.", CacheSize);
- m_UnderlyingBiomeGen = m_BiomeGen;
- m_BiomeGen = new cBioGenCache(m_UnderlyingBiomeGen, CacheSize);
- }
- m_BiomeGen->InitializeBiomeGen(a_IniFile);
-}
-
-
-
-
-
-void cComposableGenerator::InitHeightGen(cIniFile & a_IniFile)
-{
- AString HeightGenName = a_IniFile.GetValueSet("Generator", "HeightGen", "");
- if (HeightGenName.empty())
- {
- LOGWARN("[Generator] HeightGen value not set in world.ini, using \"Biomal\".");
- HeightGenName = "Biomal";
- }
-
- int Seed = m_ChunkGenerator.GetSeed();
- bool CacheOffByDefault = false;
- if (NoCaseCompare(HeightGenName, "flat") == 0)
- {
- m_HeightGen = new cHeiGenFlat;
- CacheOffByDefault = true; // We're generating faster than a cache would retrieve data
- }
- else if (NoCaseCompare(HeightGenName, "classic") == 0)
- {
- m_HeightGen = new cHeiGenClassic(Seed);
- }
- else if (NoCaseCompare(HeightGenName, "DistortedHeightmap") == 0)
- {
- m_HeightGen = new cDistortedHeightmap(Seed, *m_BiomeGen);
- }
- else if (NoCaseCompare(HeightGenName, "End") == 0)
- {
- m_HeightGen = new cEndGen(Seed);
- }
- else if (NoCaseCompare(HeightGenName, "Noise3D") == 0)
- {
- m_HeightGen = new cNoise3DComposable(Seed);
- }
- else // "biomal" or <not found>
- {
- if (NoCaseCompare(HeightGenName, "biomal") != 0)
- {
- LOGWARN("Unknown HeightGen \"%s\", using \"Biomal\" instead.", HeightGenName.c_str());
- }
- m_HeightGen = new cHeiGenBiomal(Seed, *m_BiomeGen);
-
- /*
- // Performance-testing:
- LOGINFO("Measuring performance of cHeiGenBiomal...");
- clock_t BeginTick = clock();
- for (int x = 0; x < 500; x++)
- {
- cChunkDef::HeightMap Heights;
- m_HeightGen->GenHeightMap(x * 5, x * 5, Heights);
- }
- clock_t Duration = clock() - BeginTick;
- LOGINFO("HeightGen for 500 chunks took %d ticks (%.02f sec)", Duration, (double)Duration / CLOCKS_PER_SEC);
- //*/
- }
-
- // Read the settings:
- m_HeightGen->InitializeHeightGen(a_IniFile);
-
- // Add a cache, if requested:
- int CacheSize = a_IniFile.GetValueSetI("Generator", "HeightGenCacheSize", CacheOffByDefault ? 0 : 64);
- if (CacheSize > 0)
- {
- if (CacheSize < 4)
- {
- LOGWARNING("Heightgen cache size set too low, would hurt performance instead of helping. Increasing from %d to %d",
- CacheSize, 4
- );
- CacheSize = 4;
- }
- LOGD("Using a cache for Heightgen of size %d.", CacheSize);
- m_UnderlyingHeightGen = m_HeightGen;
- m_HeightGen = new cHeiGenCache(*m_UnderlyingHeightGen, CacheSize);
- }
-}
-
-
-
-
-
-void cComposableGenerator::InitCompositionGen(cIniFile & a_IniFile)
-{
- int Seed = m_ChunkGenerator.GetSeed();
- AString CompoGenName = a_IniFile.GetValueSet("Generator", "CompositionGen", "");
- if (CompoGenName.empty())
- {
- LOGWARN("[Generator] CompositionGen value not set in world.ini, using \"Biomal\".");
- CompoGenName = "Biomal";
- }
- if (NoCaseCompare(CompoGenName, "sameblock") == 0)
- {
- m_CompositionGen = new cCompoGenSameBlock;
- }
- else if (NoCaseCompare(CompoGenName, "debugbiomes") == 0)
- {
- m_CompositionGen = new cCompoGenDebugBiomes;
- }
- else if (NoCaseCompare(CompoGenName, "classic") == 0)
- {
- m_CompositionGen = new cCompoGenClassic;
- }
- else if (NoCaseCompare(CompoGenName, "DistortedHeightmap") == 0)
- {
- m_CompositionGen = new cDistortedHeightmap(Seed, *m_BiomeGen);
- }
- else if (NoCaseCompare(CompoGenName, "end") == 0)
- {
- m_CompositionGen = new cEndGen(Seed);
- }
- else if (NoCaseCompare(CompoGenName, "nether") == 0)
- {
- m_CompositionGen = new cCompoGenNether(Seed);
- }
- else if (NoCaseCompare(CompoGenName, "Noise3D") == 0)
- {
- m_CompositionGen = new cNoise3DComposable(m_ChunkGenerator.GetSeed());
- }
- else
- {
- if (NoCaseCompare(CompoGenName, "biomal") != 0)
- {
- LOGWARN("Unknown CompositionGen \"%s\", using \"biomal\" instead.", CompoGenName.c_str());
- }
- m_CompositionGen = new cCompoGenBiomal(Seed);
-
- /*
- // Performance-testing:
- LOGINFO("Measuring performance of cCompoGenBiomal...");
- clock_t BeginTick = clock();
- for (int x = 0; x < 500; x++)
- {
- cChunkDesc Desc(200 + x * 8, 200 + x * 8);
- m_BiomeGen->GenBiomes(Desc.GetChunkX(), Desc.GetChunkZ(), Desc.GetBiomeMap());
- m_HeightGen->GenHeightMap(Desc.GetChunkX(), Desc.GetChunkZ(), Desc.GetHeightMap());
- m_CompositionGen->ComposeTerrain(Desc);
- }
- clock_t Duration = clock() - BeginTick;
- LOGINFO("CompositionGen for 500 chunks took %d ticks (%.02f sec)", Duration, (double)Duration / CLOCKS_PER_SEC);
- //*/
- }
-
- // Read the settings from the ini file:
- m_CompositionGen->InitializeCompoGen(a_IniFile);
-
- int CompoGenCacheSize = a_IniFile.GetValueSetI("Generator", "CompositionGenCacheSize", 64);
- if (CompoGenCacheSize > 1)
- {
- m_UnderlyingCompositionGen = m_CompositionGen;
- m_CompositionGen = new cCompoGenCache(*m_UnderlyingCompositionGen, 32);
- }
-}
-
-
-
-
-
-void cComposableGenerator::InitStructureGens(cIniFile & a_IniFile)
-{
- AString Structures = a_IniFile.GetValueSet("Generator", "Structures", "Ravines, WormNestCaves, WaterLakes, LavaLakes, OreNests, Trees");
-
- int Seed = m_ChunkGenerator.GetSeed();
- AStringVector Str = StringSplitAndTrim(Structures, ",");
- for (AStringVector::const_iterator itr = Str.begin(); itr != Str.end(); ++itr)
- {
- if (NoCaseCompare(*itr, "DualRidgeCaves") == 0)
- {
- float Threshold = (float)a_IniFile.GetValueSetF("Generator", "DualRidgeCavesThreshold", 0.3);
- m_StructureGens.push_back(new cStructGenDualRidgeCaves(Seed, Threshold));
- }
- else if (NoCaseCompare(*itr, "DirectOverhangs") == 0)
- {
- m_StructureGens.push_back(new cStructGenDirectOverhangs(Seed));
- }
- else if (NoCaseCompare(*itr, "DistortedMembraneOverhangs") == 0)
- {
- m_StructureGens.push_back(new cStructGenDistortedMembraneOverhangs(Seed));
- }
- else if (NoCaseCompare(*itr, "LavaLakes") == 0)
- {
- int Probability = a_IniFile.GetValueSetI("Generator", "LavaLakesProbability", 10);
- m_StructureGens.push_back(new cStructGenLakes(Seed * 5 + 16873, E_BLOCK_STATIONARY_LAVA, *m_HeightGen, Probability));
- }
- else if (NoCaseCompare(*itr, "MarbleCaves") == 0)
- {
- m_StructureGens.push_back(new cStructGenMarbleCaves(Seed));
- }
- else if (NoCaseCompare(*itr, "MineShafts") == 0)
- {
- int GridSize = a_IniFile.GetValueSetI("Generator", "MineShaftsGridSize", 512);
- int MaxSystemSize = a_IniFile.GetValueSetI("Generator", "MineShaftsMaxSystemSize", 160);
- int ChanceCorridor = a_IniFile.GetValueSetI("Generator", "MineShaftsChanceCorridor", 600);
- int ChanceCrossing = a_IniFile.GetValueSetI("Generator", "MineShaftsChanceCrossing", 200);
- int ChanceStaircase = a_IniFile.GetValueSetI("Generator", "MineShaftsChanceStaircase", 200);
- m_StructureGens.push_back(new cStructGenMineShafts(
- Seed, GridSize, MaxSystemSize,
- ChanceCorridor, ChanceCrossing, ChanceStaircase
- ));
- }
- else if (NoCaseCompare(*itr, "OreNests") == 0)
- {
- m_StructureGens.push_back(new cStructGenOreNests(Seed));
- }
- else if (NoCaseCompare(*itr, "Ravines") == 0)
- {
- m_StructureGens.push_back(new cStructGenRavines(Seed, 128));
- }
- else if (NoCaseCompare(*itr, "Trees") == 0)
- {
- m_StructureGens.push_back(new cStructGenTrees(Seed, m_BiomeGen, m_HeightGen, m_CompositionGen));
- }
- else if (NoCaseCompare(*itr, "WaterLakes") == 0)
- {
- int Probability = a_IniFile.GetValueSetI("Generator", "WaterLakesProbability", 25);
- m_StructureGens.push_back(new cStructGenLakes(Seed * 3 + 652, E_BLOCK_STATIONARY_WATER, *m_HeightGen, Probability));
- }
- else if (NoCaseCompare(*itr, "WormNestCaves") == 0)
- {
- m_StructureGens.push_back(new cStructGenWormNestCaves(Seed));
- }
- else
- {
- LOGWARNING("Unknown structure generator: \"%s\". Ignoring.", itr->c_str());
- }
- } // for itr - Str[]
-}
-
-
-
-
-
-void cComposableGenerator::InitFinishGens(cIniFile & a_IniFile)
-{
- int Seed = m_ChunkGenerator.GetSeed();
- AString Structures = a_IniFile.GetValueSet("Generator", "Finishers", "SprinkleFoliage,Ice,Snow,Lilypads,BottomLava,DeadBushes,PreSimulator");
-
- AStringVector Str = StringSplitAndTrim(Structures, ",");
- for (AStringVector::const_iterator itr = Str.begin(); itr != Str.end(); ++itr)
- {
- // Finishers, alpha-sorted:
- if (NoCaseCompare(*itr, "BottomLava") == 0)
- {
- int DefaultBottomLavaLevel = (m_World->GetDimension() == dimNether) ? 30 : 10;
- int BottomLavaLevel = a_IniFile.GetValueSetI("Generator", "BottomLavaLevel", DefaultBottomLavaLevel);
- m_FinishGens.push_back(new cFinishGenBottomLava(BottomLavaLevel));
- }
- else if (NoCaseCompare(*itr, "DeadBushes") == 0)
- {
- m_FinishGens.push_back(new cFinishGenSingleBiomeSingleTopBlock(Seed, E_BLOCK_DEAD_BUSH, biDesert, 2, E_BLOCK_SAND, E_BLOCK_SAND));
- }
- else if (NoCaseCompare(*itr, "Ice") == 0)
- {
- m_FinishGens.push_back(new cFinishGenIce);
- }
- else if (NoCaseCompare(*itr, "LavaSprings") == 0)
- {
- m_FinishGens.push_back(new cFinishGenFluidSprings(Seed, E_BLOCK_LAVA, a_IniFile, *m_World));
- }
- else if (NoCaseCompare(*itr, "Lilypads") == 0)
- {
- m_FinishGens.push_back(new cFinishGenSingleBiomeSingleTopBlock(Seed, E_BLOCK_LILY_PAD, biSwampland, 4, E_BLOCK_WATER, E_BLOCK_STATIONARY_WATER));
- }
- else if (NoCaseCompare(*itr, "PreSimulator") == 0)
- {
- m_FinishGens.push_back(new cFinishGenPreSimulator);
- }
- else if (NoCaseCompare(*itr, "Snow") == 0)
- {
- m_FinishGens.push_back(new cFinishGenSnow);
- }
- else if (NoCaseCompare(*itr, "SprinkleFoliage") == 0)
- {
- m_FinishGens.push_back(new cFinishGenSprinkleFoliage(Seed));
- }
- else if (NoCaseCompare(*itr, "WaterSprings") == 0)
- {
- m_FinishGens.push_back(new cFinishGenFluidSprings(Seed, E_BLOCK_WATER, a_IniFile, *m_World));
- }
- } // for itr - Str[]
-}
-
-
-
-
diff --git a/source/Generating/DistortedHeightmap.cpp b/source/Generating/DistortedHeightmap.cpp
deleted file mode 100644
index 7e46c251e..000000000
--- a/source/Generating/DistortedHeightmap.cpp
+++ /dev/null
@@ -1,444 +0,0 @@
-
-// DistortedHeightmap.cpp
-
-// Implements the cDistortedHeightmap class representing the height and composition generator capable of overhangs
-
-#include "Globals.h"
-
-#include "DistortedHeightmap.h"
-#include "../OSSupport/File.h"
-#include "../../iniFile/iniFile.h"
-#include "../LinearUpscale.h"
-
-
-
-
-
-/** This table assigns a relative maximum overhang size in each direction to biomes.
-Both numbers indicate a number which will multiply the noise value for each coord;
-this means that you can have different-sized overhangs in each direction.
-Usually you'd want to keep both numbers the same.
-The numbers are "relative", not absolute maximum; overhangs of a slightly larger size are possible
-due to the way that noise is calculated.
-*/
-const cDistortedHeightmap::sGenParam cDistortedHeightmap::m_GenParam[biNumBiomes] =
-{
- /* Biome | AmpX | AmpZ */
- /* biOcean */ { 1.5f, 1.5f},
- /* biPlains */ { 0.5f, 0.5f},
- /* biDesert */ { 0.5f, 0.5f},
- /* biExtremeHills */ {16.0f, 16.0f},
- /* biForest */ { 3.0f, 3.0f},
- /* biTaiga */ { 1.5f, 1.5f},
-
- /* biSwampland */ { 0.0f, 0.0f},
- /* biRiver */ { 0.0f, 0.0f},
- /* biNether */ { 0.0f, 0.0f}, // Unused, but must be here due to indexing
- /* biSky */ { 0.0f, 0.0f}, // Unused, but must be here due to indexing
- /* biFrozenOcean */ { 0.0f, 0.0f},
- /* biFrozenRiver */ { 0.0f, 0.0f},
- /* biIcePlains */ { 0.0f, 0.0f},
- /* biIceMountains */ { 8.0f, 8.0f},
- /* biMushroomIsland */ { 4.0f, 4.0f},
- /* biMushroomShore */ { 0.0f, 0.0f},
- /* biBeach */ { 0.0f, 0.0f},
- /* biDesertHills */ { 5.0f, 5.0f},
- /* biForestHills */ { 6.0f, 6.0f},
- /* biTaigaHills */ { 8.0f, 8.0f},
- /* biExtremeHillsEdge */ { 7.0f, 7.0f},
- /* biJungle */ { 0.0f, 0.0f},
- /* biJungleHills */ { 8.0f, 8.0f},
-} ;
-
-
-
-
-
-cDistortedHeightmap::cDistortedHeightmap(int a_Seed, cBiomeGen & a_BiomeGen) :
- m_NoiseDistortX(a_Seed + 1000),
- m_NoiseDistortZ(a_Seed + 2000),
- m_OceanFloorSelect(a_Seed + 3000),
- m_BiomeGen(a_BiomeGen),
- m_UnderlyingHeiGen(a_Seed, a_BiomeGen),
- m_HeightGen(m_UnderlyingHeiGen, 64)
-{
- m_NoiseDistortX.AddOctave((NOISE_DATATYPE)1, (NOISE_DATATYPE)0.5);
- m_NoiseDistortX.AddOctave((NOISE_DATATYPE)0.5, (NOISE_DATATYPE)1);
- m_NoiseDistortX.AddOctave((NOISE_DATATYPE)0.25, (NOISE_DATATYPE)2);
-
- m_NoiseDistortZ.AddOctave((NOISE_DATATYPE)1, (NOISE_DATATYPE)0.5);
- m_NoiseDistortZ.AddOctave((NOISE_DATATYPE)0.5, (NOISE_DATATYPE)1);
- m_NoiseDistortZ.AddOctave((NOISE_DATATYPE)0.25, (NOISE_DATATYPE)2);
-}
-
-
-
-
-
-void cDistortedHeightmap::Initialize(cIniFile & a_IniFile)
-{
- if (m_IsInitialized)
- {
- return;
- }
-
- // Read the params from the INI file:
- m_SeaLevel = a_IniFile.GetValueSetI("Generator", "DistortedHeightmapSeaLevel", 62);
- m_FrequencyX = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "DistortedHeightmapFrequencyX", 10);
- m_FrequencyY = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "DistortedHeightmapFrequencyY", 10);
- m_FrequencyZ = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "DistortedHeightmapFrequencyZ", 10);
-
- m_IsInitialized = true;
-}
-
-
-
-
-
-void cDistortedHeightmap::PrepareState(int a_ChunkX, int a_ChunkZ)
-{
- if ((m_CurChunkX == a_ChunkX) && (m_CurChunkZ == a_ChunkZ))
- {
- return;
- }
- m_CurChunkX = a_ChunkX;
- m_CurChunkZ = a_ChunkZ;
-
-
- m_HeightGen.GenHeightMap(a_ChunkX, a_ChunkZ, m_CurChunkHeights);
- UpdateDistortAmps();
- GenerateHeightArray();
-}
-
-
-
-
-
-void cDistortedHeightmap::GenerateHeightArray(void)
-{
- // Generate distortion noise:
- NOISE_DATATYPE DistortNoiseX[DIM_X * DIM_Y * DIM_Z];
- NOISE_DATATYPE DistortNoiseZ[DIM_X * DIM_Y * DIM_Z];
- NOISE_DATATYPE Workspace[DIM_X * DIM_Y * DIM_Z];
- NOISE_DATATYPE StartX = ((NOISE_DATATYPE)(m_CurChunkX * cChunkDef::Width)) / m_FrequencyX;
- NOISE_DATATYPE EndX = ((NOISE_DATATYPE)((m_CurChunkX + 1) * cChunkDef::Width - 1)) / m_FrequencyX;
- NOISE_DATATYPE StartY = 0;
- NOISE_DATATYPE EndY = ((NOISE_DATATYPE)(257)) / m_FrequencyY;
- NOISE_DATATYPE StartZ = ((NOISE_DATATYPE)(m_CurChunkZ * cChunkDef::Width)) / m_FrequencyZ;
- NOISE_DATATYPE EndZ = ((NOISE_DATATYPE)((m_CurChunkZ + 1) * cChunkDef::Width - 1)) / m_FrequencyZ;
-
- m_NoiseDistortX.Generate3D(DistortNoiseX, DIM_X, DIM_Y, DIM_Z, StartX, EndX, StartY, EndY, StartZ, EndZ, Workspace);
- m_NoiseDistortZ.Generate3D(DistortNoiseZ, DIM_X, DIM_Y, DIM_Z, StartX, EndX, StartY, EndY, StartZ, EndZ, Workspace);
-
- // The distorted heightmap, before linear upscaling
- NOISE_DATATYPE DistHei[DIM_X * DIM_Y * DIM_Z];
-
- // Distort the heightmap using the distortion:
- for (int z = 0; z < DIM_Z; z++)
- {
- int AmpIdx = z * DIM_X;
- for (int y = 0; y < DIM_Y; y++)
- {
- int NoiseArrayIdx = z * DIM_X * DIM_Y + y * DIM_X;
- for (int x = 0; x < DIM_X; x++)
- {
- NOISE_DATATYPE DistX = DistortNoiseX[NoiseArrayIdx + x] * m_DistortAmpX[AmpIdx + x];
- NOISE_DATATYPE DistZ = DistortNoiseZ[NoiseArrayIdx + x] * m_DistortAmpZ[AmpIdx + x];
- DistX += (NOISE_DATATYPE)(m_CurChunkX * cChunkDef::Width + x * INTERPOL_X);
- DistZ += (NOISE_DATATYPE)(m_CurChunkZ * cChunkDef::Width + z * INTERPOL_Z);
- // Adding 0.5 helps alleviate the interpolation artifacts
- DistHei[NoiseArrayIdx + x] = (NOISE_DATATYPE)GetHeightmapAt(DistX, DistZ) + (NOISE_DATATYPE)0.5;
- }
- }
- }
-
- // Upscale the distorted heightmap into full dimensions:
- LinearUpscale3DArray(
- DistHei, DIM_X, DIM_Y, DIM_Z,
- m_DistortedHeightmap, INTERPOL_X, INTERPOL_Y, INTERPOL_Z
- );
-
- // DEBUG: Debug3DNoise(m_DistortedHeightmap, 17, 257, 17, Printf("DistortedHeightmap_%d_%d", m_CurChunkX, m_CurChunkZ));
-}
-
-
-
-
-
-void cDistortedHeightmap::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- PrepareState(a_ChunkX, a_ChunkZ);
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int NoiseArrayIdx = x + 17 * 257 * z;
- cChunkDef::SetHeight(a_HeightMap, x, z, m_SeaLevel - 1);
- for (int y = cChunkDef::Height - 1; y > m_SeaLevel - 1; y--)
- {
- int HeightMapHeight = (int)m_DistortedHeightmap[NoiseArrayIdx + 17 * y];
- if (y < HeightMapHeight)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, y);
- break;
- }
- } // for y
- } // for x
- } // for z
-}
-
-
-
-
-
-void cDistortedHeightmap::InitializeHeightGen(cIniFile & a_IniFile)
-{
- Initialize(a_IniFile);
-}
-
-
-
-
-
-void cDistortedHeightmap::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- // Frequencies for the ocean floor selecting noise:
- NOISE_DATATYPE FrequencyX = 3;
- NOISE_DATATYPE FrequencyZ = 3;
-
- // Prepare the internal state for generating this chunk:
- PrepareState(a_ChunkDesc.GetChunkX(), a_ChunkDesc.GetChunkZ());
-
- // Compose:
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int NoiseArrayIdx = x + 17 * 257 * z;
- int LastAir = a_ChunkDesc.GetHeight(x, z) + 1;
- bool HasHadWater = false;
- for (int y = LastAir - 1; y > 0; y--)
- {
- int HeightMapHeight = (int)m_DistortedHeightmap[NoiseArrayIdx + 17 * y];
-
- if (y >= HeightMapHeight)
- {
- // "air" part
- LastAir = y;
- if (y < m_SeaLevel)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_STATIONARY_WATER);
- HasHadWater = true;
- }
- continue;
- }
- // "ground" part:
- if (y < LastAir - 4)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_STONE);
- continue;
- }
- if (HasHadWater)
- {
- // Decide between clay, sand and dirt
- NOISE_DATATYPE NoiseX = ((NOISE_DATATYPE)(m_CurChunkX * cChunkDef::Width + x)) / FrequencyX;
- NOISE_DATATYPE NoiseY = ((NOISE_DATATYPE)(m_CurChunkZ * cChunkDef::Width + z)) / FrequencyZ;
- NOISE_DATATYPE Val = m_OceanFloorSelect.CubicNoise2D(NoiseX, NoiseY);
- if (Val < -0.95)
- {
- // Clay:
- switch (LastAir - y)
- {
- case 0:
- case 1:
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_CLAY);
- break;
- }
- case 2:
- case 3:
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_SAND);
- break;
- }
- case 4:
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_SANDSTONE);
- break;
- }
- } // switch (floor depth)
- }
- else if (Val < 0)
- {
- a_ChunkDesc.SetBlockType(x, y, z, (y < LastAir - 3) ? E_BLOCK_SANDSTONE : E_BLOCK_SAND);
- }
- else
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_DIRT);
- }
- }
- else
- {
- switch (a_ChunkDesc.GetBiome(x, z))
- {
- case biOcean:
- case biPlains:
- case biExtremeHills:
- case biForest:
- case biTaiga:
- case biSwampland:
- case biRiver:
- case biFrozenOcean:
- case biFrozenRiver:
- case biIcePlains:
- case biIceMountains:
- case biForestHills:
- case biTaigaHills:
- case biExtremeHillsEdge:
- case biJungle:
- case biJungleHills:
- {
- a_ChunkDesc.SetBlockType(x, y, z, (y == LastAir - 1) ? E_BLOCK_GRASS : E_BLOCK_DIRT);
- break;
- }
- case biDesertHills:
- case biDesert:
- case biBeach:
- {
- a_ChunkDesc.SetBlockType(x, y, z, (y < LastAir - 3) ? E_BLOCK_SANDSTONE : E_BLOCK_SAND);
- break;
- }
- case biMushroomIsland:
- case biMushroomShore:
- {
- a_ChunkDesc.SetBlockType(x, y, z, (y == LastAir - 1) ? E_BLOCK_MYCELIUM : E_BLOCK_DIRT);
- break;
- }
- }
- }
- } // for y
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- } // for x
- } // for z
-}
-
-
-
-
-
-void cDistortedHeightmap::InitializeCompoGen(cIniFile & a_IniFile)
-{
- Initialize(a_IniFile);
-}
-
-
-
-
-
-int cDistortedHeightmap::GetHeightmapAt(NOISE_DATATYPE a_X, NOISE_DATATYPE a_Z)
-{
- int ChunkX = (int)floor(a_X / (NOISE_DATATYPE)16);
- int ChunkZ = (int)floor(a_Z / (NOISE_DATATYPE)16);
- int RelX = (int)(a_X - (NOISE_DATATYPE)ChunkX * cChunkDef::Width);
- int RelZ = (int)(a_Z - (NOISE_DATATYPE)ChunkZ * cChunkDef::Width);
-
- // If we're withing the same chunk, return the pre-cached heightmap:
- if ((ChunkX == m_CurChunkX) && (ChunkZ == m_CurChunkZ))
- {
- return cChunkDef::GetHeight(m_CurChunkHeights, RelX, RelZ);
- }
-
- // Ask the cache:
- HEIGHTTYPE res = 0;
- if (m_HeightGen.GetHeightAt(ChunkX, ChunkZ, RelX, RelZ, res))
- {
- // The height was in the cache
- return res;
- }
-
- // The height is not in the cache, generate full heightmap and get it there:
- cChunkDef::HeightMap Heightmap;
- m_HeightGen.GenHeightMap(ChunkX, ChunkZ, Heightmap);
- return cChunkDef::GetHeight(Heightmap, RelX, RelZ);
-}
-
-
-
-
-
-void cDistortedHeightmap::UpdateDistortAmps(void)
-{
- BiomeNeighbors Biomes;
- for (int z = -1; z <= 1; z++)
- {
- for (int x = -1; x <= 1; x++)
- {
- m_BiomeGen.GenBiomes(m_CurChunkX + x, m_CurChunkZ + z, Biomes[x + 1][z + 1]);
- } // for x
- } // for z
-
- for (int z = 0; z < DIM_Z; z++)
- {
- for (int x = 0; x < DIM_Z; x++)
- {
- GetDistortAmpsAt(Biomes, x * INTERPOL_X, z * INTERPOL_Z, m_DistortAmpX[x + DIM_X * z], m_DistortAmpZ[x + DIM_X * z]);
- }
- }
-}
-
-
-
-
-
-void cDistortedHeightmap::GetDistortAmpsAt(BiomeNeighbors & a_Neighbors, int a_RelX, int a_RelZ, NOISE_DATATYPE & a_DistortAmpX, NOISE_DATATYPE & a_DistortAmpZ)
-{
- // Sum up how many biomes of each type there are in the neighborhood:
- int BiomeCounts[biNumBiomes];
- memset(BiomeCounts, 0, sizeof(BiomeCounts));
- int Sum = 0;
- for (int z = -8; z <= 8; z++)
- {
- int FinalZ = a_RelZ + z + cChunkDef::Width;
- int IdxZ = FinalZ / cChunkDef::Width;
- int ModZ = FinalZ % cChunkDef::Width;
- int WeightZ = 9 - abs(z);
- for (int x = -8; x <= 8; x++)
- {
- int FinalX = a_RelX + x + cChunkDef::Width;
- int IdxX = FinalX / cChunkDef::Width;
- int ModX = FinalX % cChunkDef::Width;
- EMCSBiome Biome = cChunkDef::GetBiome(a_Neighbors[IdxX][IdxZ], ModX, ModZ);
- if ((Biome < 0) || (Biome >= ARRAYCOUNT(BiomeCounts)))
- {
- continue;
- }
- int WeightX = 9 - abs(x);
- BiomeCounts[Biome] += WeightX + WeightZ;
- Sum += WeightX + WeightZ;
- } // for x
- } // for z
-
- if (Sum <= 0)
- {
- // No known biome around? Weird. Return a bogus value:
- ASSERT(!"cHeiGenBiomal: Biome sum failed, no known biome around");
- a_DistortAmpX = 16;
- a_DistortAmpZ = 16;
- }
-
- // For each biome type that has a nonzero count, calc its amps and add it:
- NOISE_DATATYPE AmpX = 0;
- NOISE_DATATYPE AmpZ = 0;
- for (unsigned int i = 0; i < ARRAYCOUNT(BiomeCounts); i++)
- {
- AmpX += BiomeCounts[i] * m_GenParam[i].m_DistortAmpX;
- AmpZ += BiomeCounts[i] * m_GenParam[i].m_DistortAmpZ;
- }
- a_DistortAmpX = AmpX / Sum;
- a_DistortAmpZ = AmpZ / Sum;
-}
-
-
-
-
diff --git a/source/Generating/EndGen.cpp b/source/Generating/EndGen.cpp
deleted file mode 100644
index 90a8071fa..000000000
--- a/source/Generating/EndGen.cpp
+++ /dev/null
@@ -1,217 +0,0 @@
-
-// EndGen.cpp
-
-// Implements the cEndGen class representing the generator for the End, both as a HeightGen and CompositionGen
-
-#include "Globals.h"
-#include "EndGen.h"
-#include "../../iniFile/iniFile.h"
-#include "../LinearUpscale.h"
-
-
-
-
-
-enum
-{
- // Interpolation cell size:
- INTERPOL_X = 4,
- INTERPOL_Y = 4,
- INTERPOL_Z = 4,
-
- // Size of chunk data, downscaled before interpolation:
- DIM_X = 16 / INTERPOL_X + 1,
- DIM_Y = 256 / INTERPOL_Y + 1,
- DIM_Z = 16 / INTERPOL_Z + 1,
-} ;
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cEndGen:
-
-cEndGen::cEndGen(int a_Seed) :
- m_Seed(a_Seed),
- m_IslandSizeX(256),
- m_IslandSizeY(96),
- m_IslandSizeZ(256),
- m_FrequencyX(80),
- m_FrequencyY(80),
- m_FrequencyZ(80)
-{
- m_Perlin.AddOctave(1, 1);
- m_Perlin.AddOctave(2, 0.5);
- m_Perlin.AddOctave(4, 0.25);
-}
-
-
-
-
-
-void cEndGen::Initialize(cIniFile & a_IniFile)
-{
- m_IslandSizeX = a_IniFile.GetValueSetI("Generator", "EndGenIslandSizeX", m_IslandSizeX);
- m_IslandSizeY = a_IniFile.GetValueSetI("Generator", "EndGenIslandSizeY", m_IslandSizeY);
- m_IslandSizeZ = a_IniFile.GetValueSetI("Generator", "EndGenIslandSizeZ", m_IslandSizeZ);
-
- m_FrequencyX = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "EndGenFrequencyX", m_FrequencyX);
- m_FrequencyY = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "EndGenFrequencyY", m_FrequencyY);
- m_FrequencyZ = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "EndGenFrequencyZ", m_FrequencyZ);
-
- // Recalculate the min and max chunk coords of the island
- m_MaxChunkX = (m_IslandSizeX + cChunkDef::Width - 1) / cChunkDef::Width;
- m_MinChunkX = -m_MaxChunkX;
- m_MaxChunkZ = (m_IslandSizeZ + cChunkDef::Width - 1) / cChunkDef::Width;
- m_MinChunkZ = -m_MaxChunkZ;
-}
-
-
-
-
-
-/// Unless the LastChunk coords are equal to coords given, prepares the internal state (noise array)
-void cEndGen::PrepareState(int a_ChunkX, int a_ChunkZ)
-{
- ASSERT(!IsChunkOutsideRange(a_ChunkX, a_ChunkZ)); // Should be filtered before calling this function
-
- if ((m_LastChunkX == a_ChunkX) && (m_LastChunkZ == a_ChunkZ))
- {
- return;
- }
-
- m_LastChunkX = a_ChunkX;
- m_LastChunkZ = a_ChunkZ;
-
- GenerateNoiseArray();
-}
-
-
-
-
-
-/// Generates the m_NoiseArray array for the current chunk
-void cEndGen::GenerateNoiseArray(void)
-{
- NOISE_DATATYPE NoiseData[DIM_X * DIM_Y * DIM_Z]; // [x + DIM_X * z + DIM_X * DIM_Z * y]
- NOISE_DATATYPE Workspace[DIM_X * DIM_Y * DIM_Z]; // [x + DIM_X * z + DIM_X * DIM_Z * y]
-
- // Generate the downscaled noise:
- NOISE_DATATYPE StartX = ((NOISE_DATATYPE)(m_LastChunkX * cChunkDef::Width)) / m_FrequencyX;
- NOISE_DATATYPE EndX = ((NOISE_DATATYPE)((m_LastChunkX + 1) * cChunkDef::Width)) / m_FrequencyX;
- NOISE_DATATYPE StartZ = ((NOISE_DATATYPE)(m_LastChunkZ * cChunkDef::Width)) / m_FrequencyZ;
- NOISE_DATATYPE EndZ = ((NOISE_DATATYPE)((m_LastChunkZ + 1) * cChunkDef::Width)) / m_FrequencyZ;
- NOISE_DATATYPE StartY = 0;
- NOISE_DATATYPE EndY = ((NOISE_DATATYPE)257) / m_FrequencyY;
- m_Perlin.Generate3D(NoiseData, DIM_X, DIM_Z, DIM_Y, StartX, EndX, StartZ, EndZ, StartY, EndY, Workspace);
-
- // Add distance:
- int idx = 0;
- for (int y = 0; y < DIM_Y; y++)
- {
- NOISE_DATATYPE ValY = (NOISE_DATATYPE)(2 * INTERPOL_Y * y - m_IslandSizeY) / m_IslandSizeY;
- ValY = ValY * ValY;
- for (int z = 0; z < DIM_Z; z++)
- {
- NOISE_DATATYPE ValZ = (NOISE_DATATYPE)(m_LastChunkZ * cChunkDef::Width + (z * cChunkDef::Width / (DIM_Z - 1))) / m_IslandSizeZ;
- ValZ = ValZ * ValZ;
- for (int x = 0; x < DIM_X; x++)
- {
- // NOISE_DATATYPE ValX = StartX + (EndX - StartX) * x / (DIM_X - 1);
- NOISE_DATATYPE ValX = (NOISE_DATATYPE)(m_LastChunkX * cChunkDef::Width + (x * cChunkDef::Width / (DIM_X - 1))) / m_IslandSizeX;
- ValX = ValX * ValX;
- NoiseData[idx++] += ValX + ValZ + ValY;
- } // for x
- } // for z
- } // for y
-
- // Upscale into real chunk size:
- LinearUpscale3DArray(NoiseData, DIM_X, DIM_Z, DIM_Y, m_NoiseArray, INTERPOL_X, INTERPOL_Z, INTERPOL_Y);
-}
-
-
-
-
-
-/// Returns true if the chunk is outside of the island's dimensions
-bool cEndGen::IsChunkOutsideRange(int a_ChunkX, int a_ChunkZ)
-{
- return (
- (a_ChunkX < m_MinChunkX) || (a_ChunkX > m_MaxChunkX) ||
- (a_ChunkZ < m_MinChunkZ) || (a_ChunkZ > m_MaxChunkZ)
- );
-}
-
-
-
-
-
-void cEndGen::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- if (IsChunkOutsideRange(a_ChunkX, a_ChunkZ))
- {
- for (unsigned int i = 0; i < ARRAYCOUNT(a_HeightMap); i++)
- {
- a_HeightMap[i] = 0;
- }
- return;
- }
-
- PrepareState(a_ChunkX, a_ChunkZ);
-
- int MaxY = std::min((int)(1.75 * m_IslandSizeY + 1), cChunkDef::Height - 1);
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, MaxY);
- for (int y = MaxY; y > 0; y--)
- {
- if (m_NoiseArray[y * 17 * 17 + z * 17 + x] <= 0)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, y);
- break;
- }
- } // for y
- } // for x
- } // for z
-}
-
-
-
-
-
-void cEndGen::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- if (IsChunkOutsideRange(a_ChunkDesc.GetChunkX(), a_ChunkDesc.GetChunkZ()))
- {
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
- return;
- }
-
- PrepareState(a_ChunkDesc.GetChunkX(), a_ChunkDesc.GetChunkZ());
-
- int MaxY = std::min((int)(1.75 * m_IslandSizeY + 1), cChunkDef::Height - 1);
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- for (int y = MaxY; y > 0; y--)
- {
- if (m_NoiseArray[y * 17 * 17 + z * 17 + x] <= 0)
- {
- a_ChunkDesc.SetBlockTypeMeta(x, y, z, E_BLOCK_END_STONE, 0);
- }
- else
- {
- a_ChunkDesc.SetBlockTypeMeta(x, y, z, E_BLOCK_AIR, 0);
- }
- } // for y
- } // for x
- } // for z
-}
-
-
-
-
diff --git a/source/Generating/HeiGen.cpp b/source/Generating/HeiGen.cpp
deleted file mode 100644
index 5dee181b7..000000000
--- a/source/Generating/HeiGen.cpp
+++ /dev/null
@@ -1,390 +0,0 @@
-
-// HeiGen.cpp
-
-// Implements the various terrain height generators
-
-#include "Globals.h"
-#include "HeiGen.h"
-#include "../LinearUpscale.h"
-#include "../../iniFile/iniFile.h"
-
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cHeiGenFlat:
-
-void cHeiGenFlat::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- for (int i = 0; i < ARRAYCOUNT(a_HeightMap); i++)
- {
- a_HeightMap[i] = m_Height;
- }
-}
-
-
-
-
-
-void cHeiGenFlat::InitializeHeightGen(cIniFile & a_IniFile)
-{
- m_Height = a_IniFile.GetValueSetI("Generator", "FlatHeight", m_Height);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cHeiGenCache:
-
-cHeiGenCache::cHeiGenCache(cTerrainHeightGen & a_HeiGenToCache, int a_CacheSize) :
- m_HeiGenToCache(a_HeiGenToCache),
- m_CacheSize(a_CacheSize),
- m_CacheOrder(new int[a_CacheSize]),
- m_CacheData(new sCacheData[a_CacheSize]),
- m_NumHits(0),
- m_NumMisses(0),
- m_TotalChain(0)
-{
- for (int i = 0; i < m_CacheSize; i++)
- {
- m_CacheOrder[i] = i;
- m_CacheData[i].m_ChunkX = 0x7fffffff;
- m_CacheData[i].m_ChunkZ = 0x7fffffff;
- }
-}
-
-
-
-
-
-cHeiGenCache::~cHeiGenCache()
-{
- delete[] m_CacheData;
- delete[] m_CacheOrder;
-}
-
-
-
-
-
-void cHeiGenCache::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- /*
- if (((m_NumHits + m_NumMisses) % 1024) == 10)
- {
- LOGD("HeiGenCache: %d hits, %d misses, saved %.2f %%", m_NumHits, m_NumMisses, 100.0 * m_NumHits / (m_NumHits + m_NumMisses));
- LOGD("HeiGenCache: Avg cache chain length: %.2f", (float)m_TotalChain / m_NumHits);
- }
- //*/
-
- for (int i = 0; i < m_CacheSize; i++)
- {
- if (
- (m_CacheData[m_CacheOrder[i]].m_ChunkX != a_ChunkX) ||
- (m_CacheData[m_CacheOrder[i]].m_ChunkZ != a_ChunkZ)
- )
- {
- continue;
- }
- // Found it in the cache
- int Idx = m_CacheOrder[i];
-
- // Move to front:
- for (int j = i; j > 0; j--)
- {
- m_CacheOrder[j] = m_CacheOrder[j - 1];
- }
- m_CacheOrder[0] = Idx;
-
- // Use the cached data:
- memcpy(a_HeightMap, m_CacheData[Idx].m_HeightMap, sizeof(a_HeightMap));
-
- m_NumHits++;
- m_TotalChain += i;
- return;
- } // for i - cache
-
- // Not in the cache:
- m_NumMisses++;
- m_HeiGenToCache.GenHeightMap(a_ChunkX, a_ChunkZ, a_HeightMap);
-
- // Insert it as the first item in the MRU order:
- int Idx = m_CacheOrder[m_CacheSize - 1];
- for (int i = m_CacheSize - 1; i > 0; i--)
- {
- m_CacheOrder[i] = m_CacheOrder[i - 1];
- } // for i - m_CacheOrder[]
- m_CacheOrder[0] = Idx;
- memcpy(m_CacheData[Idx].m_HeightMap, a_HeightMap, sizeof(a_HeightMap));
- m_CacheData[Idx].m_ChunkX = a_ChunkX;
- m_CacheData[Idx].m_ChunkZ = a_ChunkZ;
-}
-
-
-
-
-
-void cHeiGenCache::InitializeHeightGen(cIniFile & a_IniFile)
-{
- m_HeiGenToCache.InitializeHeightGen(a_IniFile);
-}
-
-
-
-
-
-bool cHeiGenCache::GetHeightAt(int a_ChunkX, int a_ChunkZ, int a_RelX, int a_RelZ, HEIGHTTYPE & a_Height)
-{
- for (int i = 0; i < m_CacheSize; i++)
- {
- if ((m_CacheData[i].m_ChunkX == a_ChunkX) && (m_CacheData[i].m_ChunkZ == a_ChunkZ))
- {
- a_Height = cChunkDef::GetHeight(m_CacheData[i].m_HeightMap, a_RelX, a_RelZ);
- return true;
- }
- } // for i - m_CacheData[]
- return false;
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cHeiGenClassic:
-
-cHeiGenClassic::cHeiGenClassic(int a_Seed) :
- m_Seed(a_Seed),
- m_Noise(a_Seed)
-{
-}
-
-
-
-
-
-float cHeiGenClassic::GetNoise(float x, float y)
-{
- float oct1 = m_Noise.CubicNoise2D(x * m_HeightFreq1, y * m_HeightFreq1) * m_HeightAmp1;
- float oct2 = m_Noise.CubicNoise2D(x * m_HeightFreq2, y * m_HeightFreq2) * m_HeightAmp2;
- float oct3 = m_Noise.CubicNoise2D(x * m_HeightFreq3, y * m_HeightFreq3) * m_HeightAmp3;
-
- float height = m_Noise.CubicNoise2D(x * 0.1f, y * 0.1f ) * 2;
-
- float flatness = ((m_Noise.CubicNoise2D(x * 0.5f, y * 0.5f) + 1.f) * 0.5f) * 1.1f; // 0 ... 1.5
- flatness *= flatness * flatness;
-
- return (oct1 + oct2 + oct3) * flatness + height;
-}
-
-
-
-
-
-void cHeiGenClassic::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- const float zz = (float)(a_ChunkZ * cChunkDef::Width + z);
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- const float xx = (float)(a_ChunkX * cChunkDef::Width + x);
-
- int hei = 64 + (int)(GetNoise(xx * 0.05f, zz * 0.05f) * 16);
- if (hei < 10)
- {
- hei = 10;
- }
- if (hei > 250)
- {
- hei = 250;
- }
- cChunkDef::SetHeight(a_HeightMap, x , z, hei);
- } // for x
- } // for z
-}
-
-
-
-
-
-void cHeiGenClassic::InitializeHeightGen(cIniFile & a_IniFile)
-{
- m_HeightFreq1 = (float)a_IniFile.GetValueSetF("Generator", "ClassicHeightFreq1", 0.1);
- m_HeightFreq2 = (float)a_IniFile.GetValueSetF("Generator", "ClassicHeightFreq2", 1.0);
- m_HeightFreq3 = (float)a_IniFile.GetValueSetF("Generator", "ClassicHeightFreq3", 2.0);
- m_HeightAmp1 = (float)a_IniFile.GetValueSetF("Generator", "ClassicHeightAmp1", 1.0);
- m_HeightAmp2 = (float)a_IniFile.GetValueSetF("Generator", "ClassicHeightAmp2", 0.5);
- m_HeightAmp3 = (float)a_IniFile.GetValueSetF("Generator", "ClassicHeightAmp3", 0.5);
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cHeiGenBiomal:
-
-const cHeiGenBiomal::sGenParam cHeiGenBiomal::m_GenParam[biNumBiomes] =
-{
- /* Fast-changing | Middle-changing | Slow-changing |*/
- /* Biome | Freq1 | Amp1 | Freq2 | Amp2 | Freq3 | Amp3 | BaseHeight */
- /* biOcean */ { 0.1f, 2.0f, 0.05f, 12.0f, 0.01f, 10.0f, 40},
- /* biPlains */ { 0.1f, 1.0f, 0.05f, 1.5f, 0.01f, 4.0f, 68},
- /* biDesert */ { 0.1f, 1.0f, 0.05f, 1.5f, 0.01f, 4.0f, 68},
- /* biExtremeHills */ { 0.2f, 4.0f, 0.05f, 20.0f, 0.01f, 16.0f, 100},
- /* biForest */ { 0.1f, 1.0f, 0.05f, 2.0f, 0.01f, 4.0f, 70},
- /* biTaiga */ { 0.1f, 1.0f, 0.05f, 2.0f, 0.01f, 4.0f, 70},
- /* biSwampland */ { 0.1f, 1.1f, 0.05f, 1.5f, 0.02f, 2.5f, 61.5},
- /* biRiver */ { 0.2f, 0.1f, 0.05f, 0.1f, 0.01f, 0.1f, 56},
- /* biNether */ { 0.1f, 0.0f, 0.01f, 0.0f, 0.01f, 0.0f, 0}, // Unused, but must be here due to indexing
- /* biSky */ { 0.1f, 0.0f, 0.01f, 0.0f, 0.01f, 0.0f, 0}, // Unused, but must be here due to indexing
- /* biFrozenOcean */ { 0.1f, 2.0f, 0.05f, 12.0f, 0.01f, 10.0f, 40},
- /* biFrozenRiver */ { 0.2f, 0.1f, 0.05f, 0.1f, 0.01f, 0.1f, 56},
- /* biIcePlains */ { 0.1f, 1.0f, 0.05f, 1.5f, 0.01f, 4.0f, 68},
- /* biIceMountains */ { 0.2f, 2.0f, 0.05f, 10.0f, 0.01f, 8.0f, 80},
- /* biMushroomIsland */ { 0.1f, 2.0f, 0.05f, 8.0f, 0.01f, 6.0f, 80},
- /* biMushroomShore */ { 0.1f, 1.0f, 0.05f, 2.0f, 0.01f, 4.0f, 64},
- /* biBeach */ { 0.1f, 0.5f, 0.05f, 1.0f, 0.01f, 1.0f, 64},
- /* biDesertHills */ { 0.2f, 2.0f, 0.05f, 5.0f, 0.01f, 4.0f, 75},
- /* biForestHills */ { 0.2f, 2.0f, 0.05f, 12.0f, 0.01f, 10.0f, 80},
- /* biTaigaHills */ { 0.2f, 2.0f, 0.05f, 12.0f, 0.01f, 10.0f, 80},
- /* biExtremeHillsEdge */ { 0.2f, 3.0f, 0.05f, 16.0f, 0.01f, 12.0f, 80},
- /* biJungle */ { 0.1f, 3.0f, 0.05f, 6.0f, 0.01f, 6.0f, 70},
- /* biJungleHills */ { 0.2f, 3.0f, 0.05f, 12.0f, 0.01f, 10.0f, 80},
-} ;
-
-
-
-
-
-void cHeiGenBiomal::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- // Generate a 3x3 chunk area of biomes around this chunk:
- BiomeNeighbors Biomes;
- for (int z = -1; z <= 1; z++)
- {
- for (int x = -1; x <= 1; x++)
- {
- m_BiomeGen.GenBiomes(a_ChunkX + x, a_ChunkZ + z, Biomes[x + 1][z + 1]);
- } // for x
- } // for z
-
- /*
- _X 2013_04_22:
- There's no point in precalculating the entire perlin noise arrays, too many values are calculated uselessly,
- resulting in speed DEcrease.
- */
-
- //*
- // Linearly interpolate 4x4 blocks of heightmap:
- // Must be done on a floating point datatype, else the results are ugly!
- const int STEPZ = 4; // Must be a divisor of 16
- const int STEPX = 4; // Must be a divisor of 16
- NOISE_DATATYPE Height[17 * 17];
- for (int z = 0; z < 17; z += STEPZ)
- {
- for (int x = 0; x < 17; x += STEPX)
- {
- Height[x + 17 * z] = GetHeightAt(x, z, a_ChunkX, a_ChunkZ, Biomes);
- }
- }
- LinearUpscale2DArrayInPlace(Height, 17, 17, STEPX, STEPZ);
-
- // Copy into the heightmap
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, (int)Height[x + 17 * z]);
- }
- }
- //*/
-
- /*
- // For each height, go through neighboring biomes and add up their idea of height:
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, GetHeightAt(x, z, a_ChunkX, a_ChunkZ, Biomes));
- } // for x
- }
- //*/
-}
-
-
-
-
-
-void cHeiGenBiomal::InitializeHeightGen(cIniFile & a_IniFile)
-{
- // No user-settable params
-}
-
-
-
-
-
-NOISE_DATATYPE cHeiGenBiomal::GetHeightAt(int a_RelX, int a_RelZ, int a_ChunkX, int a_ChunkZ, const cHeiGenBiomal::BiomeNeighbors & a_BiomeNeighbors)
-{
- // Sum up how many biomes of each type there are in the neighborhood:
- int BiomeCounts[biNumBiomes];
- memset(BiomeCounts, 0, sizeof(BiomeCounts));
- int Sum = 0;
- for (int z = -8; z <= 8; z++)
- {
- int FinalZ = a_RelZ + z + cChunkDef::Width;
- int IdxZ = FinalZ / cChunkDef::Width;
- int ModZ = FinalZ % cChunkDef::Width;
- int WeightZ = 9 - abs(z);
- for (int x = -8; x <= 8; x++)
- {
- int FinalX = a_RelX + x + cChunkDef::Width;
- int IdxX = FinalX / cChunkDef::Width;
- int ModX = FinalX % cChunkDef::Width;
- EMCSBiome Biome = cChunkDef::GetBiome(a_BiomeNeighbors[IdxX][IdxZ], ModX, ModZ);
- if ((Biome < 0) || (Biome >= ARRAYCOUNT(BiomeCounts)))
- {
- continue;
- }
- int WeightX = 9 - abs(x);
- BiomeCounts[Biome] += WeightX + WeightZ;
- Sum += WeightX + WeightZ;
- } // for x
- } // for z
-
- // For each biome type that has a nonzero count, calc its height and add it:
- if (Sum > 0)
- {
- NOISE_DATATYPE Height = 0;
- int BlockX = a_ChunkX * cChunkDef::Width + a_RelX;
- int BlockZ = a_ChunkZ * cChunkDef::Width + a_RelZ;
- for (int i = 0; i < ARRAYCOUNT(BiomeCounts); i++)
- {
- if (BiomeCounts[i] == 0)
- {
- continue;
- }
- NOISE_DATATYPE oct1 = m_Noise.CubicNoise2D(BlockX * m_GenParam[i].m_HeightFreq1, BlockZ * m_GenParam[i].m_HeightFreq1) * m_GenParam[i].m_HeightAmp1;
- NOISE_DATATYPE oct2 = m_Noise.CubicNoise2D(BlockX * m_GenParam[i].m_HeightFreq2, BlockZ * m_GenParam[i].m_HeightFreq2) * m_GenParam[i].m_HeightAmp2;
- NOISE_DATATYPE oct3 = m_Noise.CubicNoise2D(BlockX * m_GenParam[i].m_HeightFreq3, BlockZ * m_GenParam[i].m_HeightFreq3) * m_GenParam[i].m_HeightAmp3;
- Height += BiomeCounts[i] * (m_GenParam[i].m_BaseHeight + oct1 + oct2 + oct3);
- }
- NOISE_DATATYPE res = Height / Sum;
- return std::min((NOISE_DATATYPE)250, std::max(res, (NOISE_DATATYPE)5));
- }
-
- // No known biome around? Weird. Return a bogus value:
- ASSERT(!"cHeiGenBiomal: Biome sum failed, no known biome around");
- return 5;
-}
-
-
-
-
-
diff --git a/source/Generating/Noise3DGenerator.cpp b/source/Generating/Noise3DGenerator.cpp
deleted file mode 100644
index 03626a800..000000000
--- a/source/Generating/Noise3DGenerator.cpp
+++ /dev/null
@@ -1,576 +0,0 @@
-
-// Nosie3DGenerator.cpp
-
-// Generates terrain using 3D noise, rather than composing. Is a test.
-
-#include "Globals.h"
-#include "Noise3DGenerator.h"
-#include "../OSSupport/File.h"
-#include "../../iniFile/iniFile.h"
-#include "../LinearInterpolation.h"
-#include "../LinearUpscale.h"
-
-
-
-
-
-/*
-// Perform an automatic test of upscaling upon program start (use breakpoints to debug):
-
-class Test
-{
-public:
- Test(void)
- {
- DoTest1();
- DoTest2();
- }
-
-
- void DoTest1(void)
- {
- float In[3 * 3 * 3];
- for (int i = 0; i < ARRAYCOUNT(In); i++)
- {
- In[i] = (float)(i % 5);
- }
- Debug3DNoise(In, 3, 3, 3, "Upscale3D in");
- float Out[17 * 33 * 35];
- LinearUpscale3DArray(In, 3, 3, 3, Out, 8, 16, 17);
- Debug3DNoise(Out, 17, 33, 35, "Upscale3D test");
- }
-
-
- void DoTest2(void)
- {
- float In[3 * 3];
- for (int i = 0; i < ARRAYCOUNT(In); i++)
- {
- In[i] = (float)(i % 5);
- }
- Debug2DNoise(In, 3, 3, "Upscale2D in");
- float Out[17 * 33];
- LinearUpscale2DArray(In, 3, 3, Out, 8, 16);
- Debug2DNoise(Out, 17, 33, "Upscale2D test");
- }
-
-} gTest;
-//*/
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cNoise3DGenerator:
-
-cNoise3DGenerator::cNoise3DGenerator(cChunkGenerator & a_ChunkGenerator) :
- super(a_ChunkGenerator),
- m_Perlin(1000),
- m_Cubic(1000)
-{
- m_Perlin.AddOctave(1, (NOISE_DATATYPE)0.5);
- m_Perlin.AddOctave((NOISE_DATATYPE)0.5, 1);
- m_Perlin.AddOctave((NOISE_DATATYPE)0.5, 2);
-
- #if 0
- // DEBUG: Test the noise generation:
- // NOTE: In order to be able to run MCS with this code, you need to increase the default thread stack size
- // In MSVC, it is done in Project Settings -> Configuration Properties -> Linker -> System, set Stack reserve size to at least 64M
- m_SeaLevel = 62;
- m_HeightAmplification = 0;
- m_MidPoint = 75;
- m_FrequencyX = 4;
- m_FrequencyY = 4;
- m_FrequencyZ = 4;
- m_AirThreshold = 0.5;
-
- const int NumChunks = 4;
- NOISE_DATATYPE Noise[NumChunks][cChunkDef::Width * cChunkDef::Width * cChunkDef::Height];
- for (int x = 0; x < NumChunks; x++)
- {
- GenerateNoiseArray(x, 5, Noise[x]);
- }
-
- // Save in XY cuts:
- cFile f1;
- if (f1.Open("Test_XY.grab", cFile::fmWrite))
- {
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int y = 0; y < cChunkDef::Height; y++)
- {
- for (int i = 0; i < NumChunks; i++)
- {
- int idx = y * cChunkDef::Width + z * cChunkDef::Width * cChunkDef::Height;
- unsigned char buf[cChunkDef::Width];
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- buf[x] = (unsigned char)(std::min(256, std::max(0, (int)(128 + 32 * Noise[i][idx++]))));
- }
- f1.Write(buf, cChunkDef::Width);
- }
- } // for y
- } // for z
- } // if (XY file open)
-
- cFile f2;
- if (f2.Open("Test_XZ.grab", cFile::fmWrite))
- {
- for (int y = 0; y < cChunkDef::Height; y++)
- {
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int i = 0; i < NumChunks; i++)
- {
- int idx = y * cChunkDef::Width + z * cChunkDef::Width * cChunkDef::Height;
- unsigned char buf[cChunkDef::Width];
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- buf[x] = (unsigned char)(std::min(256, std::max(0, (int)(128 + 32 * Noise[i][idx++]))));
- }
- f2.Write(buf, cChunkDef::Width);
- }
- } // for z
- } // for y
- } // if (XZ file open)
- #endif // 0
-}
-
-
-
-
-
-cNoise3DGenerator::~cNoise3DGenerator()
-{
- // Nothing needed yet
-}
-
-
-
-
-
-void cNoise3DGenerator::Initialize(cWorld * a_World, cIniFile & a_IniFile)
-{
- m_World = a_World;
-
- // Params:
- m_SeaLevel = a_IniFile.GetValueSetI("Generator", "Noise3DSeaLevel", 62);
- m_HeightAmplification = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DHeightAmplification", 0);
- m_MidPoint = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DMidPoint", 75);
- m_FrequencyX = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DFrequencyX", 8);
- m_FrequencyY = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DFrequencyY", 8);
- m_FrequencyZ = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DFrequencyZ", 8);
- m_AirThreshold = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DAirThreshold", 0.5);
-}
-
-
-
-
-
-void cNoise3DGenerator::GenerateBiomes(int a_ChunkX, int a_ChunkZ, cChunkDef::BiomeMap & a_BiomeMap)
-{
- for (unsigned int i = 0; i < ARRAYCOUNT(a_BiomeMap); i++)
- {
- a_BiomeMap[i] = biExtremeHills;
- }
-}
-
-
-
-
-
-void cNoise3DGenerator::DoGenerate(int a_ChunkX, int a_ChunkZ, cChunkDesc & a_ChunkDesc)
-{
- NOISE_DATATYPE Noise[17 * 257 * 17];
- GenerateNoiseArray(a_ChunkX, a_ChunkZ, Noise);
-
- // Output noise into chunk:
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int y = 0; y < cChunkDef::Height; y++)
- {
- int idx = z * 17 * 257 + y * 17;
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- NOISE_DATATYPE n = Noise[idx++];
- BLOCKTYPE BlockType;
- if (n > m_AirThreshold)
- {
- BlockType = (y > m_SeaLevel) ? E_BLOCK_AIR : E_BLOCK_STATIONARY_WATER;
- }
- else
- {
- BlockType = E_BLOCK_STONE;
- }
- a_ChunkDesc.SetBlockType(x, y, z, BlockType);
- }
- }
- }
-
- UpdateHeightmap(a_ChunkDesc);
- ComposeTerrain (a_ChunkDesc);
-}
-
-
-
-
-
-void cNoise3DGenerator::GenerateNoiseArray(int a_ChunkX, int a_ChunkZ, NOISE_DATATYPE * a_OutNoise)
-{
- NOISE_DATATYPE NoiseO[DIM_X * DIM_Y * DIM_Z]; // Output for the Perlin noise
- NOISE_DATATYPE NoiseW[DIM_X * DIM_Y * DIM_Z]; // Workspace that the noise calculation can use and trash
-
- // Our noise array has different layout, XZY, instead of regular chunk's XYZ, that's why the coords are "renamed"
- NOISE_DATATYPE StartX = ((NOISE_DATATYPE)(a_ChunkX * cChunkDef::Width)) / m_FrequencyX;
- NOISE_DATATYPE EndX = ((NOISE_DATATYPE)((a_ChunkX + 1) * cChunkDef::Width) - 1) / m_FrequencyX;
- NOISE_DATATYPE StartZ = ((NOISE_DATATYPE)(a_ChunkZ * cChunkDef::Width)) / m_FrequencyZ;
- NOISE_DATATYPE EndZ = ((NOISE_DATATYPE)((a_ChunkZ + 1) * cChunkDef::Width) - 1) / m_FrequencyZ;
- NOISE_DATATYPE StartY = 0;
- NOISE_DATATYPE EndY = ((NOISE_DATATYPE)256) / m_FrequencyY;
-
- m_Perlin.Generate3D(NoiseO, DIM_X, DIM_Y, DIM_Z, StartX, EndX, StartY, EndY, StartZ, EndZ, NoiseW);
-
- // DEBUG: Debug3DNoise(NoiseO, DIM_X, DIM_Y, DIM_Z, Printf("Chunk_%d_%d_orig", a_ChunkX, a_ChunkZ));
-
- // Precalculate a "height" array:
- NOISE_DATATYPE Height[DIM_X * DIM_Z]; // Output for the cubic noise heightmap ("source")
- m_Cubic.Generate2D(Height, DIM_X, DIM_Z, StartX / 25, EndX / 25, StartZ / 25, EndZ / 25);
- for (unsigned int i = 0; i < ARRAYCOUNT(Height); i++)
- {
- Height[i] = abs(Height[i]) * m_HeightAmplification + 1;
- }
-
- // Modify the noise by height data:
- for (int y = 0; y < DIM_Y; y++)
- {
- NOISE_DATATYPE AddHeight = (y * UPSCALE_Y - m_MidPoint) / 20;
- AddHeight *= AddHeight * AddHeight;
- for (int z = 0; z < DIM_Z; z++)
- {
- NOISE_DATATYPE * CurRow = &(NoiseO[y * DIM_X + z * DIM_X * DIM_Y]);
- for (int x = 0; x < DIM_X; x++)
- {
- CurRow[x] += AddHeight / Height[x + DIM_X * z];
- }
- }
- }
-
- // DEBUG: Debug3DNoise(NoiseO, DIM_X, DIM_Y, DIM_Z, Printf("Chunk_%d_%d_hei", a_ChunkX, a_ChunkZ));
-
- // Upscale the Perlin noise into full-blown chunk dimensions:
- LinearUpscale3DArray(
- NoiseO, DIM_X, DIM_Y, DIM_Z,
- a_OutNoise, UPSCALE_X, UPSCALE_Y, UPSCALE_Z
- );
-
- // DEBUG: Debug3DNoise(a_OutNoise, 17, 257, 17, Printf("Chunk_%d_%d_lerp", a_ChunkX, a_ChunkZ));
-}
-
-
-
-
-
-void cNoise3DGenerator::UpdateHeightmap(cChunkDesc & a_ChunkDesc)
-{
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- for (int y = cChunkDef::Height - 1; y > 0; y--)
- {
- if (a_ChunkDesc.GetBlockType(x, y, z) != E_BLOCK_AIR)
- {
- a_ChunkDesc.SetHeight(x, z, y);
- break;
- }
- } // for y
- } // for x
- } // for z
-}
-
-
-
-
-
-void cNoise3DGenerator::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- // Make basic terrain composition:
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int LastAir = a_ChunkDesc.GetHeight(x, z) + 1;
- bool HasHadWater = false;
- for (int y = LastAir - 1; y > 0; y--)
- {
- switch (a_ChunkDesc.GetBlockType(x, y, z))
- {
- case E_BLOCK_AIR:
- {
- LastAir = y;
- break;
- }
- case E_BLOCK_STONE:
- {
- if (LastAir - y > 3)
- {
- break;
- }
- if (HasHadWater)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_SAND);
- }
- else
- {
- a_ChunkDesc.SetBlockType(x, y, z, (LastAir == y + 1) ? E_BLOCK_GRASS : E_BLOCK_DIRT);
- }
- break;
- }
- case E_BLOCK_STATIONARY_WATER:
- {
- LastAir = y;
- HasHadWater = true;
- break;
- }
- } // switch (GetBlockType())
- } // for y
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- } // for x
- } // for z
-}
-
-
-
-
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-// cNoise3DComposable:
-
-cNoise3DComposable::cNoise3DComposable(int a_Seed) :
- m_Noise1(a_Seed + 1000),
- m_Noise2(a_Seed + 2000),
- m_Noise3(a_Seed + 3000)
-{
-}
-
-
-
-
-
-void cNoise3DComposable::Initialize(cIniFile & a_IniFile)
-{
- // Params:
- m_SeaLevel = a_IniFile.GetValueSetI("Generator", "Noise3DSeaLevel", 62);
- m_HeightAmplification = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DHeightAmplification", 0);
- m_MidPoint = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DMidPoint", 75);
- m_FrequencyX = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DFrequencyX", 10);
- m_FrequencyY = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DFrequencyY", 10);
- m_FrequencyZ = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DFrequencyZ", 10);
- m_AirThreshold = (NOISE_DATATYPE)a_IniFile.GetValueSetF("Generator", "Noise3DAirThreshold", 0.5);
-}
-
-
-
-
-
-void cNoise3DComposable::GenerateNoiseArrayIfNeeded(int a_ChunkX, int a_ChunkZ)
-{
- if ((a_ChunkX == m_LastChunkX) && (a_ChunkZ == m_LastChunkZ))
- {
- // The noise for this chunk is already generated in m_Noise
- return;
- }
- m_LastChunkX = a_ChunkX;
- m_LastChunkZ = a_ChunkZ;
-
- // Upscaling parameters:
- const int UPSCALE_X = 8;
- const int UPSCALE_Y = 4;
- const int UPSCALE_Z = 8;
-
- // Precalculate a "height" array:
- NOISE_DATATYPE Height[17 * 17]; // x + 17 * z
- for (int z = 0; z < 17; z += UPSCALE_Z)
- {
- NOISE_DATATYPE NoiseZ = ((NOISE_DATATYPE)(a_ChunkZ * cChunkDef::Width + z)) / m_FrequencyZ;
- for (int x = 0; x < 17; x += UPSCALE_X)
- {
- NOISE_DATATYPE NoiseX = ((NOISE_DATATYPE)(a_ChunkX * cChunkDef::Width + x)) / m_FrequencyX;
- NOISE_DATATYPE val = abs(m_Noise1.CubicNoise2D(NoiseX / 5, NoiseZ / 5)) * m_HeightAmplification + 1;
- Height[x + 17 * z] = val * val * val;
- }
- }
-
- for (int y = 0; y < 257; y += UPSCALE_Y)
- {
- NOISE_DATATYPE NoiseY = ((NOISE_DATATYPE)y) / m_FrequencyY;
- NOISE_DATATYPE AddHeight = (y - m_MidPoint) / 20;
- AddHeight *= AddHeight * AddHeight;
- NOISE_DATATYPE * CurFloor = &(m_NoiseArray[y * 17 * 17]);
- for (int z = 0; z < 17; z += UPSCALE_Z)
- {
- NOISE_DATATYPE NoiseZ = ((NOISE_DATATYPE)(a_ChunkZ * cChunkDef::Width + z)) / m_FrequencyZ;
- for (int x = 0; x < 17; x += UPSCALE_X)
- {
- NOISE_DATATYPE NoiseX = ((NOISE_DATATYPE)(a_ChunkX * cChunkDef::Width + x)) / m_FrequencyX;
- CurFloor[x + 17 * z] =
- m_Noise1.CubicNoise3D(NoiseX, NoiseY, NoiseZ) * (NOISE_DATATYPE)0.5 +
- m_Noise2.CubicNoise3D(NoiseX / 2, NoiseY / 2, NoiseZ / 2) +
- m_Noise3.CubicNoise3D(NoiseX / 4, NoiseY / 4, NoiseZ / 4) * 2 +
- AddHeight / Height[x + 17 * z];
- }
- }
- // Linear-interpolate this XZ floor:
- LinearUpscale2DArrayInPlace(CurFloor, 17, 17, UPSCALE_X, UPSCALE_Z);
- }
-
- // Finish the 3D linear interpolation by interpolating between each XZ-floors on the Y axis
- for (int y = 1; y < cChunkDef::Height; y++)
- {
- if ((y % UPSCALE_Y) == 0)
- {
- // This is the interpolation source floor, already calculated
- continue;
- }
- int LoFloorY = (y / UPSCALE_Y) * UPSCALE_Y;
- int HiFloorY = LoFloorY + UPSCALE_Y;
- NOISE_DATATYPE * LoFloor = &(m_NoiseArray[LoFloorY * 17 * 17]);
- NOISE_DATATYPE * HiFloor = &(m_NoiseArray[HiFloorY * 17 * 17]);
- NOISE_DATATYPE * CurFloor = &(m_NoiseArray[y * 17 * 17]);
- NOISE_DATATYPE Ratio = ((NOISE_DATATYPE)(y % UPSCALE_Y)) / UPSCALE_Y;
- int idx = 0;
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- CurFloor[idx] = LoFloor[idx] + (HiFloor[idx] - LoFloor[idx]) * Ratio;
- idx += 1;
- }
- idx += 1; // Skipping one X column
- }
- }
-
- // The noise array is now fully interpolated
- /*
- // DEBUG: Output two images of the array, sliced by XY and XZ:
- cFile f1;
- if (f1.Open(Printf("Chunk_%d_%d_XY.raw", a_ChunkX, a_ChunkZ), cFile::fmWrite))
- {
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int y = 0; y < cChunkDef::Height; y++)
- {
- int idx = y * 17 * 17 + z * 17;
- unsigned char buf[16];
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- buf[x] = (unsigned char)(std::min(256, std::max(0, (int)(128 + 128 * m_Noise[idx++]))));
- }
- f1.Write(buf, 16);
- } // for y
- } // for z
- } // if (XY file open)
-
- cFile f2;
- if (f2.Open(Printf("Chunk_%d_%d_XZ.raw", a_ChunkX, a_ChunkZ), cFile::fmWrite))
- {
- for (int y = 0; y < cChunkDef::Height; y++)
- {
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- int idx = y * 17 * 17 + z * 17;
- unsigned char buf[16];
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- buf[x] = (unsigned char)(std::min(256, std::max(0, (int)(128 + 128 * m_Noise[idx++]))));
- }
- f2.Write(buf, 16);
- } // for z
- } // for y
- } // if (XZ file open)
- */
-}
-
-
-
-
-
-void cNoise3DComposable::GenHeightMap(int a_ChunkX, int a_ChunkZ, cChunkDef::HeightMap & a_HeightMap)
-{
- GenerateNoiseArrayIfNeeded(a_ChunkX, a_ChunkZ);
-
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, m_SeaLevel);
- for (int y = cChunkDef::Height - 1; y > m_SeaLevel; y--)
- {
- if (m_NoiseArray[y * 17 * 17 + z * 17 + x] <= m_AirThreshold)
- {
- cChunkDef::SetHeight(a_HeightMap, x, z, y);
- break;
- }
- } // for y
- } // for x
- } // for z
-}
-
-
-
-
-
-void cNoise3DComposable::ComposeTerrain(cChunkDesc & a_ChunkDesc)
-{
- GenerateNoiseArrayIfNeeded(a_ChunkDesc.GetChunkX(), a_ChunkDesc.GetChunkZ());
-
- a_ChunkDesc.FillBlocks(E_BLOCK_AIR, 0);
-
- // Make basic terrain composition:
- for (int z = 0; z < cChunkDef::Width; z++)
- {
- for (int x = 0; x < cChunkDef::Width; x++)
- {
- int LastAir = a_ChunkDesc.GetHeight(x, z) + 1;
- bool HasHadWater = false;
- for (int y = LastAir; y < m_SeaLevel; y++)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_STATIONARY_WATER);
- }
- for (int y = LastAir - 1; y > 0; y--)
- {
- if (m_NoiseArray[x + 17 * z + 17 * 17 * y] > m_AirThreshold)
- {
- // "air" part
- LastAir = y;
- if (y < m_SeaLevel)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_STATIONARY_WATER);
- HasHadWater = true;
- }
- continue;
- }
- // "ground" part:
- if (LastAir - y > 4)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_STONE);
- continue;
- }
- if (HasHadWater)
- {
- a_ChunkDesc.SetBlockType(x, y, z, E_BLOCK_SAND);
- }
- else
- {
- a_ChunkDesc.SetBlockType(x, y, z, (LastAir == y + 1) ? E_BLOCK_GRASS : E_BLOCK_DIRT);
- }
- } // for y
- a_ChunkDesc.SetBlockType(x, 0, z, E_BLOCK_BEDROCK);
- } // for x
- } // for z
-}
-
-
-
-
diff --git a/source/Generating/Caves.cpp b/src/Generating/Caves.cpp
index df45bb4c2..df45bb4c2 100644
--- a/source/Generating/Caves.cpp
+++ b/src/Generating/Caves.cpp
diff --git a/source/Generating/Caves.h b/src/Generating/Caves.h
index 70cf6fe8c..70cf6fe8c 100644
--- a/source/Generating/Caves.h
+++ b/src/Generating/Caves.h
diff --git a/source/Generating/ChunkDesc.cpp b/src/Generating/ChunkDesc.cpp
index 6050430fd..6050430fd 100644
--- a/source/Generating/ChunkDesc.cpp
+++ b/src/Generating/ChunkDesc.cpp
diff --git a/source/Generating/ChunkDesc.h b/src/Generating/ChunkDesc.h
index e130c463f..e130c463f 100644
--- a/source/Generating/ChunkDesc.h
+++ b/src/Generating/ChunkDesc.h
diff --git a/source/Generating/ChunkGenerator.h b/src/Generating/ChunkGenerator.h
index 2d3bb8082..2d3bb8082 100644
--- a/source/Generating/ChunkGenerator.h
+++ b/src/Generating/ChunkGenerator.h
diff --git a/source/Generating/CompoGen.h b/src/Generating/CompoGen.h
index 2ee286b06..2ee286b06 100644
--- a/source/Generating/CompoGen.h
+++ b/src/Generating/CompoGen.h
diff --git a/source/Generating/ComposableGenerator.h b/src/Generating/ComposableGenerator.h
index d5e33a439..d5e33a439 100644
--- a/source/Generating/ComposableGenerator.h
+++ b/src/Generating/ComposableGenerator.h
diff --git a/source/Generating/DistortedHeightmap.h b/src/Generating/DistortedHeightmap.h
index 6d7007375..6d7007375 100644
--- a/source/Generating/DistortedHeightmap.h
+++ b/src/Generating/DistortedHeightmap.h
diff --git a/source/Generating/EndGen.h b/src/Generating/EndGen.h
index 4904a0e3d..4904a0e3d 100644
--- a/source/Generating/EndGen.h
+++ b/src/Generating/EndGen.h
diff --git a/source/Generating/FinishGen.cpp b/src/Generating/FinishGen.cpp
index 8899e4bd0..8899e4bd0 100644
--- a/source/Generating/FinishGen.cpp
+++ b/src/Generating/FinishGen.cpp
diff --git a/source/Generating/FinishGen.h b/src/Generating/FinishGen.h
index ed7df5909..ed7df5909 100644
--- a/source/Generating/FinishGen.h
+++ b/src/Generating/FinishGen.h
diff --git a/source/Generating/HeiGen.h b/src/Generating/HeiGen.h
index 1b246c70a..1b246c70a 100644
--- a/source/Generating/HeiGen.h
+++ b/src/Generating/HeiGen.h
diff --git a/source/Generating/MineShafts.cpp b/src/Generating/MineShafts.cpp
index f42240e55..f42240e55 100644
--- a/source/Generating/MineShafts.cpp
+++ b/src/Generating/MineShafts.cpp
diff --git a/source/Generating/MineShafts.h b/src/Generating/MineShafts.h
index c53d3bc53..c53d3bc53 100644
--- a/source/Generating/MineShafts.h
+++ b/src/Generating/MineShafts.h
diff --git a/source/Generating/Noise3DGenerator.h b/src/Generating/Noise3DGenerator.h
index 0d211cddc..0d211cddc 100644
--- a/source/Generating/Noise3DGenerator.h
+++ b/src/Generating/Noise3DGenerator.h
diff --git a/source/Generating/Ravines.cpp b/src/Generating/Ravines.cpp
index 6413b963b..6413b963b 100644
--- a/source/Generating/Ravines.cpp
+++ b/src/Generating/Ravines.cpp
diff --git a/source/Generating/Ravines.h b/src/Generating/Ravines.h
index 05164a5b2..05164a5b2 100644
--- a/source/Generating/Ravines.h
+++ b/src/Generating/Ravines.h
diff --git a/source/Generating/StructGen.cpp b/src/Generating/StructGen.cpp
index 2180261aa..2180261aa 100644
--- a/source/Generating/StructGen.cpp
+++ b/src/Generating/StructGen.cpp
diff --git a/source/Generating/StructGen.h b/src/Generating/StructGen.h
index 853748bb8..853748bb8 100644
--- a/source/Generating/StructGen.h
+++ b/src/Generating/StructGen.h
diff --git a/source/Generating/Trees.cpp b/src/Generating/Trees.cpp
index 7ca30c60f..7ca30c60f 100644
--- a/source/Generating/Trees.cpp
+++ b/src/Generating/Trees.cpp
diff --git a/source/Generating/Trees.h b/src/Generating/Trees.h
index f5148ad6f..f5148ad6f 100644
--- a/source/Generating/Trees.h
+++ b/src/Generating/Trees.h