FLEX3 SWFLoader 與RemoteObject的問題

var swf : SWFLoader = new SWFLoader();

swf.source="test.swf";

 

如果loader進來的SWF文件用至RemoteObject,只load一個進來是沒有問題的,但如果再load一個進來就提示錯誤:

TypeError: Error #1034: 強制轉換類型失敗:無法將 mx.messaging.messages::ErrorMessage@392f779 轉換爲 mx.messaging.messages.ErrorMessage。

 

解決方法:

var swf : SWFLoader = new SWFLoader();

var lc : LoaderContext = new LoaderContext();
lc.applicationDomain = ApplicationDomain.currentDomain;

swf.loaderContext = lc;

swf.source="test.swf";

 

指定SWFloader的loaderContext.loaderContext的說明如下:

flash.system
public class LoaderContext
繼承 LoaderContext InheritanceObject
子類 JPEGLoaderContext
語言版本:  ActionScript 3.0
運行時版本:  AIR 1.0 Flash Player 9

LoaderContext 類提供多種選項,以使用 Loader 類來加載 SWF 文件和其它媒體。LoaderContext 類用作 Loader 類的 load()loadBytes() 方法的 context 參數。

 

使用 Loader.load() 方法加載 SWF 文件時,需要做出兩個決定:應將所加載的 SWF 文件放置到哪個安全域中,以及應放置到該安全域中的哪個應用程序域中? 有關這些選擇的更多詳細信息,請參閱 applicationDomainsecurityDomain 屬性。

 

使用 Loader.loadBytes() 方法加載 SWF 文件時,與使用 Loader.load() 時一樣,也要選擇應用程序域,但不必指定安全域,這是因爲 Loader.loadBytes() 始終將其加載的 SWF 文件放置到執行加載的 SWF 文件的安全域。

 

如果是加載圖像(JPEG、GIF 或 PNG)而不是 SWF 文件,則無需指定安全域或應用程序域,這是因爲這些概念只對 SWF 有意義。此時您只需做出一個決定:是否需要以編程方式訪問所加載圖像的像素? 如果需要,請參閱 checkPolicyFile 屬性。如果要在加載圖像時應用解塊,請使用 JPEGLoaderContext 類替代 LoaderContext 類。

公共屬性
  屬性 定義方
    AIR-only  allowLoadBytesCodeExecution : Boolean = false
指定是否可以使用 Loader 對象的 loadBytes() 方法下載具有可執行代碼的內容,如 SWF 文件。
LoaderContext
    applicationDomain : ApplicationDomain = null
指定用於 Loader.load() 或 Loader.loadBytes() 方法的應用程序域。
LoaderContext
    checkPolicyFile : Boolean = false
指定在開始加載對象本身之前,應用程序是否應該嘗試從所加載對象的服務器下載 URL 策略文件。
LoaderContext
  Inherited constructor : Object
對類對象或給定對象實例的構造函數的引用。
Object
  Inherited prototype : Object
[靜態] 對類或函數對象的原型對象的引用。
Object
    securityDomain : SecurityDomain = null
指定用於 Loader.load() 操作的安全域。
LoaderContext

公共方法
  方法 定義方
   
LoaderContext (checkPolicyFile:Boolean = false, applicationDomain:ApplicationDomain = null, securityDomain:SecurityDomain = null)
創建帶有指定設置的新 LoaderContext 對象。
LoaderContext
  Inherited
指示對象是否已經定義了指定的屬性。
Object
  Inherited
指示 Object 類的實例是否在指定爲參數的對象的原型鏈中。
Object
  Inherited
指示指定的屬性是否存在、是否可枚舉。
Object
  Inherited
setPropertyIsEnumerable (name:String , isEnum:Boolean = true):void
設置循環操作動態屬性的可用性。
Object
  Inherited
返回指定對象的字符串表示形式。
Object
  Inherited
返回指定對象的原始值。
Object

屬性詳細信息

AIR-only  allowLoadBytesCodeExecution 屬性

public var allowLoadBytesCodeExecution:Boolean = false

運行時版本:  AIR 1.0

指定是否可以使用 Loader 對象的 loadBytes() 方法下載具有可執行代碼的內容,如 SWF 文件。在此屬性設置爲 false (默認值)的情況下,loadBytes() 方法僅限於執行安全操作,如加載圖像。

在位於應用程序安全沙箱的 AIR 內容中,默認值爲 false 。在非應用程序內容中,默認值爲 true

注意: 在未來的 AIR 版本中,很可能會替換此 API。發生這種情況時,將需要調整代碼以使用新的 API,並在針對新版本的 AIR 發佈應用程序之前進行重新編譯。

applicationDomain 屬性  

public var applicationDomain:ApplicationDomain = null

語言版本:  ActionScript 3.0
運行時版本:  AIR 1.0 Flash Player 9

