Embedding multiple instances of a flash component in a Flex application - apache-flex

I have a flash application (pure AS, no Flex framework) that I'd like to embed inside of a flex application using SWFLoader.
Embedding one instance works well. However, when I try to embed multiple instances (each with a separate SwfLoader), there is really strange behavior that seems to be caused by clashes among the class definitions of the multiple instances. This flash application is written with a lot of singleton classes, so my guess is that these singletons are overriding each other and causing the weird behavior.
I tried loading the flash application into a child applicationdomain, but that doesn't seem to help much either. Has anyone faced this problem?

You would want to load the SWF into its own application domain (not a child) to avoid name clashing.
There are three types of application domains:
var swfLoader:Loader = new Loader();
var loaderContext:LoaderContext = new LoaderContext();
// child SWF adds its unique definitions to
// parent SWF; both SWFs share the same domain
// child SWFs definitions do not overwrite parents
loaderContext.applicationDomain = new ApplicationDomain(ApplicationDomain.currentDomain);
// child SWF uses parent domain definitions
// if defined there, otherwise its own
loaderContext.applicationDomain = ApplicationDomain.currentDomain;
// child SWF domain is completely separate and
// each SWF uses its own definitions
loaderContext.applicationDomain = new ApplicationDomain();
// Load the swf file
swfLoader.load(new URLRequest("file.swf"), loaderContext);
I would suggest using the first method, as it will not overwrite definitions.

Related

How to add flex controls to my AS3 project?

I'm absolute newbie in Flash development but anyway I need to do something.
I have a pure AS3 project that plays video from youtube (chromeless player). I need to add some controls to manage this player. I don't know how to do that? If I just add mxml file into the project nothing happens. How to bind this file to as3?
Thanks
Flex components need to have UIComponent parent to function properly. If your player is based on Sprite, controls will not be initialized.
There is a trick to use Flex controls in the Sprite, but only after initialization in Flex Application. If you don't have Application, no luck.
You could use an AS3-only alternative. One library I've used is minimalcomps which offers some simple but effective controls for use in any AS3 project.
You can't use MXML, but nobody stops you to create your own controls if they are simple.
A short and simple example of how to add a button with an image:
loader = new Loader();
loader.contentLoaderInfo.addEventListener(Event.COMPLETE, onComplete);
loader.load(new URLRequest('http://i1.nyt.com/images/misc/nytlogo379x64.gif'));
function onComplete(event:Event):void
{
var button:Sprite = new Sprite();
button.addChild(event.currentTarget.content);
addChild(button);
button.buttonMode = true;
button.addEventListener(MouseEvent.CLICK, onButtonClick);
}
function onButtonClick(event:MouseEvent):void
{
trace ('click');
}
This would be the most basic version of a button with a loaded bitmap image.
Normally you would like to check for errors as well... what to do if the image is not found, or when you're not allowed to access it.
If you're going to need more then one button you could make a class which accepts an url, so you could just pass the url to the class and the button would be created.
A completely other way to approach this is with an SWC file, you could create the buttons in the Flash IDE and export them as an swc, which you can embed and use in your pure AS3 project.

how to use UIComponent/Flash in Flex

I am new to Flash/Flex.
I would like to use a Component I created in Flash extending fl.core.UIComponent. How do I use this in Flex? Do I just export it as a swc or do I have to use the Flash Flex 3 kit which will convert it to a UIMovieClip. That does not sound right.
I would appreciate a few simple steps describing the process.
Thanks
Sanoran
You can publish your file as a .swf and use the SWFLoader to load it, just remember the paths are relative to your run/debug directories.
My understanding is swc files are generally library files, rather than visual components, because you want the libraries included at compile time (swc) rather than at runtime (swf).
var loader = new SWFLoader();
// set autoload to false just so we KNOW when it loads. Also prevents
// us from accidently loading it twice by calling load() later
loader.autoLoad = false;
loader.addEventListener(Event.INIT, function (nt:Event) {
// Remove event listener so can be garbage collected
event.currentTarget.removeEventListener(event.type, arguments.callee);
// note we can the loader, rather than
// loader.content
someIVisualElementContainer.addElement(loader);
});
// relative to bin-debug or bin-release
loader.source = "movie.swf";
loader.load();
Just import the .as file into your flex app. Use rawChildren.addChild instead of plain addChild to add it to the display list because flex overrides the default addChild method to accept only mx.core.UIComponent and its derived classes.
Update: You can't use FLA in flex, so if your component is not just an AS class extending fl.core.UIComponent, you should either export it to SWC or load the corresponding SWF at runtime to the flex app.

Flex: How to call function of embedded swf?

