private void AddBeaches([NotNull] Map map) { if (map == null) { throw new ArgumentNullException("map"); } int beachExtentSqr = (args.BeachExtent + 1) * (args.BeachExtent + 1); for (int x = 0; x < map.Width; x++) { for (int y = 0; y < map.Length; y++) { for (int z = args.WaterLevel; z <= args.WaterLevel + args.BeachHeight; z++) { if (map.GetBlock(x, y, z) != bGroundSurface) { continue; } bool found = false; for (int dx = -args.BeachExtent; !found && dx <= args.BeachExtent; dx++) { for (int dy = -args.BeachExtent; !found && dy <= args.BeachExtent; dy++) { for (int dz = -args.BeachHeight; dz <= 0; dz++) { if (dx * dx + dy * dy + dz * dz > beachExtentSqr) { continue; } int xx = x + dx; int yy = y + dy; int zz = z + dz; if (xx < 0 || xx >= map.Width || yy < 0 || yy >= map.Length || zz < 0 || zz >= map.Height) { continue; } Block block = map.GetBlock(xx, yy, zz); if (block == bWater || block == bWaterSurface) { found = true; break; } } } } if (found) { map.SetBlock(x, y, z, bSeaFloor); if (z > 0 && map.GetBlock(x, y, z - 1) == bGround) { map.SetBlock(x, y, z - 1, bSeaFloor); } } } } } }
void AddBeaches(Map map) { int beachExtentSqr = (args.BeachExtent + 1) * (args.BeachExtent + 1); for (int x = 0; x < map.WidthX; x++) { for (int y = 0; y < map.WidthY; y++) { for (int h = args.WaterLevel; h <= args.WaterLevel + args.BeachHeight; h++) { if (map.GetBlock(x, y, h) != bGroundSurface) { continue; } bool found = false; for (int dx = -args.BeachExtent; !found && dx <= args.BeachExtent; dx++) { for (int dy = -args.BeachExtent; !found && dy <= args.BeachExtent; dy++) { for (int dh = -args.BeachHeight; dh <= 0; dh++) { if (dx * dx + dy * dy + dh * dh > beachExtentSqr) { continue; } int xx = x + dx; int yy = y + dy; int hh = h + dh; if (xx < 0 || xx >= map.WidthX || yy < 0 || yy >= map.WidthY || hh < 0 || hh >= map.Height) { continue; } Block block = map.GetBlock(xx, yy, hh); if (block == bWater || block == bWaterSurface) { found = true; break; } } } } if (found) { map.SetBlock(x, y, h, bSeaFloor); if (h > 0 && map.GetBlock(x, y, h - 1) == bGround) { map.SetBlock(x, y, h - 1, bSeaFloor); } } } } } }
static void CopyCallback([NotNull] Player player, [NotNull] Vector3I[] marks, [NotNull] object tag) { int sx = Math.Min(marks[0].X, marks[1].X); int ex = Math.Max(marks[0].X, marks[1].X); int sy = Math.Min(marks[0].Y, marks[1].Y); int ey = Math.Max(marks[0].Y, marks[1].Y); int sz = Math.Min(marks[0].Z, marks[1].Z); int ez = Math.Max(marks[0].Z, marks[1].Z); BoundingBox bounds = new BoundingBox(sx, sy, sz, ex, ey, ez); int volume = bounds.Volume; if (!player.CanDraw(volume)) { player.MessageNow( "You are only allowed to run commands that affect up to {0} blocks. This one would affect {1} blocks.", player.Info.Rank.DrawLimit, volume); return; } // remember dimensions and orientation CopyState copyInfo = new CopyState(marks[0], marks[1]); Map map = player.WorldMap; World playerWorld = player.World; if (playerWorld == null) { PlayerOpException.ThrowNoWorld(player); } for (int x = sx; x <= ex; x++) { for (int y = sy; y <= ey; y++) { for (int z = sz; z <= ez; z++) { copyInfo.Blocks[x - sx, y - sy, z - sz] = map.GetBlock(x, y, z); } } } copyInfo.OriginWorld = playerWorld.Name; copyInfo.CopyTime = DateTime.UtcNow; player.SetCopyState(copyInfo); player.MessageNow("{0} blocks copied into slot #{1}, origin at {2} corner. You can now &H/Paste", volume, player.CopySlot + 1, copyInfo.OriginCorner); Logger.Log(LogType.UserActivity, "{0} copied {1} blocks from world {2} (between {3} and {4}).", player.Name, volume, playerWorld.Name, bounds.MinVertex, bounds.MaxVertex); }
private static void SealLiquids(Map map, byte sealantType) { for (int x = 1; x < map.Width - 1; x++) { for (int z = 1; z < map.Height; z++) { for (int y = 1; y < map.Length - 1; y++) { int index = map.Index(x, y, z); if ((map.Blocks[index] == 10 || map.Blocks[index] == 11 || map.Blocks[index] == 8 || map.Blocks[index] == 9) && (map.GetBlock(x - 1, y, z) == Block.Air || map.GetBlock(x + 1, y, z) == Block.Air || map.GetBlock(x, y - 1, z) == Block.Air || map.GetBlock(x, y + 1, z) == Block.Air || map.GetBlock(x, y, z - 1) == Block.Air)) { map.Blocks[index] = sealantType; } } } } }
static void SealLiquids(Map map, byte sealantType) { for (int x = 1; x < map.WidthX - 1; x++) { for (int h = 1; h < map.Height; h++) { for (int y = 1; y < map.WidthY - 1; y++) { int index = map.Index(x, y, h); if ((map.Blocks[index] == 10 || map.Blocks[index] == 11 || map.Blocks[index] == 8 || map.Blocks[index] == 9) && (map.GetBlock(x - 1, y, h) == Block.Air || map.GetBlock(x + 1, y, h) == Block.Air || map.GetBlock(x, y - 1, h) == Block.Air || map.GetBlock(x, y + 1, h) == Block.Air || map.GetBlock(x, y, h - 1) == Block.Air)) { map.Blocks[index] = sealantType; } } } } }
private static void SetUpMines() { for (short i = 0; i <= _map.Width; ++i) { for (short j = 0; j <= _map.Length; ++j) { if (_map.GetBlock(i, j, _ground) != Block.Red && _map.GetBlock(i, j, _ground) != Block.Green && _map.GetBlock(i, j, _ground) != Block.Water) { _map.SetBlock(i, j, _ground, Block.Dirt); _map.SetBlock(i, j, _ground - 1, Block.Dirt); if (_rand.Next(1, 100) > 96) { Vector3I vec = new Vector3I(i, j, _ground); Mines.TryAdd(vec.ToString(), vec); //_map.SetBlock(vec, Block.Red);// } } } } }
public static bool CanPlacePortal(short x, short y, short z, Map map) { var count = 0; var Z = z; for (; Z < z + 2; Z++) { var check = map.GetBlock(x, y, Z); if (check != Block.Air && check != Block.Water && check != Block.Lava) { count++; } } return(count == 2); }
private static void DrawOneBlock(Player player, Map map, Block drawBlock, Vector3I coord, BlockChangeContext context, ref int blocks, ref int blocksDenied, fCraft.Drawing.UndoState undoState) { if (map == null) { return; } if (player == null) { throw new ArgumentNullException("player"); } if (!map.InBounds(coord)) { return; } Block block = map.GetBlock(coord); if (block == drawBlock) { return; } if (player.CanPlace(map, coord, drawBlock, context) != CanPlaceResult.Allowed) { blocksDenied++; return; } map.QueueUpdate(new BlockUpdate(null, coord, drawBlock)); Player.RaisePlayerPlacedBlockEvent(player, map, coord, block, drawBlock, context); if (!undoState.IsTooLargeToUndo) { if (!undoState.Add(coord, block)) { player.Message("NOTE: This draw command is too massive to undo."); player.LastDrawOp = null; } } blocks++; }
public static bool CanPlacePortal(short x, short y, short z, Map map) { int Count = 0; for (short Z = z; Z < z + 2; Z++) { Block check = map.GetBlock(x, y, Z); if (check != Block.Air && check != Block.Water && check != Block.Lava) { Count++; } } if (Count == 2) { return(true); } else { return(false); } }
static int DistanceToBlock(Map map, Vector3F coord, Vector3F vec, Block blockType, bool invert) { coord += HalfBlock; int iterations = 0; while (map.InBounds(new Vector3I(coord))) { Block blockAtPos = map.GetBlock(new Vector3I(coord)); if ((blockAtPos == blockType && !invert) || (blockAtPos != blockType && invert)) { break; } else { coord += vec; iterations++; } } return(iterations); }
public static bool CanPlacePortal(short x, short y, short z, Map map) { int Count = 0; for (short Z = z; Z < z + 2; Z++) { Block check = map.GetBlock(x, y, Z); if (check != Block.Air && check != Block.Water && check != Block.Lava) { Count++; } } if (Count == 2) { return true; } else { return false; } }
//stolen from BuildingCommands #region DrawOneBlock static void DrawOneBlock ( Player player, Map map, Block drawBlock, Vector3I coord, BlockChangeContext context, ref int blocks, ref int blocksDenied, fCraft.Drawing.UndoState undoState ) { if ( map == null ) return; if ( player == null ) throw new ArgumentNullException( "player" ); if ( !map.InBounds( coord ) ) return; Block block = map.GetBlock( coord ); if ( block == drawBlock ) return; if ( player.CanPlace( map, coord, drawBlock, context ) != CanPlaceResult.Allowed ) { blocksDenied++; return; } map.QueueUpdate( new BlockUpdate( null, coord, drawBlock ) ); Player.RaisePlayerPlacedBlockEvent( player, map, coord, block, drawBlock, context ); if ( !undoState.IsTooLargeToUndo ) { if ( !undoState.Add( coord, block ) ) { player.Message( "NOTE: This draw command is too massive to undo." ); player.LastDrawOp = null; } } blocks++; }
private void GenerateTrees([NotNull] Map map) { if (map == null) { throw new ArgumentNullException("map"); } int minHeight = args.TreeHeightMin; int maxHeight = args.TreeHeightMax; int minTrunkPadding = args.TreeSpacingMin; int maxTrunkPadding = args.TreeSpacingMax; const int topLayers = 2; const double odds = 0.618; Random rn = new Random(); map.CalculateShadows(); for (int x = 0; x < map.Width; x += rn.Next(minTrunkPadding, maxTrunkPadding + 1)) { for (int y = 0; y < map.Length; y += rn.Next(minTrunkPadding, maxTrunkPadding + 1)) { int nx = x + rn.Next(-(minTrunkPadding / 2), (maxTrunkPadding / 2) + 1); int ny = y + rn.Next(-(minTrunkPadding / 2), (maxTrunkPadding / 2) + 1); if (nx < 0 || nx >= map.Width || ny < 0 || ny >= map.Length) { continue; } int nz = map.Shadows[nx, ny]; if ((map.GetBlock(nx, ny, nz) == bGroundSurface) && slopemap[nx, ny] < .5) { // Pick a random height for the tree between Min and Max, // discarding this tree if it would breach the top of the map int nh; if ((nh = rn.Next(minHeight, maxHeight + 1)) + nz + nh / 2 > map.Height) { continue; } // Generate the trunk of the tree for (int z = 1; z <= nh; z++) { map.SetBlock(nx, ny, nz + z, Block.Log); } for (int i = -1; i < nh / 2; i++) { // Should we draw thin (2x2) or thicker (4x4) foliage int radius = (i >= (nh / 2) - topLayers) ? 1 : 2; // Draw the foliage for (int xoff = -radius; xoff < radius + 1; xoff++) { for (int yoff = -radius; yoff < radius + 1; yoff++) { // Drop random leaves from the edges if (rn.NextDouble() > odds && Math.Abs(xoff) == Math.Abs(yoff) && Math.Abs(xoff) == radius) { continue; } // By default only replace an existing block if its air if (map.GetBlock(nx + xoff, ny + yoff, nz + nh + i) == Block.Air) { map.SetBlock(nx + xoff, ny + yoff, nz + nh + i, Block.Leaves); } } } } } } } }
static void SealLiquids(Map map, byte sealantType) { for (int x = 1; x < map.Width - 1; x++) { for (int z = 1; z < map.Height; z++) { for (int y = 1; y < map.Length - 1; y++) { int index = map.Index(x, y, z); if ((map.Blocks[index] == 10 || map.Blocks[index] == 11 || map.Blocks[index] == 8 || map.Blocks[index] == 9) && (map.GetBlock(x - 1, y, z) == Block.Air || map.GetBlock(x + 1, y, z) == Block.Air || map.GetBlock(x, y - 1, z) == Block.Air || map.GetBlock(x, y + 1, z) == Block.Air || map.GetBlock(x, y, z - 1) == Block.Air)) { map.Blocks[index] = sealantType; } } } } }
static int DistanceToBlock( Map map, Vector3F coord, Vector3F vec, Block blockType, bool invert ) { coord += HalfBlock; int iterations = 0; while( map.InBounds( new Vector3I( coord ) ) ) { Block blockAtPos = map.GetBlock( new Vector3I( coord ) ); if( (blockAtPos == blockType && !invert) || (blockAtPos != blockType && invert) ) { break; } else { coord += vec; iterations++; } } return iterations; }
// Plant a single tree - Based on Minecraft Classic's "com.mojang.minecraft.level.maybeGrowTree" void GrowTree(Random treeRand, int startX, int startY, int startZ) { int treeHeight = treeRand.Next(3) + 4; Block blockUnder = map.GetBlock(startX, startY, startZ - 1); if ((blockUnder != Block.Grass) || (startZ >= map.Height - treeHeight - 1)) { return; } for (int z = startZ; z <= startZ + 1 + treeHeight; z++) { int extent = 1; if (z == startZ) { extent = 0; } if (z >= startZ + 1 + treeHeight - 2) { extent = 2; } for (int x = startX - extent; (x <= startX + extent); x++) { for (int y = startY - extent; (y <= startY + extent); y++) { if ((x >= 0) && (z >= 0) && (y >= 0) && (x < map.Width) && (z < map.Height) && (y < map.Length)) { if (map.GetBlock(x, y, z) != Block.Air) { return; } } else { return; } } } } map.SetBlock(startX, startY, startZ - 1, Block.Dirt); for (int z = startZ - 3 + treeHeight; z <= startZ + treeHeight; z++) { int n = z - (startZ + treeHeight); int foliageExtent = 1 - n / 2; for (int x = startX - foliageExtent; x <= startX + foliageExtent; x++) { int j = x - startX; for (int y = startY - foliageExtent; y <= startY + foliageExtent; y++) { int i3 = y - startY; if ((Math.Abs(j) == foliageExtent) && (Math.Abs(i3) == foliageExtent) && ((treeRand.Next(2) == 0) || (n == 0))) { continue; } map.SetBlock(x, y, z, Block.Leaves); } } } for (int z = 0; z < treeHeight; z++) { map.SetBlock(startX, startY, startZ + z, Block.Log); } }