001 package net.minecraft.src;
002
003 import java.util.Random;
004
005 public class BiomeDecorator
006 {
007 /** The world the BiomeDecorator is currently decorating */
008 protected World currentWorld;
009
010 /** The Biome Decorator's random number generator. */
011 protected Random randomGenerator;
012
013 /** The X-coordinate of the chunk currently being decorated */
014 protected int chunk_X;
015
016 /** The Z-coordinate of the chunk currently being decorated */
017 protected int chunk_Z;
018
019 /** The biome generator object. */
020 protected BiomeGenBase biome;
021
022 /** The clay generator. */
023 protected WorldGenerator clayGen = new WorldGenClay(4);
024
025 /** The sand generator. */
026 protected WorldGenerator sandGen;
027
028 /** The gravel generator. */
029 protected WorldGenerator gravelAsSandGen;
030
031 /** The dirt generator. */
032 protected WorldGenerator dirtGen;
033 protected WorldGenerator gravelGen;
034 protected WorldGenerator coalGen;
035 protected WorldGenerator ironGen;
036
037 /** Field that holds gold WorldGenMinable */
038 protected WorldGenerator goldGen;
039
040 /** Field that holds redstone WorldGenMinable */
041 protected WorldGenerator redstoneGen;
042
043 /** Field that holds diamond WorldGenMinable */
044 protected WorldGenerator diamondGen;
045
046 /** Field that holds Lapis WorldGenMinable */
047 protected WorldGenerator lapisGen;
048
049 /** Field that holds one of the plantYellow WorldGenFlowers */
050 protected WorldGenerator plantYellowGen;
051
052 /** Field that holds one of the plantRed WorldGenFlowers */
053 protected WorldGenerator plantRedGen;
054
055 /** Field that holds mushroomBrown WorldGenFlowers */
056 protected WorldGenerator mushroomBrownGen;
057
058 /** Field that holds mushroomRed WorldGenFlowers */
059 protected WorldGenerator mushroomRedGen;
060
061 /** Field that holds big mushroom generator */
062 protected WorldGenerator bigMushroomGen;
063
064 /** Field that holds WorldGenReed */
065 protected WorldGenerator reedGen;
066
067 /** Field that holds WorldGenCactus */
068 protected WorldGenerator cactusGen;
069
070 /** The water lily generation! */
071 protected WorldGenerator waterlilyGen;
072
073 /** Amount of waterlilys per chunk. */
074 protected int waterlilyPerChunk;
075
076 /**
077 * The number of trees to attempt to generate per chunk. Up to 10 in forests, none in deserts.
078 */
079 protected int treesPerChunk;
080
081 /**
082 * The number of yellow flower patches to generate per chunk. The game generates much less than this number, since
083 * it attempts to generate them at a random altitude.
084 */
085 protected int flowersPerChunk;
086
087 /** The amount of tall grass to generate per chunk. */
088 protected int grassPerChunk;
089
090 /**
091 * The number of dead bushes to generate per chunk. Used in deserts and swamps.
092 */
093 protected int deadBushPerChunk;
094
095 /**
096 * The number of extra mushroom patches per chunk. It generates 1/4 this number in brown mushroom patches, and 1/8
097 * this number in red mushroom patches. These mushrooms go beyond the default base number of mushrooms.
098 */
099 protected int mushroomsPerChunk;
100
101 /**
102 * The number of reeds to generate per chunk. Reeds won't generate if the randomly selected placement is unsuitable.
103 */
104 protected int reedsPerChunk;
105
106 /**
107 * The number of cactus plants to generate per chunk. Cacti only work on sand.
108 */
109 protected int cactiPerChunk;
110
111 /**
112 * The number of sand patches to generate per chunk. Sand patches only generate when part of it is underwater.
113 */
114 protected int sandPerChunk;
115
116 /**
117 * The number of sand patches to generate per chunk. Sand patches only generate when part of it is underwater. There
118 * appear to be two separate fields for this.
119 */
120 protected int sandPerChunk2;
121
122 /**
123 * The number of clay patches to generate per chunk. Only generates when part of it is underwater.
124 */
125 protected int clayPerChunk;
126
127 /** Amount of big mushrooms per chunk */
128 protected int bigMushroomsPerChunk;
129
130 /** True if decorator should generate surface lava & water */
131 public boolean generateLakes;
132
133 public BiomeDecorator(BiomeGenBase par1BiomeGenBase)
134 {
135 this.sandGen = new WorldGenSand(7, Block.sand.blockID);
136 this.gravelAsSandGen = new WorldGenSand(6, Block.gravel.blockID);
137 this.dirtGen = new WorldGenMinable(Block.dirt.blockID, 32);
138 this.gravelGen = new WorldGenMinable(Block.gravel.blockID, 32);
139 this.coalGen = new WorldGenMinable(Block.oreCoal.blockID, 16);
140 this.ironGen = new WorldGenMinable(Block.oreIron.blockID, 8);
141 this.goldGen = new WorldGenMinable(Block.oreGold.blockID, 8);
142 this.redstoneGen = new WorldGenMinable(Block.oreRedstone.blockID, 7);
143 this.diamondGen = new WorldGenMinable(Block.oreDiamond.blockID, 7);
144 this.lapisGen = new WorldGenMinable(Block.oreLapis.blockID, 6);
145 this.plantYellowGen = new WorldGenFlowers(Block.plantYellow.blockID);
146 this.plantRedGen = new WorldGenFlowers(Block.plantRed.blockID);
147 this.mushroomBrownGen = new WorldGenFlowers(Block.mushroomBrown.blockID);
148 this.mushroomRedGen = new WorldGenFlowers(Block.mushroomRed.blockID);
149 this.bigMushroomGen = new WorldGenBigMushroom();
150 this.reedGen = new WorldGenReed();
151 this.cactusGen = new WorldGenCactus();
152 this.waterlilyGen = new WorldGenWaterlily();
153 this.waterlilyPerChunk = 0;
154 this.treesPerChunk = 0;
155 this.flowersPerChunk = 2;
156 this.grassPerChunk = 1;
157 this.deadBushPerChunk = 0;
158 this.mushroomsPerChunk = 0;
159 this.reedsPerChunk = 0;
160 this.cactiPerChunk = 0;
161 this.sandPerChunk = 1;
162 this.sandPerChunk2 = 3;
163 this.clayPerChunk = 1;
164 this.bigMushroomsPerChunk = 0;
165 this.generateLakes = true;
166 this.biome = par1BiomeGenBase;
167 }
168
169 /**
170 * Decorates the world. Calls code that was formerly (pre-1.8) in ChunkProviderGenerate.populate
171 */
172 public void decorate(World par1World, Random par2Random, int par3, int par4)
173 {
174 if (this.currentWorld != null)
175 {
176 throw new RuntimeException("Already decorating!!");
177 }
178 else
179 {
180 this.currentWorld = par1World;
181 this.randomGenerator = par2Random;
182 this.chunk_X = par3;
183 this.chunk_Z = par4;
184 this.decorate();
185 this.currentWorld = null;
186 this.randomGenerator = null;
187 }
188 }
189
190 /**
191 * The method that does the work of actually decorating chunks
192 */
193 protected void decorate()
194 {
195 this.generateOres();
196 int var1;
197 int var2;
198 int var3;
199
200 for (var1 = 0; var1 < this.sandPerChunk2; ++var1)
201 {
202 var2 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
203 var3 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
204 this.sandGen.generate(this.currentWorld, this.randomGenerator, var2, this.currentWorld.getTopSolidOrLiquidBlock(var2, var3), var3);
205 }
206
207 for (var1 = 0; var1 < this.clayPerChunk; ++var1)
208 {
209 var2 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
210 var3 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
211 this.clayGen.generate(this.currentWorld, this.randomGenerator, var2, this.currentWorld.getTopSolidOrLiquidBlock(var2, var3), var3);
212 }
213
214 for (var1 = 0; var1 < this.sandPerChunk; ++var1)
215 {
216 var2 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
217 var3 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
218 this.sandGen.generate(this.currentWorld, this.randomGenerator, var2, this.currentWorld.getTopSolidOrLiquidBlock(var2, var3), var3);
219 }
220
221 var1 = this.treesPerChunk;
222
223 if (this.randomGenerator.nextInt(10) == 0)
224 {
225 ++var1;
226 }
227
228 int var4;
229
230 for (var2 = 0; var2 < var1; ++var2)
231 {
232 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
233 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
234 WorldGenerator var5 = this.biome.getRandomWorldGenForTrees(this.randomGenerator);
235 var5.setScale(1.0D, 1.0D, 1.0D);
236 var5.generate(this.currentWorld, this.randomGenerator, var3, this.currentWorld.getHeightValue(var3, var4), var4);
237 }
238
239 for (var2 = 0; var2 < this.bigMushroomsPerChunk; ++var2)
240 {
241 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
242 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
243 this.bigMushroomGen.generate(this.currentWorld, this.randomGenerator, var3, this.currentWorld.getHeightValue(var3, var4), var4);
244 }
245
246 int var7;
247
248 for (var2 = 0; var2 < this.flowersPerChunk; ++var2)
249 {
250 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
251 var4 = this.randomGenerator.nextInt(128);
252 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
253 this.plantYellowGen.generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
254
255 if (this.randomGenerator.nextInt(4) == 0)
256 {
257 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
258 var4 = this.randomGenerator.nextInt(128);
259 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
260 this.plantRedGen.generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
261 }
262 }
263
264 for (var2 = 0; var2 < this.grassPerChunk; ++var2)
265 {
266 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
267 var4 = this.randomGenerator.nextInt(128);
268 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
269 WorldGenerator var6 = this.biome.getRandomWorldGenForGrass(this.randomGenerator);
270 var6.generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
271 }
272
273 for (var2 = 0; var2 < this.deadBushPerChunk; ++var2)
274 {
275 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
276 var4 = this.randomGenerator.nextInt(128);
277 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
278 (new WorldGenDeadBush(Block.deadBush.blockID)).generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
279 }
280
281 for (var2 = 0; var2 < this.waterlilyPerChunk; ++var2)
282 {
283 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
284 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
285
286 for (var7 = this.randomGenerator.nextInt(128); var7 > 0 && this.currentWorld.getBlockId(var3, var7 - 1, var4) == 0; --var7)
287 {
288 ;
289 }
290
291 this.waterlilyGen.generate(this.currentWorld, this.randomGenerator, var3, var7, var4);
292 }
293
294 for (var2 = 0; var2 < this.mushroomsPerChunk; ++var2)
295 {
296 if (this.randomGenerator.nextInt(4) == 0)
297 {
298 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
299 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
300 var7 = this.currentWorld.getHeightValue(var3, var4);
301 this.mushroomBrownGen.generate(this.currentWorld, this.randomGenerator, var3, var7, var4);
302 }
303
304 if (this.randomGenerator.nextInt(8) == 0)
305 {
306 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
307 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
308 var7 = this.randomGenerator.nextInt(128);
309 this.mushroomRedGen.generate(this.currentWorld, this.randomGenerator, var3, var7, var4);
310 }
311 }
312
313 if (this.randomGenerator.nextInt(4) == 0)
314 {
315 var2 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
316 var3 = this.randomGenerator.nextInt(128);
317 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
318 this.mushroomBrownGen.generate(this.currentWorld, this.randomGenerator, var2, var3, var4);
319 }
320
321 if (this.randomGenerator.nextInt(8) == 0)
322 {
323 var2 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
324 var3 = this.randomGenerator.nextInt(128);
325 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
326 this.mushroomRedGen.generate(this.currentWorld, this.randomGenerator, var2, var3, var4);
327 }
328
329 for (var2 = 0; var2 < this.reedsPerChunk; ++var2)
330 {
331 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
332 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
333 var7 = this.randomGenerator.nextInt(128);
334 this.reedGen.generate(this.currentWorld, this.randomGenerator, var3, var7, var4);
335 }
336
337 for (var2 = 0; var2 < 10; ++var2)
338 {
339 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
340 var4 = this.randomGenerator.nextInt(128);
341 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
342 this.reedGen.generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
343 }
344
345 if (this.randomGenerator.nextInt(32) == 0)
346 {
347 var2 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
348 var3 = this.randomGenerator.nextInt(128);
349 var4 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
350 (new WorldGenPumpkin()).generate(this.currentWorld, this.randomGenerator, var2, var3, var4);
351 }
352
353 for (var2 = 0; var2 < this.cactiPerChunk; ++var2)
354 {
355 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
356 var4 = this.randomGenerator.nextInt(128);
357 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
358 this.cactusGen.generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
359 }
360
361 if (this.generateLakes)
362 {
363 for (var2 = 0; var2 < 50; ++var2)
364 {
365 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
366 var4 = this.randomGenerator.nextInt(this.randomGenerator.nextInt(120) + 8);
367 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
368 (new WorldGenLiquids(Block.waterMoving.blockID)).generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
369 }
370
371 for (var2 = 0; var2 < 20; ++var2)
372 {
373 var3 = this.chunk_X + this.randomGenerator.nextInt(16) + 8;
374 var4 = this.randomGenerator.nextInt(this.randomGenerator.nextInt(this.randomGenerator.nextInt(112) + 8) + 8);
375 var7 = this.chunk_Z + this.randomGenerator.nextInt(16) + 8;
376 (new WorldGenLiquids(Block.lavaMoving.blockID)).generate(this.currentWorld, this.randomGenerator, var3, var4, var7);
377 }
378 }
379 }
380
381 /**
382 * Standard ore generation helper. Generates most ores.
383 */
384 protected void genStandardOre1(int par1, WorldGenerator par2WorldGenerator, int par3, int par4)
385 {
386 for (int var5 = 0; var5 < par1; ++var5)
387 {
388 int var6 = this.chunk_X + this.randomGenerator.nextInt(16);
389 int var7 = this.randomGenerator.nextInt(par4 - par3) + par3;
390 int var8 = this.chunk_Z + this.randomGenerator.nextInt(16);
391 par2WorldGenerator.generate(this.currentWorld, this.randomGenerator, var6, var7, var8);
392 }
393 }
394
395 /**
396 * Standard ore generation helper. Generates Lapis Lazuli.
397 */
398 protected void genStandardOre2(int par1, WorldGenerator par2WorldGenerator, int par3, int par4)
399 {
400 for (int var5 = 0; var5 < par1; ++var5)
401 {
402 int var6 = this.chunk_X + this.randomGenerator.nextInt(16);
403 int var7 = this.randomGenerator.nextInt(par4) + this.randomGenerator.nextInt(par4) + (par3 - par4);
404 int var8 = this.chunk_Z + this.randomGenerator.nextInt(16);
405 par2WorldGenerator.generate(this.currentWorld, this.randomGenerator, var6, var7, var8);
406 }
407 }
408
409 /**
410 * Generates ores in the current chunk
411 */
412 protected void generateOres()
413 {
414 this.genStandardOre1(20, this.dirtGen, 0, 128);
415 this.genStandardOre1(10, this.gravelGen, 0, 128);
416 this.genStandardOre1(20, this.coalGen, 0, 128);
417 this.genStandardOre1(20, this.ironGen, 0, 64);
418 this.genStandardOre1(2, this.goldGen, 0, 32);
419 this.genStandardOre1(8, this.redstoneGen, 0, 16);
420 this.genStandardOre1(1, this.diamondGen, 0, 16);
421 this.genStandardOre2(1, this.lapisGen, 16, 16);
422 }
423 }