本文最后更新于186 天前,其中的信息可能已经过时,如有错误请发送邮件到big_fw@foxmail.com

场景“目标选择面板”与“技能选择面板基本一致”
在选择技能之后应根据技能类型刷新技能可作用的对象
技能选择面板、目标选择面板、battle_scene & battle manager相互作用流程:
1.当双击技能后: 自动调用”按下使用按钮”方法->发出skill_selected信号->battle_scene将此信号绑定到此信号的处理函数“_on_skill_selected”
func _on_skill_selected(skill: SkillData) -> void:
current_selected_skill = skill
# 根据技能目标类型决定下一步操作
match skill.target_type:
SkillData.TargetType.SELF:
# 自身技能无需选择目标
battle_manager.player_select_action("skill", battle_manager.current_turn_character, skill)
SkillData.TargetType.ENEMY_SINGLE:
# 显示敌人目标选择菜单
var valid_targets = battle_manager.get_valid_enemy_targets()
if !valid_targets.is_empty():
target_selection_menu.show_targets(valid_targets)
else:
update_battle_info("没有可选择的敌方目标!")
_on_skill_selection_cancelled()
SkillData.TargetType.ENEMY_ALL:
# 群体敌人技能无需选择目标
var valid_targets = battle_manager.get_valid_enemy_targets()
if !valid_targets.is_empty():
battle_manager.player_select_action("skill", null, skill, valid_targets)
else:
update_battle_info("没有可选择的敌方目标!")
_on_skill_selection_cancelled()
SkillData.TargetType.ALLY_SINGLE:
# 显示我方(不含自己)目标选择菜单
var valid_targets = battle_manager.get_valid_ally_targets(false)
if !valid_targets.is_empty():
target_selection_menu.show_targets(valid_targets)
else:
update_battle_info("没有可选择的友方目标!")
_on_skill_selection_cancelled()
SkillData.TargetType.ALLY_SINGLE_INC_SELF:
# 显示我方(含自己)目标选择菜单
var valid_targets = battle_manager.get_valid_ally_targets(true)
if !valid_targets.is_empty():
target_selection_menu.show_targets(valid_targets)
else:
update_battle_info("没有可选择的友方目标!")
_on_skill_selection_cancelled()
SkillData.TargetType.ALLY_ALL:
# 群体我方(不含自己)技能
var valid_targets = battle_manager.get_valid_ally_targets(false)
if !valid_targets.is_empty():
battle_manager.player_select_action("skill", null, skill, valid_targets)
else:
update_battle_info("没有可选择的友方目标!")
_on_skill_selection_cancelled()
SkillData.TargetType.ALLY_ALL_INC_SELF:
# 群体我方(含自己)技能
var valid_targets = battle_manager.get_valid_ally_targets(true)
if !valid_targets.is_empty():
battle_manager.player_select_action("skill", null, skill, valid_targets)
else:
update_battle_info("没有可选择的友方目标!")
_on_skill_selection_cancelled()
_:
update_battle_info("未处理的目标类型: " + str(skill.target_type))
_on_skill_selection_cancelled()
2.假设选择的是“火球术‘,此时根据火球术的技能类型:敌方单体,会调用battle_manager的get_valid_enemy_targets()便利还存活的地方角色返回一个数组“valid_targets[]”.–>将此数组”valid_targets[]”通过show_targets(targets:Array[Character])展示在目标选择面板上。
func show_targets(targets: Array[Character]) -> void:
self.available_targets = targets
target_list.clear()
selected_target_index = -1
select_button.disabled = true
for i in range(targets.size()):
var character = targets[i]
if character:
var item_text = character.character_name + " (HP: " + str(character.current_hp) + "/" + str(character.max_hp) + ")"
target_list.add_item(item_text)
# 如果目标已死亡,标记为不可选
if character.current_hp <= 0:
target_list.set_item_disabled(i, true)
target_list.set_item_custom_fg_color(i, Color(0.5, 0.5, 0.5))
show()
target_list.grab_focus()
3.选择目标后容器Itemlist会返回一个Index,此时双击会发出一个信号"target_selected"(信号的参数是选择的目标对应的Index即battle_scene以及battle_manager返回的可选取对象数组对应的编号)————》target_selected会由_on_...来处理,如果判断确实使用的是单体技能就调用battle_manager的player_select_action函数
func player_select_action(action_type: String, target = null, skill_data: SkillData = null, targets : Array[Character] = []) -> void:
print("玩家选择行动: ", action_type)
# 执行选择的行动
match action_type:
"attack":
if target and target is Character:
_execute_attack(current_turn_character, target)
else:
# 默认选择第一个敌人作为目标
var default_target = null
for enemy in enemy_characters:
if enemy.current_hp > 0:
default_target = enemy
break
if default_target:
_execute_attack(current_turn_character, default_target)
else:
print("错误:没有可用的目标")
return
"defend":
_execute_defend(current_turn_character)
"skill":
var skill_targets : Array[Character] = targets
if skill_targets.is_empty():
skill_targets.append(target)
_execute_skill(current_turn_character, skill_targets, skill_data)
_:
print("未知行动类型: ", action_type)
return
# 检查战斗是否结束
if check_battle_end_condition():
return # 战斗已结束
state_manager.change_state(BattleStateManager.BattleState.TURN_END)
4.此时判断玩家使用的行动是“skill”经过判断之后执行”_execute_skill”检查mp是否足以释放技能,再判断是治疗技能还是伤害技能,在这里是伤害技能,执行“_execute_damage_skill”
5.然后调用“_calculate_skill_damage‘计算技能伤害
func _calculate_skill_damage(caster: Character, target: Character, skill: SkillData) -> int:
# 基础伤害计算
var base_damage = skill.power + (caster.magic_attack * 0.8)
# 考虑目标防御
var damage_after_defense = base_damage - (target.magic_defense * 0.5)
# 加入随机浮动因素 (±10%)
var random_factor = randf_range(0.9, 1.1)
var final_damage = damage_after_defense * random_factor
# 确保伤害至少为1
return max(1, round(final_damage))
6.对选择的目标造成这个计算出的伤害(调用Character里面的take_damage)
func take_damage(base_damage: int) -> int:
var final_damage: int = base_damage
# 如果处于防御状态,则减免伤害
if _is_defending:
final_damage = round(final_damage * 0.5)
print(character_name + " 正在防御,伤害减半!")
set_defending(false) # 防御效果通常在受到一次攻击后解除
final_damage = max(1, final_damage) # 保证至少1点伤害
current_hp = max(0, current_hp - final_damage)
hp_changed.emit(current_hp, max_hp)
if current_hp == 0:
die()
print_rich("[color=red]" + character_name + " 受到 " + str(final_damage) + " 点伤害![/color]")
return final_damage
7.再调用“spawn_damage_number”生成伤害数字
func spawn_damage_number(position: Vector2, amount: int, color : Color) -> void:
var damage_number = DAMAGE_NUMBER_SCENE.instantiate()
get_parent().add_child(damage_number)
damage_number.global_position = position + Vector2(0, -50)
damage_number.show_number(str(amount), color)


