mvc flex cairngrom

来源:互联网 发布:人工智能的利与弊论文 编辑:程序博客网 时间:2024/05/22 16:49


1 MVC


 使用过Web框架Struts、Webwork或者其它框架的人,对MVC应该都很熟悉。
      所谓MVC,就是Model、View和Controller。
     
      Model就是数据模型。
      View就是用户界面。
      Controller就是控制器。
     
      MVC是Xerox PARC在80年代为编程语言Smalltalk-80发明的一种设计模式,被广泛使用。后来被推荐为Sun公司(已经被Oracle收购了)J2EE平台的设计模式。
      MVC已经基本成为WEB框架公认的设计模式,现有的流行的WEB框架也基本遵循这一设计模式。
 
      MVC设计模式的好处在什么地方呢?
      1、低耦合性。
      也就是说视图层和业务层是分开的。
      2、高复用性。
      多个视图(也就是用户界面了,通俗的说,呵呵)可以共用一个数据模型。比如无论用户想用传统的网页、Flash页面或者WAP页面,都可以用一个模型进行处理。
      3、可维护性。
      业务层和视图层分开,更利于代码的维护。
      4、快速开发。
      MVC模式使得开发时间缩短。使得JAVA程序人员更专注于业务层,WEB页面可发人员更关注于页面。
      呵呵,说这句话,很多人都会说,现在公司都希望一个人全都干了,还分什么分?
      可能大部分情况是这样,但是这种开发的好处作者是经历过的。
      做中国移动传输网管开发的时候,业务层和页面就是分开开发,这样配合,进度很快,因为页面开发的人不需要专注于复杂的业务,而后台开发的人只使用JAVA语言而不关


心复杂的JSP页面和繁琐的JAVAScript。
      有用就是有用。
      5、软件化管理。
      分层明确,层次分明,不利于代码管理才怪,呵呵。
 
      有好就有坏,不过要理解这个坏就要对MVC设计模式深入了解,作者在此就简单提及一下,有兴趣的读者可以深入研究。
     
      很显然,分层了,代码文件就会增多,这是必然的。呵呵,这也算缺点,当然算了。不过这个缺点相对MVC带来的好处实在不值
得一提。不过缺点就是缺点,再小也是缺点啊。勿以善小而不为,勿以恶小而为之(为啥说这对句话呢?就当凑合文字吧,在枯燥的技术理论中来点小幽默)。
 
      至于MVC的图解作者就不画了,网上很多。
      写这讲内容就是要让读者重视而且是非常重视之重视这个概念。如果这个不理解,对于FLEX开发框架Caringorm的理解就会大大折扣甚至不懂甚懂,这样对读者造成的困惑大


于理解,对技术这条路就产生了怀疑。
      所以,凡是技术,要懂得原理。就像作者,使用过了Struts,Webwork、Caringorm等等都是手到擒来(吹一下牛,见谅啊,文人都相轻,做技术的,我觉得还是相重,所以


就原谅我的这句大话吧,哈哈)。




2 Cairngrom


Caringorm是Adobe官方的FLEX基于MVC(初学者不知道MVC和其原理不用着急,下一讲我会专门讲这个)的开源框架。


  目前除了Caringorm框架外,比较流行的还有PureMVC、Model-Glue、Gua-sax等等。


  作者就以官方的Caringorm作为Flex的开发框架作为讲解,如果读者有兴趣,可以根据实际情况自己研究其它的开发框架,其实只要是深入懂得MVC的原理,作者相信这些框架


本身对于读者是没有什么难度的。


  之所以作者选择Caringorm进行讲解,原因也是有的,主要如下:


  1、Caringorm作为开源框架,为Adobe官方所有(Flex本身也是Adobe公司的);


  2、Caringorm是最早也最成熟的框架。尽管Flex的各种框架还都不能做到真正的轻量级的开发,但是仍然不能成为否认Caringorm作为Flex的优秀开发框架之一的理由(是不是


挺绕口的,呵呵);


  Caringorm的官方网址是:http://opensource.adobe.com/wiki/display/cairngorm/Cairngorm。






  官方的简介如下: 


  Cairngorm is the lightweight micro-architecture for Rich Internet Applications built in Flex or AIR. A collaboration of recognized design patterns, 


