最新更新 sitemap 网站制作设计本站搜索
网页设计
国外网站 韩国网站 个人主页 手提袋设计 CSS 网页特效 平面设计 网站设计 Flash CMS技巧 服装网站 php教程 photoshop 画册 服务器选用 数据库 Office
虚拟主机 域名注册 云主机 网页设计 客服QQ:8208442
当前位置:首页 > 网络设计学院 > Flash教程

如何设计良好的FLASH项目架构

日期:11-11    来源:中国设计秀    作者:cnwebshow.com

单例模式(Singleton)确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例单例模式。单例模式只应在有真正的“单一实例”的需求时才可使用enj中国设计秀
为什么要在FLASH中使用单例模式?enj中国设计秀
首先我们明白,"单例"-即在软件运行时只提供一个实例,大家知道在面向对象编程中,实例化一个对象就意味着需要在内存中开辟一单元供这个对象的实例使用.而经常的,我们编写的一个类或函数需要在系统的很多地方被引用,不得已我们每次都需要去获取这个类的实例以供使用.以至于我们要不断的去new一个对象,如此一来,不但给系统增加负担,而且会给用户带来坏的使用体验-.enj中国设计秀
就象我们制作一个工具,我们希望完成后,在以后随时随地我们都可以很方便地拿出这个工具来协助我们工作.而不是每次需要使用这个工具的时候都需要花时间花力气去重新制作这个工具. enj中国设计秀
在FLASH中使用单例模式的目的即是如此.但是首先需要明确:enj中国设计秀
1,这个工具是我们经常使用的.enj中国设计秀
2,这个工具必须可以灵活使用,而不是就单针对着特定的某一件工作.正确的说,这个工具可以应付我同一类型的一系列工作,而不是异想天开的替我解决所有问题.enj中国设计秀
3,不要让其他人使用这个工具,确保这个工具的专利属于我.enj中国设计秀
在FLASH中什么情况适合使用单例模式?enj中国设计秀
在具备以下的需求时,我们可以考虑使用单例模式:需要一个通用的业务逻辑处理器来处理同一类型的工作任务,需要一个数据访问对象来处理一系列的外部数据交互工作,前提是使用一致的数据访问手段.enj中国设计秀
由于FLASH是基于客户端的软件,客户端基本上就是一个人在使用,所以我们可以忽略通常在软件设计中需要考虑的线程并发问题(在B/S,C/S架构的系统中,通常这些任务由服务器来做).而且,虽然FLASH本身是多线程的,但是它并没有允许我们编程控制线程.enj中国设计秀
因此,我们在FLASH中使用单例模式的好处就是:节约系统开销,增大代码重用性.其实最大的好处就仅是节约系统开销而已.至于代码重用我们可以基于自身对软件设计的经验使用各种方式做到.enj中国设计秀
一个基本的单例模式:enj中国设计秀

class SingletonClass{ enj中国设计秀
  private static var singletonClass:SingletonClass = null; enj中国设计秀
  private function SingletonClass{} enj中国设计秀
  public static function getInstance():SingletonClass{ enj中国设计秀
    if(singletonClass == null){ enj中国设计秀
      SingletonClass.singletonClass = new singletonClass(); enj中国设计秀
    } enj中国设计秀
    return singletonClass; enj中国设计秀
  } enj中国设计秀
}enj中国设计秀

在第一行代码.我们申明了一个静态(static)的变量,他的类型为SingletonClass类本身.既然申明的变量为static,那么在程序运行期间这个变量将会长驻在内存中而不会自动销毁enj中国设计秀
第二行代码,我们写了一个空的构造函数,而且它是私有的(private),这意味着这个类不可以在外部被实例化,这也正是我们的目的.(我们专利的工具将不会被外人模仿使用)enj中国设计秀
在 getInstance方法中,我们通过判断singletonClass的值是否为null来取决是否需要实例化singletonClass.第一次将singletonClass实例化以后,之后将不需要再实例化singletonClass.最后,这个方法将会返回一个SingletonClass实例的引用-singletonClassenj中国设计秀
看到这里,相信大家都已经明白单例模式的构成原理enj中国设计秀
 enj中国设计秀
下面我们来做一个应用单例模式的DEMOenj中国设计秀
我们将做一个用户信息查询的模块,应用单例模式主要的目的是保证在用户活动过程中,相关用户信息的外部数据调用工作只做一次.enj中国设计秀
考虑到设计良好的应用结构,我们将会稍微在单例模式的原则上做一些改动.我们将这一应用分为:用户模型,业务逻辑控制器,FLASH视图三部分,数据访问对象将会由FLASH内置的XML对象来充当(其实这种架构是参考常用的B/S软件结构来设计,从实际B/S系统结构的原则上讲,整个FLASH应用程序都只将作为表示层).enj中国设计秀
代表用户实体的类enj中国设计秀

