diff --git a/server/gameserver/creature.cc b/server/gameserver/creature.cc index 99adaad..5269fb9 100644 --- a/server/gameserver/creature.cc +++ b/server/gameserver/creature.cc @@ -102,6 +102,16 @@ void InternalShot(Creature* c, { if (weapon_meta->i->_inventory_slot() == IS_TRAP || weapon_meta->i->_inventory_slot() == IS_MINE) { + if (skill_id == 0) { + c->room->frame_event.AddShot(c->GetWeakPtrRef()); + } + if (weapon_meta->i->cast_time() > 0) { + int buff_uniid = c->TryAddBuff(c, kVertigoBuffId); + Buff* buff = c->GetBuffByUniId(buff_uniid); + if (buff && buff->remover_timer) { + c->room->xtimer.ModifyTimer(buff->remover_timer, weapon_meta->i->cast_time() / FRAME_RATE_MS); + } + } a8::Vec2 old_context_dir = c->context_dir; a8::Vec2 old_context_pos = c->context_pos; c->context_dir =c->GetAttackDir(); @@ -2622,81 +2632,23 @@ void Creature::AutoSwitchWeapon() bool switch_ok = false; int slot_id = weapon_meta->i->_inventory_slot(); - switch (slot_id) { - case IS_FRAG: //手雷 - case IS_SMOKE: //烟雾弹 - { - if (c->GetCurrWeapon()->ammo <= 0) { - if (c->GetInventory(slot_id) > 0) { - } else { - int weapon_idx = c->GetCurrWeapon()->weapon_idx; - *c->GetCurrWeapon() = Weapon(); - c->GetCurrWeapon()->weapon_idx = weapon_idx; - Weapon* next_weapon = c->ChooseNextWeapon(slot_id, SPEC1_IS_BEGIN, SPEC1_IS_END); - if (!next_weapon) { - next_weapon = c->ChooseNextWeapon(SPEC2_IS_BEGIN, SPEC2_IS_BEGIN, SPEC2_IS_END); - } - if (!next_weapon) { - next_weapon = c->AutoChgWeapon(); - } - c->SetCurrWeapon(next_weapon); - switch_ok = true; - } + if (c->GetCurrWeapon()->ammo <= 0 && slot_id > 0) { + if (c->GetInventory(slot_id) > 0) { + } else { + int weapon_idx = c->GetCurrWeapon()->weapon_idx; + *c->GetCurrWeapon() = Weapon(); + c->GetCurrWeapon()->weapon_idx = weapon_idx; + Weapon* next_weapon = c->ChooseNextSpecWeapon(slot_id); + if (!next_weapon) { + next_weapon = c->AutoChgWeapon(); + } + if (next_weapon) { + c->SetCurrWeapon(next_weapon); + switch_ok = true; + } else { + abort(); } } - break; - case IS_POSION_GAS_BOMB: //毒气弹 - case IS_MOLOTOR_COCKTAIL: //燃烧瓶 - case IS_TRAP: //陷井 - case IS_MINE: //地雷 - { - if (c->GetCurrWeapon()->ammo <= 0) { - if (c->GetInventory(slot_id) > 0) { - } else { - int weapon_idx = c->GetCurrWeapon()->weapon_idx; - *c->GetCurrWeapon() = Weapon(); - c->GetCurrWeapon()->weapon_idx = weapon_idx; - Weapon* next_weapon = c->ChooseNextWeapon(slot_id, SPEC2_IS_BEGIN, SPEC2_IS_END); - if (!next_weapon) { - next_weapon = c->ChooseNextWeapon(SPEC1_IS_BEGIN, SPEC1_IS_BEGIN, SPEC1_IS_END); - } - if (!next_weapon) { - next_weapon = c->AutoChgWeapon(); - } - c->SetCurrWeapon(next_weapon); - switch_ok = true; - } - } - } - break; - case IS_C4: - case IS_SHIELD_WALL: - case IS_SINGAL_GUN: - case IS_OIL_BUCKET: - { - if (c->GetCurrWeapon()->ammo <= 0) { - if (c->GetInventory(slot_id) > 0) { - } else { - int weapon_idx = c->GetCurrWeapon()->weapon_idx; - *c->GetCurrWeapon() = Weapon(); - c->GetCurrWeapon()->weapon_idx = weapon_idx; - Weapon* next_weapon = c->ChooseNextWeapon(slot_id, SPEC3_IS_BEGIN, SPEC3_IS_END); - if (!next_weapon) { - next_weapon = c->ChooseNextWeapon(SPEC1_IS_BEGIN, SPEC1_IS_BEGIN, SPEC1_IS_END); - } - if (!next_weapon) { - next_weapon = c->AutoChgWeapon(); - } - c->SetCurrWeapon(next_weapon); - switch_ok = true; - } - } - } - break; - default: - { - } - break; } if (switch_ok) { c->need_sync_active_player = true; @@ -2754,3 +2706,37 @@ void Creature::CheckLoadingBullet() } } } + +Weapon* Creature::ChooseNextSpecWeapon(int curr_weapon_slot_id) +{ + Weapon* next_weapon = nullptr; + int data[][3]= { + {SPEC1_IS_BEGIN, SPEC1_IS_END, 0}, + {SPEC2_IS_BEGIN, SPEC2_IS_END, 0}, + {SPEC3_IS_BEGIN, SPEC3_IS_END, 0} + }; + int idx = -1; + for (int i = 0; i < sizeof(data) /sizeof(data[0]); ++i) { + int start_id = data[i][0]; + int end_id = data[i][1]; + if (curr_weapon_slot_id >= start_id && + curr_weapon_slot_id <= end_id) { + idx = i; + data[i][2] = 1; + break; + } + } + if (idx > -1) { + for (int i = 0; i < sizeof(data) /sizeof(data[0]); ++i) { + int real_i = (i + idx) % sizeof(data) /sizeof(data[0]); + int start_id = data[real_i][0]; + int end_id = data[real_i][1]; + int flag = data[real_i][2]; + next_weapon = ChooseNextWeapon(flag ? curr_weapon_slot_id : start_id, start_id, end_id); + if (next_weapon) { + break; + } + } + } + return next_weapon; +} diff --git a/server/gameserver/creature.h b/server/gameserver/creature.h index ff1a9b3..5b9670c 100644 --- a/server/gameserver/creature.h +++ b/server/gameserver/creature.h @@ -186,6 +186,7 @@ class Creature : public MoveableEntity CreatureWeakPtr& GetWeakPtrRef(); Weapon* AutoChgWeapon(); Weapon* ChooseNextWeapon(int curr_weapon_slot_id, int begin_slot_id, int end_slot_id); + Weapon* ChooseNextSpecWeapon(int curr_weapon_slot_id); Weapon* GetCurrWeapon() { return curr_weapon_; }; void SetCurrWeapon(Weapon* weapon); void ResetAllSkillCd();