This commit is contained in:
aozhiwei 2021-03-08 16:35:41 +08:00
parent 3fe0802f45
commit ae4a083fe3
4 changed files with 52 additions and 182 deletions

View File

@ -333,9 +333,11 @@ enum AIMode_e
enum ColliderTag_e
{
kHalfWallTag = 1,
kColliderSpecTag_Begin = 2,
kColliderTag_Grass = 2, //草丛
kColliderTag_Water = 3, //水
kColliderTag_Ice = 4, //冰
kColliderSpecTag_End = 4,
};
enum GameChannel_e
@ -409,3 +411,5 @@ const int PASSENGER_BUFFID = 6004;
const int GRASS_HIDE_BUFF_ID = 6005;
const int WATER_BUFF_ID = 6006;
const int ICE_BUFF_ID = 6007;
const long long SPEC_MAP_OBJECT_FLAGS = A8_DEFINE_RANGE_BIT(long long, kColliderSpecTag_Begin, kColliderSpecTag_End);

View File

@ -4284,179 +4284,44 @@ void Human::DoGetOnWithCar(Car* car)
void Human::CheckSpecObject()
{
long long spec_flags = 0;
a8::SetBitFlag(spec_flags, kColliderTag_Grass);
a8::SetBitFlag(spec_flags, kColliderTag_Water);
a8::SetBitFlag(spec_flags, kColliderTag_Ice);
std::set<ColliderComponent*> colliders;
room->map_service->GetSpecColliders(spec_flags, room, GetPos().x, GetPos().y, colliders);
room->map_service->GetSpecColliders(SPEC_MAP_OBJECT_FLAGS, room, GetPos().x, GetPos().y, colliders);
bool in_grass = false;
bool in_water = false;
bool in_ice = false;
long long flags = 0;
for (const ColliderComponent* collider : colliders) {
switch (collider->owner->GetEntityType()) {
case ET_Obstacle:
case ET_Building:
{
if (TestCollision(room, (ColliderComponent*)collider)) {
flags |= collider->tag;
}
}
break;
default:
break;
}
}
if (in_grass) {
if (!HasBuffEffect(kBET_InGrass)) {
OnEnterGrass();
}
} else {
if (HasBuffEffect(kBET_InGrass)) {
OnLeaveGrass();
}
}
if (in_water) {
if (!HasBuffEffect(kBET_InWater)) {
OnEnterWater();
}
} else {
if (HasBuffEffect(kBET_InWater)) {
OnLeaveWater();
}
}
if (in_ice) {
if (!HasBuffEffect(kBET_InIce)) {
OnEnterIce();
}
} else {
if (HasBuffEffect(kBET_InIce)) {
OnLeaveIce();
for (int i = kColliderSpecTag_Begin; i <= kColliderSpecTag_End; ++i) {
SpecMapObject& map_obj = spec_map_objects_[i - kColliderSpecTag_Begin];
int buff_effect = 0;
if (a8::HasBitFlag(flags, i)) {
if (!HasBuffEffect(buff_effect)) {
OnEnterSpecMapArea(i, map_obj);
}
} else {
if (HasBuffEffect(buff_effect)) {
OnLeaveSpecMapArea(i, map_obj);
}
}
}
}
void Human::OnEnterGrass()
void Human::OnEnterSpecMapArea(int tag, SpecMapObject& map_obj)
{
if (leave_grass_timer_) {
room->xtimer.DeleteTimer(leave_grass_timer_);
leave_grass_timer_ = nullptr;
}
if (hide_grass_timer_) {
room->xtimer.DeleteTimer(hide_grass_timer_);
hide_grass_timer_ = nullptr;
}
hide_grass_timer_ = room->xtimer.AddDeadLineTimerAndAttach
(MetaMgr::Instance()->grass_invisible_time * SERVER_FRAME_RATE,
a8::XParams()
.SetSender(this),
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
MetaData::Buff* buff_meta = MetaMgr::Instance()->GetBuff(GRASS_HIDE_BUFF_ID);
if (buff_meta) {
hum->AddBuff(hum, buff_meta, 1);
}
},
&xtimer_attacher.timer_list_,
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->hide_grass_timer_ = nullptr;
});
}
void Human::OnLeaveGrass()
{
if (hide_grass_timer_) {
room->xtimer.DeleteTimer(hide_grass_timer_);
hide_grass_timer_ = nullptr;
}
if (leave_grass_timer_) {
room->xtimer.DeleteTimer(leave_grass_timer_);
}
leave_grass_timer_ = room->xtimer.AddDeadLineTimerAndAttach
(MetaMgr::Instance()->grass_show_time * SERVER_FRAME_RATE,
a8::XParams()
.SetSender(this),
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->leave_grass_timer_ = nullptr;
hum->RemoveBuffById(GRASS_HIDE_BUFF_ID);
},
&xtimer_attacher.timer_list_,
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->leave_grass_timer_ = nullptr;
});
}
void Human::OnEnterWater()
{
if (leave_water_timer_) {
room->xtimer.DeleteTimer(leave_water_timer_);
leave_water_timer_ = nullptr;
}
if (hide_water_timer_) {
room->xtimer.DeleteTimer(hide_water_timer_);
hide_water_timer_ = nullptr;
}
hide_water_timer_ = room->xtimer.AddDeadLineTimerAndAttach
(MetaMgr::Instance()->water_invisible_time * SERVER_FRAME_RATE,
a8::XParams()
.SetSender(this),
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
MetaData::Buff* buff_meta = MetaMgr::Instance()->GetBuff(WATER_BUFF_ID);
if (buff_meta) {
hum->AddBuff(hum, buff_meta, 1);
}
},
&xtimer_attacher.timer_list_,
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->hide_water_timer_ = nullptr;
});
}
void Human::OnLeaveWater()
{
if (hide_water_timer_) {
room->xtimer.DeleteTimer(hide_water_timer_);
hide_water_timer_ = nullptr;
}
if (leave_water_timer_) {
room->xtimer.DeleteTimer(leave_water_timer_);
}
leave_water_timer_ = room->xtimer.AddDeadLineTimerAndAttach
(MetaMgr::Instance()->water_show_time * SERVER_FRAME_RATE,
a8::XParams()
.SetSender(this),
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->RemoveBuffById(WATER_BUFF_ID);
},
&xtimer_attacher.timer_list_,
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->leave_water_timer_ = nullptr;
});
}
void Human::OnEnterIce()
{
if (leave_ice_timer_) {
room->xtimer.DeleteTimer(leave_ice_timer_);
leave_ice_timer_ = nullptr;
}
if (hide_ice_timer_) {
room->xtimer.DeleteTimer(hide_ice_timer_);
hide_ice_timer_ = nullptr;
}
hide_ice_timer_ = room->xtimer.AddDeadLineTimerAndAttach
ClearSpecMapAreaTimer(map_obj);
map_obj.enter_timer = room->xtimer.AddDeadLineTimerAndAttach
(MetaMgr::Instance()->ice_invisible_time * SERVER_FRAME_RATE,
a8::XParams()
.SetSender(this),
@ -4471,21 +4336,14 @@ void Human::OnEnterIce()
&xtimer_attacher.timer_list_,
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->hide_ice_timer_ = nullptr;
Human* hum = (Human*)param.sender.GetUserData();
});
}
void Human::OnLeaveIce()
void Human::OnLeaveSpecMapArea(int tag, SpecMapObject& map_obj)
{
if (hide_ice_timer_) {
room->xtimer.DeleteTimer(hide_ice_timer_);
hide_ice_timer_ = nullptr;
}
if (leave_ice_timer_) {
room->xtimer.DeleteTimer(leave_ice_timer_);
}
leave_ice_timer_ = room->xtimer.AddDeadLineTimerAndAttach
ClearSpecMapAreaTimer(map_obj);
map_obj.leave_timer = room->xtimer.AddDeadLineTimerAndAttach
(MetaMgr::Instance()->ice_show_time * SERVER_FRAME_RATE,
a8::XParams()
.SetSender(this),
@ -4498,6 +4356,17 @@ void Human::OnLeaveIce()
[] (const a8::XParams& param)
{
Human* hum = (Human*)param.sender.GetUserData();
hum->leave_ice_timer_ = nullptr;
});
}
void Human::ClearSpecMapAreaTimer(SpecMapObject& map_obj)
{
if (map_obj.leave_timer) {
room->xtimer.DeleteTimer(map_obj.leave_timer);
map_obj.leave_timer = nullptr;
}
if (map_obj.enter_timer) {
room->xtimer.DeleteTimer(map_obj.enter_timer);
map_obj.enter_timer = nullptr;
}
}