指定用於 Loader.load()Loader.loadBytes() 方法的應用程序域。只應在加載使用 ActionScript 3.0 編寫的 SWF 文件(不是圖像或使用 ActionScript 1.0 或 ActionScript 2.0 編寫的 SWF 文件)時才使用此屬性。

 

每 個安全域被分成一個或多個由 ApplicationDomain 對象表示的應用程序域。應用程序域並不是用於安全目的;它們用於管理 ActionScript 代碼的協作單元。如果是從其它域加載 SWF 文件,並允許將它放置到另外一個安全域中,則您將無法控制所加載的 SWF 文件被放置到哪個應用程序域中;即使您指定應選擇某個應用程序域,也會忽略。但是,如果是將 SWF 文件加載到您自己的安全域中(因爲此 SWF 文件來自您自己的域,或者您正在將它導入到您的安全域中),您就可以控制爲所加載的 SWF 文件選擇哪個應用程序域。

 

LoaderContext.applicationDomain 中,您只可以傳遞您自己的安全域中的應用程序域。如果試圖傳遞任何其它安全域中的應用程序域,則會引發 SecurityError 異常。

 

有四種 ApplicationDomain 屬性可供您選擇使用:

  • 加載器的 ApplicationDomain 的子級。 默認值。可以使用語法 new ApplicationDomain(ApplicationDomain.currentDomain) 顯式表示這種選擇。這將允許所加載的 SWF 文件直接使用父級的類,例如,可通過編寫 new MyClassDefinedInParent() 來使用。但是父級則不能使用此語法;如果父級要使用子級的類,它必須調用 ApplicationDomain.getDefinition() 來檢索它們。這種選擇的優點是,如果子級定義的類與父級已經定義的類同名,不會出現錯誤結果;子級只會繼承父級對該類的定義,除非子級或父級調用 ApplicationDomain.getDefinition() 方法來檢索子級的衝突定義,否則將不使用此定義。
  • 加載器自己的 ApplicationDomain。 使用 ApplicationDomain.currentDomain 時請使用此應用程序域。加載完成後,父級和子級可以直接使用對方的類。如果子級試圖定義的類與父級已定義的類同名,則使用父類並忽略子類。
  • 系統 ApplicationDomain 的子級。 使用 new ApplicationDomain(null) 時請使用此應用程序域。這將完全分離加載方和被加載方,從而允許它們使用相同的名稱定義各自版本的類並且不會產生衝突或隱藏。一方查看另一方的類的唯一方式是調用 ApplicationDomain.getDefinition() 方法。
  • 其它 ApplicationDomain 的子級。 有時可能會有更復雜的 ApplicationDomain 層次結構。可以將 SWF 文件從您自己的 SecurityDomain 加載到任何 ApplicationDomain 中。例如,new ApplicationDomain(ApplicationDomain.currentDomain.parentDomain.parentDomain) 將 SWF 文件加載到當前域父級的父級的新子級中。

加載完成後,爲調用 ApplicationDomain.getDefinition() ,任一方(加載方或被加載方)都可能需要找到它自己的 ApplicationDomain 或另一方的 ApplicationDomain。任一方都可以通過使用 ApplicationDomain.currentDomain 來檢索對它自己的應用程序域的引用。執行加載的 SWF 文件可以通過 Loader.contentLoaderInfo.applicationDomain 來檢索對被加載的 SWF 文件的 ApplicationDomain 的引用。如果被加載的 SWF 文件知道自己的加載方式,則它可以找到執行加載的 SWF 文件的 ApplicationDomain 對象。例如,如果子級是以默認方式被加載的,則它可以通過使用 ApplicationDomain.currentDomain.parentDomain 找到執行加載的 SWF 文件的應用程序域。

 

有關詳細信息,請參閱《ActionScript 3.0 編程》 中“客戶端系統環境”一章的“ApplicationDomain 類”一節。

 

checkPolicyFile 屬性  

public var checkPolicyFile:Boolean = false

語言版本:  ActionScript 3.0
運行時版本:  AIR 1.0 Flash Player 9

指定在開始加載對象本身之前,應用程序是否應該嘗試從所加載對象的服務器下載 URL 策略文件。此標誌適用於 Loader.load() 方法,但不適用於 Loader.loadBytes() 方法。

 

如果您從執行調用的 SWF 文件所在的域之外加載圖像(JPEG、GIF 或 PNG),並且您預計將需要從 ActionScript 訪問該圖像的內容,請將此標誌設置爲 true 。訪問圖像內容的示例包括引用 Loader.content 屬性以獲得 Bitmap 對象,以及調用 BitmapData.draw() 方法以獲得所加載圖像像素的副本。如果您在加載時沒有指定 checkPolicyFile 就嘗試執行這些操作之一,您可能會得到一個 SecurityError 異常,這是因爲尚未下載所需的策略文件。

 

