Unity——观察者模式
观察者模式
一、Demo展示

二、设计思路
我们假设一种情况,在app中修改了头像,在所有显示头像的UI中都需要更改相应的图片,一个个去获取然后调用刷新会非常麻烦;
因此我们需要一个自动响应机制——观察者模式;
核心:一个key对应多个Action(委托);
流程:
1.提前在每个需要响应的UI中添加监听事件;
2.修改数据同时注册观察者,需要参数可传参;
3.每一帧在LateUpdate中调用响应函数,把所有添加了注册了事件执行一遍;
三、关键类
1.带参数委托
由于参数类型不确定,所以使用object类型;
public delegate void obsAct(object args);
2.ObserverMa(单例)
字段:
private Dictionary<string, List<obsAct>> dicAll //存储所有事件和响应
private List<string> curAct = new List<string>();//存储当前帧注册的事件key值
private ArrayList objArgs = new ArrayList(); //存储key对应的参数
方法:
1)添加监听
public void AddListener(string key, obsAct act)
{
if (dicAll.ContainsKey(key))
{
dicAll[key].Add(act);
}
else
{
List<obsAct> actions = new List<obsAct>();
actions.Add(act);
dicAll.Add(key, actions);
}
}
2)注册事件
public void Register(string key,object args = null)
{
if (dicAll.ContainsKey(key))
{
curAct.Add(key);
objArgs.Add(args);
}
else
{
Debug.Log("未注册观察事件");
}
}
3)响应事件
public void Respond()
{
for (int i = 0; i < curAct.Count; ++i)
{
List<obsAct> acts = dicAll[curAct[i]];
for (int j = 0; j < acts.Count; ++j)
{
acts[j](objArgs[i]);
}
}
curAct.Clear();
objArgs.Clear();
}
四、测试类
这里为了方便,我只用了InputFiled和Text组件来完成;
InputFiled输入文字,结束时通知4个Text,Text显示输入的文字;
在Canvas上了脚本UIMa,UIMa的LateUpdate方法中调用了ObserverMa.I.Respond();

