麒麟子

~~

导航

<2010年4月>
28293031123
45678910
11121314151617
18192021222324
2526272829301
2345678

统计

常用链接

留言簿(12)

随笔分类

随笔档案

Friends

WebSites

积分与排名

最新随笔

最新评论

阅读排行榜

评论排行榜

监听器在游戏开发中的应用----消息回调

我一向是不太喜欢给一些东西强加上个名字。但为了随波逐流,我还是这样做了。

 

在我们的游戏开发中,通常会遇到两个模块之间的通信。 回调估计是最常用的方式了。 回调的设计思想很简单,就是两个对象相互注册,然后在需要的时候调用对方的函数。

如下:

 

 

这样,当A执行自己的某些动作的时候,就调用B的函数,这样B就会进行自己的更新或是一些处理。

 

但是,由于两个对象的直接回调,导致了许多不方便之处。特别是当A和B的功能需要扩展的时候。例如:现在A在执行过程中,需要调用B中其它的功能函数。这时候就不得不修改A和B的接口。然后大家都重新编译,连接,执行。

 

于是,我们就会想会不会有一种更好的方法来解决这一问题。 大家可以想想,WINDOWS中的通信机制:通过解析消息类型来进行处理。是的,消息回调的好处就是方便扩展。 当然我们这里要讲的不是像WINDOWS中那样的消息通信机制,对于我们来说,那种做法过繁琐。

假设现在是想让A通知B一些事情。那么,我们可以把B的void DoB();函数作一点点修改:

 

同理,当B要通知A的时候,也这样做就行了。

 

但是,这样也很麻烦,关键在于,如果现在写类A的人并不知道类B的人会怎么写,或者说,类B不知道什么时候要写。另外,如果我们强制类B要实现这样的接口,会有点不现实。

 

此时,我们决定使用一个中间对象来连接他们。

 


这就是我们传说中的监听器了。 在OGRE或是一些广泛采用面向对象思想的源程序中,随处可见这样的模式。

 

还是假设是A需要通知B一些事情。那么,可以在A中注册这个对象,然后调用它的方法就可以了。

 

而我们在实现B的时候,除了要实现B自己的东西以外,还需要将ICallBack派生并实现 void Do(int Msg)函数;

 

这样,双方便很自然地通了信。而写类A的人根本不需要理会类B的人会怎么写,也不用去管类B会是什么样的类名。只要告诉写类B的人,你需要实现这个Callback接口,并且对应的MsgID是干什么用的就OK了。

 

也许初初的一看,这是吃力不讨好的工作。毕竟一个写A的人,会去想那么多事情。 而一个写B的人,还要去实现一个Callback类。但是,从可扩展性,和降低耦合上来讲,的确会起不少的作用。

 

而上面的void Do(int MsgID);函数,可以做得更强大一点。

写成void Do(void* pData); 而这个pData怎么使用,就要看A和B通信的具体内容了。

 

 

 

我正尽力地试着把自己想要说的讲清楚,谢谢!

 

posted on 2010-04-24 14:39 麒麟子 阅读(2009) 评论(5)  编辑 收藏 引用 所属分类: Game and Engine

评论

# re: 监听器在游戏开发中的应用----消息回调 2010-04-24 15:41 zuhd

这种情况我一般会这样做,
class A
{
Root* m_pRoot;
}

class B
{
Root* m_pRoot;
}

class Root
{
A* m_a;
b* m_b;
}

让Root来统一管理所有的数据,然后root提供出一些接口,让a和b来做他们自己想做的事情,a,b去拿root的数据,root来回调a,b这样能解决单向的callback.  回复  更多评论   

# re: 监听器在游戏开发中的应用----消息回调 2010-04-24 15:43 zuhd

如果单模块的逻辑单一而且复杂,那就考虑拆出来单独一个进程网络通讯吧,那就永远没有callback了  回复  更多评论   

# re: 监听器在游戏开发中的应用----消息回调 2010-04-24 16:15 小时候可靓了

要看处在什么角度了。。不同的场合有不同的用法。。上面两位给的建议很不错。。我又学到了两种方法。。谢谢!  回复  更多评论   

# re: 监听器在游戏开发中的应用----消息回调 2010-04-25 23:11 expter

不就是Command吗?  回复  更多评论   

# re: 监听器在游戏开发中的应用----消息回调 2010-11-24 10:16 李现民

观察者模式应用起来的确有些复杂,也许你可以考虑仿写一个c#的delegate,这样的话可以支持多播, 而且编程实现上要简单不少。

  回复  更多评论   


只有注册用户登录后才能发表评论。
【推荐】超50万行VC++源码: 大型组态工控、电力仿真CAD与GIS源码库
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理