Unity 使用事件代理实现任务管理功能(初学者日记)
本功能是一个unity初学者基于消息中心 https://blog.csdn.net/Over_The_Clouds/article/details/102563065之上完成,杀死敌人任务测试正常,其余暂未测试
贴出代码:
任务管理中心
using System.Collections.Generic;
using System.Linq;
/// <summary>
/// 任务中心
/// </summary>
public class TaskManager
{
private int id;
private static TaskManager missionManager;
/// <summary>
/// 该对象的单例引用,并初始化了事件监听
/// </summary>
/// <returns></returns>
public static TaskManager GetInstance() {
if (missionManager == null) {
missionManager = new TaskManager();
//注册任务监听
EventManager.CreateInstance().AddListener(TypeEvent.AddItem,
new DelegateEvent.Handle(missionManager.updateTask));
EventManager.CreateInstance().AddListener(TypeEvent.dialogue,
new DelegateEvent.Handle(missionManager.updateTask));
EventManager.CreateInstance().AddListener(TypeEvent.KillMonster,
new DelegateEvent.Handle(missionManager.updateTask));
}
return missionManager;
}
//在对象被销毁前删除该监听
~TaskManager() {
EventManager.CreateInstance().RemoveListener(TypeEvent.AddItem,
new DelegateEvent.Handle(missionManager.updateTask));
EventManager.CreateInstance().RemoveListener(TypeEvent.dialogue,
new DelegateEvent.Handle(missionManager.updateTask));
EventManager.CreateInstance().RemoveListener(TypeEvent.KillMonster,
new DelegateEvent.Handle(missionManager.updateTask));
}
/// <summary>
/// 任务列表
/// </summary>
private Dictionary<int, Task> listTask = new Dictionary<int, Task>();
/// <summary>
/// 获取一个任务id值
/// </summary>
/// <returns></returns>
public int getTaskIndex() {
return id++;
}
/// <summary>
/// 增加一个任务
/// </summary>
/// <param name="task">任务内容</param>
public bool addListTask(Task task) {
if (!listTask.ContainsKey(task.id)) {
listTask.Add(task.id,task);
return true;
}
return false;
}
/// <summary>
/// 删除一条任务
/// </summary>
/// <param name="id">任务id</param>
public void RemoveListTask(int id) {
if (listTask.ContainsKey(id))
listTask.Remove(id);
}
/// <summary>
/// 获取指定任务
/// </summary>
/// <param name="id">任务id</param>
/// <returns></returns>
public Task getTaskById(int id) {
if (listTask.ContainsKey(id))
return listTask[id];
return null;
}
/// <summary>
/// 监听任务进程的方法
/// </summary>
/// <param name="data"></param>
private void updateTask(EventData data) {
foreach (Task task in listTask.Values) {
if (task.state)
break;
if(data.type == TypeEvent.AddItem)
if (task.maxItem != null)
task.updateTask0(data.data as Item);
if (data.type == TypeEvent.KillMonster)
if (task.maxKill != null)
task.updateTask1(data.data as Bean);
if (data.type == TypeEvent.dialogue)
if (task.dialogTask != null)
task.updateTask2(data.data as Bean);
task.updateTaskState();
}
}
/// <summary>
/// 获取全部任务列表
/// </summary>
/// <returns></returns>
public List<Task> getListTask() {
return listTask.Values.ToList();
}
/// <summary>
/// 获取已完成或未完成的任务列表
/// </summary>
/// <returns></returns>
public List<Task> getListTask(bool t)
{
List<Task> tasks = new List<Task>();
foreach (Task task in listTask.Values)
if (t == task.state)
tasks.Add(task);
return tasks;
}
}
任务类:
using System;
using System.Collections.Generic;
using System.Linq;
public class Task
{
/// <summary>
/// 任务Id
/// </summary>
public int id;
/// <summary>
/// 任务名称
/// </summary>
private string name;
/// <summary>
/// 任务状态
/// </summary>
public bool state = false;
/// <summary>
/// 提交状态
/// </summary>
public bool submit = false;
/// <summary>
/// 任务介绍
/// </summary>
public string introduce;
/// <summary>
/// 任务奖励
/// </summary>
public TaskReward reward;
/// <summary>
/// 需要收集的物品及数量(0:物品名称 1:物品)
/// </summary>
public Dictionary<string, Item> maxItem;
/// <summary>
/// 当前已收集的物品及数量(0:物品名称 1:物品)
/// </summary>
public Dictionary<string, Item> thisItem;
/// <summary>
/// 需要kill的怪物及数量(0:怪物名称 1:怪物数量)
/// </summary>
public Dictionary<string, int> maxKill;
/// <summary>
/// 当前kill的怪物及数量(0:怪物名称 1:怪物数量)
/// </summary>
public Dictionary<string, int> thisKill;
/// <summary>
/// 需跟某些人物进行对话(0:人物名称 1:是否完成)
/// </summary>
public Dictionary<string, bool>dialogTask;
/// <summary>
/// 当前条件完成度
/// </summary>
public Dictionary<TypeEvent, bool> taskState = new Dictionary<TypeEvent, bool>{
{TypeEvent.AddItem, false},
{TypeEvent.KillMonster,false},
{TypeEvent.dialogue,false}
};
/// <summary>
/// 获得Task实例
/// </summary>
/// <param name="id">id</param>
/// <param name="name">任务名称</param>
/// <param name="introduce">任务介绍</param>
/// <param name="maxItem">物品</param>
/// <param name="maxKill">杀敌</param>
/// <param name="dialogTask">对话</param>
/// /// <param name="reward">任务奖励</param>
public Task(int id, string name, string introduce, Dictionary<string, Item> maxItem,
Dictionary<string, int> maxKill,Dictionary<string, bool> dialogTask, TaskReward reward)
{
this.id = id;
this.name = name;
this.introduce = introduce;
this.maxItem = maxItem;
this.maxKill = maxKill;
this.dialogTask = dialogTask;
this.reward = reward;
if (maxItem != null)
{
this.thisItem = new Dictionary<string, Item>();
foreach (Item item in maxItem.Values)
this.thisItem.Add(item.name, item);
}
else
this.taskState[TypeEvent.AddItem] = true;
if (maxKill != null)
{
this.thisKill = new Dictionary<string, int>();
foreach (string s in maxKill.Keys)
this.thisKill.Add(s,0);
}else
this.taskState[TypeEvent.KillMonster] = true;
if(dialogTask == null)
this.taskState[TypeEvent.dialogue] = true;
}
/// <summary>
/// 当获得一个物品时被调用,判断当前获得物品是否在任务列表之中,是则加上该物品数量
/// </summary>
/// <param name="item">物品</param>
public void updateTask0(Item item)
{
//如果当前物品存在任务列表中
if (thisItem.ContainsKey(item.name))
{
//使已获得数量+当前获得数量
thisItem[item.name].number += item.number;
}
}
/// <summary>
/// 当kill一个怪物时被调用,判断当前怪物是否在任务列表之中,是则加上该怪物数量
/// </summary>
/// <param name="bean">怪物</param>
public void updateTask1(Bean bean)
{
//如果当前怪物存在任务列表中
if (thisKill.ContainsKey(bean.name))
{
//使已获得数量+当前获得数量
thisKill[bean.name] += 1;
}
}
/// <summary>
/// 当跟一个角色进行对话时被调用
/// </summary>
/// <param name="bean">角色</param>
public void updateTask2(Bean bean)
{
//当前对话的角色存在任务列表中
if (dialogTask.ContainsKey(name)) {
if (!dialogTask[name])
dialogTask[name] = true;
}
}
/// <summary>
/// 更新任务状态
/// </summary>
public void updateTaskState() {
updateItemTask();
updateKillTask();
updateDialogueTask();
//更新本次任务的状态
foreach (bool state in taskState.Values)
if (!state)
return;
//设置任务完成
this.state = true;
}
private void updateItemTask() {
//更新收集物品条件状态
if (thisItem!=null && !taskState[TypeEvent.AddItem])
{
foreach (Item item in thisItem.Values)
{
if (item.number < maxItem[item.name].number)
return;
}
taskState[TypeEvent.AddItem] = true;
}
}
private void updateKillTask()
{
//更新杀死怪物条件状态
if (thisKill != null && !taskState[TypeEvent.KillMonster])
{
foreach (string name in thisKill.Keys)
{
if (thisKill[name] < maxKill[name])
return;
}
taskState[TypeEvent.KillMonster] = true;
}
}
private void updateDialogueTask()
{
//更新对话条件 的状态
if (dialogTask != null && !taskState[TypeEvent.dialogue])
{
foreach (bool state in dialogTask.Values)
{
if (!state)
return;
}
taskState[TypeEvent.dialogue] = true;
}
}
}
//调用测试
public void setTask() {
//未设置任务
if (!settask)
{
//添加任务奖励
List<Item> items = new List<Item> {new Item("急救丸",2)};
//获得任务实例
Task task = new Task(11, "修复机器人", "请帮我把机器人全部修复", null,
new Dictionary<string, int> { { "机器人", 5 } }, null, new TaskReward(1000,100,items)); ;
//将任务添加进任务管理中心
TaskManager.GetInstance().addListTask(task);
//设置任务已发送
settask = true;
}
else {
//根据id在任务列表中获取任务
Task t = TaskManager.GetInstance().getTaskById(11);
//如果任务完成
if (t.state) {
text.text = "哦,谢谢你";
if (t.submit)
return;
t.submit = true;
Debug.Log("获得奖励:"+t.reward);
}
else
text.text = "你还没有完成哦,已经修复了 "+t.thisKill["机器人"]+" 个机器人了,总共有 "+t.maxKill["机器人"]+" 个";
}
}