diff --git a/server/gameserver/obstacle.cc b/server/gameserver/obstacle.cc index 41f5504..6d2806a 100644 --- a/server/gameserver/obstacle.cc +++ b/server/gameserver/obstacle.cc @@ -10,6 +10,8 @@ #include "typeconvert.h" #include "bullet.h" #include "perfmonitor.h" +#include "roomobstacle.h" +#include "loot.h" enum ObstacleDataFlags_e { @@ -570,6 +572,18 @@ void Obstacle::OnBulletHit(Bullet* bullet) ((bullet->gun_meta->special_damage_type & meta->receive_special_damage_type) == 0)) { return; } + if (meta->i->thing_type() == kObstacleOilBucket) { + Entity* real_object = AsRoomObstacle()->GetRealObject(bullet->room); + if (real_object->IsEntityType(ET_Loot)) { + Loot* loot = (Loot*)real_object; + if (loot->pickuped) { + return; + } + loot->pickuped = true; + bullet->room->RemoveObjectLater(loot); + bullet->room->RemoveObjectLater(AsRoomObstacle()); + } + } float dmg = bullet->GetAtk() * (1 + bullet->sender.Get()->GetAttrRate(kHAT_Atk)) + bullet->sender.Get()->GetAttrAbs(kHAT_Atk); float def = 0; @@ -761,3 +775,13 @@ bool Obstacle::IsOpenInteraction() { return meta->i->interaction_mode() == 2; } + +bool Obstacle::IsRoomObstacle() +{ + return !IsPermanent(); +} + +RoomObstacle* Obstacle::AsRoomObstacle() +{ + return (RoomObstacle*)this; +} diff --git a/server/gameserver/obstacle.h b/server/gameserver/obstacle.h index 6e8d42a..c59eb3e 100644 --- a/server/gameserver/obstacle.h +++ b/server/gameserver/obstacle.h @@ -20,6 +20,7 @@ class Building; class CircleCollider; class AabbCollider; class Bullet; +class RoomObstacle; class Obstacle : public Entity { public: @@ -69,6 +70,8 @@ class Obstacle : public Entity bool Throughable(); bool IsTouchInteraction(); bool IsOpenInteraction(); + bool IsRoomObstacle(); + RoomObstacle* AsRoomObstacle(); protected: Obstacle(); @@ -97,3 +100,4 @@ protected: friend class EntityFactory; }; + diff --git a/server/gameserver/player.cc b/server/gameserver/player.cc index 81010d3..fb1bbad 100644 --- a/server/gameserver/player.cc +++ b/server/gameserver/player.cc @@ -752,6 +752,19 @@ void Player::LootInteraction(Loot* entity) } entity->pickuped = true; room->RemoveObjectLater(entity); + if (entity->dummy_thing_uniid != 0) { + Entity* dummy_obj = room->GetEntityByUniId(entity->dummy_thing_uniid); + if (dummy_obj && dummy_obj->GetEntityType() == ET_Obstacle) { + Obstacle* obstacle = (Obstacle*)dummy_obj; + if (!obstacle->IsPermanent()) { + if (!obstacle->IsDead(room)) { + obstacle->Die(room); + obstacle->BroadcastFullState(room); + } + room->RemoveObjectLater((RoomObstacle*)obstacle); + } + } + } } void Player::HumanInteraction(Human* hum) diff --git a/server/gameserver/room.cc b/server/gameserver/room.cc index ecf7765..e31a090 100644 --- a/server/gameserver/room.cc +++ b/server/gameserver/room.cc @@ -558,6 +558,7 @@ int Room::CreateLootEx(int equip_id, a8::Vec2 born_pos, a8::Vec2 pos, int count, } RoomObstacle* dummy_obj = CreateObstacle(equip_meta->int_param1, pos.x, pos.y); entity->dummy_thing_uniid = dummy_obj->GetUniId(); + dummy_obj->real_object_uniid = entity->GetUniId(); } return entity->GetUniId(); } else { diff --git a/server/gameserver/roomobstacle.cc b/server/gameserver/roomobstacle.cc index f59d691..29b565a 100644 --- a/server/gameserver/roomobstacle.cc +++ b/server/gameserver/roomobstacle.cc @@ -582,3 +582,8 @@ void RoomObstacle::SummonAirDropBox(int box_id) ); } + +Entity* RoomObstacle::GetRealObject(Room* room) +{ + return room->GetEntityByUniId(real_object_uniid); +} diff --git a/server/gameserver/roomobstacle.h b/server/gameserver/roomobstacle.h index a33219d..48fb3aa 100644 --- a/server/gameserver/roomobstacle.h +++ b/server/gameserver/roomobstacle.h @@ -12,6 +12,7 @@ class RoomObstacle : public Obstacle bool is_treasure_box = false; bool is_terminator_airdrop_box = false; CreatureWeakPtr master; + int real_object_uniid = 0; virtual ~RoomObstacle() override; virtual void Initialize() override; @@ -25,6 +26,7 @@ class RoomObstacle : public Obstacle void DetachFromMaster(); virtual void Die(Room* room) override; virtual void Explosion() override; + Entity* GetRealObject(Room* room); private: void SpecExplosion();