书接上回。在展示了App最顶层的代码后,我们去看看各模块怎样编程。

为了能看懂各模块的代码,首先须要铺垫一下Softchip架构的基本概念和设计规范。

1、随意模块不持有其它模块的实例。自然不再显式使用句柄调用不论什么方法。

这意味着模块之间不存在编码期和编译期的耦合。

2、每一个模块在形式上仅仅与Machine之间存在接口。该接口以APIEvent两种形态存在。

API将直接映射到函数入口地址,使用者可直接调用,执行期性能高。主要用于Utility性质的方法和须要高性能的场合。

Event也是同步调用,但执行期性低于API。它的关键作用是在逻辑上分割冗长的调用链。在传统套路中。一个模块在完毕自己的处理后。往往还要辛苦地触发其它模块的相关兴许动作,这在逻辑上相当于惦记着“别人的事儿”。Event的引入相当于将原来长长的调用链在时间上切分为一个一个的阶段状态。

每一个模块仅仅须要告诉Machine“X的事情Y完了”,Machine会自己主动查找谁须要在“X的事情Y完了”之后继续。Machine寻找兴许操作的根据就是目标模块在自己的接口中所做的事件监听声明。

3、模块接口由自行声明,包含:

3-1) outAPI  : 自己须要调用的API名称列表。

3-2) inAPI   : 自己能够提供其它模块调用的API名称列表(附带相应的函数入口地址)。

3-3) inEvent : 自己要监听的事件名称列表(附带相应的事件处理函数入口地址)。

3-4) outEvent: 自己是否要发送事件。

基于各模块声明。Machine自己主动将各模块“插入”。完毕执行期API的绑定和event的分发。

4、概括来说,各模块基本仅仅须要关心“自己的事情”:

4-1) 我提供什么API?

4-2) 我须要调用什么API?

4-3) 我监听并处理什么事件?

4-4) 我产生什么事件?

反过来讲,模块不须要关心“别人的事情”:

4-5) 谁使用我的API?

4-6) 谁提供API给我用?

4-7) 我监听的事件是谁产生的?(我干活之前是谁在干?)

4-8) 我产生的事件谁处理?(我干完了谁来继续?)

   

举个简单的样例,在TextChat的设计中,LoginWindow登录成功后,不须要显式通知ChatWindow,由于那是ChatWindow的事情。LoginWindow仅仅须要告诉Machine“LoginWindow登录成功了”。

Machine会自己主动找到ChatWindow出来干活,由于ChatWindow之前已经告诉过Machine,假设“LiginWindow登录成功了”。请通知我。

OK,有了上面的铺垫,以下的代码就比較easy看懂了。基本套路是:

1、每一个模块都继承Chip类。

2、实现_DefineInterface()方法以完毕接口声明。

3、实现_PowerOn()方法以接收Machine发出的"上电"通知。

除此以外,每一个模块就全然自由了。爱怎么玩就怎么玩吧。

新版的模块关系參照下图。

