Mastering the External Interface.
It surprises me how many people know so little about the External Interface and what can be done with it.
You can communicate back and forth from ActionScript to JavaScript using the External Interface.
Many wonderful things are possible.
I have made a class called DOMEx that utilizes the External Interface and JavaScript stored as XML to aid in the communication between JavaScript and ActionScript.
To get a quick idea of some of the things that can be done, you can view some of the examples I’ve made using the DOMEx set of classes.
Dragging a green circle outside and back into the flash
Three D Cube following the mouse no matter where the mouse is
The swf responding to the wrappers key events
Basic Overview
Basic use of the External Interface.
import flash.external.ExternalInterface;
if (ExternalInterface.available) ExternalInterface.call("function () { alert('Hello World'); }");
//or
var javaScript:XML =
<script>
<![CDATA[
function (words) {
alert(words);
}
]]>
</script>;
if (ExternalInterface.available) ExternalInterface.call(javaScript, "Howdy Ya'll");
//and
var browserLocation:String = ExternalInterface.call("window.location.toString()");
trace(browserLocation);
//adding a callback
if (ExternalInterface.available) ExternalInterface.addCallback("javaScriptCalling", myActionScriptFunction);
function myActionScriptFunction(...args):void {
//do something in the swf
}
Things To Know
The External Interface has been around for some time now, (Flash 8) but got popular with AS3.
You can pass, Strings, Numbers, Booleans, Arrays, basic Objects, and XML back and forth between ActionScript and JavaScript.
XML is converted to a string when accessed via JavaScript, and sometimes has a hard time getting back to an ActionScript form.
When communicating between the two, it is best to just stick to the main types of Objects (Strings, Numbers, Arrays)
When adding a call back for javaScript to call, there are some words that are reserved and will not work in Internet Explorer as callbacks.
GetVariable, SetVariable, Play, and most of the words found here as methods or properties:
http://www.adobe.com/support/flash/publishexport/scriptingwithflash/scriptingwithflash_03.html
When testing in the Flash IDE, ExternalInterface.available may return true.
You can test against that by doing something like this:
var javascript:XML=<script><![CDATA[function(){return ["some", "array"];}]]></script>;
if (ExternalInterface.available && ExternalInterface.call(javascript) == null) {
//you may be in the IDE
}
The DOMEx Class
The DOMEx Class makes it possible to easily communicate back and forth between AS and JS,
without having to set anything up in the wrapper.
The documentation is here: DOMEx Documentation
Tags: ActionScript, DOMEx, ExternalInterface, JavaScript
Your right. Basically. But there is a whole lot that goes on behind the scenes whenever you make any ExternalInterface call.
Flash automatically creates a set of functions to change JavaScript objects into AS objects and back. One function for changing JS Arrays into AS ready Arrays, one for Objects, one for Numbers etc…
Those functions work by wrapping things in XML, use IEs developer tool and you will be able to see them.
So, your right, when you wrap your javascript in an xml variable and call like ExternalInterface(myJavaScriptXML, “Howdy”)
whatever is in myJavaScriptXML gets written to the browser… but, it does get reused automatically and not re-written until the page is refreshed.
Take a look at my DOMEx examples above, in IE, with the developer tool, and you’ll be able to see how all the JavaScript gets placed in to the wrapper, ready to be called on…
But the key thing with putting your javascript in an XML variable, or embedding it in the swf some other way, is that when you do those things, the resulting weight of the javascript will be much less. Note the post I wrote about embedding jQuery inside of your swf.
By itself, embedded in a webpage, jQuery min is 56kb. When you embed it into a swf, and use that swf instead, the kbs go all the way down to 25! That’s more than half savings.
But in general you are more than correct, if a project does not call for heavy flash and js integration, there’s really no need to put it all in XML variables rather than just normal js files.
So I’ve been playing around with what I learned from this article and I’m really enjoying it except for one performance concern. Wouldn’t it be more efficient to define JS functions in JS rather than in AS3′s XML objects or strings? Because whenever you execute
ExternalInterface.call(javaScript, “Howdy Ya’ll”);
I’m guessing that the function defined in the object javaScript is first defined in the actual browser’s JS and then called. So if you had to call this function several times, wouldn’t you rather define it in JS just once and call it from the memory? Does this make any sense or am I completely wrong here?
Essentially you do have to pass a function as the first argument, it’s just that you can wrap that function in a string, or even in xml.
Using an xml variable not only allows you to place javascript right inside of your swf, but also gives a neat way to organize your code.
Thanks for the comment!
Thanks, Tad, for sharing these things. It may take me some time to really understand how ExternalInterface.call() works. I thought that the first argument of ExternalInterface.call() has to be a javascript function name, like “alert” or “myJSFunction”, but clearly, I was wrong about that. Looks like you can write whole JS statements in the first argument. Thanks again!