2.游戏中的Buff系统设计

1.分析游戏中的Buff系统

2.Buff系统的类结构

3.游戏中存在很多种buff, 是否需要创建不同的buff实体


1.分析游戏中的Buff系统

csharp 复制代码
a.Buff系统的类结构

b.游戏中存在很多种buff, 是否需要创建不同的buff实体

2.Buff系统的类结构

csharp 复制代码
将Buff分为三个部分: 数据, 行为, 表现

a.Buff数据(BuffData): 定义Buff的静态属性, 如BuffID、持续时间、效果类型、效果值等; 这些数据可以从配置表读取

b.Buff实例(BuffInstance): 每个Buff在角色身上的一个实例, 它包含动态数据, 如剩余时间、层数等, 并持有对BuffData

的引用

c.Buff行为(BuffBehavior): 负责Buff的效果逻辑, 如应用效果、移除效果、定时更新等; 这部分可以放在BuffInstance中

也可以分离出来

d.Buff表现(BuffView): 负责Buff的视觉和听觉表现, 如特效、音效等; 这部分应该与行为分离, 通过监听Buff的状态变化

来触发表现

csharp 复制代码
// Buff事件系统
public class BuffEvent
{
    public static event Action<Buff, GameObject> OnBuffApply;
    public static event Action<Buff, GameObject> OnBuffRefresh; 
    public static event Action<Buff, GameObject> OnBuffRemove;
    public static event Action<Buff, GameObject> OnBuffExpire;
    
    public static void TriggerApply(Buff buff, GameObject target) 
        => OnBuffApply?.Invoke(buff, target);
    // ... 其他触发方法
}

// 简化的Buff基类
public abstract class Buff
{
    public BuffData Data { get; protected set; }
    
    public virtual void Apply(GameObject target)
    {
        // 业务逻辑
        BuffEvent.TriggerApply(this, target);
    }
    
    public virtual void Remove(GameObject target)
    {
        // 业务逻辑
        BuffEvent.TriggerRemove(this, target);
    }
}

// 独立的Buff表现控制器
public class BuffVisualController : MonoBehaviour
{
    private Dictionary<Buff, GameObject> activeVisuals = new Dictionary<Buff, GameObject>();
    
    private void OnEnable()
    {
        BuffEvent.OnBuffApply += OnBuffApplied;
        BuffEvent.OnBuffRemove += OnBuffRemoved;
        BuffEvent.OnBuffRefresh += OnBuffRefreshed;
    }
    
    private void OnDisable()
    {
        BuffEvent.OnBuffApply -= OnBuffApplied;
        BuffEvent.OnBuffRemove -= OnBuffRemoved;
        BuffEvent.OnBuffRefresh -= OnBuffRefreshed;
    }
    
    private void OnBuffApplied(Buff buff, GameObject target)
    {
        // 播放获得特效
        PlayOneShotEffect(buff.Data.applyEffect, target.transform);
        
        // 开始持续特效
        if(buff.Data.loopEffect != null)
        {
            var effect = Instantiate(buff.Data.loopEffect, target.transform);
            activeVisuals[buff] = effect;
        }
        
        // 更新UI图标等
        UIManager.Instance.ShowBuffIcon(buff);
    }
    
    private void OnBuffRemoved(Buff buff, GameObject target)
    {
        // 播放消失特效
        PlayOneShotEffect(buff.Data.removeEffect, target.transform);
        
        // 停止持续特效
        if(activeVisuals.TryGetValue(buff, out var effect))
        {
            Destroy(effect);
            activeVisuals.Remove(buff);
        }
        
        // 移除UI图标
        UIManager.Instance.HideBuffIcon(buff);
    }
    
    private void OnBuffRefreshed(Buff buff, GameObject target)
    {
        // 播放刷新特效(如闪光一下)
        PlayOneShotEffect(buff.Data.refreshEffect, target.transform);
    }
}

3.游戏中存在很多种buff, 是否需要创建不同的buff实体

csharp 复制代码
a.继承体系: 创建一个抽象的Buff基类, 然后为每种不同类型的Buff创建子类; 这种方式直观, 但当Buff行为复杂且组合多

变时, 会导致类层次过深或子类数量过多

b.组件化(策略模式): 将Buff的行为拆分成多个组件(例如:效果应用、持续时间管理、叠加规则等), 然后通过组合这些组

件来构建不同的Buff; 这种方式更灵活, 易于扩展

csharp 复制代码
将Buff的行为拆分为多个可组合的部分