from Softchip import Chip
class Controller(Chip):
def __init__(self, chipID):
Chip.__init__(self, chipID) def _DefineInterface(self):
outAPIList = [
u'connect_server',
u'disconnect_server',
] inAPIList = [
(u'api_start_work', self.__apiStartWork),
] inEventList = [
(u'evt_logout_done', self.__evtOnLogoutDone),
] self.__interface = {
Chip.TYPE_INT_API : inAPIList,
Chip.TYPE_OUT_API : outAPIList,
Chip.TYPE_OUT_EVENT: None,
} return self.__interface def _PowerOn(self):
self._eHandler = self.__interface[CHIP.TYPE_OUT_EVENT] apiMap = self._DefineInterface[CHIP.TYPE_OUT_API]
self.__apiConnect = apiMap[u'connect_server']
self.__apiDisconnect = apiMap[u'disconnect_server'] def __apiStartWork(self, serverHost, serverPort):
succeeded = self.__apiConnect(serverHost, serverPort) if not succeeded:
self._eHandler(u'evt_connect_failed')
return self._eHandler(u'evt_connect_succeeded') def __evtOnLogoutDone(self):
self.__apiDisconnect() class CommunicationManager(Chip):
def __init__(self, chipID):
Chip.__init__(self, chipID) def _DefineInterface(self):
inAPIList = [
(u'connect_server', self.__Connect ),
(u'disconnect_server', self.__DisConnect ),
(u'log_in', self.__Login ),
(u'log_out', self.__Logout ),
(u'invite_friend', self.__InviteFriend),
(u'send_message', self.__SendMessage ),
] self.__interface = {
Chip.TYPE_IN_API : inAPIList,
Chip.TYPE_OUT_EVENT: None,
} return self.__interface def _PowerOn(self):
self._eHandler = self.__interface[Chip.TYPE_OUT_EVENT] def __Connect(serverHost, serverPort):
pass def __DisConnect(serverHost, serverPort):
pass def __Login(username, password):
pass def __Logout():
pass def __InviteFriend(friendName):
...
self.__MessageReceiveThread()
... def __SendMessage(message):
pass def __MessageReceiveThread():
while(True):
...
message = xxx
self._eHandler(u'evt_message_arrived', message)
... class LoginWindow(Chip):
def __init__(self, chipID):
Chip.__init__(self, chipID) def _DefineInterface(self):
outAPIList = [
u'log_in',
u'log_out',
] inEventList = [
(u'evt_connect_succeeded', self.__evtOnConnectSucceeded),
(u'evt_chat_closed', self.__evtOnChatClosed ),
] self.__interface = {
Chip.TYPE_OUT_API : outAPIList,
Chip.TYPE_INT_EVENT: inEventList,
Chip.TYPE_OUT_EVENT: None,
} return self.__interface def _PowerOn(self):
self._eHandler = self.__interface[CHIP.TYPE_OUT_EVENT] apiMap = self._DefineInterface[CHIP.TYPE_OUT_API]
self.__apiLogin = apiMap[u'log_in']
self.__apiLogout = apiMap[u'log_out'] def __evtOnConnectSucceeded(self):
self.Show() def __evtOnChatClosed(self):
self.__apiLogout() self._eHandler(u'evt_logout_done') def __OnLoginButtonPressed(self):
username = xxx.GetValue()
password = xxx.GetValue()
succeeded = self.__apiLogin(username, password) if not succeeded:
self._eHandler(u'evt_login_failed')
return self._eHandler(u'evt_login_succeeded')
self.Hide() class ChatWindow(Chip):
def __init__(self, chipID):
Chip.__init__(self, chipID) def _DefineInterface(self):
outAPIList = [
u'invite_friend',
u'send_message',
u'log_out',
u'disconnect_server',
] inEventList = [
(u'evt_login_succeeded', self.__evtOnLoginSucceeded ),
(u'evt_message_arrived', self.__evtOnMessageReceived),
] self.__interface = {
Chip.TYPE_OUT_API : outAPIList,
Chip.TYPE_IN_API : inEventList,
Chip.TYPE_OUT_EVENT: None,
} return self.__interface def _PowerOn(self):
self._eHandler = self.__interface[CHIP.TYPE_OUT_EVENT] apiMap = self._DefineInterface[CHIP.TYPE_OUT_API]
self.__apiInvite = apiMap[u'invite_friend']
self.__apiSendMsg = apiMap[u'send_message']
self.__apiLogout = apiMap[u'log_out']
self.__apiDisconnect = apiMap[u'disconnect_server'] def __evtOnLoginSucceeded(self):
self.Show() def __evtOnMessageReceived(self, message):
xxx.ShowText(message) def __OnInviteButtonPressed(self):
friendName = xxx.GetValue() succeeded = self.__apiInvite(friendName, self.__OnMessageReceived)
if not succeeded:
self._eHandler(u'evt_invite_failed')
return self._eHandler(u'evt_invite_succeeded') def __OnSendButtonPressed(self):
message = xxx.GetValue() self.__apiSendMsg(message) def __OnWindowClosing(self):
self._eHandle(u'evt_chat_closed')

在本系列的下一篇。我们将简要分析一下Softchip框架的意义。

最新文章

  1. poj 2393 Yogurt factory
  2. zookeeper 的多线程和单线程库使用对比
  3. CyanogenMod wiki reading tips | Android tips
  4. MyEclipse for Spring启动时报错"An internal error occurred during: 'Updating indexes'.Java heap space"的解决办法
  5. 完全搞懂傅里叶变换和小波(1)——总纲<转载>
  6. php验证是否是md5编码的代码
  7. 5中方式实现String反转
  8. Identity Card(水题)
  9. G - I Think I Need a Houseboat(简单题,粘贴下来是因为数据精度需要注意)
  10. APK 代码混淆
  11. window环境变量
  12. 关于Xmanager使用问题的总结
  13. C#来操作Word
  14. unity发布的WebGL部署到IIS
  15. maven 控制台 打包
  16. IOS 获取的时间显示为NAN 解决方法
  17. Call actvity after viewpager is finished
  18. html常用对照表
  19. PHP(三)运算符、流程控制和函数初步
  20. 基于 Axis2的webService接口的基本开发步骤

热门文章

  1. WEB框架——WEB框架本质
  2. 【04】在webstorm里Export declarations are not supported by current JavaScript version
  3. Linux下文件打包与解包
  4. [android开放篇] wifi-direct接口网址
  5. 【java基础 6】java的发展史简介
  6. sqlserver查询表大小
  7. UVa——1600Patrol Robot(A*或普通BFS)
  8. Codeforces Round #354 (Div. 2)——C. Vasya and String(尺取)
  9. 【2018.9.26】K-D Tree详解
  10. cf682E Alyona and Triangles