原文地址:http://chengduyi.com/blog/?post=27

在游戏设计中,通常会将一些实现了具体功能的模块进行封装,达到重用的目的。这些功能模块包括:1、网络通信模块(实现连接,断开,消息发送、接收,错误等处理);2、资源加载管理模块(实现资源加载,缓存,进度通知,分类型加载、管理等)。

设计实现这些功能模块的方法很多,设计过程中最好做到使这些模块在外部启动简单、使用方便、重用容易。

我在设计中使用了代理模式的思想,就是将封装的功能留出一个代理类供外部继承实现。使用时候的具体步骤是:1、重写该代理类;2、实例化重写的代理类,并将该对象设置到管理器中;3、创建消息的逻辑处理类对象,并使用方法setDelegate设置映射;4、访问该代理类对象实现操作。

注意地方有:重写的代理类最好是单例的,方便调用。步骤2是在游戏启动的时候完成。步骤3里消息的逻辑处理类可能是很多个,最好也是单例的,方便调用,该步骤最好在步骤2中代理类的构造函数里调用完成。

现在来模拟设计一个网络通信模块,整个功能比较简单,定义了两个类(NetManager、NetProxy)和一个接口(INetDelegate),其中NetManager和NetProxy存在对象共享,必须在一个包内。

INetDelegate接口的伪代码:

/** 定义网络数据处理逻辑接 */
interface INetDelegate public function receive(data:ByteArray):void;

NetManager类的伪代码:

/** 单例的,外部只能设置一次该类的只写属性netProxy */
class NetManager /** 将socket封装,外部不可直接访问 */
private var socket:Socket; /** 通过只设置一次实现系统初始化管理 */
private var _netProxy:NetProxy;
public function set netProxy(proxy:NetProxy):void{
if(_netProxy){
//报错处理,只能设置一次该代理
}else{
_netProxy = proxy;
//与同包的NetProxy共享该属性
_netProxy.socket = socket;
}
} /** 在构造函数中创建好socket对象后调用 */
private function configureListeners():void {
socket.addEventListener(Event.CLOSE, closeHandler);
socket.addEventListener(Event.CONNECT, connectHandler);
socket.addEventListener(IOErrorEvent.IO_ERROR,
ioErrorHandler);
socket.addEventListener(SecurityErrorEvent.SECURITY_ERROR,
securityErrorHandler);
socket.addEventListener(ProgressEvent.SOCKET_DATA,
socketDataHandler);
} private function closeHandler(event:Event):void {
_netProxy.onClose();//移交处理权
} private function connectHandler(event:Event):void {
_netProxy.onConnect();//移交处理权
} private function ioErrorHandler(event:IOErrorEvent):void {
_netProxy.onError(IOErrorEvent.IO_ERROR);//移交处理权
} private function securityErrorHandler(event:SecurityErrorEvent):void {
//移交处理权
_netProxy.onError(SecurityErrorEvent.SECURITY_ERROR);
} private function socketDataHandler(event:ProgressEvent):void {
//TODO:处理断包、连包,读取消息长度,如果剩余长度够数据包,
//读取一个数据包到data里,继续执行,否则返回。
_netProxy.receive(data);//移交处理权
}

NetProxy类的伪代码:

/**
* 不是单例的,外部通过继承该类实现功能,外部继承类最好是单例的
* 并将他设置给NetManager的netProxy属性。
*/
class NetProxy /**
* 不会直接创建,在设置给NetManager时让NetManager共享出来
* 且包内封装,外部不能直接访问网络实体对象
*/
internal var socket:Socket; /**
* 消息处理逻辑类的字典
* 将消息头与逻辑类对应
* 逻辑类必须实现接口INetDelegate
*/
private var dictDelegate = new Dictionary(); final public function open(host:String, port:int){
socket.connect(host, port):
} final public function close():void{
socket.close();
} public function onError(errorType:String):void{
//外部继承类重写该方法实现
} public function onOpen():void{
//外部继承类重写该方法实现
} public function onClose():void{
//外部继承类重写该方法实现
} internal function receive(data:ByteArray):void{
//TODO:读取消息头
//分发到dictDelegate中对应的
//逻辑类(INetDelegate)的receive方法处理
} final public function send(head:uint, body:ByteArray):void{
//TODO:构建消息,发送
//虽然可以在能获得实例的任何地方调用
//但最好在INetDelegate的实现类中调用,达到逻辑封装
} final protected function setDelegate(head:uint,
delegate:INetDelegate):void{
//TODO:在dictDelegate中添加映射
//相同head只能一个处理逻辑类,重复设置报错
//最好在外部继承类的构造函数中调用,做到网络功能模块启动时
//就设置好了处理映射
}
附件下载:
netcontrol.rar 8.39KB

