public FileToVoxCore.Drawing.Color GetVegetation(BiomeSettings biome, float random) { float acumProb = 0; int index = 0; for (int t = 0; t < biome.Vegetation.Length; t++) { acumProb += biome.Vegetation[t].Probability; if (random < acumProb) { index = t; break; } } return(biome.Vegetation[index].Color); }
public void PaintChunk(VoxelChunk chunk) { Vector3 position = chunk.Position; if (position.Y + TerrainEnvironment.CHUNK_HALF_SIZE < MinHeight) { return; } int bedrockRow = -1; if (position.Y < MinHeight + TerrainEnvironment.CHUNK_HALF_SIZE) { bedrockRow = (int)(MinHeight - (position.Y - TerrainEnvironment.CHUNK_HALF_SIZE) + 1) * ONE_Y_ROW - 1; } position.X -= TerrainEnvironment.CHUNK_HALF_SIZE; position.Y -= TerrainEnvironment.CHUNK_HALF_SIZE; position.Z -= TerrainEnvironment.CHUNK_HALF_SIZE; Vector3 pos = new Vector3(); int waterLevel = WaterLevel > 0 ? WaterLevel : -1; Voxel[] voxels = chunk.Voxels; mGeneration++; TerrainEnvironment.Instance.GetHeightMapInfo(position.X, position.Z, mHeightChunkData); int shiftAmount = (int)MathF.Log(TerrainEnvironment.CHUNK_SIZE, 2); for (int arrayIndex = 0; arrayIndex < TerrainEnvironment.CHUNK_SIZE * TerrainEnvironment.CHUNK_SIZE; arrayIndex++) { float groundLevel = mHeightChunkData[arrayIndex].GroundLevel; float surfaceLevel = waterLevel > groundLevel ? waterLevel : groundLevel; if (surfaceLevel < pos.Y) { continue; } BiomeSettings biome = mHeightChunkData[arrayIndex].Biome; if (biome == null) { biome = TerrainEnvironment.Instance.WorldTerrainData.DefaultBiome; if (biome == null) { continue; } } int y = (int)(surfaceLevel - position.Y); if (y >= TerrainEnvironment.CHUNK_SIZE) { y = TerrainEnvironment.CHUNK_SIZE - 1; } pos.Y = position.Y + y; pos.X = position.X + (arrayIndex & (TerrainEnvironment.CHUNK_SIZE - 1)); pos.Z = position.Z + (arrayIndex >> shiftAmount); int voxelIndex = y * ONE_Y_ROW + arrayIndex; if (voxelIndex < 0) { continue; } if (pos.Y > groundLevel) { while (pos.Y > groundLevel && voxelIndex >= 0) { voxels[voxelIndex].Color = WaterColor.ColorToUInt(); voxelIndex -= ONE_Y_ROW; pos.Y--; } } else if (pos.Y == groundLevel) { voxels[voxelIndex].Color = 0; if (voxels[voxelIndex].Color == 0) { if (pos.Y == waterLevel) { voxels[voxelIndex].Color = ShoreColor.ColorToUInt(); } else { //float moisture = mHeightChunkData[arrayIndex].Moisture; //Color colorTop = biome.VoxelTop; //Color newColor = Color.FromArgb((int) (colorTop.R * moisture), (int)(colorTop.G * moisture), (int)(colorTop.B * moisture)); //voxels[voxelIndex].Color = newColor.ColorToUInt(); voxels[voxelIndex].Color = biome.VoxelTop.ColorToUInt(); if (pos.Y > waterLevel) { float rdn = WorldRandom.GetValue(pos); if (biome.TreeDensity > 0 && rdn < biome.TreeDensity && biome.Trees.Length > 0) { TerrainEnvironment.Instance.RequestTreeCreation(chunk, pos, TerrainEnvironment.Instance.GetTree(biome.Trees, rdn / biome.TreeDensity)); } else if (biome.VegetationDensity > 0 && rdn < biome.VegetationDensity && biome.Vegetation.Length > 0) { if (voxelIndex >= (TerrainEnvironment.CHUNK_SIZE - 1) * ONE_Y_ROW) { TerrainEnvironment.Instance.RequestVegetationCreation(chunk.Top, voxelIndex - ONE_Y_ROW * (TerrainEnvironment.CHUNK_SIZE - 1), TerrainEnvironment.Instance.GetVegetation(biome, rdn / biome.VegetationDensity)); } else { voxels[voxelIndex + ONE_Y_ROW].Color = TerrainEnvironment.Instance.GetVegetation(biome, rdn / biome.VegetationDensity).ColorToUInt(); } } } } voxelIndex -= ONE_Y_ROW; pos.Y--; } } biome.BiomeGeneration = mGeneration; while (voxelIndex >= 0 && voxels[voxelIndex].Color == 0 && pos.Y <= waterLevel) { voxels[voxelIndex].Color = WaterColor.ColorToUInt(); voxelIndex -= ONE_Y_ROW; pos.Y--; } for (; voxelIndex > bedrockRow; voxelIndex -= ONE_Y_ROW, pos.Y--) { if (voxels[voxelIndex].Color == 0) { voxels[voxelIndex].Color = biome.VoxelDirt.ColorToUInt(); } else if (voxels[voxelIndex].Color == 0 && pos.Y <= waterLevel) { // hole under water level -> fill with water voxels[voxelIndex].Color = WaterColor.ColorToUInt(); } } if (bedrockRow >= 0 && voxelIndex >= 0) { voxels[voxelIndex].Color = BedrockColor.ColorToUInt(); } } }