Kaynağa Gözat

spawn Block items if a block gets destroyed

Kolja Strohm 3 yıl önce
ebeveyn
işleme
d3bf7460f0

+ 33 - 0
FactoryCraft/AddEntityUpdate.cpp

@@ -0,0 +1,33 @@
+#include "AddEntityUpdate.h"
+#include "Dimension.h"
+#include "EntityType.h"
+#include "StaticRegistry.h"
+
+
+AddEntityUpdate::AddEntityUpdate( Entity* entity, int dimension )
+    : WorldUpdate( AddEntityUpdateType::ID, dimension, entity->getPosition(), entity->getPosition() ),
+    entity( entity )
+{}
+
+AddEntityUpdate::~AddEntityUpdate()
+{
+    entity->release();
+}
+
+
+void AddEntityUpdate::onUpdate( Dimension* zDimension )
+{
+    zDimension->addEntity( dynamic_cast<Entity*>(entity->getThis()) );
+}
+
+void AddEntityUpdate::write( Framework::StreamWriter* zWriter )
+{
+    int id = entity->zType()->getId();
+    zWriter->schreibe( (char*)&id, 4 );
+    StaticRegistry<EntityType>::INSTANCE.zElement( id )->saveEntity( entity, zWriter );
+}
+
+
+AddEntityUpdateType::AddEntityUpdateType()
+    : WorldUpdateType( ID )
+{}

+ 25 - 0
FactoryCraft/AddEntityUpdate.h

@@ -0,0 +1,25 @@
+#pragma once
+#include "WorldUpdate.h"
+#include "Entity.h"
+
+class AddEntityUpdate : public WorldUpdate
+{
+private:
+    Entity* entity;
+
+public:
+    AddEntityUpdate( Entity* entity, int dimension );
+    ~AddEntityUpdate();
+
+    void onUpdate( Dimension* zDimension ) override;
+    void write( Framework::StreamWriter* zWriter ) override;
+};
+
+class AddEntityUpdateType : WorldUpdateType
+{
+    REGISTRABLE( AddEntityUpdateType )
+
+protected:
+    AddEntityUpdateType();
+};
+REGISTER( AddEntityUpdateType, WorldUpdateType )

+ 17 - 1
FactoryCraft/Block.cpp

@@ -5,6 +5,9 @@
 #include "BlockChangedUpdate.h"
 #include "PlaceBlockUpdate.h"
 #include "BlockRemovedUpdate.h"
+#include "ItemEntity.h"
+#include "AddEntityUpdate.h"
+
 
 Block::Block( const BlockType* zType, ItemType* zTool, Framework::Vec3<int> pos, bool hasInventory )
     : Inventory( pos, hasInventory )
@@ -32,6 +35,19 @@ Block::Block( const BlockType* zType, ItemType* zTool, Framework::Vec3<int> pos,
 Block::~Block()
 {}
 
+void Block::onDestroy()
+{
+    Item* blockItem = zType->getItemFromBlock( this );
+    if( blockItem )
+    {
+        ItemEntity* itemEntity = new ItemEntity( location + Framework::Vec3<float>( 0.5f, 0.5f, 0.5f ), dimensionId, Game::INSTANCE->getNextEntityId() );
+        ItemStack* stack = new ItemStack( blockItem, 1, blockItem->getMaxStackSize() );
+        itemEntity->unsaveAddItem( stack, NO_DIRECTION );
+        stack->release();
+        Game::INSTANCE->requestWorldUpdate( new AddEntityUpdate( itemEntity, dimensionId ) );
+    }
+}
+
 void Block::tick( TickQueue* zQueue )
 {
     if( wasTicked )
@@ -192,7 +208,7 @@ void Block::setHP( float hp )
             }
         }
         Game::INSTANCE->requestWorldUpdate( new BlockRemovedUpdate( getPos(), dimensionId ) );
-        // TODO: generate item stacks and drop them
+        onDestroy();
     }
     else
         requestTransmission();

+ 1 - 0
FactoryCraft/Block.h

@@ -58,6 +58,7 @@ protected:
     /// the order of blocks called will be exactly the same as onTick
     /// </summary>
     virtual void onPostTick() = 0;
+    virtual void onDestroy();
 
 public:
     Block( const BlockType* zType, ItemType* zTool, Framework::Vec3<int> pos, bool hasInventory );

+ 2 - 1
FactoryCraft/Entity.h

@@ -8,10 +8,11 @@
 #include "Effect.h"
 #include "Inventory.h"
 #include "NetworkResponse.h"
