public override Cuboidf GetParticleBreakBox(IBlockAccessor blockAccess, BlockPos pos, BlockFacing facing) { BEMPMultiblock be = blockAccess.GetBlockEntity(pos) as BEMPMultiblock; if (be == null || be.Principal == null) { return(base.GetParticleBreakBox(blockAccess, pos, facing)); } // being broken by player: break the main block instead Block principalBlock = blockAccess.GetBlock(be.Principal); return(principalBlock.GetParticleBreakBox(blockAccess, be.Principal, facing)); }
public override Cuboidf[] GetSelectionBoxes(IBlockAccessor blockAccessor, BlockPos pos) { BlockEntityAnvil bea = blockAccessor.GetBlockEntity(pos) as BlockEntityAnvil; if (bea != null) { Cuboidf[] selectionBoxes = bea.GetSelectionBoxes(blockAccessor, pos); selectionBoxes[0] = this.SelectionBoxes[0]; return(selectionBoxes); } return(base.GetSelectionBoxes(blockAccessor, pos)); }
//Need to override because this fake block has no texture of its own (no texture gives black breaking particles) public override int GetRandomColor(ICoreClientAPI capi, BlockPos pos, BlockFacing facing) { IBlockAccessor blockAccess = capi.World.BlockAccessor; BEMPMultiblock be = blockAccess.GetBlockEntity(pos) as BEMPMultiblock; if (be == null || be.Centre == null) { return(0); } Block centreBlock = blockAccess.GetBlock(be.Centre); return(centreBlock.GetRandomColor(capi, be.Centre, facing)); }
public override Cuboidf[] GetCollisionBoxes(IBlockAccessor blockAccessor, BlockPos pos) { BlockEntityChisel bec = blockAccessor.GetBlockEntity(pos) as BlockEntityChisel; if (bec != null) { Cuboidf[] selectionBoxes = bec.GetCollisionBoxes(blockAccessor, pos); return(selectionBoxes); } return(base.GetSelectionBoxes(blockAccessor, pos)); }
public override Cuboidf[] GetSelectionBoxes(IBlockAccessor blockAccessor, BlockPos pos) { BlockEntityKnappingSurface bea = blockAccessor.GetBlockEntity(pos) as BlockEntityKnappingSurface; if (bea != null) { Cuboidf[] selectionBoxes = bea.GetSelectionBoxes(blockAccessor, pos); return(selectionBoxes); } return(base.GetSelectionBoxes(blockAccessor, pos)); }
public override byte[] GetLightHsv(IBlockAccessor blockAccessor, BlockPos pos, ItemStack stack = null) { if (pos != null) { BlockEntityPitKiln beb = blockAccessor.GetBlockEntity(pos) as BlockEntityPitKiln; if (beb != null && beb.Lit) { return(litKilnLightHsv); } } return(base.GetLightHsv(blockAccessor, pos, stack)); }
public override Cuboidf GetParticleBreakBox(IBlockAccessor blockAccess, BlockPos pos, BlockFacing facing) { BEMPMultiblock be = blockAccess.GetBlockEntity(pos) as BEMPMultiblock; if (be == null || be.Centre == null) { return(base.GetParticleBreakBox(blockAccess, pos, facing)); } // being broken by player: break the centre block instead Block centreBlock = blockAccess.GetBlock(be.Centre); return(centreBlock.GetParticleBreakBox(blockAccess, be.Centre, facing)); }
// Need to override because this fake block has no texture of its own (no texture gives black breaking particles) public override int GetRandomColor(ICoreClientAPI capi, BlockPos pos, BlockFacing facing, int rndIndex = -1) { IBlockAccessor blockAccess = capi.World.BlockAccessor; BEMPMultiblock be = blockAccess.GetBlockEntity(pos) as BEMPMultiblock; if (be == null || be.Principal == null) { return(0); } Block centerBlock = blockAccess.GetBlock(be.Principal); return(centerBlock.GetRandomColor(capi, be.Principal, facing, rndIndex)); }
public override Cuboidf[] GetSelectionBoxes(IBlockAccessor blockAccessor, BlockPos pos) { BlockEntityAnvil bea = blockAccessor.GetBlockEntity(pos) as BlockEntityAnvil; if (bea != null) { Cuboidf[] selectionBoxes = bea.GetSelectionBoxes(blockAccessor, pos); float angledeg = Math.Abs(bea.MeshAngle * GameMath.RAD2DEG); selectionBoxes[0] = angledeg == 0 || angledeg == 180 ? SelectionBoxes[0] : SelectionBoxes[1]; return(selectionBoxes); } return(base.GetSelectionBoxes(blockAccessor, pos)); }
public override Cuboidf[] GetSelectionBoxes(IBlockAccessor blockAccessor, BlockPos pos) { if (Variant["attachment"] == "wall") { return(base.GetCollisionBoxes(blockAccessor, pos)); } BlockEntitySign besign = blockAccessor.GetBlockEntity(pos) as BlockEntitySign; if (besign != null) { return(besign.colSelBox); } return(base.GetSelectionBoxes(blockAccessor, pos)); }
public void MoveBlock(BlockPos fromPos, BlockPos toPos) { Block block = bA.GetBlock(fromPos); if (block.EntityClass != null) { TreeAttribute attribs = new TreeAttribute(); BlockEntity be = bA.GetBlockEntity(fromPos); if (be != null) { be.ToTreeAttributes(attribs); attribs.SetInt("posx", toPos.X); attribs.SetInt("posy", toPos.Y); attribs.SetInt("posz", toPos.Z); bA.SetBlock(0, fromPos); bA.SetBlock(block.BlockId, toPos); BlockEntity be2 = bA.GetBlockEntity(toPos); if (be2 != null) { be2.FromTreeAtributes(attribs, api.World); } } } else { bA.SetBlock(0, fromPos); bA.SetBlock(block.BlockId, toPos); if (bA.GetBlock(toPos).Id != 0) { api.World.SpawnCubeParticles(toPos, toPos.ToVec3d().Add(0.5), 4, 32); } } }
public override byte[] GetLightHsv(IBlockAccessor blockAccessor, BlockPos pos, ItemStack stack = null) { if (pos == null) { return(base.GetLightHsv(blockAccessor, pos, stack)); } BlockEntityBoiler be = blockAccessor.GetBlockEntity(pos) as BlockEntityBoiler; if (be != null && be.firepitStage == 6) { return(firepitBlock.LightHsv); } return(base.GetLightHsv(blockAccessor, pos, stack)); }
public override byte[] GetLightHsv(IBlockAccessor blockAccessor, BlockPos pos, ItemStack stack = null) { if (pos == null) { return(base.GetLightHsv(blockAccessor, pos, stack)); } BlockEntityCoalPile bea = blockAccessor.GetBlockEntity(pos) as BlockEntityCoalPile; if (bea?.IsBurning == true) { return new byte[] { 0, 7, 8 } } ; return(base.GetLightHsv(blockAccessor, pos, stack)); }
public override bool TryPlaceBlockForWorldGen(IBlockAccessor blockAccessor, BlockPos pos, BlockFacing onBlockFace, LCGRandom worldGenRand) { BlockPos rootPos = onBlockFace.IsHorizontal ? pos.AddCopy(onBlockFace) : pos.AddCopy(onBlockFace.Opposite); var block = blockAccessor.GetBlock(rootPos); if (!block.HasBehavior <BehaviorMyceliumHost>()) { rootPos.Down(); block = blockAccessor.GetBlock(rootPos); if (!block.HasBehavior <BehaviorMyceliumHost>()) { return(false); } } blockAccessor.SpawnBlockEntity("Mycelium", rootPos); (blockAccessor.GetBlockEntity(rootPos) as BlockEntityMycelium).OnGenerated(blockAccessor, worldGenRand, this); return(true); }
public override byte[] GetLightHsv(IBlockAccessor blockAccessor, BlockPos pos, ItemStack stack = null) { if (pos != null) { BELantern be = blockAccessor.GetBlockEntity(pos) as BELantern; if (be != null) { return(be.GetLightHsv()); } } if (stack != null) { string lining = stack.Attributes.GetString("lining"); byte[] lightHsv = new byte[] { this.LightHsv[0], this.LightHsv[1], (byte)(this.LightHsv[2] + (lining != "plain" ? 2 : 0)) }; return(lightHsv); } return(base.GetLightHsv(blockAccessor, pos, stack)); }
/// <summary> /// vert parameter 'suggests' an orientation for newly placed block to be opposite to existing chute /// </summary> protected virtual bool HasConnector(IBlockAccessor worldmap, BlockPos pos, BlockFacing face, out BlockFacing vert) { if (worldmap.GetBlock(pos) is BlockChute chute) { if (chute.HasItemFlowConnectorAt(BlockFacing.UP) && !chute.HasItemFlowConnectorAt(BlockFacing.DOWN)) { vert = BlockFacing.DOWN; } else if (chute.HasItemFlowConnectorAt(BlockFacing.DOWN) && !chute.HasItemFlowConnectorAt(BlockFacing.UP)) { vert = BlockFacing.UP; } else { vert = null; } return(chute.HasItemFlowConnectorAt(face)); } vert = null; return(worldmap.GetBlockEntity(pos) is BlockEntityContainer); }
private bool TryPlace(Block block, int dx, int dy, int dz) { IBlockAccessor blockAccess = entity.World.BlockAccessor; BlockPos pos = entity.ServerPos.XYZ.AsBlockPos.Add(dx, dy, dz); Block blockAtPos = blockAccess.GetBlock(pos); if (blockAtPos.IsReplacableBy(block) && blockAccess.GetBlock(pos.X, pos.Y - 1, pos.Z).SideSolid[BlockFacing.UP.Index]) { blockAccess.SetBlock(block.BlockId, pos); // Instantly despawn the block again if it expired already BlockEntityTransient betran = blockAccess.GetBlockEntity(pos) as BlockEntityTransient; betran?.SetPlaceTime(TotalHoursUntilPlace); if (betran?.IsDueTransition() == true) { blockAccess.SetBlock(0, pos); } return(true); } return(false); }
private bool SuitablePosition(IBlockAccessor blockAccessor, BlockSelection blockSel) { Block attachingBlock = blockAccessor.GetBlock(blockSel.Position); if (attachingBlock.SideSolid[blockSel.Face.Index] || (attachingBlock is BlockMicroBlock && (blockAccessor.GetBlockEntity(blockSel.Position) as BlockEntityMicroBlock).sideAlmostSolid[blockSel.Face.Index])) { EnumBlockMaterial targetMaterial = attachingBlock.GetBlockMaterial(blockAccessor, blockSel.Position); for (int i = 0; i < paintableOnBlockMaterials.Length; i++) { if (targetMaterial == paintableOnBlockMaterials[i]) { return(true); } } } return(false); }
/// <summary> /// For placement of ruins during worldgen, replaces the topsoil with the area specific soil (e.g. sand) /// </summary> /// <param name="blockAccessor"></param> /// <param name="blocks"></param> /// <param name="startPos"></param> /// <param name="climateUpLeft"></param> /// <param name="climateUpRight"></param> /// <param name="climateBotLeft"></param> /// <param name="climateBotRight"></param> /// <param name="replaceblockids"></param> /// <returns></returns> public int PlaceRespectingBlockLayers(IBlockAccessor blockAccessor, IWorldAccessor worldForCollectibleResolve, BlockPos startPos, int climateUpLeft, int climateUpRight, int climateBotLeft, int climateBotRight, ushort[] replaceblockids) { BlockPos curPos = new BlockPos(); int placed = 0; int chunksize = blockAccessor.ChunkSize; for (int x = 0; x < SizeX; x++) { for (int z = 0; z < SizeZ; z++) { curPos.Set(x + startPos.X, startPos.Y, z + startPos.Z); ushort rockblockid = blockAccessor.GetMapChunkAtBlockPos(curPos).TopRockIdMap[(curPos.Z % chunksize) * chunksize + curPos.X % chunksize]; int depth = 0; for (int y = SizeY - 1; y >= 0; y--) { curPos.Set(x + startPos.X, y + startPos.Y, z + startPos.Z); Block newBlock = blocksByPos[x, y, z]; if (newBlock == null) { continue; } if (newBlock.Replaceable < 1000) { if (replaceblockids.Length > depth && newBlock.BlockId == replaceblockids[depth]) { int climate = GameMath.BiLerpRgbColor((float)x / chunksize, (float)z / chunksize, climateUpLeft, climateUpRight, climateBotLeft, climateBotRight); newBlock = GetBlockLayerBlock((climate >> 8) & 0xff, (climate >> 16) & 0xff, startPos.Y, rockblockid, depth, newBlock, worldForCollectibleResolve.Blocks); } depth++; } Block oldBlock = blockAccessor.GetBlock(curPos); placed += handler(blockAccessor, curPos, oldBlock, newBlock); byte[] lightHsv = newBlock.GetLightHsv(blockAccessor, curPos); if (lightHsv[2] > 0 && blockAccessor is IWorldGenBlockAccessor) { int chunkSize = blockAccessor.ChunkSize; ((IWorldGenBlockAccessor)blockAccessor).ScheduleBlockLightUpdate(curPos.Copy(), oldBlock.BlockId, newBlock.BlockId); } } } } foreach (var val in BlockEntities) { uint index = val.Key; int dx = (int)(index & 0x1ff); int dy = (int)((index >> 20) & 0x1ff); int dz = (int)((index >> 10) & 0x1ff); curPos.Set(startPos.X + dx, startPos.Y + dy, startPos.Z + dz); BlockEntity be = blockAccessor.GetBlockEntity(curPos); if (be != null) { be.FromTreeAtributes(DecodeBlockEntityData(val.Value), worldForCollectibleResolve); be.OnLoadCollectibleMappings(worldForCollectibleResolve, BlockCodes, ItemCodes); be.pos = curPos.Copy(); } } return(placed); }
/// <summary> /// Places all the entities and blocks in the schematic at the position. /// </summary> /// <param name="blockAccessor"></param> /// <param name="worldForCollectibleResolve"></param> /// <param name="startPos"></param> public void PlaceEntitiesAndBlockEntities(IBlockAccessor blockAccessor, IWorldAccessor worldForCollectibleResolve, BlockPos startPos) { BlockPos curPos = new BlockPos(); int schematicSeed = worldForCollectibleResolve.Rand.Next(); foreach (var val in BlockEntities) { uint index = val.Key; int dx = (int)(index & 0x1ff); int dy = (int)((index >> 20) & 0x1ff); int dz = (int)((index >> 10) & 0x1ff); curPos.Set(dx + startPos.X, dy + startPos.Y, dz + startPos.Z); BlockEntity be = blockAccessor.GetBlockEntity(curPos); // Block entities need to be manually initialized for world gen block access if (be == null && blockAccessor is IWorldGenBlockAccessor) { Block block = blockAccessor.GetBlock(curPos); if (block.EntityClass != null) { blockAccessor.SpawnBlockEntity(block.EntityClass, curPos); be = blockAccessor.GetBlockEntity(curPos); } } if (be != null) { Block block = blockAccessor.GetBlock(curPos); if (block.EntityClass != worldForCollectibleResolve.ClassRegistry.GetBlockEntityClass(be.GetType())) { worldForCollectibleResolve.Logger.Warning("Could not import block entity data for schematic at {0}. There is already {1}, expected {2}. Probably overlapping ruins.", curPos, be.GetType(), block.EntityClass); continue; } ITreeAttribute tree = DecodeBlockEntityData(val.Value); tree.SetInt("posx", curPos.X); tree.SetInt("posy", curPos.Y); tree.SetInt("posz", curPos.Z); be.FromTreeAttributes(tree, worldForCollectibleResolve); be.OnLoadCollectibleMappings(worldForCollectibleResolve, BlockCodes, ItemCodes, schematicSeed); be.Pos = curPos.Copy(); } } foreach (string entityData in Entities) { using (MemoryStream ms = new MemoryStream(Ascii85.Decode(entityData))) { BinaryReader reader = new BinaryReader(ms); string className = reader.ReadString(); Entity entity = worldForCollectibleResolve.ClassRegistry.CreateEntity(className); entity.FromBytes(reader, false); entity.DidImportOrExport(startPos); // Not ideal but whatever if (blockAccessor is IWorldGenBlockAccessor) { (blockAccessor as IWorldGenBlockAccessor).AddEntity(entity); } else { worldForCollectibleResolve.SpawnEntity(entity); } } } }
public override Cuboidf[] GetSelectionBoxes(IBlockAccessor blockAccessor, BlockPos pos) { var bebranch = blockAccessor.GetBlockEntity(pos) as BlockEntityFruitTreeBranch; return(bebranch?.GetColSelBox() ?? base.GetCollisionBoxes(blockAccessor, pos)); }
private void ExplodeBlock(Block blockToExplode, BlockPos explosionPos, Vec3d shrapnelDirection) { AssetLocation blockCode = blockToExplode.Code; //-- Explosions do not destroy water, mantle or air blocks --// switch (blockCode.Path) { case "water-still-7": break; case "mantle": break; case "air": break; default: //-- If a block being destroyed is an inventory, then throw all the contents of it on the ground. Otherwise, for terrain blocks, only spawn items based on a % chance --// if (blockToExplode is BlockGenericTypedContainer || blockToExplode is BlockShelf || blockToExplode is BlockDisplayCase || blockToExplode is BlockMoldRack) { BlockEntityContainer entityContainer = blockAccessor.GetBlockEntity(explosionPos) as BlockEntityContainer; foreach (ItemSlot slot in entityContainer.Inventory) { if (!slot.Empty) { entity.World.SpawnItemEntity(slot.Itemstack, explosionPos.ToVec3d(), GetNewItemStackVector(shrapnelDirection, itemStackVelocityModifier)); } } } else if (blockToExplode is BlockToolRack) { BlockEntityToolrack blockEntityToolrack = blockAccessor.GetBlockEntity(explosionPos) as BlockEntityToolrack; foreach (ItemSlot slot in blockEntityToolrack.inventory) { if (!slot.Empty) { entity.World.SpawnItemEntity(slot.Itemstack, explosionPos.ToVec3d(), GetNewItemStackVector(shrapnelDirection, itemStackVelocityModifier)); } } } else { foreach (BlockDropItemStack itemStack in blockAccessor.GetBlock(explosionPos).Drops) { if (explosionRand.Next(0, 101) < terrainDropChance) { entity.World.SpawnItemEntity(itemStack.GetNextItemStack(), explosionPos.ToVec3d(), GetNewItemStackVector(shrapnelDirection, itemStackVelocityModifier)); } } } if (fillWithLiquid == false) { blockAccessor.SetBlock(0, explosionPos); } else { if (explosionPos.Y <= fillHeight) { blockAccessor.SetBlock(serverAPI.WorldManager.GetBlockId(liquidAsset), explosionPos); } else { blockAccessor.SetBlock(0, explosionPos); } } blockAccessor.TriggerNeighbourBlockUpdate(explosionPos); break; } }