I've got an AS3 SWF that I'm going to be loading other SWFs into. These child SWFs all take a single parameter on the URL. I can't seem to get it working when loading an AS2 child, and it needs to be able to handle both.
so I have
var request:URLRequest = new URLRequest();
var loader:URLLoader = new URLLoader();
request.url = "http://domain/as2.swf?param=foo";
loader.load(request);
// etc on to the eventListeners, addChild, etc
When the as2 SWF gets loaded, it can't see the parameter I've passed to it. It's looking for _root.param. Am I doing this wrong or am I attempting the impossible?
EDIT: I should add that I can load a SWF with those URL params from an AS2 loader and it works just fine.
It's not trivial to communicate between AS2 and AS3 since they run in different virtual machines. Check this http://www.gskinner.com/blog/archives/2007/07/swfbridge_easie.html for some hints.
Edit: If you cannot change the loaded as2 content your only options is creating a 'wrapper' as2 loader that uses the linked example above to communicate with the as3 and interfaces with the loaded as2 content using _root.varname This is not pretty but it might just work.
It might be worth trying to assign the variables dynamically after the SWF has loaded but before you add it to the stage. Ie.
loader.contentLoaderInfo.addEventListener(Event.COMPLETE, movieLoaded);
function movieLoadedHandler(event : Event) : void
{
var loaderInfo : LoaderInfo = event.target as LoaderInfo;
var clip : DisplayObject = loaderInfo.content;
for each(var prop in varsToTransfer)
{
clip[prop] = varsToTransfer[prop];
}
// add to parent
}
Let me know how that goes.
AS3 -> AS3
Movie 1(www.domain1.com):
Load the external movie when click a "buy" button...
buy.addEventListener(MouseEvent.CLICK,function(){
var ldr:Loader = new Loader();
var url:String = "http://www.domain2.com/movie.swf?a=b&c=d";
var urlReq:URLRequest = new URLRequest(url);
ldr.load(urlReq);
addChild(ldr);
});
Movie 2(http://www.domain2.com/movie.swf):
var mc:MovieClip = this as MovieClip;
var ldi:LoaderInfo = mc.loaderInfo;
var lobj:Object = ldi.parameters as Object;
for (var l in lobj) {
dumper.htmlText += l+" => "+lobj[l]+"<br />";
}
"dumper" is the name of the Dynamic Textbox field located in Movie2.
The output should look like:
a => b
c => d
Instead of looking for _root.param, use _root._url then parse out your parameters by hand.
var url: String = _root._url;
var param: String = 'param=';
var paramStart: Number = url.lastIndexOf(param);
var paramValue: String = url.substring(paramStart + param.length, url.length);
trace(paramValue);
SWFBridge is awesome and overkill for something like this.
You are doing it wrong.
"http://domain/as2.swf?param=foo"
Is a request for the file named as2.swf, on the server named domain. Any ?param=foo parameters that are part of that http request are lost when the request is complete. If the server needed to do something according to these variables, it would, but you are asking a .swf file to detect these variables, that's just silly.
Put a variable in your Global object (Global namespace) for the flash player, then when the as2 .swf is loaded into that flash player it will have access to the variable you set in your Global object.
I am not proficient in as2, but in as3, the Global object can be accessed with the this keyword, at the package level (probly is the same for as2, just dont worry about setting it at a package level).
Related
I just trying to control buttons of external loaded swf .
var swfRequest:URLRequest = new URLRequest('http://mysite.com/player/001.swf');
var swfLoader:Loader = new Loader();
swfLoader.load(swfRequest);
var holder:MovieClip = new MovieClip();
holder.addChild(swfLoader);
addChild(holder);
And in main swf I created new button with Instance Name : pauseBtn , I want this button communicate to external swf witch has pause button with Instance Name : pausebtn in action script 2.0
external btn:
on (release)
{
status_playing = false;
playbtn._visible = true;
pausebtn._visible = false;
stop ();
}
Please help me how to communicate with these buttons.
Normally, I don't think you can directly communicate between AS3 content and AS2 content. One way around it is using a LocalConnection object to handle the communication between the two.
How it would work after creating the objects and connecting them, is the main swf would send a message to it's LocalConnection object and the loaded swf would receive that message on and use it to handle whatever you need it to.
LocalConnection - AS3 Reference: http://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/net/LocalConnection.html
LocalConnection - AS2 Reference: http://help.adobe.com/en_US/AS2LCR/Flash_10.0/help.html?content=00001176.html#312868
I am embedding an swf file that has some children on its timeline. Like this:
[Embed(source="assets/skyscraper200x600.swf")]
private var Skyscraper :Class;
All children in the swf have an instance name, I double checked that when creating the swf in Flash CS5.
I am trying to access those children by name like this:
_bg = MovieClip(new Skyscraper());
_pig = MovieClip(_bg.getChildByName("chara_pig"));
_arrow = MovieClip(_bg.getChildByName("arrow_banner"));
However, both _pig and _arrow end up being null.
What's even stranger is that when I look at the Skyscraper object in the debugger, it shows a rather strange class name and a Loader as its only child (which in turn has no children). What's up with this?
.
I can access them like above if I do not embed the swf, but load it with a Loader. But I cannot do it in this case. I need to embed the swf.
So, how can you access children of embedded swfs?
I am not talking about accessing classes in the library of the embedded swf, but the instances on the timeline.
Here is a solution. You can also see the steps who helped me find this solution (describeType is your friend) :
public class Demo extends Sprite {
[Embed(source="test.swf")]
private var Test:Class
public function Demo() {
//first guess is that embed SWF is a MovieClip
var embedSWF:MovieClip = new Test() as MovieClip;
addChild(embedSWF);
//well, emebed SWF is more than just a MovieClip...
trace(describeType(embedSWF));//mx.core::MovieClipLoaderAsset
trace(embedSWF.numChildren);//1
trace(describeType(embedSWF.getChildAt(0)));//flash.display::Loader
var loader:Loader = embedSWF.getChildAt(0) as Loader;
//the content is not already loaded...
trace(loader.content);//null
loader.contentLoaderInfo.addEventListener(Event.COMPLETE, function(){
var swf:MovieClip = loader.content as MovieClip;
var child:MovieClip = swf.getChildByName("$blob") as MovieClip;
//do nasty stuff with your MovieClip !
});
}
}
At the end of this tutorial http://jadendreamer.wordpress.com/2010/12/20/flash-as3-embedding-symbols-from-external-swf-game-tutorial there is an example of how it can be done
One solution is to embed the swf as an octet stream and reconstitute its bytes. However, I seem to remember reading somewhere that if you just set the mimeType to "application/x-shockwave-flash", you get a MovieClip that works as normal.
I have had several posts like this but I have not gotten down to the final answer so I put this image together to try and explain what I am trying to do. I AM SO CLOSE.
if you can help me THANK YOU SOOOO MUCH. Worked days on this so far.
HOW DO I CONTROL CHILDREN INSIDE AN EXTERNALLY LOADED SWF FROM CODE IN ANOTHER EXTERNALLY LOADED SWF?
EDIT: Below is THEE code located in "ONE.swf" that I need help with. Just one or two lines I know but I JUST CANT get it.
function FunctionInOne()
{
var parentObj:Object = this.parent.parent as Object; //// GIVES ACCESS TO "Content.swf"
var TheStage:Object = this.parent.parent.parent as Object; //// GIVES ACCESS TO STAGE
trace(TheStage.stage.stageWidth);
trace(parentObj); /// [object MainTimeline]
trace(parentObj.ONE); /// [object Loader]
trace(parentObj.TWO); /// [object Loader]
parentObj.alpha = .3; /// NOW I CONTROL THE ALPHA OF "Content.swf" from ONE.swf
var ControlTWO:Loader = parentObj.TWO; // GIVES ACCES TO LOADER TWO
ControlTWO.alpha = .3; // NOW I CONTROL THE ALPHA OF TWO.swf from ONE.swf
BUT HOW DO I GET ACCESS TO CONTROL THE CHILDREN IN "TWO.swf" from "ONE.swf"
var TWOchildren:MovieClip = MovieClip(TWO.content); // DOES NOT WORK
TWOchildren.ChildInTWO.alpha = .3;
var TWOchildren = TWO.content as MovieClip; // DOES NOT WORK
TWOchildren.ChildInTWO.alpha = .3; // DOES NOT WORK
TWOchidren.FunctionInTWO(); /// DOES NOT WORK
}
EDIT: March 16th, 2012
I am able to access the swf TWO.swf from ONE.swf and control it's alpha with this line:
trace(MovieClip(parent.parent).ONE);
But I need to control a child in that so I thought this following code would work but it doesn't:
MovieClip(parent.parent).ONE.TheChild.alpha = .3;
END EDIT---------------
Here is another link to it if you can see it: http://mycontactcorner.com/sandbox/testing/ChildTwo.jpg
Ok I found it!
var InsideConent:Object = this.parent.parent as Object; //// GIVES ACCESS TO "Content.swf"
var ItWorksNow:Sprite = MovieClip(InsideConent.TWO.content).ChildInTWO; ///
ItWorksNow.x = 333; /// I can control property x
ItWorksNow.alpha = .3; /// I can control the ALPHA! :)
Is see hard style of programming :]
to Your loaders add this , it should help:
import flash.system.ApplicationDomain;
import flash.system.LoaderContext;
var loader:Loader = new Loader ( urlRequest , new LoaderContext(false, ApplicationDomain.currentDomain));
Second thing :
You should try access to content if You make sure that its loaded .
So put start loading of second SWF to loading complete function of first SWF and You should trace(TWO.content) and see is there anything already loaded.
MovieClip(parent.parent).function();
vise versa reference the movieclip.OtherChildmoviename.function();
this structure you can call a function from where ever or anymovie for better explanation check actionscript 2 as it uses the _root, this may make the above clearer
let us no how you go;
I am attempting to import some simple XML data into Flash ActionScript 3.0. I can easily do this as an import that is posted to the stage, but I want to save it as a global variable instead. Here is the XML file that I am pulling from:
<utilitySavings>
<nameof file="academicWaterSavings">
<waterValue>100</waterValue>
<elecValue>200</elecValue>
</nameof>
<nameof file="dormWaterSavings">
<waterValue>300</waterValue>
<elecValue>400</elecValue>
</nameof>
<nameof file="greekWaterSavings">
<waterValue>500</waterValue>
<elecValue>600</elecValue>
</nameof>
<nameof file="totalWaterSavings">
<waterValue>1500</waterValue>
<elecValue>1600</elecValue>
</nameof>
...and here is the actionscript:
var req:URLRequest = new URLRequest("data.xml");
var loader:URLLoader = new URLLoader();
var utilitySavings:XML;
function xmlLoaded(event:Event):void
{
utilitySavings = new XML(loader.data);
academicWater.text = utilitySavings.nameof[0].waterValue;
academicElec.text = utilitySavings.nameof[0].elecValue;
var dormWater:String = utilitySavings.nameof[1].waterValue;
trace (dormWater);
}
loader.addEventListener(Event.COMPLETE, xmlLoaded);
loader.load(req);
trace(academicWater.text);
Notice the 'trace (dormWater)' I want to trace this outside of the function so it is accessible in later in my script. I can trace within the function, but this does me no good. I also am able to get the dynamic text to show up on the stage but, likewise, this does me little good.
I appreciate any help or insights.
I can see a couple of ways of achieving this , if you want to create a globally accessible Object, create a Singleton( not recommended ) , load your XML data into it then every object in your app will be able to access the loaded XML data.
http://www.gskinner.com/blog/archives/2006/07/as3_singletons.html
The resulting code would give you something like this:
//Available throughout your app after the XML has been loaded & parsed
var dormWater:String = Singleton.dormWater;
Although you state you don't want Events, I think that using Signals could be a better approach. Load your XML and dispatch a Signal containing the relevant String to the object that needs it, when receiving the Signal , assign the String to a variable.
http://www.peterelst.com/blog/2010/01/22/as3-signals-the-best-thing-since-sliced-bread/
//In a specific class
private var _dormWater:String;
private function signalListener(value:Object ):void
{
_dormWater = value.dormWater;
}
When you load a SWF into another, the loader SWF can get specific definitions from the loaded SWF using ApplicationDomain.getDefinition(name:String). For example:
package
{
// ... imports
public class SWFLoader extends Sprite
{
private var loadedAppDomain:ApplicationDomain;
public function SWFLoader()
{
var request:URLRequest = new URLRequest("test.swf");
var loader:Loader = new Loader();
loader.contentLoaderInfo.addEventListener(Event.COMPLETE, onTestLoadComplete);
loader.load(request);
}
private function onTestLoadComplete(event:Event):void
{
var loaderInfo:LoaderInfo = LoaderInfo(event.target);
loadedAppDomain = loaderInfo.applicationDomain;
// Here we can get ANY defined symbol (class, namespace or function according to Adobe Flash help)
var someSymbolClass:Class = Class(loadedAppDomain.getDefinition("SomeSymbol"));
var someSymbolSprite:Sprite = Sprite(new someSymbolClass());
addChild(sprite);
}
}
}
How can I get all of the definitions in a SWF, without specifying each explicitly?
As of Flash Player 11.3, you can use ApplicationDomain.getQualifiedDefinitionNames().
See the official documentation for the method and this blog post about the Flash Player release.
EDIT: This is the quickest solution to your problem : http://www.bytearray.org/?p=175
Hi, you could use this library : https://github.com/claus/as3swf/wiki/
Don't have the time to do deeper test, but here is what i found :
1 - I have created a .swf containing in the library 2 exported MC, $Test and $Test2
2 - Once the .swf loaded by a Loader, i run this code :
var swf : SWF = new SWF(loader.contentLoaderInfo.bytes);
trace(swf);
3 - In the output you'll notice theses lines :
[76:SymbolClass]
Symbols:
[0] TagID: 2, Name: $Test2
[1] TagID: 1, Name: $Test
I think that there is a way to obtain this info directly thru the library API
You have to put the loaded SWF in the current ApplicationDomain.
Use ApplicationDomain.currentDomain to do that, on the ContextLoader info.
loader.load(request, new ContextLoader(false, ApplicationDomain.currentDomain));
It should work.
Following from the answer I received from a previous question I asked here a few days ago (it's about SWC , but in your case, it doesn't really make a difference )
Working with SWCs - getDefinitionByName issue
If both SWFs share the same ApplicationDomain, you should be able to access the loaded SWF classes directly by doing this:
//provided that SomeSymbol extends Sprite...
var someSymbolSprite:Sprite =new SomeSymbol();
On the other hand, you won't be able to do this
var SomeSymbol:Class = getDefinitionByName("SomeSymbol");
unless you create a library of objects from the loaded SWF
var ssym:SomeSymbol;
Check the above link for more details.