From 222b6ec3cc7f7839f30bf60ce39c9b2b652d99de Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 22 Aug 2013 22:31:38 +0200 Subject: Projectile entities get saved into MCA files --- source/WorldStorage/NBTChunkSerializer.cpp | 67 ++++++++++++++++++++++++++++-- source/WorldStorage/NBTChunkSerializer.h | 2 + 2 files changed, 65 insertions(+), 4 deletions(-) (limited to 'source/WorldStorage') diff --git a/source/WorldStorage/NBTChunkSerializer.cpp b/source/WorldStorage/NBTChunkSerializer.cpp index 706e913ef..baae0dc01 100644 --- a/source/WorldStorage/NBTChunkSerializer.cpp +++ b/source/WorldStorage/NBTChunkSerializer.cpp @@ -22,6 +22,8 @@ #include "../Entities/Minecart.h" #include "../Mobs/Monster.h" #include "../Entities/Pickup.h" +#include "../Entities/ProjectileEntity.h" + @@ -330,6 +332,62 @@ void cNBTChunkSerializer::AddPickupEntity(cPickup * a_Pickup) +void cNBTChunkSerializer::AddProjectileEntity(cProjectileEntity * a_Projectile) +{ + m_Writer.BeginCompound(""); + AddBasicEntity(a_Projectile, a_Projectile->GetMCAClassName()); + Vector3d Pos = a_Projectile->GetPosition(); + m_Writer.AddShort("xTile", (Int16)floor(Pos.x)); + m_Writer.AddShort("yTile", (Int16)floor(Pos.y)); + m_Writer.AddShort("zTile", (Int16)floor(Pos.z)); + m_Writer.AddShort("inTile", 0); // TODO: Query the block type (is it needed?) + m_Writer.AddShort("shake", 0); // TODO: Any shake? + m_Writer.AddByte ("inGround", a_Projectile->IsInGround() ? 1 : 0); + + switch (a_Projectile->GetProjectileKind()) + { + case cProjectileEntity::pkArrow: + { + m_Writer.AddByte("inData", 0); // TODO: Query the block meta (is it needed?) + m_Writer.AddByte("pickup", ((cArrowEntity *)a_Projectile)->GetPickupState()); + m_Writer.AddDouble("damage", ((cArrowEntity *)a_Projectile)->GetDamageCoeff()); + break; + } + case cProjectileEntity::pkGhastFireball: + { + m_Writer.AddInt("ExplosionPower", 1); + // fall-through: + } + case cProjectileEntity::pkFireCharge: + case cProjectileEntity::pkWitherSkull: + { + m_Writer.BeginList("Motion", TAG_Double); + m_Writer.AddDouble("", a_Projectile->GetSpeedX()); + m_Writer.AddDouble("", a_Projectile->GetSpeedY()); + m_Writer.AddDouble("", a_Projectile->GetSpeedZ()); + m_Writer.EndList(); + break; + } + default: + { + ASSERT(!"Unsaved projectile entity!"); + } + } // switch (ProjectileKind) + cEntity * Creator = a_Projectile->GetCreator(); + if (Creator != NULL) + { + if (Creator->GetEntityType() == cEntity::etPlayer) + { + m_Writer.AddString("ownerName", ((cPlayer *)Creator)->GetName()); + } + } + m_Writer.EndCompound(); +} + + + + + void cNBTChunkSerializer::AddMinecartChestContents(cMinecartWithChest * a_Minecart) { m_Writer.BeginList("Items", TAG_Compound); @@ -403,10 +461,11 @@ void cNBTChunkSerializer::Entity(cEntity * a_Entity) switch (a_Entity->GetEntityType()) { - case cEntity::etFallingBlock: AddFallingBlockEntity((cFallingBlock *)a_Entity); break; - case cEntity::etMinecart: AddMinecartEntity ((cMinecart *) a_Entity); break; - case cEntity::etMonster: AddMonsterEntity ((cMonster *) a_Entity); break; - case cEntity::etPickup: AddPickupEntity ((cPickup *) a_Entity); break; + case cEntity::etFallingBlock: AddFallingBlockEntity((cFallingBlock *) a_Entity); break; + case cEntity::etMinecart: AddMinecartEntity ((cMinecart *) a_Entity); break; + case cEntity::etMonster: AddMonsterEntity ((cMonster *) a_Entity); break; + case cEntity::etPickup: AddPickupEntity ((cPickup *) a_Entity); break; + case cEntity::etProjectile: AddProjectileEntity ((cProjectileEntity *)a_Entity); break; case cEntity::etPlayer: return; // Players aren't saved into the world default: { diff --git a/source/WorldStorage/NBTChunkSerializer.h b/source/WorldStorage/NBTChunkSerializer.h index cd1388f89..481c578f3 100644 --- a/source/WorldStorage/NBTChunkSerializer.h +++ b/source/WorldStorage/NBTChunkSerializer.h @@ -36,6 +36,7 @@ class cMinecartWithHopper; class cMonster; class cPickup; class cItemGrid; +class cProjectileEntity; @@ -97,6 +98,7 @@ protected: void AddMinecartEntity (cMinecart * a_Minecart); void AddMonsterEntity (cMonster * a_Monster); void AddPickupEntity (cPickup * a_Pickup); + void AddProjectileEntity (cProjectileEntity * a_Projectile); void AddMinecartChestContents(cMinecartWithChest * a_Minecart); -- cgit v1.2.3 From 4bbade9fc6eeeb68644657a0d67f84894dd4a21c Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 25 Aug 2013 21:32:17 +0200 Subject: Arrows get loaded from MCA. Somehow they still don't spawn visibly on the client. --- source/WorldStorage/WSSAnvil.cpp | 51 ++++++++++++++++++++++++++++++++++++---- source/WorldStorage/WSSAnvil.h | 1 + 2 files changed, 48 insertions(+), 4 deletions(-) (limited to 'source/WorldStorage') diff --git a/source/WorldStorage/WSSAnvil.cpp b/source/WorldStorage/WSSAnvil.cpp index 72d583e2b..3ab64148e 100644 --- a/source/WorldStorage/WSSAnvil.cpp +++ b/source/WorldStorage/WSSAnvil.cpp @@ -20,13 +20,13 @@ #include "../Item.h" #include "../ItemGrid.h" #include "../StringCompression.h" -#include "../Entities/Entity.h" #include "../OSSupport/MakeDir.h" #include "FastNBT.h" +#include "../Mobs/Monster.h" #include "../Entities/FallingBlock.h" #include "../Entities/Minecart.h" -#include "../Mobs/Monster.h" #include "../Entities/Pickup.h" +#include "../Entities/ProjectileEntity.h" @@ -956,6 +956,10 @@ void cWSSAnvil::LoadEntityFromNBT(cEntityList & a_Entities, const cParsedNBT & a { LoadPickupFromNBT(a_Entities, a_NBT, a_EntityTagIdx); } + if (strncmp(a_IDTag, "Arrow", a_IDTagLength) == 0) + { + LoadArrowFromNBT(a_Entities, a_NBT, a_EntityTagIdx); + } // TODO: other entities } @@ -1043,7 +1047,7 @@ void cWSSAnvil::LoadMinecartTFromNBT(cEntityList & a_Entities, const cParsedNBT return; } - //TODO: Everything to do with TNT carts + // TODO: Everything to do with TNT carts a_Entities.push_back(Minecart.release()); } @@ -1060,7 +1064,7 @@ void cWSSAnvil::LoadMinecartHFromNBT(cEntityList & a_Entities, const cParsedNBT return; } - //TODO: Everything to do with hopper carts + // TODO: Everything to do with hopper carts a_Entities.push_back(Minecart.release()); } @@ -1093,6 +1097,45 @@ void cWSSAnvil::LoadPickupFromNBT(cEntityList & a_Entities, const cParsedNBT & a +void cWSSAnvil::LoadArrowFromNBT(cEntityList & a_Entities, const cParsedNBT & a_NBT, int a_TagIdx) +{ + std::auto_ptr Arrow(new cArrowEntity(NULL, 0, 0, 0, Vector3d(0, 0, 0))); + if (!LoadEntityBaseFromNBT(*Arrow.get(), a_NBT, a_TagIdx)) + { + return; + } + + // Load pickup state: + int PickupIdx = a_NBT.FindChildByName(a_TagIdx, "pickup"); + if (PickupIdx > 0) + { + Arrow->SetPickupState((cArrowEntity::ePickupState)a_NBT.GetByte(PickupIdx)); + } + else + { + // Try the older "player" tag: + int PlayerIdx = a_NBT.FindChildByName(a_TagIdx, "player"); + if (PlayerIdx > 0) + { + Arrow->SetPickupState((a_NBT.GetByte(PlayerIdx) == 0) ? cArrowEntity::psNoPickup : cArrowEntity::psInSurvivalOrCreative); + } + } + + // Load damage: + int DamageIdx = a_NBT.FindChildByName(a_TagIdx, "damage"); + if (DamageIdx > 0) + { + Arrow->SetDamageCoeff(a_NBT.GetDouble(DamageIdx)); + } + + // Store the new arrow in the entities list: + a_Entities.push_back(Arrow.release()); +} + + + + + bool cWSSAnvil::LoadEntityBaseFromNBT(cEntity & a_Entity, const cParsedNBT & a_NBT, int a_TagIdx) { double Pos[3]; diff --git a/source/WorldStorage/WSSAnvil.h b/source/WorldStorage/WSSAnvil.h index 47fda3f7b..b2556ab50 100644 --- a/source/WorldStorage/WSSAnvil.h +++ b/source/WorldStorage/WSSAnvil.h @@ -145,6 +145,7 @@ protected: void LoadMinecartTFromNBT (cEntityList & a_Entities, const cParsedNBT & a_NBT, int a_TagIdx); void LoadMinecartHFromNBT (cEntityList & a_Entities, const cParsedNBT & a_NBT, int a_TagIdx); void LoadPickupFromNBT (cEntityList & a_Entities, const cParsedNBT & a_NBT, int a_TagIdx); + void LoadArrowFromNBT (cEntityList & a_Entities, const cParsedNBT & a_NBT, int a_TagIdx); /// Loads entity common data from the NBT compound; returns true if successful bool LoadEntityBaseFromNBT(cEntity & a_Entity, const cParsedNBT & a_NBT, int a_TagIdx); -- cgit v1.2.3