001 package net.minecraft.src; 002 003 import java.util.List; 004 import java.util.Random; 005 006 public abstract class ComponentVillage extends StructureComponent 007 { 008 /** The number of villagers that have been spawned in this component. */ 009 private int villagersSpawned; 010 011 /** The starting piece of the village. */ 012 protected ComponentVillageStartPiece startPiece; 013 014 protected ComponentVillage(ComponentVillageStartPiece par1ComponentVillageStartPiece, int par2) 015 { 016 super(par2); 017 this.startPiece = par1ComponentVillageStartPiece; 018 } 019 020 /** 021 * Gets the next village component, with the bounding box shifted -1 in the X and Z direction. 022 */ 023 protected StructureComponent getNextComponentNN(ComponentVillageStartPiece par1ComponentVillageStartPiece, List par2List, Random par3Random, int par4, int par5) 024 { 025 switch (this.coordBaseMode) 026 { 027 case 0: 028 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.minX - 1, this.boundingBox.minY + par4, this.boundingBox.minZ + par5, 1, this.getComponentType()); 029 case 1: 030 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.minX + par5, this.boundingBox.minY + par4, this.boundingBox.minZ - 1, 2, this.getComponentType()); 031 case 2: 032 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.minX - 1, this.boundingBox.minY + par4, this.boundingBox.minZ + par5, 1, this.getComponentType()); 033 case 3: 034 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.minX + par5, this.boundingBox.minY + par4, this.boundingBox.minZ - 1, 2, this.getComponentType()); 035 default: 036 return null; 037 } 038 } 039 040 /** 041 * Gets the next village component, with the bounding box shifted +1 in the X and Z direction. 042 */ 043 protected StructureComponent getNextComponentPP(ComponentVillageStartPiece par1ComponentVillageStartPiece, List par2List, Random par3Random, int par4, int par5) 044 { 045 switch (this.coordBaseMode) 046 { 047 case 0: 048 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.maxX + 1, this.boundingBox.minY + par4, this.boundingBox.minZ + par5, 3, this.getComponentType()); 049 case 1: 050 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.minX + par5, this.boundingBox.minY + par4, this.boundingBox.maxZ + 1, 0, this.getComponentType()); 051 case 2: 052 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.maxX + 1, this.boundingBox.minY + par4, this.boundingBox.minZ + par5, 3, this.getComponentType()); 053 case 3: 054 return StructureVillagePieces.getNextStructureComponent(par1ComponentVillageStartPiece, par2List, par3Random, this.boundingBox.minX + par5, this.boundingBox.minY + par4, this.boundingBox.maxZ + 1, 0, this.getComponentType()); 055 default: 056 return null; 057 } 058 } 059 060 /** 061 * Discover the y coordinate that will serve as the ground level of the supplied BoundingBox. (A median of all the 062 * levels in the BB's horizontal rectangle). 063 */ 064 protected int getAverageGroundLevel(World par1World, StructureBoundingBox par2StructureBoundingBox) 065 { 066 int var3 = 0; 067 int var4 = 0; 068 069 for (int var5 = this.boundingBox.minZ; var5 <= this.boundingBox.maxZ; ++var5) 070 { 071 for (int var6 = this.boundingBox.minX; var6 <= this.boundingBox.maxX; ++var6) 072 { 073 if (par2StructureBoundingBox.isVecInside(var6, 64, var5)) 074 { 075 var3 += Math.max(par1World.getTopSolidOrLiquidBlock(var6, var5), par1World.provider.getAverageGroundLevel()); 076 ++var4; 077 } 078 } 079 } 080 081 if (var4 == 0) 082 { 083 return -1; 084 } 085 else 086 { 087 return var3 / var4; 088 } 089 } 090 091 protected static boolean canVillageGoDeeper(StructureBoundingBox par0StructureBoundingBox) 092 { 093 return par0StructureBoundingBox != null && par0StructureBoundingBox.minY > 10; 094 } 095 096 /** 097 * Spawns a number of villagers in this component. Parameters: world, component bounding box, x offset, y offset, z 098 * offset, number of villagers 099 */ 100 protected void spawnVillagers(World par1World, StructureBoundingBox par2StructureBoundingBox, int par3, int par4, int par5, int par6) 101 { 102 if (this.villagersSpawned < par6) 103 { 104 for (int var7 = this.villagersSpawned; var7 < par6; ++var7) 105 { 106 int var8 = this.getXWithOffset(par3 + var7, par5); 107 int var9 = this.getYWithOffset(par4); 108 int var10 = this.getZWithOffset(par3 + var7, par5); 109 110 if (!par2StructureBoundingBox.isVecInside(var8, var9, var10)) 111 { 112 break; 113 } 114 115 ++this.villagersSpawned; 116 EntityVillager var11 = new EntityVillager(par1World, this.getVillagerType(var7)); 117 var11.setLocationAndAngles((double)var8 + 0.5D, (double)var9, (double)var10 + 0.5D, 0.0F, 0.0F); 118 par1World.spawnEntityInWorld(var11); 119 } 120 } 121 } 122 123 /** 124 * Returns the villager type to spawn in this component, based on the number of villagers already spawned. 125 */ 126 protected int getVillagerType(int par1) 127 { 128 return 0; 129 } 130 131 /** 132 * Gets the replacement block for the current biome 133 */ 134 protected int getBiomeSpecificBlock(int par1, int par2) 135 { 136 if (this.startPiece.inDesert) 137 { 138 if (par1 == Block.wood.blockID) 139 { 140 return Block.sandStone.blockID; 141 } 142 143 if (par1 == Block.cobblestone.blockID) 144 { 145 return Block.sandStone.blockID; 146 } 147 148 if (par1 == Block.planks.blockID) 149 { 150 return Block.sandStone.blockID; 151 } 152 153 if (par1 == Block.stairCompactPlanks.blockID) 154 { 155 return Block.stairsSandStone.blockID; 156 } 157 158 if (par1 == Block.stairCompactCobblestone.blockID) 159 { 160 return Block.stairsSandStone.blockID; 161 } 162 163 if (par1 == Block.gravel.blockID) 164 { 165 return Block.sandStone.blockID; 166 } 167 } 168 169 return par1; 170 } 171 172 /** 173 * Gets the replacement block metadata for the current biome 174 */ 175 protected int getBiomeSpecificBlockMetadata(int par1, int par2) 176 { 177 if (this.startPiece.inDesert) 178 { 179 if (par1 == Block.wood.blockID) 180 { 181 return 0; 182 } 183 184 if (par1 == Block.cobblestone.blockID) 185 { 186 return 0; 187 } 188 189 if (par1 == Block.planks.blockID) 190 { 191 return 2; 192 } 193 } 194 195 return par2; 196 } 197 198 /** 199 * current Position depends on currently set Coordinates mode, is computed here 200 */ 201 protected void placeBlockAtCurrentPosition(World par1World, int par2, int par3, int par4, int par5, int par6, StructureBoundingBox par7StructureBoundingBox) 202 { 203 int var8 = this.getBiomeSpecificBlock(par2, par3); 204 int var9 = this.getBiomeSpecificBlockMetadata(par2, par3); 205 super.placeBlockAtCurrentPosition(par1World, var8, var9, par4, par5, par6, par7StructureBoundingBox); 206 } 207 208 /** 209 * arguments: (World worldObj, StructureBoundingBox structBB, int minX, int minY, int minZ, int maxX, int maxY, int 210 * maxZ, int placeBlockId, int replaceBlockId, boolean alwaysreplace) 211 */ 212 protected void fillWithBlocks(World par1World, StructureBoundingBox par2StructureBoundingBox, int par3, int par4, int par5, int par6, int par7, int par8, int par9, int par10, boolean par11) 213 { 214 int var12 = this.getBiomeSpecificBlock(par9, 0); 215 int var13 = this.getBiomeSpecificBlockMetadata(par9, 0); 216 int var14 = this.getBiomeSpecificBlock(par10, 0); 217 int var15 = this.getBiomeSpecificBlockMetadata(par10, 0); 218 super.fillWithMetadataBlocks(par1World, par2StructureBoundingBox, par3, par4, par5, par6, par7, par8, var12, var13, var14, var15, par11); 219 } 220 221 /** 222 * Overwrites air and liquids from selected position downwards, stops at hitting anything else. 223 */ 224 protected void fillCurrentPositionBlocksDownwards(World par1World, int par2, int par3, int par4, int par5, int par6, StructureBoundingBox par7StructureBoundingBox) 225 { 226 int var8 = this.getBiomeSpecificBlock(par2, par3); 227 int var9 = this.getBiomeSpecificBlockMetadata(par2, par3); 228 super.fillCurrentPositionBlocksDownwards(par1World, var8, var9, par4, par5, par6, par7StructureBoundingBox); 229 } 230 }