Cairngorm exemplifies and encourages best-practices for RIA development advocated by Adobe Consulting, encourages best-practice leverage of the underlying 


Flex framework, while making it easier for medium to large teams of software engineers deliver medium to large scale, mission-critical Rich Internet 


Applications. Cairngorm is now evolving towards a project that will invite community leaders and enterprise adopters to partner with Adobe Consulting in the 


ongoing development of Cairngorm.


  Cairngorm框架就是为企业RIA开发者提供一个开发框架。如果只是编写一个简单的应用或者只有一个视图的应用,就没必要使用Cairngorm等框架了。


  Cairngorm框架的优点就在于开发复杂的RIA应用的时候就会体现的淋漓尽致(有点夸张,但仍然恰如其分,典型的废话,呵呵),框架之所以为框架,就在于如此,不止


Caringorm,其它框架亦如此。






  下载完Caringorm,就准备应用开发了。


  不过下几讲的内容不着急于Demo,作者根据以前的文章,发现有很多的初学者,因此会把MVC着重讲一下,然后把Caringorm的一些基础原理讲一下,这样大家在做Demo的时候


,理解起来就会很方便了,呵呵,说了这么多,Let's go!






3  cairngorm 组成部分
http://tech.ddvip.com/2009-09/1252506624131817.html


4 cairngorm 环境准备
http://tech.ddvip.com/2009-09/1252506696131818.html


5  cairngorm demo
http://tech.ddvip.com/2009-09/1252506764131819.html


6 cairngorm 代码结构
http://tech.ddvip.com/2009-09/1252506898131820.html


7 cairngorm model locator
http://tech.ddvip.com/2009-09/1252506982131821.html
Model Locator的概念已经讲过,就是在一个地方存储程序中所有的值对象(ValueObjects,数据)并共享变量。


  也就是说,Model Locator用来集中管理程序所需要的变量。


  下边把Demo15的ModelLocator.as代码如下:(作者增加相应的注释)


import mx.collections.ArrayCollection;
 
 [Bindable]
 public class ModelLocator
 {


  //定义程序需要的变量,作者建议读者把该部分定义放在最下边,而不是示例中的上边,原因就是在于代码更整齐(因人而异,仅作者的个人建议,呵呵)
  public var photoData:ArrayCollection=new ArrayCollection();
  public var purchasedPhotos:ArrayCollection=new ArrayCollection();


  


  //定义ModelLocator的Single Instance,这就是设计模式的单例模式(不明白的读者可以看设计模式中的该模式讲解)
  static private var __instance:ModelLocator=null;
  //返回single instance
  static public function getInstance():ModelLocator
  {
   if(__instance == null)
   {
    __instance=new ModelLocator();
   }
   return __instance;
  }
 }


  对于ModelLocator的instance和getInstance的代码编写,这部分代码读者在写新的代码过程中,除非重新定义一个自己的ModelLocator(基于IModelLocator 接口实现),这部


分代码就这么写了,呵呵,即使是自己定义,其也大同小异。


  对于getInstance来说,会判断程序是否已经有ModelLocator的实例,如果有则读取,没有则创建。


  而[Bindable]的特性,使自己定义的变量在任何一个使用定义变量的地方自动更新,这也是ModelLocator的共享变量的概念所在。


  ValueObject下的photo.as对象作者就不解释了,实在没啥解释的,呵呵。


  下一讲就要对Cairngorm的核心控制流程进行讲解了,也就是bussiness下的各部分和event的复杂关系,可能读者刚接触会觉得很绕,没关系,呵呵,Step By Step,作者讲解