+#include "ItemSkill.h"
+
 
 class EntityType;
 class Dimension;
-class ItemSkill;
 
 class ActionTarget
 {

+ 6 - 0
FactoryCraft/EntityType.cpp

@@ -27,6 +27,9 @@ void EntityType::loadSuperEntity( Entity* zEntity, Framework::StreamReader* zRea
     zReader->lese( (char*)&zEntity->faceDir.x, 4 );
     zReader->lese( (char*)&zEntity->faceDir.y, 4 );
     zReader->lese( (char*)&zEntity->currentDimensionId, 4 );
+    zReader->lese( (char*)&zEntity->location.x, 4 );
+    zReader->lese( (char*)&zEntity->location.y, 4 );
+    zReader->lese( (char*)&zEntity->location.z, 4 );
 }
 
 void EntityType::saveSuperEntity( Entity* zEntity, Framework::StreamWriter* zWriter ) const
@@ -47,6 +50,9 @@ void EntityType::saveSuperEntity( Entity* zEntity, Framework::StreamWriter* zWri
     zWriter->schreibe( (char*)&zEntity->faceDir.x, 4 );
     zWriter->schreibe( (char*)&zEntity->faceDir.y, 4 );
     zWriter->schreibe( (char*)&zEntity->currentDimensionId, 4 );
+    zWriter->schreibe( (char*)&zEntity->location.x, 4 );
+    zWriter->schreibe( (char*)&zEntity->location.y, 4 );
+    zWriter->schreibe( (char*)&zEntity->location.z, 4 );
 }
 
 void EntityType::createSuperEntity( Entity* zEntity ) const

+ 4 - 0
FactoryCraft/FactoryCraft.vcxproj

@@ -93,6 +93,7 @@
   </PropertyGroup>
   <ItemGroup>
     <ClInclude Include="AddChunkUpdate.h" />
+    <ClInclude Include="AddEntityUpdate.h" />
     <ClInclude Include="Area.h" />
     <ClInclude Include="BasicBlocks.h" />
     <ClInclude Include="BasicInterpolator.h" />
@@ -114,6 +115,7 @@
     <ClInclude Include="GrasslandBiom.h" />
     <ClInclude Include="Inventory.h" />
     <ClInclude Include="Item.h" />
+    <ClInclude Include="ItemEntity.h" />
     <ClInclude Include="ItemFilter.h" />
     <ClInclude Include="ItemSkill.h" />
     <ClInclude Include="ItemSlot.h" />
@@ -139,6 +141,7 @@
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="AddChunkUpdate.cpp" />
+    <ClCompile Include="AddEntityUpdate.cpp" />
     <ClCompile Include="Area.cpp" />
     <ClCompile Include="BasicBlock.cpp" />
     <ClCompile Include="BasicInterpolator.cpp" />
@@ -157,6 +160,7 @@
     <ClCompile Include="GrasslandBiom.cpp" />
     <ClCompile Include="Inventory.cpp" />
     <ClCompile Include="Item.cpp" />
+    <ClCompile Include="ItemEntity.cpp" />
     <ClCompile Include="ItemFilter.cpp" />
     <ClCompile Include="ItemSkill.cpp" />
     <ClCompile Include="ItemSlot.cpp" />

+ 12 - 0
FactoryCraft/FactoryCraft.vcxproj.filters

@@ -189,6 +189,12 @@
     <ClInclude Include="BlockRemovedUpdate.h">
       <Filter>world\update</Filter>
     </ClInclude>
+    <ClInclude Include="ItemEntity.h">
+      <Filter>entities</Filter>
+    </ClInclude>
+    <ClInclude Include="AddEntityUpdate.h">
+      <Filter>world\update</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="Server.cpp">
@@ -314,5 +320,11 @@
     <ClCompile Include="BlockRemovedUpdate.cpp">
       <Filter>world\update</Filter>
     </ClCompile>
+    <ClCompile Include="ItemEntity.cpp">
+      <Filter>entities</Filter>
+    </ClCompile>
+    <ClCompile Include="AddEntityUpdate.cpp">
+      <Filter>world\update</Filter>
+    </ClCompile>
   </ItemGroup>
 </Project>

+ 5 - 0
FactoryCraft/Inventory.cpp

@@ -488,4 +488,9 @@ void Inventory::addItems( ItemStack* items, Direction dir )
 InventoryInteraction Inventory::interactWith( Inventory* zInventory, Direction dir )
 {
     return InventoryInteraction( this, zInventory, dir );
+}
+
+void Inventory::unsaveAddItem( ItemStack* zStack, Direction dir )
+{
+    addItems( zStack, dir );
 }

+ 1 - 0
FactoryCraft/Inventory.h

@@ -56,6 +56,7 @@ public:
     Inventory( const Framework::Vec3<float> location, bool hasInventory );
     virtual ~Inventory();
     InventoryInteraction interactWith( Inventory* zInventory, Direction dir );
+    void unsaveAddItem( ItemStack* zStack, Direction dir );
 
     friend InventoryInteraction;
 };

