2009-04-27 4 views
2

응용 프로그램 용 플러그인 시스템을 구현하려고하는데 동적으로로드 된 SWF 파일을 가져 오는 데 악영향을 끼치 지 않으면 추가 SWF 파일을로드합니다.Flex에서 플러그인 만들기 - 중첩 된 SWF 파일로드

그것은 이런 식입니다 :

  1. 기본 응용 프로그램 쉘로드 ...
  2. --------- + 응용 프로그램로드 ...
  3. ------ 나는 응용 프로그램을 얻을 수 없다 내가 수도로 ----------- + 플러그인 (들)

내가 2

그러나 응용 프로그램 번호를로드하는 응용 프로그램 # 1을 받고 아무 문제가 시도 로드 할 # 2 stantiate # 3

나는 ModuleManager를 사용하여 다양한 순열을 시도했지만 이것이 가장 가까운 것이다. onLoadComplete 메서드가 호출되면 SWF가로드 된 것을 볼 수 있지만 팩토리는 항상 NULL을 반환합니다.

흥미로운 점은 자체 애플리케이션에서이를 추출 할 때 제대로 작동한다는 것입니다. 이 문제는 동적으로로드 된 SWF에서 플러그인을로드한다는 사실에 의해 발생합니다.

나는 이것이 ApplicationDomain으로 인한 것이라고 생각하지만, 머리 또는 꼬리를 만들 수 없습니다. currentDomain, new ApplicationDomain(Application.currentDomain)new ApplicationDomain()을 지정하지 않고 시도했습니다.

또한 본질적으로 우리는 그들이 무엇을 포함 할 지 미리 알 수 없으므로 두 응용 프로그램에서 Foo 클래스에 대한 참조를 참조 할 수 없다는 점에 유의해야합니다.

주위에, 이것은 꽤 알려진 문제인 것 같지만 아직 (명확한) 해결책을 찾지 못했습니다. joshtynjala @

. 
. 
. 
assetModule = ModuleManager.getModule("Foo.swf");  
assetModule.addEventListener(ModuleEvent.READY, onLoadComplete); 
assetModule.addEventListener(ModuleEvent.ERROR, onLoadError); 
assetModule.load(); 
. 
. 
. 
private var _pluginInstance:Plugin; 

private function onLoadComplete(event:Event):void 
{ 
    trace("module loaded"); 

    _pluginInstance = assetModule.factory.create() as Plugin; 
    if(_pluginInstance) 
     _pluginInstance.startup(); 
    else 
     Alert.show("unable to instantiate module"); 
} 

private function onLoadError(event:Event):void 
{ 
     Alert.show("error"); 
} 

My Plugin looks like this: 

package 
{ 
    import mx.collections.ArrayCollection; 
    import mx.modules.ModuleBase; 

     public class Plugin extends ModuleBase 

     public function startup():void 
     { 

     } 
. 
. 
. 
} 

package 
{ 
    import Plugin; 
    import mx.modules.ModuleBase; 

    public class Foo extends Plugin 
    { 
     public function Foo() 
     { 
      trace("foo constructor invoked"); 
     } 

     override public function startup():void 
     { 
        trace("foo started"); 
     } 
. 
. 
. 
} 
+1

나는 오랫동안 응용 프로그램 도메인으로 근무 한 적이없는, 그래서 나는이 질문에 대한 완전한 해답을 제공 할 수 없습니다,하지만 문제가 여기에 무슨 일이 일어나고 있음을 알 수 있습니다 : assetModule.factory.create() 플러그인으로; 모듈의 Plugin 클래스와 기본 앱의 Plugin 클래스가 VM에 관한 한 동일하지 않습니다. Plugin! = Plugin이므로 "Plugin"으로 변환하면 null이 반환됩니다. (Object 또는 뭔가로 캐스팅하는 것 이외의)이를 해결하는 방법은 기억이 나지 않지만 ApplicationDomain 클래스를 조사하는 올바른 길을 걷고 있습니다. – joshtynjala

답변

0

는 권리입니다. 그냥 Object를 사용하여 메서드를 호출하면 (캐스팅하지 마십시오) 발견되었습니다.

var MyPlugin : Object = getPlugin(); MyPlugin.doPluginFunc();

일반적으로 system/flex 클래스 간에는 아무런 문제가 없습니다. 런타임 라이브러리로 Plugin을 넣는 것이 도움이 될지 모르겠다.

0

플러그인과 응용 프로그램간에 공통 인터페이스를 사용하려면 응용 프로그램의 Plugin 클래스가 Plugin 클래스와 같아야합니다. 이렇게하려면 동일한 ApplicationDomain에 b가 있어야합니다.

//In an external library 
public interface Plugin {} 

//In your application 
_pluginInstance = assetModule.factory.create() as Plugin; 
... 


//In your plugin 
public class MyPlugin implements Plugin 

문제는 플러그인 swf를 컴파일 할 때 플러그인을 컴파일한다는 것입니다. 이 문제가되지 않습니다,하지만 당신은 자신과 동일한의 응용 프로그램 알려줄 필요가 :

var loader:Loader = new Loader(); 
loader.addEventListener(Event.COMPLETE, onLoadComplete); 
loader.load(new URLRequest("plugin.swf"), new LoaderContext(false, ApplicationDomain.currentDomain));  

ApplicationDomain.currentDomain을 여기에 키입니다.docs을 참조하는 경우 :

로더 자신의 ApplicationDomain. 너 ApplicationDomain.currentDomain을 사용할 때이 응용 프로그램 도메인을 사용하십시오. 로드가 완료되면 부모와 자식 은 서로의 클래스를 직접 사용할 수 있습니다. 자식이 부모에 의해 이미 정의 된 클래스 과 동일한 이름을 가진 클래스를 정의하려고하면 부모 클래스가 사용되고 자식 클래스는 무시됩니다.

관련 문제