事件中心模块

Posted wei1349

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了事件中心模块相关的知识,希望对你有一定的参考价值。

事件中心模块

在游戏中,许多事件之间往往会互相触发的,里面的逻辑错综复杂,比如说:在网游中,“怪物死亡”会调用“玩家经验增加” +“任务记录杀死怪物数”+“其他”等事件。

如果是这样的话,那么“怪物死亡”的函数中就需要写调用 “其他事件所对应的函数” 的代码,同理则每一个 “需要调用其他函数的函数” 都需要重复写这些代码,导致每一个函数都与很多个函数关联,逻辑复杂,就增加了函数的耦合度。

作用:

1、减少函数的耦合度

事件中心就好比是一个中间人,负责监察各个事件的发生,然后去调用 “与之相关的函数” ,这样,就不需要在 “事件所对应的函数” 中编写调用 ”与之相关的函数“ 的代码了,只需被调用的函数委托事件中心:”当某某某事件发生时就调用我“。

2、提高程序的效率

不需要写重复的代码,进行有序的调用

代码

事件中心模块代码

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Events;

/// <summary>
/// 实践中心 单例模式对象
/// 1、字典
/// 2、委托
/// 3、观察者设计模式
/// </summary>
public class EventCenter : BaseManager<EventCenter>
{
    //key-- 事件的名字
    //value-- 对应的是监听这一事件的委托
    private Dictionary<string, UnityAction<object>> eventDic = new Dictionary<string, UnityAction<object>>();

    /// <summary>
    /// 添加事件的监听
    /// </summary>
    /// <param name="name">事件的名字</param>
    /// <param name="action">准备用来处理事件的委托函数</param>
    public void AddEventListenr(string name,UnityAction<object> action)
    {
        //有没有对应的事件监听
        //有的情况
        if (eventDic.ContainsKey(name))
        {
            eventDic[name] = eventDic[name] + action;
        }
        //没有的情况
        else
        {
            eventDic.Add(name, action);
        }
    }
    /// <summary>
    /// 移除对应的事件监听
    /// </summary>
    /// <param name="name">事件的名字</param>
    /// <param name="action">对应之前添加的委托函数</param>
    public void RemoveEventListener(string name,UnityAction<object> action)
    {
        if (eventDic.ContainsKey(name))
        {
            eventDic[name] = eventDic[name] - action;
        }
    }
    /// <summary>
    /// 事件触发
    /// </summary>
    /// <param name="name">哪一个名字的事件触发了</param>
     public void EventTrigger(string name,object info)
    {
        //有没有对应的事件监听
        //有的情况
        if (eventDic.ContainsKey(name))
        {
            eventDic[name].Invoke(info);
        }
    }
    /// <summary>
    /// 清空事件中心
    /// 主要用在场景切换上
    /// </summary>
    public void Clear()
    {
        eventDic.Clear();
    }
}

实例

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Monster : MonoBehaviour
{
    void Start()
    {
        Dead();
    }
    /// <summary>
    /// 死亡方法
    /// </summary>
    void Dead()
    {
        Debug.Log("怪物死亡");
        //触发事件
        EventCenter.GetInstance().EventTrigger("MonsterDead",this);
    }
}

 

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Player : MonoBehaviour
{
    // Start is called before the first frame update
    void Start()
    {
        EventCenter.GetInstance().AddEventListenr("MonsterDead",MonsterDeadDo );
    }
    /// <summary>
    /// 怪物死亡时发生的事情
    /// </summary>
    public void MonsterDeadDo(object info)
    {
        Debug.Log("玩家得奖励"+(info as Monster).name);
    }

    void OnDestroy()
    {
        EventCenter.GetInstance().RemoveEventListener("MonsterDead", MonsterDeadDo);
    }
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Task : MonoBehaviour
{
    void Start()
    {
        EventCenter.GetInstance().AddEventListenr("MonsterDead", TaskWaitMonsterDeadDo);
    }
    /// <summary>
    /// 怪物死亡时发生的事情
    /// </summary>
    public void TaskWaitMonsterDeadDo(object info)
    {
        Debug.Log("任务记录更新");
    }
    void OnDestroy()
    {
        EventCenter.GetInstance().RemoveEventListener("MonsterDead", TaskWaitMonsterDeadDo);
    }
}

 

以上是关于事件中心模块的主要内容,如果未能解决你的问题,请参考以下文章

如何在android中的地图片段内中心线性布局?

Android 事件分发事件分发源码分析 ( Activity 中各层级的事件传递 | Activity -> PhoneWindow -> DecorView -> ViewGroup )(代码片段

如何有条件地将 C 代码片段编译到我的 Perl 模块?

#yyds干货盘点#vue使用事件总线进行模块之间的通信

如何使用事件侦听器来加载动画片段的循环

Android开发——UI_片段