I have a Flex 3.4 app that embeds a swf with mx:SwfLoader...
That swf has a public function named "playIt". I've tried dispatching events to gettingHere.content, casting gettingHere.content as a MovieClip and other stuff...
var swfApp:MovieClip = MovieClip(gettingHere.content);
if (swfApp.hasOwnProperty("playIt")) {
var helloWorld:Function = (swfApp["playIt"] as Function);
helloWorld();
}
to no avail. Help!
See the example here for interacting with a loaded Flex application.
Essentially:
var swfLoader:SWFLoader; // assuming loading complete
var loadedSM:SystemManager = SystemManager(swfLoader.content);
var loadedApp:Object = loadedSM.application;
app.playIt();
Are you able to load the swf into Flex at runtime rather than embed it? I've had good results loading swfs into Flex after launch, whereas embedding tends to be problematic for accessing a swf API.
Either use Loaders with eventListeners in a script or mx:SWFLoader in MXML with a listener on complete should work for you.

AS2 .swf loadmovie() and unloadmovie() fail when nested inside an AS3 .swf container

I have an AS2 .swf being loaded as a child of a parent AS3 .swf. The AS2.swf calls loadmovie() and unloadmovie() to display 3 jpeg files. The images load the first time, but after that, a call to loadmovie() to replace the image, or a call to unloadmovie() fail. I found the following Adobe Bug report (https://bugs.adobe.com/jira/browse/ASC-3338?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel) that has said this has been resolved, and also said that child movieclips could be replaced without a problem. Here is the code I'm calling.
_root.help_mc.scenes_image1_mc.loadMovie("first.jpg");
_root.help_mc.scenes_image2_mc.loadMovie("second.jpg");
_root.help_mc.scenes_image3_mc.loadMovie("third.jpg");
_root.help_mc.scenes_image1_mc.unloadMovie();
_root.help_mc.scenes_image2_mc.unloadMovie();
_root.help_mc.scenes_image3_mc.unloadMovie();
I'm not well versed in ActionScript, so I'm afraid I might not be referencing the movieclip in the correct way. The bug report said child swf's cannot replace themseleves, but if the AS2 swf is acting as the psuedo root, can I reference the movieclip through the AS2 swf?
AS2 doesn't work along-side AS3. Flash Player 9 and above have two different virtual machines - one for AS1, AS2 and the other for AS3 and only one of them is loaded at once, meaning that you can execute either AS3 or AS2 but not both.
http://en.wikipedia.org/wiki/ActionScript#Timeline_by_ActionScript_version
In ActionScript 3 you load a movie like this:
var myLoader:Loader = new Loader();
var url:URLRequest = new URLRequest("first.jpg");
myLoader.load(url);
addChild(myLoader);

Flex: Passing MXML file as XML Parameter

Is it Possible to pass MXML it self as parameter(XML param) from external application and load in Flash Player dynamically to create page. For e.g
passing xml = <mx:canvas><mx:label text="hello" /></mx:canvas> to Flex and flex should create canvas with label control in it. Is there any example related to it.
Thanx
MXML code needs to be compiled down to ActionScript before Flash Player can do anything with it. MXML is not interpreted by Flash Player at runtime.
What you are wanting to do is not possible. Like brd6644 said, mxml is compiled down to bytecode in the swf which is interpreted by the flash player. The mxml (and even actionscript) is not understood by the flash player.
That being said, there is a JSP library that you can use for dynamic MXML. See here:
http://www.adobe.com/devnet/flex/articles/server_perf_05.html
That link is old, and right now I can't seem to find an updated link, but I know the project still exists. I believe it actually ships as part of ColdFusion still. It allows you to create dynamic mxml which gets JIT compiled at the request. It of course has a substantial performance hit because of it, but if you need dynamic MXML it is an option.
I will update this comment with a better link when I find it.
Just store the properties of the
component to a XML and put a className
attribute so that if you load the XML
you can have a function to set the
attributes of the XML to the
properties of your created component
which will be determined in your
className attribute
My initial guess is no, it would still be of type "XML", and there is no "eval" in Actionscript 3. I did a quick search and am going to have to say no, this is not possible.
I have however, done something similar in an app I created.
What I did was store in a database the object type, and some properties (x,y,width,height, etc). This data is returned from a remote object call and these objects are then created at runtime, which can get a similar effect you are trying to achieve.
For example:
var resultAC:ArrayCollection = event.result as ArrayCollection;
var tmpCanvas:Canvas;
for(var i:int = 0; i < resultAC.length; i++)
{
if(resultAC.getItemAt(i).type == "Canvas")
{
tmpCanvas = new Canvas();
tmpCanvas.x = resultAC.getItemAt(i).x;
tmpCanvas.y = resultAC.getItemAt(i).y;
...
parent.addChild(tmpCanvas);
}
}

Resources