LoaderContext.checkPolicyFile 設置爲 true 的情況下調用 Loader.load() 方法時,應用程序直到成功下載了相關的 URL 策略文件或發現不存在此類策略文件時纔開始下載 URLRequest.url 中的指定對象。Flash Player 或 AIR 首先考慮已經下載的策略文件,然後嘗試下載調用 Security.loadPolicyFile() 方法過程中指定的任何待下載策略文件,然後嘗試從與 URLRequest.url 對應的默認位置(即 URLRequest.url 所在服務器上的 /crossdomain.xml )下載策略文件。在所有情況下,給定的策略文件必須位於 URLRequest.url (根據策略文件的位置而定),且策略文件必須通過一個或多個 <allow-access-from> 標籤允許進行訪問。

 

如果將 checkPolicyFile 設置爲 true ,則 Loader.load() 方法中指定的主下載將在完全處理該策略文件之後開始下載。因此,只要您需要的策略文件存在,一旦您收到來自 Loader 對象的 contentLoaderInfo 屬性的任何 ProgressEvent.PROGRESSEvent.COMPLETE 事件,就說明該策略文件下載已完成,您就可以安全地開始執行需要該策略文件的操作。

 

如果您將 checkPolicyFile 設置爲 true ,並且未找到相關的策略文件,則除非您嘗試執行的操作引發了 SecurityError 異常,否則您將不會收到任何錯誤指示。但是,一旦 LoaderInfo 對象調度 ProgressEvent.PROGRESSEvent.COMPLETE 事件,您就可以通過檢查 LoaderInfo.childAllowsParent 屬性的值來測試是否找到了相關的策略文件。

 

如果不需要對正在加載的圖像進行像素級的訪問,則不應將 checkPolicyFile 屬性設置爲 true 。在這種情況下不必再檢查是否存在策略文件,因爲這樣會延遲下載的開始時間,並且可能會不必要地佔用網絡帶寬。

如果是使用 Loader.load() 方法下載 SWF 文件,也儘量不要將 checkPolicyFile 設置爲 true 。這是因爲 SWF 到 SWF 的權限不是由策略文件控制的,而是由 Security.allowDomain() 方法控制的,因此在加載 SWF 文件時 checkPolicyFile 不起任何作用。在這種情況下不必再檢查是否存在策略文件,因爲這樣會延遲 SWF 文件的下載,並且可能會不必要地佔用網絡帶寬 (Flash Player 或 AIR 無法判斷主下載將是 SWF 文件還是圖像,這是因爲策略文件下載先於主下載進行。)

 

如果是從可能使用服務器端 HTTP 重定向的 URL 下載對象,則使用 checkPolicyFile 時要小心。始終從 URLRequest.url 中指定的相應初始 URL 檢索策略文件。如果由於 HTTP 重定向而導致最終對象來自其它 URL,則最初下載的策略文件可能不適用於該對象的最終 URL,而最終 URL 對於安全性決策非常重要。如果發現處於這種情況,可以在收到 ProgressEvent.PROGRESSEvent.COMPLETE 事件後檢查 LoaderInfo.url 的值,它會告訴您該對象的最終 URL。接着,用一個基於該對象的最終 URL 的策略文件 URL 調用 Security.loadPolicyFile() 方法。然後輪詢 LoaderInfo.childAllowsParent 的值,直到它變爲 true

不需要爲運行於應用程序沙箱中的 AIR 內容設置此屬性。AIR 應用程序沙箱中的內容調用 BitmapData.draw() 方法時可以使用任何已加載的圖像內容作爲源。

 

securityDomain 屬性  

public var securityDomain:SecurityDomain = null

語言版本:  ActionScript 3.0

指定用於 Loader.load() 操作的安全域。只應在加載 SWF 文件(而不是圖像)時使用此屬性。

只有在被加載的 SWF 文件與執行加載的 SWF 文件可能來自不同的域(不同的服務器)時,選擇安全域纔有意義。從您自己的域加載 SWF 文件時,始終會將它放置到您的安全域中。但是,在從其它域加載 SWF 文件時,您有兩種選擇: 您可以允許將被加載的 SWF 文件放置到其“自然的”安全域中,此安全域與執行加載的 SWF 文件的安全域不同;這是默認設置。另一種選擇是通過將 myLoaderContext.securityDomain 設置爲與 SecurityDomain.currentDomain 相同,指出您希望將被加載的 SWF 文件放置到執行加載的 SWF 文件所在的安全域中。這稱作導入加載 ,就安全性而言,它等同於將被加載的 SWF 文件複製到您自己的服務器,然後從該服務器加載它。爲使導入加載成功完成,被加載的 SWF 文件的服務器必須具有一個策略文件,並且該策略文件必須信任執行加載的 SWF 文件的域。

您只能在 LoaderContext.securityDomain 中傳遞您自己的安全域。如果試圖傳遞任何其它安全域,則會引發 SecurityError 異常。

AIR 應用程序安全沙箱中的內容無法將其他沙箱中的內容加載到其 SecurityDomain 中。

有關詳細信息,請參閱《ActionScript 3.0 編程》 中的“安全性”一章。

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章