a.效果(IEffect): 定义Buff的具体效果, 如伤害、修改属性等

b.持续时间(IDuration): 管理Buff的持续时间

c.叠加规则(IStacking): 定义Buff如何叠加
csharp 复制代码
public interface IEffect
{
    void OnApply(GameObject target);
    void OnUpdate(GameObject target, float deltaTime);
    void OnRemove(GameObject target);
}

public interface IDuration
{
    float Duration { get; set; }
    bool IsExpired { get; }
    void Update(float deltaTime);
}

public interface IStacking
{
    int Stacks { get; set; }
    void Stack(Buff buff);
}

public class Buff
{
    public GameObject Target { get; private set; }
    public IEffect Effect { get; private set; }
    public IDuration Duration { get; private set; }
    public IStacking Stacking { get; private set; }

    public Buff(IEffect effect, IDuration duration, IStacking stacking)
    {
        Effect = effect;
        Duration = duration;
        Stacking = stacking;
    }

    public void Apply(GameObject target)
    {
        Target = target;
        Effect.OnApply(target);
    }

    public void Update(float deltaTime)
    {
        Duration.Update(deltaTime);
        Effect.OnUpdate(Target, deltaTime);
    }

    public void Remove()
    {
        Effect.OnRemove(Target);
    }

    public void Stack(Buff other)
    {
        Stacking.Stack(other);
    }
}

// 具体效果实现
public class DamageOverTimeEffect : IEffect
{
    private float tickInterval;
    private float timeSinceLastTick;
    private float damagePerTick;

    public DamageOverTimeEffect(float tickInterval, float damagePerTick)
    {
        this.tickInterval = tickInterval;
        this.damagePerTick = damagePerTick;
        timeSinceLastTick = 0f;
    }

    public void OnApply(GameObject target) { }

    public void OnUpdate(GameObject target, float deltaTime)
    {
        timeSinceLastTick += deltaTime;
        if (timeSinceLastTick >= tickInterval)
        {
            Health health = target.GetComponent<Health>();
            if (health != null)
            {
                health.TakeDamage(damagePerTick);
            }
            timeSinceLastTick = 0f;
        }
    }

    public void OnRemove(GameObject target) { }
}

// 具体持续时间实现
public class FixedDuration : IDuration
{
    public float Duration { get; set; }
    public bool IsExpired => Duration <= 0f;

    public FixedDuration(float duration)
    {
        Duration = duration;
    }

    public void Update(float deltaTime)
    {
        Duration -= deltaTime;
    }
}

// 具体叠加规则实现
public class SimpleStacking : IStacking
{
    public int Stacks { get; set; } = 1;

    public void Stack(Buff other)
    {
        // 简单叠加:层数+1,刷新持续时间
        Stacks++;
        if (other.Duration is FixedDuration fixedDuration)
        {
            // 刷新持续时间,例如:重置为初始持续时间
            // 这里需要知道初始持续时间,所以可能需要扩展设计
        }
    }
}
相关推荐
hn小菜鸡6 小时前
LeetCode 1306.跳跃游戏III
算法·leetcode·游戏
咕噜企业分发小米9 小时前
腾讯云游戏音视频方案如何助力初创公司提升用户粘性?
游戏·音视频·腾讯云
da_vinci_x9 小时前
PS 消失点:贴图透视总画歪?无需建模,2D 也能“空间绘图”
游戏·aigc·设计师·贴图·技术美术·游戏美术·关卡设计
gis分享者10 小时前
学习threejs,生成复杂3D迷宫游戏
学习·游戏·3d·threejs·cannon·迷宫·cannon-es
zore_c10 小时前
【C语言】EasyX图形库——实现游戏音效(详解)(要游戏音效的看过来!!!)
c语言·开发语言·经验分享·笔记·游戏
AA陈超1 天前
虚幻引擎5 GAS开发俯视角RPG游戏 P07-18.生成火球术
c++·游戏·ue5·游戏引擎·虚幻
_大学牲1 天前
Flutter 勇闯2D像素游戏之路(三):人物与地图元素的交互
flutter·游戏·游戏开发
游戏技术分享1 天前
【鸿蒙游戏技术分享 第71期】资质证明文件是否通过
游戏·华为·harmonyos
reddingtons1 天前
PS 参考图像:线稿上色太慢?AI 3秒“喂”出精细厚涂
前端·人工智能·游戏·ui·aigc·游戏策划·游戏美术
BT-BOX2 天前
普中开发板基于51单片机贪吃蛇游戏设计
单片机·游戏·51单片机