+ 45 - 0
FactoryCraft/ItemEntity.cpp

@@ -0,0 +1,45 @@
+#include "ItemEntity.h"
+
+
+ItemEntity::ItemEntity( Framework::Vec3<float> location, int dimensionId, int entityId )
+    : Entity( ItemEntityType::INSTANCE, location, dimensionId, entityId )
+{
+    ItemSlot* slot = new ItemSlot( __INT32_MAX__, 0, 0, 0, ANY_DIRECTION, 0 );
+    addSlot( slot );
+    faceOffset = { 0.f, 0.f, 0.f };
+    maxHP = 10;
+    currentHP = 10;
+    stamina = 10;
+    maxStamina = 10;
+    hunger = 10;
+    maxHunger = 10;
+    thirst = 10;
+    maxThirst = 10;
+    targetDistanceLimit = 4;
+}
+
+void ItemEntity::tick( const Dimension* zDimension )
+{
+    // TODO: add speed to next entity with free inventory
+}
+
+void ItemEntity::api( Framework::StreamReader* zRequest, NetworkResponse* zResponse )
+{
+
+}
+
+void ItemEntity::onFall( float collisionSpeed )
+{
+    if( collisionSpeed >= 50.f )
+        this->currentHP = 0;
+}
+
+
+ItemEntityType::ItemEntityType()
+    : EntityType( ID )
+{}
+
+Entity* ItemEntityType::createEntity( Framework::Vec3<float> position, int dimensionId, int entityId ) const
+{
+    return new ItemEntity( position, dimensionId, entityId );
+}

+ 30 - 0
FactoryCraft/ItemEntity.h

@@ -0,0 +1,30 @@
+#pragma once
+
+#include "Entity.h"
+#include "EntityType.h"
+
+class ItemEntityType;
+
+class ItemEntity : public Entity
+{
+public:
+    ItemEntity( Framework::Vec3<float> location, int dimensionId, int entityId );
+
+    void tick( const Dimension* zDimension ) override;
+
+    void api( Framework::StreamReader* zRequest, NetworkResponse* zResponse ) override;
+    void onFall( float collisionSpeed ) override;
+
+    friend ItemEntityType;
+};
+
+class ItemEntityType : public EntityType
+{
+    REGISTRABLE( ItemEntityType )
+
+public:
+    ItemEntityType();
+
+    virtual Entity* createEntity( Framework::Vec3<float> position, int dimensionId, int entityId ) const override;
+};
+REGISTER( ItemEntityType, EntityType )

+ 6 - 2
FactoryCraft/Player.cpp

@@ -258,10 +258,14 @@ PlayerEntityType::PlayerEntityType()
 {}
 
 void PlayerEntityType::loadSuperEntity( Entity* zEntity, Framework::StreamReader* zReader ) const
-{}
+{
+    EntityType::loadSuperEntity( zEntity, zReader );
+}
 
 void PlayerEntityType::saveSuperEntity( Entity* zEntity, Framework::StreamWriter* zWriter ) const
-{}
+{
+    EntityType::saveSuperEntity( zEntity, zWriter );
+}
 
 Entity* PlayerEntityType::createEntity( Framework::Vec3<float> position, int dimensionId, int entityId ) const
 {

+ 3 - 1
FactoryCraft/StaticInitializerOrder.cpp

@@ -22,10 +22,12 @@ const c *c::INSTANCE = new c();
 #include "OverworldDimension.h"
 // entities
 #include "Player.h"
+#include "ItemEntity.h"
 // item skills
 #include "PlayerHand.h"
 // world updates
 #include "AddChunkUpdate.h"
 #include "PlaceBlockUpdate.h"
 #include "BlockChangedUpdate.h"
-#include "BlockRemovedUpdate.h"
+#include "BlockRemovedUpdate.h"
+#include "AddEntityUpdate.h"