跳到主要内容

伤害系统

EMC 玩家属性提供完整的伤害计算框架,支持 6 种伤害类型和链式伤害处理器。

伤害类型

类型中文说明
PHYSICAL物理伤害受物理防御减免,受护甲穿透影响
MAGIC魔法伤害受魔法防御减免,受魔抗穿透影响
TRUE_DAMAGE真实伤害无视防御,但受伤害减免影响
PURE纯粹伤害无视一切减免
ENVIRONMENT环境伤害摔落、溺水、火焰等环境伤害
CUSTOM自定义伤害由其他插件定义的特殊伤害

伤害上下文 (DamageContext)

每次伤害事件都会创建一个 DamageContext 对象,包含伤害计算所需的全部信息:

  • 攻击者 — 造成伤害的玩家/实体
  • 受害者 — 承受伤害的玩家/实体
  • 伤害类型 — 上述 6 种之一
  • 基础伤害 — 初始伤害值
  • 最终伤害 — 经过处理链后的伤害值
  • 是否暴击 — 暴击标记
  • 是否取消 — 处理器可取消伤害

伤害处理链

多个伤害处理器按优先级顺序执行,形成处理链。每个处理器可以修改伤害值、标记暴击或取消伤害。

处理流程

原始伤害事件

DamageContext 创建

处理器 1 (优先级 0) — 武器属性计算

处理器 2 (优先级 10) — 饰品加成计算

处理器 3 (优先级 20) — 技能加成(第三方)

处理器 N ...

最终伤害应用

触发 CustomDamageEvent

内置处理器

处理器来源优先级功能
WeaponDamageHandlerEMC 自定义武器0应用武器攻击力、暴击、元素伤害
AccessoryDamageHandlerEMC 自定义饰品10应用饰品属性加成、触发效果

自定义事件

CustomDamageEvent

伤害计算完成后触发,其他插件可监听此事件进行二次处理。

@EventHandler
public void onCustomDamage(CustomDamageEvent event) {
DamageContext ctx = event.getContext();
// 获取最终伤害
double finalDamage = ctx.getFinalDamage();
// 是否暴击
boolean isCrit = ctx.isCritical();
// 修改伤害
ctx.setFinalDamage(finalDamage * 1.5);
// 取消伤害
ctx.setCancelled(true);
}

PlayerAttributeChangeEvent

玩家属性发生变化时触发。

@EventHandler
public void onAttrChange(PlayerAttributeChangeEvent event) {
Player player = event.getPlayer();
Attribute attr = event.getAttribute();
double oldValue = event.getOldValue();
double newValue = event.getNewValue();
}

PlayerAttributeRecalculateEvent

玩家属性重新计算时触发(装备变更、Buff 更新等)。

@EventHandler
public void onRecalculate(PlayerAttributeRecalculateEvent event) {
Player player = event.getPlayer();
// 在重算完成后添加额外修改
}

伤害计算公式参考

物理伤害

有效防御 = 物理防御 × (1 - 护甲穿透百分比) - 护甲穿透固定值
减免率 = 有效防御 / (有效防御 + 常数)
最终伤害 = 物理攻击 × (1 - 减免率) × (1 - 物理伤害减免) × (1 - 伤害减免)

魔法伤害

有效魔抗 = 魔法防御 × (1 - 魔抗穿透百分比) - 魔抗穿透固定值
减免率 = 有效魔抗 / (有效魔抗 + 常数)
最终伤害 = 魔法攻击 × (1 - 减免率) × (1 - 魔法伤害减免) × (1 - 伤害减免)

暴击

if (随机值 < 暴击率):
最终伤害 = 最终伤害 × 暴击伤害倍率

吸血

物理吸血回复 = 物理伤害 × 物理吸血率
魔法吸血回复 = 魔法伤害 × 魔法吸血率