之后,读者就不会有那种感觉了。




8 cairngorm 核心控制流程
http://tech.ddvip.com/2009-09/1252507074131823.html


 这一讲结合Demo对Cairngorm的核心控制流程进行讲解,也帮助读者梳理一下对Demo代码的认知。


  下图就是Caringorm的事件流程:


View -> Dispatch Event -> Front Controller ->Command -> Model -> View


 在操作View也就是页面的过程中会派发Event,然后由Front Controller影射分配给对应的Command,Command做完相应的业务处理更新ModelLocator的数据,由于ModelLocator(


上一讲讲过)共享的原因,View自动会更新所显示的内容。


  了解了这个基本流程后,读者对核心控制流程的认知就会更加清晰了:


  Events:就是操作View或者其它设计产生的事件;


  FrontController:就是注册Command和Event的对应关系,来把Event进行影射分配给相应的Command;


  Command:进行业务处理,更新ModelLocator(至于Command部分如何利用Delegate和Service连接则在下一讲中进行详细描述);


  这下读者就很清楚了这三者之间的关系以及Cairngorm这么做的基本原理。


  很显然,也就对应了以下的代码结构:


  events目录下的AddPhotoToCartEvent.as和LoadPhotosEvent.as,继承自CairngormEvent。PhotoEvent让操作者选择图片时发出事件(FStop.mxml中操作事件触发)。


  在FSController.as中定义(建议读者建一个controller的目录),继承自FrontController,负责将Event注册到Command,也就是接收到Event就分配给Command,代码如下:


     addCommand(LoadPhotosEvent.EVENT_ID,LoadPhotosCommand);
     addCommand(AddPhotoToCartEvent.EVENT_ID,AddPhotoToCartCommand);


  在FStop.mxml中操作者触发代码:


     //选择图片时触发AddPhotoToCartEvent


   private function photoSelectedHandler(event:PhotoEvent):void 
   {
    var addEvent:AddPhotoToCartEvent=new AddPhotoToCartEvent(event.selectedPhoto);
    addEvent.dispatch();
   }


   //初始化系统时触发LoadPhotosEvent


   private function initApp():void 
   {
    var event:LoadPhotosEvent=new LoadPhotosEvent();
    event.dispatch();
   }


  这下读者对代码是不是清晰很多了:)


  下一讲对Command如何利用Delegate和Service连接进行讲解(说句实话,尽管作者也遵照这个规范去编写,但是仍然感觉Cairngorm架构对业务层的处理定义的过于复杂了,仅


个人观点,非官方,呵呵)。




9 cairngorm command 部分
http://tech.ddvip.com/2009-09/1252507124131824.html
这一讲对Command部分进行详细解释,也就是command如何通过Delegate部分去做Services(Remoting,Webservices...等等)。


  从上一讲中读者可以知道,Event触发通过FrontController影射到对应的Command进行业务处理。


  而如果系统要和后台的数据库进行数据交互的话,Command就会产生Delegate,将远程访问(HTTP,WebServices等等)实例化,并将结果返回给Command。


  Service则就是用来定义服务器端访问以获取数据的。


  这样读者就很清晰Command部分的处理流程了,对照代码解释如下:


  LoadPhotosCommand.as中需要加载图片访问服务器数据(该实例简化就定义在本地xml中,不过原理一样的),通过onResults_loadPhotos这个,将获取的图片数据加载到


ModelLocator中,这样View就可以显示所获取的数据了。


  而在PhotoDelegate中,就是将远程访问实例化而已:__service = __locator.getHTTPService("photosIn");


  Services.mxml中定义了访问数据的方式:<mx:HTTPService id="photosIn" url="assets/photos.xml"/>。


  读者通过Demo15及对其的详细讲解,应该有一个很基础的认知了,至于框架本身如何,在实际系统的开发中,都要很好的去遵循框架本身的要求。