webgame设计之功能模块的代理模式的更多相关文章

  1. php 23种设计模型 - 代理模式

    代理模式(Proxy) 在代理模式(Proxy Pattern)中,一个类代表另一个类的功能.这种类型的设计模式属于结构型模式. 在代理模式中,我们创建具有现有对象的对象,以便向外界提供功能接口. 介 ...

  2. JAVA设计模式(09):结构型-代理模式(Proxy)

    代理模式是经常使用的结构型设计模式之中的一个,当无法直接訪问某个对象或訪问某个对象存在困难时能够通过一个代理对象来间接訪问,为了保证client使用的透明性,所訪问的真实对象与代理对象须要实现同样的接 ...

  3. C#设计模式之代理模式(二)

    15.3 代理模式应用实例 下面通过一个应用实例来进一步学习和理解代理模式.        1. 实例说明        某软件公司承接了某信息咨询公司的收费商务信息查询系统的开发任务,该系统的基本需 ...

  4. 设计模式(十三):从“FQ”中来认识代理模式(Proxy Pattern)

    我们知道Google早就被墙了,所以FQ才能访问Google呢,这个“FQ”的过程就是一个代理的过程.“代理模式”在之前的博客中不止一次的提及过,之前的委托回调就是代理模式的具体应用.今天我们就从“F ...

  5. Java中的代理模式

    代理模式在Java Web的框架中经常使用到.比如说在对数据库的访问中,核心功能是对数据库的增删改查,而连接数据库.处理事务等功能我们在开发中也要考虑到.所以我们将数据库的CRUD抽象到接口中,然后实 ...

  6. javascript设计模式与开发实践阅读笔记(6)——代理模式

    代理模式:是为一个对象提供一个代用品或占位符,以便控制对它的访问. 代理模式的关键是,当客户不方便直接访问一个对象或者不满足需要的时候,提供一个替身对象来控制对这个对象的访问,客户实际上访问的是替身对 ...

  7. 【Java千问】你了解代理模式吗?

    代理模式详解 1 什么是代理模式? 一句话描述:代理模式是一种使用代理对象来执行目标对象的方法并在代理对象中增强目标对象方法的一种设计模式. 详细描述: 1.理论基础-代理模式是设计原则中的“开闭原则 ...

  8. 设计模式:代理模式是什么,Spring AOP还和它有关系?

    接着学习设计模式系列,今天讲解的是代理模式. 定义 什么是代理模式? 代理模式,也叫委托模式,其定义是给某一个对象提供一个代理对象,并由代理对象控制对原对象的引用.它包含了三个角色: Subject: ...

  9. javascript设计模式实践之代理模式--图片预加载

    图片的预加载就是在加载大图片前,先显示一个loading.gif,就算在网络比较慢的时候也能让人知道正在加载,总比啥反应都没有强. 下面这段代码就是预加载的一个简单的实现,假设先不处理加载图片时的on ...

随机推荐

  1. mysql输入密码后闪退怎么办?

    第一: 首先需要想到的是mysql的服务可能没开,首先打开mysql的服务 第二: 打开Mysql的命令行输入密码即可 第三: 登录成功 第四: 顺便验证自己安装的mysql是否成功 输入显示所有数据 ...

  2. Maven学习总结(八)——使用Maven构建多模块项目

    在平时的Javaweb项目开发中为了便于后期的维护,我们一般会进行分层开发,最常见的就是分为domain(域模型层).dao(数据库访问层).service(业务逻辑层).web(表现层),这样分层之 ...

  3. Leetcoede 112 Path Sum 二叉树

    二叉树的从叶子到根的和是否存在 /** * Definition for binary tree * struct TreeNode { * int val; * TreeNode *left; * ...

  4. Android中的IOC框架,完全注解方式就可以进行UI绑定和事件绑定

    转载请注明出处:http://blog.csdn.net/blog_wang/article/details/38468547 相信很多使用过Afinal和Xutils的朋友会发现框架中自带View控 ...

  5. 诚聘Android开发工程师

    职位要求1.有1年以上Android应用项目经验或相关经验: 2.熟悉Android操作系统和Android SDK,GUI编程及GDI的使用:熟练掌握Android 的 UI 系统控件及常用布局.动 ...

  6. Android Studio使用小技巧:提取方法代码片段

    http://www.jb51.net/article/65510.htm 今天来给大家介绍一个非常有用的Studio Tips,有些时候我们在一个方法内部写了过多的代码,然后想要把一些代码提取出来再 ...

  7. Python:字符编码详解

    相关文章 Python中文编码问题:为何在控制台下输出中文会乱码及其原理 1. 字符编码简介 1.1. ASCII ASCII(American Standard Code for Informati ...

  8. IIS下使用appcmd批量搭建网站

    使用 cmd 运行如下命令 > %windir%\system32\inetsrv\appcmd list site /config /xml > d:\sites.xml 修改 d 盘 ...

  9. Intrinsics头文件与SIMD指令集、Visual Studio版本对应表(转)

    File:Intrinsics头文件 描述:指令集描述VS:Visual Studio版本号VisualStudio:Visual Studio版本名 File 描述 VS VisualStudio ...

  10. Java多线程(3) Volatile的实现原理

    Volatile变量 在程序设计中,尤其是在C语言.C++.C#和Java语言中,使用volatile关键字声明的变量或对象通常拥有和优化和(或)多线程相关的特殊属性.通常,volatile关键字用来 ...