完整代码:
1.InputFiled
public class InputStr : MonoBehaviour
{
private InputField strInput;
private string str = "";
private bool isAdd = false;
private void Start()
{
strInput = GetComponent<InputField>();
}
void Update()
{
if (strInput.isFocused && !isAdd)
{
isAdd = true;
}
if (!strInput.isFocused && isAdd)
{
ObserverMa.I.Register(ObsStr.inputStr, strInput.text);
isAdd = false;
}
}
}
2.Text
public class Text1 : MonoBehaviour
{
public Text text;
private void Start()
{
text = GetComponent<Text>();
obsAct act = (str) => { text.text = str as string;};
ObserverMa.I.AddListener(ObsStr.inputStr,act);
}
}
五、优化方案
1.所有的key值可以自动使用const string 类替代,避免每次注册需要手动输入字符串,且容易出错;
2.无参委托和有参委托可以分开写,写两套重写的注册方法,数据也分开存储,减少Object = null的存储;
以上是我对观察者模式的理解,如果有更好的想法可以给我留言;
Unity——观察者模式的更多相关文章
- 【Unity与23种设计模式】观察者模式(Observer)
GoF中定义: "在对象之间定义一个一对多的连接方法,当一个对象变换状态时,其他关联的对象都会自动收到通知." 现实中,社交网络就是个例子. 以前的报社,每次出新刊的时候, 报刊便 ...
- 【Unity技巧】统一管理回调函数——观察者模式
这次的内容有点类似设计模式里的观察者模式.但是和常规意义上的观察者模式也不是完全一致,所以各位就不要咬文嚼字啦!咦?设计模式?!不懂!没关系,说不定你以前就用过. 开场白 我们来想象一个场景.在加载一 ...
- Unity C# 多态 委托 事件 匿名委托 Lambda表达式 观察者模式 .NET 框架中的委托和事件
一.多态 里氏替换原则: 任何能用基类的地方,可以用子类代替,反过来不行.子类能够在基类的基础上增加新的行为.面向对象设计的基本原则之一. 开放封闭原则: 对扩展开放,意味着有新的需求或变化时,可以对 ...
- Unity基于响应式编程(Reactive programming)入门
系列目录 [Unity3D基础]让物体动起来①--基于UGUI的鼠标点击移动 [Unity3D基础]让物体动起来②--UGUI鼠标点击逐帧移动 时光煮雨 Unity3D让物体动起来③—UGUI DoT ...
- 【Unity3D技巧】在Unity中使用事件/委托机制(event/delegate)进行GameObject之间的通信 (二) : 引入中间层NotificationCenter
作者:王选易,出处:http://www.cnblogs.com/neverdie/ 欢迎转载,也请保留这段声明.如果你喜欢这篇文章,请点[推荐].谢谢! 一对多的观察者模式机制有什么缺点? 想要查看 ...
- Unity StrangeIoc框架 (一)
最近想项目中需要使用这个架构 因此 上网看了很多资料摸索 但是对于初学者来说大多数的资料不是那么容易理解 而且文档也是英文的阅读起来有点吃力 所以记录一下自己阅读的过程 方便以后翻阅和跟我一 ...
- 【《Effective C#》提炼总结】提高Unity中C#代码质量的21条准则
作者:Williammao, 腾讯移动客户端开发工程师 商业转载请联系腾讯WeTest获得授权,非商业转载请注明出处. 原文链接:http://wetest.qq.com/lab/view/290.h ...
- 【Unity游戏开发】用C#和Lua实现Unity中的事件分发机制EventDispatcher
一.简介 最近马三换了一家大公司工作,公司制度规范了一些,因此平时的业余时间多了不少.但是人却懒了下来,最近这一个月都没怎么研究新技术,博客写得也是拖拖拉拉,周六周天就躺尸在家看帖子.看小说,要么就是 ...
- Unity 3D中不得不说的yield协程与消息传递
1. 协程 在Unity 3D中,我们刚开始写脚本的时候肯定会遇到类似下面这样的需求:每隔3秒发射一个烟花.怪物死亡后20秒再复活之类的.刚开始的时候喜欢把这些东西都塞到Update里面去,就像下面这 ...
随机推荐
- 集合的打印、列表List、迭代器Iterators
集合的打印 必须使用 Arrays.toString() 来生成数组的可打印形式. 但是打印集合无需任何帮助. /** * 集合的打印 * @author myf */ public class Pr ...
- mzy对于枚举的理解
关于enum,其实就是简化了的class,功能就是提供一个个独立的.特定含义的常量! 在JDK5.0之前我们想模拟enum的功能,只能使用自定义类的形式: 1.首先私有化构造方法,让外部不能new对象 ...
- 寻找最短路径Dijkstra算法
1 /** 2 * 1.对于T中的每个顶点u,找到u的具有最小权重的连接边.所有到u的连接边都存储在queues.get(u)中.queues.get(u).peek()返回拥有最小权值 3 * 的连 ...
- JS方式实现隐藏手机号码中间4位数
1.截取 function test (value) { const start = value.slice(0, 3) const end = value.slice(-4) return `${s ...
- .NetCore3.1获取文件并重新命名以及大批量更新及写入数据
using Microsoft.AspNetCore.Mvc; using MySql.Data.MySqlClient; using System; using System.Collections ...
- Shell脚本基础及基本常用命令
1.概述 脚本语言(shell.python):解释性语言,用解释器解释 运行效率低 | c.java:描述性语言,运行效率高 以.sh结尾会有高亮显示 执行: sh hello.sh 或者 chmo ...
- 手写AVL平衡二叉搜索树
手写AVL平衡二叉搜索树 二叉搜索树的局限性 先说一下什么是二叉搜索树,二叉树每个节点只有两个节点,二叉搜索树的每个左子节点的值小于其父节点的值,每个右子节点的值大于其左子节点的值.如下图: 二叉搜索 ...
- Tricks
由于本人着实有些菜,因此在此积累一些巧妙的 \(Tricks\) ,以备不时之需... 与其说是 \(Tricks\) 不如说是学习笔记?? 数学 组合数 常见的数列 斐波那契数列 图论 树论 \(P ...
- noip模拟17
\(\color{white}{\mathbb{霞光划破暗淡天际,月影彷徨,鸡鸣仿佛,冀之以继往开来,名之以:黎明}}\) 今天似乎取得了有史以来最好的成绩~ 前两名都 A 掉了 \(t3\),然鹅 ...
- 命令行解析函数:getopt_long、getopt
一.前言 在学习一些项目代码时,尤其涉及到命令行传参的代码,经常遇到getopt相关的函数,对这一类函数可以说是既陌生又熟悉.陌生是因为不知道它是干啥的,熟悉呢,是因为经常遇到.于是乎在追踪了多天ip ...