public static void InsertBuilding(BlockManager bmDest, int[,] intArea, int intBlockStart, int x1dest, int z1dest, Building bldInsert) { lstInstanceSigns.Clear(); int intHighestSourceY = 0; int intSourceX = 0, intSourceZ = 0; int intRotate = -1; for (int intDistance = 0; intRotate == -1 && intDistance < 10; intDistance++) { for (int intCheck = 0; intRotate == -1 && intCheck <= bldInsert.intSize; intCheck++) { if (CheckArea(intArea, x1dest + intCheck, z1dest - intDistance) == 1) { intRotate = 0; } else if (CheckArea(intArea, x1dest - intDistance, z1dest + intCheck) == 1) { intRotate = 1; } else if (CheckArea(intArea, x1dest + bldInsert.intSize + intDistance, z1dest + intCheck) == 1) { intRotate = 2; } else if (CheckArea(intArea, x1dest + intCheck, z1dest + bldInsert.intSize + intDistance) == 1) { intRotate = 3; } } } if (intRotate == -1) { intRotate = RandomHelper.Next(4); } for (int x = 0; x < bldInsert.intSize; x++) { for (int z = 0; z < bldInsert.intSize; z++) { switch (intRotate) { case 0: intSourceX = x; intSourceZ = z; break; case 1: intSourceX = (bldInsert.intSize - 1) - z; intSourceZ = x; break; case 2: intSourceX = z; intSourceZ = (bldInsert.intSize - 1) - x; break; case 3: intSourceX = (bldInsert.intSize - 1) - x; intSourceZ = (bldInsert.intSize - 1) - z; break; } int intSourceEndY; for (intSourceEndY = 128; intSourceEndY > 64; intSourceEndY--) { if (bmSource.GetID(intSourceX + bldInsert.intSourceX, intSourceEndY, intSourceZ + bldInsert.intSourceZ) != (int)BlockType.AIR) { break; } } if (intSourceEndY > intHighestSourceY) { intHighestSourceY = intSourceEndY; } for (int y = bldInsert.intSourceStartY; y <= intSourceEndY; y++) { if (y != 64 || bmDest.GetID(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest) == (int)BlockType.AIR) { int intBlockID = bmSource.GetID(intSourceX + bldInsert.intSourceX, y, intSourceZ + bldInsert.intSourceZ); int intBlockData = bmSource.GetData(intSourceX + bldInsert.intSourceX, y, intSourceZ + bldInsert.intSourceZ); bmDest.SetID(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, intBlockID); bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, intBlockData); foreach (EntityPainting entPainting in AllEntityPainting) { if (entPainting.TileX == intSourceX + bldInsert.intSourceX && entPainting.TileY == y && entPainting.TileZ == intSourceZ + bldInsert.intSourceZ) { EntityPainting entNewPainting = (EntityPainting)entPainting.Copy(); entNewPainting.TileX = intBlockStart + x + x1dest; entNewPainting.TileY = y; entNewPainting.TileZ = intBlockStart + z + z1dest; entNewPainting.Position.X = entNewPainting.TileX; entNewPainting.Position.Z = entNewPainting.TileZ; entNewPainting.Direction = BlockHelper.RotatePortrait(entPainting.Direction, intRotate); ChunkRef chunkBuilding = cmDest.GetChunkRef((intBlockStart + x + x1dest) / 16, (intBlockStart + z + z1dest) / 16); chunkBuilding.Entities.Add(entNewPainting); cmDest.Save(); } } #region Rotation if (intRotate > 0) { switch (intBlockID) { case (int)BlockType.SIGN_POST: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateSignPost(intBlockData, intRotate)); break; case (int)BlockType.STONE_BUTTON: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateButton(intBlockData, intRotate)); break; case (int)BlockType.PUMPKIN: case (int)BlockType.JACK_O_LANTERN: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotatePumpkin(intBlockData, intRotate)); break; case (int)BlockType.IRON_DOOR: case (int)BlockType.WOOD_DOOR: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateDoor(intBlockData, intRotate)); break; case (int)BlockType.TRAPDOOR: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateTrapdoor(intBlockData, intRotate)); break; case (int)BlockType.BED: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateBed(intBlockData, intRotate)); break; case (int)BlockType.REDSTONE_TORCH_OFF: case (int)BlockType.REDSTONE_TORCH_ON: case (int)BlockType.TORCH: case (int)BlockType.LEVER: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateTorchOrLever(intBlockData, intRotate)); break; case (int)BlockType.WALL_SIGN: case (int)BlockType.LADDER: case (int)BlockType.DISPENSER: case (int)BlockType.FURNACE: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateWallSignOrLadderOrFurnanceOrDispenser(intBlockData, intRotate)); break; case (int)BlockType.COBBLESTONE_STAIRS: case (int)BlockType.WOOD_STAIRS: bmDest.SetData(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, BlockHelper.RotateStairs(intBlockData, intRotate)); break; } } #endregion #region Handle entities switch (intBlockID) { case (int)BlockType.CHEST: TileEntityChest tec = (TileEntityChest)bmSource.GetTileEntity(intSourceX + bldInsert.intSourceX, y, intSourceZ + bldInsert.intSourceZ); if (tec.Items[0] != null) { if (tec.Items[0].ID == ItemInfo.Paper.ID && tec.Items[0].Count == 3) { tec = MakeHouseChest(); } } bmDest.SetTileEntity(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, tec); break; case (int)BlockType.FURNACE: case (int)BlockType.MONSTER_SPAWNER: case (int)BlockType.NOTE_BLOCK: case (int)BlockType.JUKEBOX: case (int)BlockType.TRAPDOOR: bmDest.SetTileEntity(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, bmSource.GetTileEntity(intSourceX + bldInsert.intSourceX, y, intSourceZ + bldInsert.intSourceZ)); break; case (int)BlockType.SIGN_POST: case (int)BlockType.WALL_SIGN: #region Determine sign text int intUniqueType = 0; TileEntitySign tes = (TileEntitySign)bmSource.GetTileEntity(intSourceX + bldInsert.intSourceX, y, intSourceZ + bldInsert.intSourceZ); string strSourceSign = tes.Text1 + " " + tes.Text2 + " " + tes.Text3 + " " + tes.Text4; switch (strSourceSign.Substring(0, 1)) { case "2": case "1": case "0": intUniqueType = Convert.ToInt32(strSourceSign.Substring(0, 1)); strSourceSign = strSourceSign.Remove(0, 1); break; default: intUniqueType = 0; break; } if (strSourceSign.Contains("[")) { string strSignText; bool booDuplicate; int intFail = 0; do { strSignText = SignText(strSourceSign); booDuplicate = false; switch (intUniqueType) { case 1: // unique by instance booDuplicate = lstInstanceSigns.Contains(strSignText); break; case 2: // unique by city booDuplicate = lstCitySigns.Contains(strSignText); break; } intFail++; if (intFail > 100) { Debug.WriteLine("Could not make a unique sign for " + strSourceSign); booDuplicate = false; } } while (booDuplicate); lstCitySigns.Add(strSignText); lstInstanceSigns.Add(strSignText); string[] strRandomSign = BlockHelper.TextToSign(ConvertToSignText(strSignText)); tes.Text1 = strRandomSign[0]; tes.Text2 = strRandomSign[1]; tes.Text3 = strRandomSign[2]; tes.Text4 = strRandomSign[3]; } bmDest.SetTileEntity(intBlockStart + x + x1dest, y, intBlockStart + z + z1dest, tes); break; #endregion } #endregion } } } } }
public static void InsertBuilding(BlockManager bmDest, int[,] intArea, int intBlockStart, int x1dest, int z1dest, Building bldInsert, int y1dest) { List <Spawner> lstSpawners = new List <Spawner>(); _lstInstanceSigns.Clear(); int intRandomWoolColour = RandomHelper.Next(16); int intSourceX = 0, intSourceZ = 0; int intRotate = -1; if (bldInsert.btThis == BuildingTypes.MineshaftSection) { intRotate = 0; } else { for (int intDistance = 0; intRotate == -1 && intDistance < 10; intDistance++) { for (int intCheck = 0; intRotate == -1 && intCheck <= bldInsert.intSizeX; intCheck++) { if (CheckArea(intArea, x1dest + intCheck, z1dest - intDistance) == 1) { intRotate = 0; } else if (CheckArea(intArea, x1dest - intDistance, z1dest + intCheck) == 1) { intRotate = 1; } else if (CheckArea(intArea, x1dest + bldInsert.intSizeX + intDistance, z1dest + intCheck) == 1) { intRotate = 2; } else if (CheckArea(intArea, x1dest + intCheck, z1dest + bldInsert.intSizeZ + intDistance) == 1) { intRotate = 3; } } } } if (intRotate == -1) { intRotate = RandomHelper.Next(4); } for (int x = 0; x < bldInsert.intSizeX; x++) { for (int z = 0; z < bldInsert.intSizeZ; z++) { switch (intRotate) { case 0: intSourceX = x; intSourceZ = z; break; case 1: intSourceX = (bldInsert.intSizeX - 1) - z; intSourceZ = x; break; case 2: intSourceX = z; intSourceZ = (bldInsert.intSizeZ - 1) - x; break; case 3: intSourceX = (bldInsert.intSizeX - 1) - x; intSourceZ = (bldInsert.intSizeZ - 1) - z; break; default: Debug.Fail("Invalid switch result"); break; } int intSourceEndY; if (bldInsert.btThis == BuildingTypes.MineshaftSection) { intSourceEndY = bldInsert.intSourceStartY + 4; } else { for (intSourceEndY = 128; intSourceEndY > 64; intSourceEndY--) { if (_bmSource.GetID(intSourceX + bldInsert.intSourceX, intSourceEndY, intSourceZ + bldInsert.intSourceZ) != BlockType.AIR) { break; } } } for (int ySource = bldInsert.intSourceStartY; ySource <= intSourceEndY; ySource++) { int yDest = ySource; if (bldInsert.btThis == BuildingTypes.MineshaftSection) { yDest = y1dest + (ySource - bldInsert.intSourceStartY); } if (bldInsert.btThis == BuildingTypes.MineshaftSection || ((yDest != 64 || bmDest.GetID(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest) == BlockType.AIR) && bmDest.GetID(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest) != BlockType.WOOD_PLANK)) { int intBlockID = _bmSource.GetID(intSourceX + bldInsert.intSourceX, ySource, intSourceZ + bldInsert.intSourceZ); int intBlockData = _bmSource.GetData(intSourceX + bldInsert.intSourceX, ySource, intSourceZ + bldInsert.intSourceZ); bmDest.SetID(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, intBlockID); bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, intBlockData); #region import paintings // todo: test for mineshaft features foreach (EntityPainting entPainting in _AllEntityPainting) { if (entPainting.TileX == intSourceX + bldInsert.intSourceX && entPainting.TileY == ySource && entPainting.TileZ == intSourceZ + bldInsert.intSourceZ) { EntityPainting entNewPainting = (EntityPainting)entPainting.Copy(); entNewPainting.TileX = intBlockStart + x + x1dest; entNewPainting.TileY = yDest; entNewPainting.TileZ = intBlockStart + z + z1dest; entNewPainting.Position.X = entNewPainting.TileX; entNewPainting.Position.Z = entNewPainting.TileZ; entNewPainting.Direction = BlockHelper.RotatePortrait(entPainting.Direction, intRotate); ChunkRef chunkBuilding = _cmDest.GetChunkRef((intBlockStart + x + x1dest) / 16, (intBlockStart + z + z1dest) / 16); chunkBuilding.Entities.Add(entNewPainting); _cmDest.Save(); } } #endregion #region Rotation if (intRotate > 0) { switch (intBlockID) { case BlockType.PORTAL: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotatePortal(intBlockData, intRotate)); break; case BlockType.SIGN_POST: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateSignPost(intBlockData, intRotate)); break; case BlockType.STONE_BUTTON: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateButton(intBlockData, intRotate)); break; case BlockType.PUMPKIN: case BlockType.JACK_O_LANTERN: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotatePumpkin(intBlockData, intRotate)); break; case BlockType.IRON_DOOR: case BlockType.WOOD_DOOR: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateDoor(intBlockData, intRotate)); break; case BlockType.TRAPDOOR: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateTrapdoor(intBlockData, intRotate)); break; case BlockType.BED: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateBed(intBlockData, intRotate)); break; case BlockType.REDSTONE_TORCH_OFF: case BlockType.REDSTONE_TORCH_ON: case BlockType.TORCH: case BlockType.LEVER: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateTorchOrLever(intBlockData, intRotate)); break; case BlockType.WALL_SIGN: case BlockType.LADDER: case BlockType.DISPENSER: case BlockType.FURNACE: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateWallSignOrLadderOrFurnanceOrDispenser( intBlockData, intRotate)); break; case BlockType.COBBLESTONE_STAIRS: case BlockType.WOOD_STAIRS: bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockHelper.RotateStairs(intBlockData, intRotate)); break; // no need for a default - all other blocks are okay } } #endregion #region Handle entities switch (intBlockID) { case BlockType.SPONGE: bmDest.SetID(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockType.WOOL); bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, intRandomWoolColour); break; case BlockType.CHEST: TileEntityChest tec = (TileEntityChest)_bmSource.GetTileEntity( intSourceX + bldInsert.intSourceX, ySource, intSourceZ + bldInsert.intSourceZ); if (_booIncludeItemsInChests) { if (tec.Items[0] != null) { if (tec.Items[0].ID == ItemInfo.Paper.ID && tec.Items[0].Count == 3) { tec = MakeHouseChest(); } if (tec.Items[0].ID == ItemInfo.Paper.ID && tec.Items[0].Count == 4) { tec = MakeTreasureChest(); } } } else { tec.Items.ClearAllItems(); } bmDest.SetTileEntity(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, tec); break; case BlockType.FURNACE: case BlockType.MONSTER_SPAWNER: case BlockType.NOTE_BLOCK: bmDest.SetTileEntity(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, _bmSource.GetTileEntity(intSourceX + bldInsert.intSourceX, ySource, intSourceZ + bldInsert.intSourceZ)); break; case BlockType.SIGN_POST: case BlockType.WALL_SIGN: #region Determine sign text int intUniqueType = 0; TileEntitySign tes = (TileEntitySign)_bmSource. GetTileEntity(intSourceX + bldInsert.intSourceX, ySource, intSourceZ + bldInsert.intSourceZ); string strSourceSign = tes.Text1 + " " + tes.Text2 + " " + tes.Text3 + " " + tes.Text4; switch (strSourceSign.Substring(0, 1)) { case "2": case "1": case "0": intUniqueType = Convert.ToInt32(strSourceSign.Substring(0, 1)); strSourceSign = strSourceSign.Remove(0, 1); break; default: intUniqueType = 0; break; } if (tes.Text1.ToLower() == "commentsign" || tes.Text1.ToLower() == "comment sign") { // these exist to give advice to people in the resource world. // so we just remove them from the real world bmDest.SetID(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockType.AIR); bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, 0); } if (tes.Text1.ToLower() == "spawner" || tes.Text1.ToLower() == "gspawner") { if (!tes.Text2.ToLower().StartsWith("g") || tes.Text2.ToLower() == "[randomenemy]" || _booIncludeGhostdancerSpawners) { Spawner spawnerCurrent = new Spawner(); if (tes.Text2.ToLower() == "[randomenemy]") { if (_booIncludeGhostdancerSpawners) { spawnerCurrent.strEntityID = RandomHelper.RandomString("Creeper", "Skeleton", "Spider", "Zombie", "GGeist", "GGrim"); } else { spawnerCurrent.strEntityID = RandomHelper.RandomString("Creeper", "Skeleton", "Spider", "Zombie"); } } else { spawnerCurrent.strEntityID = tes.Text2; } if (tes.Text3.Split(' ').GetUpperBound(0) == 2) { spawnerCurrent.sy = yDest + Convert.ToInt32(tes.Text3.Split(' ')[1]); spawnerCurrent.sx = 0; spawnerCurrent.sz = 0; switch (intRotate) { case 0: spawnerCurrent.sx = intBlockStart + x + x1dest + (Convert.ToInt32(tes.Text3.Split(' ')[0])); spawnerCurrent.sz = intBlockStart + z + z1dest + (Convert.ToInt32(tes.Text3.Split(' ')[2])); break; case 1: spawnerCurrent.sx = intBlockStart + x + x1dest + (Convert.ToInt32(tes.Text3.Split(' ')[2])); spawnerCurrent.sz = intBlockStart + z + z1dest + (-1 * Convert.ToInt32(tes.Text3.Split(' ')[0])); break; case 2: spawnerCurrent.sx = intBlockStart + x + x1dest + (-1 * Convert.ToInt32(tes.Text3.Split(' ')[2])); spawnerCurrent.sz = intBlockStart + z + z1dest + (Convert.ToInt32(tes.Text3.Split(' ')[0])); break; case 3: spawnerCurrent.sx = intBlockStart + x + x1dest + (-1 * Convert.ToInt32(tes.Text3.Split(' ')[0])); spawnerCurrent.sz = intBlockStart + z + z1dest + (-1 * Convert.ToInt32(tes.Text3.Split(' ')[2])); break; } } else { spawnerCurrent.sx = intBlockStart + x + x1dest; spawnerCurrent.sy = yDest - 2; spawnerCurrent.sz = intBlockStart + z + z1dest; } if (tes.Text4.ToLower() == "no") { spawnerCurrent.booGrass = false; } else if (tes.Text4.Split(' ').GetUpperBound(0) == 2) { spawnerCurrent.gy = yDest + Convert.ToInt32(tes.Text4.Split(' ')[1]); switch (intRotate) { case 0: spawnerCurrent.gx = intBlockStart + x + x1dest + (Convert.ToInt32(tes.Text4.Split(' ')[0])); spawnerCurrent.gz = intBlockStart + z + z1dest + (Convert.ToInt32(tes.Text4.Split(' ')[2])); break; case 1: spawnerCurrent.gx = intBlockStart + x + x1dest + (-1 * Convert.ToInt32(tes.Text4.Split(' ')[2])); spawnerCurrent.gz = intBlockStart + z + z1dest + (Convert.ToInt32(tes.Text4.Split(' ')[0])); break; case 2: spawnerCurrent.gx = intBlockStart + x + x1dest + (Convert.ToInt32(tes.Text4.Split(' ')[2])); spawnerCurrent.gz = intBlockStart + z + z1dest + (-1 * Convert.ToInt32(tes.Text4.Split(' ')[0])); break; case 3: spawnerCurrent.gx = intBlockStart + x + x1dest + (-1 * Convert.ToInt32(tes.Text4.Split(' ')[0])); spawnerCurrent.gz = intBlockStart + z + z1dest + (-1 * Convert.ToInt32(tes.Text4.Split(' ')[2])); break; } spawnerCurrent.booGrass = true; } else { spawnerCurrent.gx = intBlockStart + x + x1dest; spawnerCurrent.gy = yDest - 1; spawnerCurrent.gz = intBlockStart + z + z1dest; spawnerCurrent.booGrass = true; } lstSpawners.Add(spawnerCurrent); } bmDest.SetID(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, BlockType.AIR); bmDest.SetData(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, 0); } else if (strSourceSign.Contains("[")) { string strSignText; bool booDuplicate; int intFail = 0; do { strSignText = SignText(strSourceSign); booDuplicate = false; switch (intUniqueType) { case 1: // unique by instance booDuplicate = _lstInstanceSigns.Contains(strSignText); break; case 2: // unique by city booDuplicate = _lstCitySigns.Contains(strSignText); break; } if (++intFail > 100) { Debug.WriteLine("Could not make a unique sign for " + strSourceSign); booDuplicate = false; } } while (booDuplicate); _lstCitySigns.Add(strSignText); _lstInstanceSigns.Add(strSignText); string[] strRandomSign = Utils.TextToSign(Utils.ConvertStringToSignText(strSignText)); tes.Text1 = strRandomSign[0]; tes.Text2 = strRandomSign[1]; tes.Text3 = strRandomSign[2]; tes.Text4 = strRandomSign[3]; bmDest.SetTileEntity(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, tes); } else { bmDest.SetTileEntity(intBlockStart + x + x1dest, yDest, intBlockStart + z + z1dest, tes); } break; #endregion // no need for a default - all the other blocks are okay } #endregion } } } } foreach (Spawner spnAdd in lstSpawners) { bmDest.SetID(spnAdd.sx, spnAdd.sy, spnAdd.sz, BlockType.MONSTER_SPAWNER); TileEntityMobSpawner tems = new TileEntityMobSpawner(); tems.EntityID = spnAdd.strEntityID; bmDest.SetTileEntity(spnAdd.sx, spnAdd.sy, spnAdd.sz, tems); if (spnAdd.booGrass) { bmDest.SetID(spnAdd.gx, spnAdd.gy, spnAdd.gz, BlockType.GRASS); } } }