/// <summary> /// /// </summary> /// <param name="count"></param> /// <returns></returns> protected Location pickPlace(int count) { while (count-- > 0) { Location loc = target.baseLocation; WorldDefinition w = WorldDefinition.World; int amp = F_PopAmpBase + (int)(Math.Pow(w[loc].LandPrice, F_PopAmpPower) * F_PopAmpScale); // then randomly pick nearby voxel loc.x = Rand(loc.x, amp); loc.y = Rand(loc.y, amp); loc.z = w.GetGroundLevel(loc); if (w.IsOutsideWorld(loc)) { continue; } if (loc.z < w.WaterLevel) { continue; // below water } Voxel v = w[loc]; if (v != null) { if (!IsReplaceable(v.Entity, v.LandPrice)) { continue; } } return(loc); } return(Location.Unplaced); }
/// <summary> /// Gets 4*height + mountain height. /// /// This method computes the height of the given location in fine scale. /// It returns -1 if the given location is out of the world. /// </summary> public static int getTotalHeight(Location loc, Direction d) { WorldDefinition w = WorldDefinition.World; if (w.IsOutsideWorld(loc)) { return(-1); } int z = w.GetGroundLevel(loc); MountainVoxel mv = MountainVoxel.get(new Location(loc.x, loc.y, z)); if (mv == null) { return(z * 4); } else { return(z * 4 + mv.getHeight(d)); } }
// clean it up by using MountainVoxel.isCornerMatched /// <summary> /// Return true iff the north-eastern corner of the given location /// can be raised by a quarter height unit. /// </summary> private bool canBeRaised(Location loc) { WorldDefinition w = WorldDefinition.World; if (!isFourAdjacentCornersMatched(loc)) { return(false); } Voxel baseVoxel = w[loc]; int glevel = w.GetGroundLevel(loc); if (loc.z != glevel) { return(false); //mountain can be placed only at the ground level } // true if this ground level is too close to the roof. bool nearRoof = (glevel == WorldDefinition.World.Size.z - 1); for (int x = 0; x <= 1; x++) { for (int y = -1; y <= 0; y++) { Location l = new Location(loc.x + x, loc.y + y, loc.z); Direction d = Direction.get(1 - x * 2, -y * 2 - 1); // corner to modify if (w.IsOutsideWorld(l)) { continue; // it's OK if it's beyond the border } Voxel v = w[l]; if (glevel != w.GetGroundLevel(l)) { return(false); // different ground level } if (v == null) { continue; // this voxel is unoccupied. } if (v is MountainVoxel) { int h = ((MountainVoxel)v).getHeight(d); if (h == 4) { return(false); // corner saturated. } if (nearRoof && h == 3) { return(false); // too close to the roof } continue; // otherwise OK } return(false); // occupied for another purpose } } if (WorldDefinition.World.IsOutsideWorld(loc)) { return(false); } return(true); }