MemberEntry.as enj中国设计秀
class com.hizon.domain.MemberEntry{ enj中国设计秀
    private var id:Number; enj中国设计秀
    private var email:String; enj中国设计秀
    public function getId():Number{ enj中国设计秀
        return id; enj中国设计秀
    } enj中国设计秀
    public function setId(id:Number):Void{ enj中国设计秀
        this.id = id; enj中国设计秀
    } enj中国设计秀
    public function getEmail():String{ enj中国设计秀
        return email; enj中国设计秀
    } enj中国设计秀
    public function setEmail(email:String):Void{ enj中国设计秀
        this.email = email; enj中国设计秀
    } enj中国设计秀
} enj中国设计秀
member.xml enj中国设计秀
xml version="1.0" encoding="gbk"?> enj中国设计秀
<root> enj中国设计秀
<id>1id> enj中国设计秀
<email>bhlove@gmail.comemail> enj中国设计秀
root>enj中国设计秀

负责数据访问的类enj中国设计秀

MemberDao.as enj中国设计秀
import com.hizon.domain.MemberEntry; enj中国设计秀
class com.hizon.dao.MemberDao{ enj中国设计秀
    private static var memberEntry:MemberEntry = null; enj中国设计秀
    private function MemberDao(){} enj中国设计秀
    public static function initMemberEntry(memberId:Number,event:Function):Void{ enj中国设计秀
        if(MemberDao.memberEntry == null){ enj中国设计秀
            var memberProfileDoc:XML = memberProfileDoc = new XML(); enj中国设计秀
            memberProfileDoc.ignoreWhite = true; enj中国设计秀
            memberProfileDoc.load("xml/member.xml"); enj中国设计秀
            memberProfileDoc.onLoad = function (success){ enj中国设计秀
                MemberDao.memberEntry = new MemberEntry(); enj中国设计秀
                MemberDao.memberEntry.setId(memberProfileDoc.firstChild.childNodes[0].firstChild.nodeValue); enj中国设计秀
                MemberDao.memberEntry.setEmail(memberProfileDoc.firstChild.childNodes[1].firstChild.nodeValue); enj中国设计秀
                event.call(MemberDao,MemberDao.memberEntry); enj中国设计秀
                return; enj中国设计秀
            } enj中国设计秀
        } enj中国设计秀
        event.call(MemberDao,MemberDao.memberEntry); enj中国设计秀
    } enj中国设计秀
}enj中国设计秀

在Flash中进行用户信息打印enj中国设计秀

import com.hizon.dao.MemberDao; enj中国设计秀
import com.hizon.domain.MemberEntry; enj中国设计秀
MemberDao.initMemberEntry(1,init); enj中国设计秀
function init(mb:MemberEntry){ enj中国设计秀
    trace(mb["email"]); enj中国设计秀
}enj中国设计秀

在这里,我们使用了Function对象的call方法,也许你会问,为什么不在MemberDao里直接返回一个MemberEntry对象?enj中国设计秀
原因是这样的,在FLASH中的所有基于http协议的外部数据调用工作都是异步进行的(而且,FLASH没有提供线程控制编程).这样直接导致的结构就是:当数据调用还没完成的时候,AS脚本已经获取了return值,当然,这个值会是nullenj中国设计秀
所以,我认为最好的方法就是将函数作为参数传递给方法,由方法在完成XML数据调用后执行目标函数.如果大家有更好的方法,希望不啬指教.enj中国设计秀
最后将一下我的设计思路吧enj中国设计秀
基于面向对象的设计原则(仿照JAVA设计模式).我使用了MemberEntry这个类作为用户的实体参照对象.这样在以后更多的业务逻辑中,如果我想获取/更新用户资料,我只需要针对这个对象进行get/set方法操作.然后由专门的类根据需求负责处理MemberEntryenj中国设计秀
例如:enj中国设计秀
负责向服务器提交数据的类enj中国设计秀

class com.hizon.web.Poster{ enj中国设计秀
    public function post(url:String,entry:Object,listener:Function){ enj中国设计秀
        var poster:LoadVars = new LoadVars(); enj中国设计秀
        var result_v:LoadVars = new LoadVars(); enj中国设计秀
        for(var name in entry){ enj中国设计秀
            poster[name] = entry[name]; enj中国设计秀
        } enj中国设计秀
        poster.sendAndLoad(url,result_v,"POST"); enj中国设计秀
        result_v.onLoad = function (success:Boolean){ enj中国设计秀
            if(success){ enj中国设计秀
                listener.call(Poster); enj中国设计秀
            } enj中国设计秀
        } enj中国设计秀
    } enj中国设计秀
}enj中国设计秀

这样,我只要将标准格式的实体对象作为参数交由Poster类处理,即可完成向服务器提交数据更新的工作.而不需要在多处编写POST代码.