From 58b2c78184c74fde27f1cbe38bb0223f22d48bde Mon Sep 17 00:00:00 2001 From: aozhiwei Date: Mon, 19 Jul 2021 11:18:59 +0000 Subject: [PATCH] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E5=A3=81=E5=9E=92=E9=80=BB?= =?UTF-8?q?=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- server/gameserver/bullet.cc | 3 ++ server/gameserver/constant.h | 1 + server/gameserver/constant_export.h | 1 + server/gameserver/explosion.cc | 3 ++ server/gameserver/roomobstacle.cc | 84 +++++++++++++++++++++++++++++ server/gameserver/roomobstacle.h | 3 ++ 6 files changed, 95 insertions(+) diff --git a/server/gameserver/bullet.cc b/server/gameserver/bullet.cc index dde4f86..f69479c 100644 --- a/server/gameserver/bullet.cc +++ b/server/gameserver/bullet.cc @@ -357,6 +357,9 @@ void Bullet::Check(float distance) //穿人 return; } + if (c->HasBuffEffect(kBET_BulletThrough)) { + return; + } AabbCollider aabb_box; c->GetHitAabbBox(aabb_box); if (c != sender.Get() && !c->dead && TestCollision(room, &aabb_box)) { diff --git a/server/gameserver/constant.h b/server/gameserver/constant.h index 62b8e04..ab74d22 100644 --- a/server/gameserver/constant.h +++ b/server/gameserver/constant.h @@ -359,6 +359,7 @@ enum ObstacleType_e kObstacleGully = 7, kObstacleAirDropBox = 8, kObstacleOilBucket = 9, + kObstacleKeepRangeBuff = 10, }; enum BulletHit_e diff --git a/server/gameserver/constant_export.h b/server/gameserver/constant_export.h index 24beb56..0470efa 100644 --- a/server/gameserver/constant_export.h +++ b/server/gameserver/constant_export.h @@ -67,6 +67,7 @@ enum BuffEffectType_e kBET_Rescue = 45, //救援 kBET_AddCarBuff = 46, //给载具加buff kBET_RemoveCarBuff = 47, //移除载具身上的buff + kBET_BulletThrough = 48, //穿透 kBET_FollowMaster = 49, //跟随主人 kBET_ThroughWall = 50, //穿墙 diff --git a/server/gameserver/explosion.cc b/server/gameserver/explosion.cc index 68b16e5..19a17b0 100644 --- a/server/gameserver/explosion.cc +++ b/server/gameserver/explosion.cc @@ -116,6 +116,9 @@ void Explosion::InternalAttack() } ); for (auto& target : objects) { + if (target->HasBuffEffect(kBET_BulletThrough)) { + continue; + } target->OnExplosionHit(this); } } diff --git a/server/gameserver/roomobstacle.cc b/server/gameserver/roomobstacle.cc index eeeb644..633649f 100644 --- a/server/gameserver/roomobstacle.cc +++ b/server/gameserver/roomobstacle.cc @@ -41,6 +41,9 @@ RoomObstacle::~RoomObstacle() if (!grid_list_) { A8_SAFE_DELETE(grid_list_); } + if (!hit_objects_) { + A8_SAFE_DELETE(hit_objects_); + } } void RoomObstacle::Initialize() @@ -277,6 +280,11 @@ void RoomObstacle::Active() ActiveAirDrop(); } break; + case kObstacleKeepRangeBuff: + { + ActiveKeepRangeBuff(); + } + break; default: { } @@ -465,3 +473,79 @@ Entity* RoomObstacle::GetRealObject(Room* room) { return room->GetEntityByUniId(real_object_uniid); } + +void RoomObstacle::ActiveKeepRangeBuff() +{ + auto check_cb = + [] (const a8::XParams& param) + { + RoomObstacle* obstacle = (RoomObstacle*)param.sender.GetUserData(); + obstacle->ProcKeepRangeBuff(); + }; + room->xtimer.AddRepeatTimerAndAttach + ( + 1, + a8::XParams() + .SetSender(this), + check_cb, + &xtimer_attacher.timer_list_ + ); + room->xtimer.AddDeadLineTimerAndAttach + ( + meta->i->time() / FRAME_RATE_MS, + a8::XParams() + .SetSender(this), + [] (const a8::XParams& param) + { + RoomObstacle* obstacle = (RoomObstacle*)param.sender.GetUserData(); + obstacle->DetachFromMaster(); + }, + &xtimer_attacher.timer_list_ + ); +} + +void RoomObstacle::ProcKeepRangeBuff() +{ + if (!grid_list_) { + grid_list_ = new std::set(); + room->grid_service->GetAllCellsByXy(room, GetPos().x, GetPos().y, *grid_list_); + } + if (!hit_objects_) { + hit_objects_ = new std::map(); + } + if (grid_list_ && master.Get() && !IsDead(room)) { + std::set target_list; + room->grid_service->TraverseCreatures + (room->GetRoomIdx(), + *grid_list_, + [this, &target_list] (Creature* hum, bool& stop) + { + if (master.Get()->team_id != hum->team_id && TestCollision(room, hum)) { + target_list.insert(hum); + } + } + ); + for (Creature* hum : target_list) { + for (int buff_id : meta->buff_list) { + MetaData::Buff* buff_meta = MetaMgr::Instance()->GetBuff(buff_id); + if (buff_meta && hum->GetBuffById(buff_id)) { + hum->AddBuff(master.Get(), + buff_meta, + 1); + } + } + if (hit_objects_->find(hum->GetUniId()) == hit_objects_->end()) { + (*hit_objects_)[hum->GetUniId()] = hum->GetWeakPtrRef(); + } + } + for (auto& pair : *hit_objects_) { + for (int buff_id : meta->buff_list) { + if (pair.second.Get() && target_list.find(pair.second.Get()) == target_list.end()) { + pair.second.Get()->RemoveBuffById(buff_id); + } + } + } + } else { + room->xtimer.DeleteTimer(room->xtimer.GetRunningTimer()); + } +} diff --git a/server/gameserver/roomobstacle.h b/server/gameserver/roomobstacle.h index 90bdbff..b10596c 100644 --- a/server/gameserver/roomobstacle.h +++ b/server/gameserver/roomobstacle.h @@ -38,13 +38,16 @@ private: void ActiveHideHouse(); void ActiveGully(); void ActiveAirDrop(); + void ActiveKeepRangeBuff(); void SummonAirDropBox(int box_id); + void ProcKeepRangeBuff(); protected: std::set* grid_list_ = nullptr; int explosion_times_ = 0; bool detached_ = false; + std::map* hit_objects_ = nullptr; RoomObstacle();