Files
Continentis/Assets/Scripts/MainGame/Character/CharacterBuff/CharacterCombatBuffBase.cs

202 lines
8.0 KiB
C#
Raw Normal View History

2025-10-24 09:11:22 -04:00
using System.Collections.Generic;
2025-10-03 00:02:43 -04:00
using System.Linq;
using Continentis.MainGame.Card;
2026-04-01 12:23:27 -04:00
using Continentis.MainGame.Combat;
2025-10-03 00:02:43 -04:00
using Continentis.MainGame.UI;
2026-04-17 12:01:50 -04:00
using SLSUtilities.General;
2025-10-03 00:02:43 -04:00
using UnityEngine;
namespace Continentis.MainGame.Character
{
2025-10-24 09:11:22 -04:00
public abstract partial class CharacterCombatBuffBase : CharacterBuffBase
2025-10-03 00:02:43 -04:00
{
public CardLogicBase sourceCard;
2025-10-30 04:21:28 -04:00
/// <summary>
/// 行动计数,每次行动开始时计数-1。
/// </summary>
2025-10-23 00:49:44 -04:00
public CountSubmodule actionCountSubmodule;
2025-10-30 04:21:28 -04:00
/// <summary>
/// 回合计数,每回合开始时计数-1。
/// </summary>
public CountSubmodule roundCountSubmodule;
/// <summary>
/// 首次行动计数,仅在角色本回合首次行动时计数-1。
/// </summary>
public CountSubmodule roundFirstActionCountSubmodule;
2025-10-03 00:02:43 -04:00
public UnitedStackSubmodule unitedStackSubmodule;
public IndependentStackSubmodule independentStackSubmodule;
public GeneralAttributeSubmodule generalAttributeSubmodule;
public StatusSubmodule statusSubmodule;
}
2025-10-24 09:11:22 -04:00
public partial class CharacterCombatBuffBase
2025-10-03 00:02:43 -04:00
{
2026-03-20 11:56:50 -04:00
/// <summary>
/// 基类的泛型签名由此层密封并桥接到强类型版本,子类请实现
/// <see cref="OnBuffApply(out CharacterCombatBuffBase)"/>。
/// </summary>
2025-10-03 00:02:43 -04:00
public sealed override bool OnBuffApply(out BuffBase<CharacterBase> existingBuff)
{
2026-03-20 11:56:50 -04:00
bool result = OnBuffApply(out CharacterCombatBuffBase typed);
existingBuff = typed;
return result;
2025-10-03 00:02:43 -04:00
}
2026-03-20 11:56:50 -04:00
/// <summary>
/// Buff被尝试添加到角色时调用。
/// 返回 true 表示这是全新 Buff返回 false 表示已有同类 Buff 存在(通过 out 参数返回)。
/// </summary>
2025-11-12 01:20:19 -06:00
public abstract bool OnBuffApply(out CharacterCombatBuffBase existingBuff);
2025-10-03 00:02:43 -04:00
public override void OnAfterFirstApply()
{
2025-10-24 09:11:22 -04:00
statusSubmodule?.AddStatus();
2025-11-10 12:57:04 -05:00
attachedCharacter.combatBuffSubmodule.buffList.Exclude(this).For(buff => buff.eventSubmodule?.onOtherBuffFirstApplied.Invoke(this));
2025-10-03 00:02:43 -04:00
}
2025-10-23 00:49:44 -04:00
public override void OnBuffRemove()
2025-10-03 00:02:43 -04:00
{
2025-10-23 00:49:44 -04:00
RefreshAttributes();
2025-10-24 09:11:22 -04:00
statusSubmodule?.RemoveStatus();
2025-10-23 00:49:44 -04:00
iconSubmodule?.Remove();
2025-10-03 00:02:43 -04:00
}
}
2025-10-24 09:11:22 -04:00
public partial class CharacterCombatBuffBase
2025-10-03 00:02:43 -04:00
{
2025-10-23 00:49:44 -04:00
protected bool FindExistingSameBuff<T>(out T existingBuff) where T : CharacterBuffBase
2025-10-03 00:02:43 -04:00
{
2025-12-13 23:28:23 -05:00
bool result = FindExistingSameBuffs(out List<T> existingBuffs, attachedCharacter.combatBuffSubmodule.buffList);
existingBuff = result ? existingBuffs[0] : null;
return result;
}
protected bool FindExistingSameBuffs<T>(out List<T> existingBuffs) where T : CharacterBuffBase
{
bool result = FindExistingSameBuffs(out existingBuffs, attachedCharacter.combatBuffSubmodule.buffList);
return result;
2025-10-03 00:02:43 -04:00
}
public override void Apply(CharacterBase attachedCharacter, CharacterBase sourceCharacter = null)
{
this.Apply(attachedCharacter, sourceCharacter, null);
}
public void Apply(CharacterBase attachedCharacter, CharacterBase sourceCharacter = null, CardLogicBase sourceCard = null)
{
this.attachedCharacter = attachedCharacter;
this.sourceCharacter = sourceCharacter;
this.sourceCard = sourceCard;
2025-10-23 00:49:44 -04:00
2025-10-24 09:11:22 -04:00
if (OnBuffApply(out CharacterCombatBuffBase existingBuff))
2025-10-03 00:02:43 -04:00
{
2025-10-24 09:11:22 -04:00
this.attachedCharacter.combatBuffSubmodule.buffList.AddByPriority(this);
2025-10-23 00:49:44 -04:00
2025-10-03 00:02:43 -04:00
OnAfterFirstApply();
2025-10-23 00:49:44 -04:00
if (iconSubmodule != null)
2025-10-03 00:02:43 -04:00
{
2025-10-23 00:49:44 -04:00
(attachedCharacter.characterView.hudContainer.enablingHUDs["CharacterBuffCollection"] as HUD_CharacterBuffCollection)
?.AddBuffIcon(this);
2025-10-03 00:02:43 -04:00
}
2026-04-01 12:23:27 -04:00
// 1.2c — 记录 Buff 首次施加日志
CombatLogs.Instance?.LogBuffApply(this, attachedCharacter);
2025-10-03 00:02:43 -04:00
}
else
{
2025-10-25 07:49:39 -04:00
existingBuff.iconSubmodule?.Update();
2025-10-03 00:02:43 -04:00
}
2025-11-10 12:57:04 -05:00
attachedCharacter.combatBuffSubmodule.buffList.Exclude(this).For(buff => buff.eventSubmodule?.onOtherBuffApplied.Invoke(this));
2025-10-23 00:49:44 -04:00
RefreshAttributes();
iconSubmodule?.Update();
2025-11-15 12:17:34 -05:00
attachedCharacter.deckSubmodule.GetAllCards().ForEach(card => card.RefreshCardAttributes());
2025-10-03 00:02:43 -04:00
}
public override void Remove()
{
2026-04-01 12:23:27 -04:00
// 1.2c — 记录 Buff 移除日志
CombatLogs.Instance?.LogBuffRemove(this);
2025-10-03 00:02:43 -04:00
OnBuffRemove();
2025-12-14 00:51:34 -05:00
if (iconSubmodule != null)
{
(attachedCharacter.characterView.hudContainer.enablingHUDs["CharacterBuffCollection"] as HUD_CharacterBuffCollection)
?.RemoveBuffIcon(this);
}
2025-10-03 00:02:43 -04:00
this.attachedCharacter.combatBuffSubmodule.buffList.Remove(this);
2025-11-15 12:17:34 -05:00
attachedCharacter.deckSubmodule.GetAllCards().ForEach(card => card.RefreshCardAttributes());
2025-11-10 12:57:04 -05:00
attachedCharacter.combatBuffSubmodule.buffList.Exclude(this).For(buff => buff.eventSubmodule?.onOtherBuffRemoved.Invoke(this));
2025-10-03 00:02:43 -04:00
}
public override void UntriggerRemove()
{
this.attachedCharacter.combatBuffSubmodule.buffList.Remove(this);
2025-11-15 12:17:34 -05:00
attachedCharacter.deckSubmodule.GetAllCards().ForEach(card => card.RefreshCardAttributes());
2025-10-03 00:02:43 -04:00
}
2025-10-24 09:11:22 -04:00
/// <summary>
/// 检查并处理专注类Buff的添加逻辑。
/// 如果已有相同Buff存在则返回true并通过out参数返回该Buff。
/// 如果没有相同Buff存在则返回false并在必要时移除优先级最低的专注类Buff以腾出空间。
/// </summary>
/// <param name="existingBuff"></param>
/// <returns></returns>
public bool FocusingCheck(out CharacterCombatBuffBase existingBuff)
{
2025-10-31 10:02:30 -04:00
if (buffType != BuffType.Focusing)
{
Debug.LogError("FocusingCheck只能用于专注类Buff");
existingBuff = null;
return false;
}
2025-10-24 09:11:22 -04:00
// 移除超出上限的专注类Buff
List<CharacterCombatBuffBase> focusingBuffs =
attachedCharacter.combatBuffSubmodule.buffList.Where(buff => buff.buffType == BuffType.Focusing).ToList();
focusingBuffs.Sort();
int maximumFocusingBuffAmount = attachedCharacter.GetAttribute("MaximumFocusingBuffAmount", 1);
for (int i = maximumFocusingBuffAmount; i < focusingBuffs.Count; i++)
{
focusingBuffs[i].Remove();
}
// 检查是否已有相同Buff存在
if (FindExistingSameBuff(out existingBuff))
{
return true;
}
// 如果没有相同Buff存在但已达上限则移除优先级最低的专注类Buff将由新Buff替代
if(focusingBuffs.Count >= maximumFocusingBuffAmount)
{
CharacterCombatBuffBase lowestPriorityBuff = focusingBuffs[focusingBuffs.Count - 1];
lowestPriorityBuff.Remove();
}
return false;
}
2025-10-03 00:02:43 -04:00
}
2025-10-23 00:49:44 -04:00
2025-10-24 09:11:22 -04:00
public partial class CharacterCombatBuffBase
2025-10-23 00:49:44 -04:00
{
private void RefreshAttributes()
{
2026-04-08 04:48:35 -04:00
generalAttributeSubmodule?.RefreshAllModifiedAttributes();
2025-10-23 00:49:44 -04:00
}
2026-04-01 12:23:27 -04:00
/// <summary>
/// 将一条命令加入 Reaction Lane确保 Buff 触发的动画/视觉效果
/// 在当前 Main Lane 命令完成后、下一条 Main Lane 命令执行前播放。
/// Buff 中需要动画的被动响应(反击、护盾反伤等)应使用此方法入队。
/// </summary>
protected void EnqueueReaction(CommandBase cmd)
{
CommandQueueManager.Instance.AddCommand(cmd, CommandLane.Reaction);
}
2025-10-23 00:49:44 -04:00
}
2025-10-03 00:02:43 -04:00
}