feat(skill): 添加计时buff目标覆写功能

1. 新增BuffTarget枚举定义计时buff的四种施加目标类型
2. 扩展SkillOverrides接口添加buff_target配置项
3. 实现resolveBuffTargets方法解析buff实际施加目标
4. 调整普攻buff施加逻辑适配新的目标配置规则
5. 修复伤害技能误给敌方挂友方buff的问题
6. 清理英雄技能配置中多余的summon_count参数
This commit is contained in:
panFD
2026-09-05 12:22:18 +08:00
parent 7949f7d1d7
commit 071afc8fa2
4 changed files with 63 additions and 14 deletions

View File

@@ -11,7 +11,7 @@ import { HeroInfo } from "../common/config/heroSet";
import { oops } from "db://oops-framework/core/Oops";
import { GameEvent } from "../common/config/GameEvent";
import { SkillTriggerType } from "../common/config/heroSet";
import { FieldSkillType } from "../common/config/SkillSet";
import { FieldSkillType, BuffTarget } from "../common/config/SkillSet";
import { mLogger } from "../common/Logger";
import { SkillTriggerHelper } from "./SkillTriggerHelper";
@@ -257,7 +257,7 @@ export class HeroAtkSystem extends ecs.ComblockSystem implements ecs.ISystemUpda
}
}
// 命中附带 debuff(如灼烧 DoT):仅普攻路径,复用友方 timed_buff_id 机制;
// 命中附带 buff:仅普攻路径;buff_target 缺省挂被命中者,显式配置可改为挂施法者/全体友方/全体敌方
// 施法者 ap/完整属性快照取自伤害事件,供 BuffSystem tick 缩放与暴击/冰冻/击晕判定
if (!isDot && skillConf.timed_buff_id) {
const buffChance = skillConf.buff_chance ?? 100;
@@ -265,7 +265,9 @@ export class HeroAtkSystem extends ecs.ComblockSystem implements ecs.ISystemUpda
const buffOverrides: BuffApplyOverrides = { source_attrs: damageEvent.Attrs };
if (skillConf.buff_value !== undefined) buffOverrides.value = skillConf.buff_value;
if (skillConf.buff_duration !== undefined) buffOverrides.duration = skillConf.buff_duration;
buffManager.applyBuff(target, skillConf.timed_buff_id, casterEid, damageEvent.Attrs[Attrs.ap] || 0, buffOverrides);
for (const buffTarget of this.resolveBuffTargets(target, casterEid, TAttrsComp.fac, skillConf.buff_target)) {
buffManager.applyBuff(buffTarget, skillConf.timed_buff_id, casterEid, damageEvent.Attrs[Attrs.ap] || 0, buffOverrides);
}
}
}
@@ -527,6 +529,38 @@ export class HeroAtkSystem extends ecs.ComblockSystem implements ecs.ISystemUpda
return { remainingDamage: damage - absorbed, absorbedDamage: absorbed };
}
/**
* 解析 timed_buff_id 的施加目标实体列表。
* 缺省(undefined / BuffTarget.Hit)返回被命中者;显式配置可切换到施法者自身、全体友方或全体敌方。
* @param hitTarget 被命中实体(伤害事件的 target)
* @param casterEid 施法者 eid
* @param targetFac 被命中者阵营(用于推导敌我网格)
* @param buffTarget 技能配置上的目标覆写
*/
private resolveBuffTargets(hitTarget: ecs.Entity, casterEid: number, targetFac: number, buffTarget?: BuffTarget): ecs.Entity[] {
if (buffTarget === undefined || buffTarget === BuffTarget.Hit) {
return [hitTarget];
}
if (buffTarget === BuffTarget.Self) {
const caster = ecs.getEntityByEid(casterEid);
return caster ? [caster] : [];
}
// 全体友方/敌方:以施法者阵营为基准(命中者必为敌方,施法方网格即友方)
const casterFac = targetFac === FacSet.HERO ? FacSet.MON : FacSet.HERO;
const grid = buffTarget === BuffTarget.Ally
? (casterFac === FacSet.HERO ? smc.mission.heroGrid : smc.mission.monGrid)
: (casterFac === FacSet.HERO ? smc.mission.monGrid : smc.mission.heroGrid);
const targets: ecs.Entity[] = [];
for (const eid of grid) {
if (eid < 0) continue;
const ent = ecs.getEntityByEid(eid);
if (!ent) continue;
const attrs = ent.get(HeroAttrsComp);
if (attrs && !attrs.is_dead && !attrs.is_reviving) targets.push(ent);
}
return targets;
}
/**
* 被攻击时触发的事件
*

View File

@@ -2,7 +2,7 @@ import { ecs } from "../../../../extensions/oops-plugin-framework/assets/libs/ec
import { Vec3, Prefab, instantiate, tween, Node } from "cc";
import { HeroAttrsComp } from "./HeroAttrsComp";
import { HeroViewComp } from "./HeroViewComp";
import { DTType, RType, SkillConfig, SkillKind, SkillSet, TGroup, SkillOverrides, mergeSkillParams } from "../common/config/SkillSet";
import { DTType, RType, SkillConfig, SkillKind, SkillSet, TGroup, SkillOverrides, mergeSkillParams, BuffTarget } from "../common/config/SkillSet";
import { Skill } from "../skill/Skill";
import { SkillView } from "../skill/SkillView";
import { smc } from "../common/SingletonModuleComp";
@@ -545,7 +545,8 @@ export class SCastSystem extends ecs.ComblockSystem implements ecs.ISystemUpdate
if (config.buff_type !== undefined) {
// 计时性 buff:配置了 timed_buff_id 时走 buffManager 限时路径,
// 同一技能不应既永久加成又限时加成,故提前 return 跳过下方永久 add_* 逻辑
if (config.timed_buff_id) {
// buff_target=Enemy 时 timed_buff_id 已在 applyFriendlySkillEffects 入口分流到敌方网格,此处跳过避免误挂友方
if (config.timed_buff_id && config.buff_target !== BuffTarget.Enemy) {
// 汇总 buff 覆写参数:value 覆写修饰数值,duration 覆写持续时间
const buffOverrides: { value?: number; duration?: number } = {};
if (config.buff_value !== undefined) buffOverrides.value = config.buff_value;