View File

@ -28,6 +28,12 @@ enum HumanStatus
HS_End
};
struct SpecMapObject
{
struct xtimer_list* leave_timer = nullptr;
struct xtimer_list* enter_timer = nullptr;
};
struct xtimer_list;
class CircleCollider;
class AabbCollider;
@ -356,12 +362,9 @@ private:
void DoGetOnWithLoot(Loot* loot_entity);
void DoGetOnWithCar(Car* car);
void CheckSpecObject();
void OnEnterGrass();
void OnLeaveGrass();
void OnEnterWater();
void OnLeaveWater();
void OnEnterIce();
void OnLeaveIce();
void OnEnterSpecMapArea(int tag, SpecMapObject& map_obj);
void OnLeaveSpecMapArea(int tag, SpecMapObject& map_obj);
void ClearSpecMapAreaTimer(SpecMapObject& map_obj);
protected:
int level_ = 0;
@ -426,6 +429,7 @@ private:
std::array<float, kHAT_End> buff_attr_rate_ = {};
std::array<ObjectSyncFlags, FIXED_OBJECT_MAXID> fixed_object_sync_flags_ = {};
std::array<SpecMapObject, kColliderSpecTag_End - kColliderSpecTag_Begin + 1> spec_map_objects_ = {};
bool already_report_battle_ = false;
bool sent_battlereport_ = false;
@ -436,13 +440,6 @@ private:
Entity* last_collision_door_ = nullptr;
long long jump_frameno_ = 0;
xtimer_list* leave_grass_timer_ = nullptr;
xtimer_list* hide_grass_timer_ = nullptr;
xtimer_list* leave_water_timer_ = nullptr;
xtimer_list* hide_water_timer_ = nullptr;
xtimer_list* leave_ice_timer_ = nullptr;
xtimer_list* hide_ice_timer_ = nullptr;
friend class FrameMaker;
friend class FrameEvent;
};

@ -1 +1 @@
Subproject commit a0d01a57a5792268b7dd0c144dfda00e7e171d80
Subproject commit 9f43c10312f3f3adccab2d477365c0c1d9200e03