game2006/server/gameserver/frag_mitask.cc
aozhiwei e1ba7d045c 1
2021-04-02 19:21:22 +08:00

106 lines
3.4 KiB
C++

#include "precompile.h"
#include "frag_mitask.h"
#include "room.h"
#include "player.h"
#include "metadata.h"
#include "metamgr.h"
#include "gridservice.h"
#include "creature.h"
#include "obstacle.h"
void FragMiTask::Done()
{
if (!sender.Get()) {
return;
}
room->frame_event.AddExplosionEx(sender,
meta->i->id(),
bomb_pos,
gun_meta->i->explosion_effect());
std::set<GridCell*> grid_list;
sender.Get()->room->grid_service->GetAllCellsByXy
(
sender.Get()->room,
bomb_pos.x,
bomb_pos.y,
grid_list
);
std::set<Creature*> objects;
sender.Get()->room->grid_service->TouchCreatures
(
sender.Get()->room->GetRoomIdx(),
grid_list,
[this, &objects] (Creature* c, bool& stop)
{
if (sender.Get()->IsProperTarget(c)) {
if (bomb_pos.Distance(c->GetPos()) < meta->i->explosion_range()) {
objects.insert(c);
}
}
}
);
std::set<Entity*> entitys;
sender.Get()->room->grid_service->TouchAllLayerEntityList
(
sender.Get()->room->GetRoomIdx(),
grid_list,
[this, &entitys] (Entity* entity, bool& stop)
{
}
);
for (auto& target : objects) {
if (target->HasBuffEffect(kBET_Invincible) ||
target->HasBuffEffect(kBET_AdPlaying)) {
continue;
}
if (sender.Get()->room->GetRoomMode() == kZombieMode &&
sender.Get()->GetRace() == target->GetRace()) {
continue;
}
if (!target->dead) {
float dmg = GetAtk() * (1 + sender.Get()->GetAttrRate(kHAT_Atk)) +
sender.Get()->GetAttrAbs(kHAT_Atk);
float def = target->ability.def * (1 + target->GetAttrRate(kHAT_Def)) +
target->GetAttrAbs(kHAT_Def);
float finaly_dmg = dmg * (1 - def/MetaMgr::Instance()->K);
finaly_dmg = std::max(finaly_dmg, 0.0f);
target->DecHP(finaly_dmg,
sender.Get()->GetEntityUniId(),
sender.Get()->GetName(),
gun_meta->i->id());
}
}
for (auto& target : entitys) {
if (target->GetEntityType() != ET_Obstacle) {
continue;
}
Obstacle* obstacle = (Obstacle*)target;
if (!obstacle->IsDead(room) &&
obstacle->Attackable() &&
!obstacle->IsTerminatorAirDropBox(room)) {
float dmg = GetAtk() * (1 + sender.Get()->GetAttrRate(kHAT_Atk)) +
sender.Get()->GetAttrAbs(kHAT_Atk);
float def = 0;
float finaly_dmg = dmg * (1 - def/MetaMgr::Instance()->K);
obstacle->SetHealth(room, std::max(0.0f, obstacle->GetHealth(room) - finaly_dmg));
if (obstacle->GetHealth(room) <= 0.01f) {
obstacle->Die(room);
}
if (obstacle->IsDead(room)) {
if (obstacle->meta->i->damage_dia() > 0.01f &&
obstacle->meta->i->damage() > 0.01f) {
#if 0
obstacle->Explosion(this);
#endif
}
sender.Get()->DropItems(obstacle);
}
obstacle->BroadcastFullState(room);
}
}
}