refactor(enemy): RepeatSlam 参数迁入 RepeatSlamAbilitySO(子类)

This commit is contained in:
2026-07-21 11:23:11 +08:00
parent 6873a2cd8e
commit 1e3b01705f
3 changed files with 56 additions and 25 deletions
@@ -0,0 +1,23 @@
using Animancer;
using UnityEngine;
namespace BaseGames.Enemies.Abilities
{
/// <summary>RepeatSlamAbility 的配置:起手/循环/收招动画 + 砸地行为参数。</summary>
[CreateAssetMenu(menuName = "BaseGames/Enemies/Abilities/Repeat Slam Ability", fileName = "ABL_")]
public class RepeatSlamAbilitySO : EnemyAbilitySO
{
[Header("动画")]
public ClipTransition startClip;
public ClipTransition loopClip;
public ClipTransition endClip;
[Header("行为配置")]
[Tooltip("每次砸地时 HitBox 激活时长(秒)")]
public float hitActiveTime = 0.15f;
[Tooltip("砸地次数")]
public int slamCount = 2;
[Tooltip("最后一次砸地收招后额外等待时间(秒)")]
public float staggerDuration = 1.2f;
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: a30689ce0afa0c64cb6f93b9222e1c2c
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:
@@ -12,58 +12,55 @@ namespace BaseGames.Enemies.Abilities
/// </summary> /// </summary>
public class RepeatSlamAbility : EnemyAbilityBase public class RepeatSlamAbility : EnemyAbilityBase
{ {
[Header("动画")]
[SerializeField] private ClipTransition _startClip;
[SerializeField] private ClipTransition _loopClip;
[SerializeField] private ClipTransition _endClip;
[Header("打击")] [Header("打击")]
[SerializeField] private HitBox _hitBox; [SerializeField] private HitBox _hitBox;
[Header("行为配置")] private RepeatSlamAbilitySO _cfg;
[Tooltip("每次砸地时 HitBox 激活时长(秒)")]
[SerializeField] private float _hitActiveTime = 0.15f; protected override void Awake()
[Tooltip("砸地次数")] {
[SerializeField] private int _slamCount = 2; base.Awake();
[Tooltip("最后一次砸地收招后额外等待时间(秒)")] _cfg = ResolveConfig<RepeatSlamAbilitySO>();
[SerializeField] private float _staggerDuration = 1.2f; }
protected override IEnumerator ExecuteCoroutine() protected override IEnumerator ExecuteCoroutine()
{ {
if (_cfg == null) yield break;
Phase = AbilityRunState.Active; Phase = AbilityRunState.Active;
if (_startClip.Clip != null) if (_cfg.startClip.Clip != null)
{ {
_animancer.Play(_startClip); _animancer.Play(_cfg.startClip);
yield return EnemyAbilityWaits.Get(_startClip.Clip.length); yield return EnemyAbilityWaits.Get(_cfg.startClip.Clip.length);
} }
for (int i = 0; i < _slamCount; i++) for (int i = 0; i < _cfg.slamCount; i++)
{ {
if (_loopClip.Clip != null) if (_cfg.loopClip.Clip != null)
{ {
_animancer.Play(_loopClip); _animancer.Play(_cfg.loopClip);
float preHit = Mathf.Max(0f, _loopClip.Clip.length - _hitActiveTime - 0.05f); float preHit = Mathf.Max(0f, _cfg.loopClip.Clip.length - _cfg.hitActiveTime - 0.05f);
yield return EnemyAbilityWaits.Get(preHit); yield return EnemyAbilityWaits.Get(preHit);
} }
var dmgSrc = _config?.attackSequence?.Length > 0 ? _config.attackSequence[0].damageSource : null; var dmgSrc = _config?.attackSequence?.Length > 0 ? _config.attackSequence[0].damageSource : null;
_hitBox?.Activate(dmgSrc, _transform); _hitBox?.Activate(dmgSrc, _transform);
yield return EnemyAbilityWaits.Get(_hitActiveTime); yield return EnemyAbilityWaits.Get(_cfg.hitActiveTime);
_hitBox?.Deactivate(); _hitBox?.Deactivate();
if (i < _slamCount - 1) if (i < _cfg.slamCount - 1)
yield return EnemyAbilityWaits.Get(0.1f); yield return EnemyAbilityWaits.Get(0.1f);
} }
if (_endClip.Clip != null) if (_cfg.endClip.Clip != null)
{ {
_animancer.Play(_endClip); _animancer.Play(_cfg.endClip);
yield return EnemyAbilityWaits.Get(_endClip.Clip.length + _staggerDuration); yield return EnemyAbilityWaits.Get(_cfg.endClip.Clip.length + _cfg.staggerDuration);
} }
else else
{ {
yield return EnemyAbilityWaits.Get(_staggerDuration); yield return EnemyAbilityWaits.Get(_cfg.staggerDuration);
} }
} }