This site is now just an archive over the rise and fall of Flash. The domain flashmagazine.com is available for sale
Login | Register
Passing parameters to Flash using Javascript

Passing parameters to Flash using Javascript

Want to build something that responds to user input or a custom URL? This tutorial will show you how to use Javascript to pick up parameters sent to a SWF file using only Javascript.

Ever wanted to create a menu that remembers what item you pressed? By reading parameters passed in the URL, your Flash file can display this dynamic content or respond to user input. You can use this technique to create things like navigation, slideshows, SWF files with configurable text and much more. Another nice part of this trick is that it gives you full back-button support on all browsers.

Prerequisites

This tutorial requires some basic knowledge of Actionscript, Javascript and HTML, but most should be able to follow it. The examples are done using Flash Authoring (.FLA files) but the same techniques will work in Flex as well.

Setting up SwfObject

SwfObject 2 is by far the most elegant solution for detecting if a user has Flash installed. It is considered 'the industry standard' and all new versions of Adobe's own products (Flex 4, Flash CS5) will use SwfObject for Flash Player detection. Installing it is as easy as copying a file to your server, that's all. If you have SwfObject 2 or higher installed already, skip ahead (note the version number!). If you don't have it installed or have an older version, download it from here: http://code.google.com/p/swfobject/downloads/list

Unpack the ZIP archive and copy the file swfobject.js to your webserver. Making a root folder called "js" is a good idea (so the file will be at http://myserver.com/js/swfobject.js). We'll later refer to this file in the HTML file we'll make next. If you want to use the ExpressInstall functionality (offers simpler upgrading for your users), you must copy the expressInstall.swf file to the same folder.

Setting up the HTML file

The HTML file contains two javascripts. The first is the one that will grab parameters from the URL. This was created by Matt White and is a simple, but effective script to get specific parameters from a URL. The code looks like this:

<script type="text/javascript">
/* Get URL Parameter in Javascript. Code from: http://mattwhite.me/11tmr.nsf/D6Plinks/MWHE-695L9Z */
function getURLParam(strParamName){
  var strReturn = "";
  var strHref = window.location.href;
  if ( strHref.indexOf("?") > -1 ){
    var strQueryString = strHref.substr(strHref.indexOf("?"));
    var aQueryString = strQueryString.split("&");
    for ( var iParam = 0; iParam < aQueryString.length; iParam++ ){
      if ( aQueryString[iParam].indexOf(strParamName.toLowerCase() + "=") > -1 ){
        var aParam = aQueryString[iParam].split("=");
        strReturn = aParam[1];
        break;
      }
    }
  }
  return unescape(strReturn);
}
</script>

You place this in between the HEAD tags in your HTML file. Here you will also add the line that imports the SWFObject script like this:

<script type="text/javascript" src="/js/swfobject.js"></script>

The other javascript is the embedding of the SWF file using SwfObject. You can place this exactly where you want it in the HTML page. The first thing we do is create a DIV tag that contains the text shown to those that don't have the proper Flash Player installed:

<div id="flashcontent">
	<strong>This content requires Flash Player 9 (or a more recent version).
	<noscript>Make sure JavaScript is turned on. </noscript>
	You need to <a href="http://www.adobe.com/shockwave/download/index.cgi?p1_prod_version=shockwaveflash" target="_blank">
	<span style="text-decoration: underline;">upgrade your Flash Player</span></a></strong>
</div>

You can type whatever you want inside the DIV tag. Add pictures or fallback content as you like, for the contents will be replaced with your SWF file.

Next is the javascript that does the replacement:

<script type="text/javascript">
var flashvars = { test:getURLParam("test") };
var params = {};
var attributes = {};
swfobject.embedSWF("/articlefiles/jsvars/jsvars.swf", "flashcontent", "550", "400", "9.0.0","", flashvars, params, attributes);
</script>

Note that in line 2, we call the javascript function 'getURLParam' that we already embedded in the HTML file. We are passing along the name if the parameter we want to pick up from the URL.

Creating the Flash file

Next step is creating the Flash file. Start by adding a textfield on stage. Use the properties panel to set it to be "Dynamic" and set the instance name to 'mytextField'. Also turn on the border of the textfield by clicking the 'Show border around text'-button in the properties panel while textfield is selected.

To get the parameter passed in we need to use a try/catch statement like this:

try {
    var key:String; // This will contain the name of the parameter
    var val:String; // This will contain the value of the parameter
    var flashvars:Object = LoaderInfo(this.root.loaderInfo).parameters;
    for (key in flashvars) {
        val = String(flashvars[key]);
        mytextField.text = key+": "+val;
    }
} catch (error:Error) {
    // what to do if an error occurs
}

File: jsvars_test.fla

Upload the file to your server, together with the HTML file. When you run the file, you'll see the the textfield with 'test:' inside it.

NOTE: If the SWF does not display and you only see the "Upgrade your Flash Player"-text, something is missing on the server. Make sure you've uploaded the SwfObject file (swfobject.js) to http://myserver.com/js/swfobject.js. Also make sure you have the full path to both the SwfObject file as well as the SWF file written in your HTML file (see above). If you are still having problems, take a look at the source and paths used in the examples below.

Next, try to add the test parameter like this http://www.flashmagazine.com/articlefiles/jsvars/jsvars_test.html?test=something If done correctly, you will now see 'test: something' in the text field, indicating that you've successfully passed the parameter to the Flash file.

Taking this further

You can also set this parameter from inside your SWF file. In this example http://www.flashmagazine.com/articlefiles/jsvars/jsvars.html?test=something&id=someID we've added the possibility to send parameters as well.

The FLA contains two textfields named 'variablesReceived' and 'variablesToSend', plus a button that we use to send new parameters. The HTML file for this example is set up to receive the parameters 'test' and 'id'. We start by adding a little explanatory text to the first of the textfields:

variablesReceived.text ="Variables passed in:" + " ";

Next comes the actual receiving of the variables.

try {
    var key:String;
    var val:String;
    var flashvars:Object = LoaderInfo(this.root.loaderInfo).parameters;
    for (key in flashvars) {
        val = String(flashvars[key]);
        variablesReceived.appendText("\t" + key + ": " + val + " ");
    }
} catch (error:Error) {
    variablesReceived.appendText(error.toString());
}

This will list all the Flashvars that are set using Javascript for this HTML page in the first textfield. The other main function in this file is the one we use for sending the variables:

// Sending parameters
function sendVariables(e:MouseEvent):void {
    // First we grab the URL of the HTML document and split it into an array
    var htmlUrl:String = ExternalInterface.call("window.location.href.toString");
    // split the string at the questionmark
    var splitUrl:Array = htmlUrl.split("?");
    // use only the first part (ditch existing parameters)
    var trimmedUrl:String = splitUrl[0];
    // get the parameters we want to append to the URL
    var parameters:String = variablesToSend.text;
    // combine url and parameters with a new questionmark
    var requester:URLRequest = new URLRequest(trimmedUrl+"?"+parameters);
    // reload the page
    navigateToURL(requester, '_self');
}

Here we're using a neat little trick by calling out to the browser using 'ExternalInterface.call' to get the current URL of the HTML document that the SWF is embedded in. Flash files typically only know the URL to the SWF file itself, and this trick gets past that limitation. Using ExternalInterface is enabled by default in SwfObject, but it may be turned off manually so make sure this isn't done.

We won't need the parameters that may already be in the URL (i.e. '...?test=something&id=5') so we'll split the URL at the question mark and only keep the first part of the URL. We store this in the variable 'trimmedUrl' for later use. We grab the parameters in the 'variablesToSend' textfield and combine the two into a URLRequest. By passing the request to 'navigateToURL', the browser will reload the HTML page and display the newly submitted parameters/values in the 'variablesReceived' textfield.

Note: you can't test this locally in Flash. You'll need to upload the file to a server since both FlashVars and the use of ExternalInterface requires that the SWF is embedded in a browser.

Last, by not least we must set up the Send-button to call the 'sendVariables' method using addEventListener:

sendButton.addEventListener(MouseEvent.CLICK,sendVariables);

Now you've seen how to communicate back and forth with variables through Javascript. Let's use this for something useful!

Making a navigation that keeps state

To finish off, let's make a small menu system that will highlight the currently pressed button. You can download the finished file here and play with the example here. Let's look at the code:

First we stop the SWF from playing the timeline and set up event listeners for Mouse Clicks:

stop();
// setup our 5 buttons
item1.addEventListener(MouseEvent.CLICK, gotoURL);
item2.addEventListener(MouseEvent.CLICK, gotoURL);
item3.addEventListener(MouseEvent.CLICK, gotoURL);
item4.addEventListener(MouseEvent.CLICK, gotoURL);
item5.addEventListener(MouseEvent.CLICK, gotoURL);

When any of the buttons are clicked, they will now execute the 'gotoURL' function. Next, we grab the variable passed in from the URL:

// grab variables
try {
    var key:String;
    var val:String;
    var flashvars:Object = LoaderInfo(this.root.loaderInfo).parameters;
    for (key in flashvars) {
        val = String(flashvars[key]);
        if(key == "item"){ // If the parameter is called 'item'...
            if(val.substr(0,4) == "item"){ // ... and the name of the button starts with the characters 'item'...
                // ... we can extract the number-part of the item-name and go to the correct frame
                var frameToGoTo:Number = Number( val.substr(4,1) );
                gotoAndStop( frameToGoTo+1 );
            }
        }
    }
} catch (error:Error) {
    // what to do if an error occurs
}

As you can see, this is pretty much similar to what we did before, but this time we are passing a parameter that is named 'item'. This parameter is the instance name of the button we clicked.

Next is the gotoURL function.

// Get the new page
function gotoURL(e:MouseEvent):void {
    // First we grab the URL of the HTML document and split it into an array
    var htmlUrl:String = ExternalInterface.call("window.location.href.toString");
    // split the string at the questionmark
    var splitUrl:Array = htmlUrl.split("?");
    // use only the first part (ditch existing parameters)
    var trimmedUrl:String = splitUrl[0];
    // get the name of the button clicked and set it as a parameter
    var parameters:String = "item="+e.currentTarget.name;
    // combine url and parameters with a new questionmark
    var requester:URLRequest = new URLRequest(trimmedUrl+"?"+parameters);
    // reload the page
    navigateToURL(requester, '_self');
}

We trim off any existing parameters, we create our own parameter by combining the string 'item=' with the name of the button that was clicked. We then pass the url and parameter to the navigateToURL-method that will reload our HTML page with the new parameter.

How events work: When something is clicked and we 'listen' for clicks using addEventListener (added earlier), the event will contain a reference to the symbol that was clicked. In our 'gotoURL' function, we are receiving this MouseEvent as the parameter 'e'. This has a property called 'currentTarget' that holds a reference to the clicked object (e.currentTarget), thus we can find the name by looking up e.currentTarget.name.

To turn this into a full menu system, you'll also need to make it load new URLs and not just the same as in this example. You should now know the basics required to make this yourself and it can be done in a multitude of ways. You can pass the URL as a variable, store it in the SWF, load it from an XML file and more so I'll leave that up to you. If you use this tutorial to create a solution, feel free to post a URL in the comments section below so other readers can see it in action!

 

About Jens C Brynildsen

Jens has been working with Flash since version 3 came out. Since then, he's been an active member of the Flash community. He's created more than a hundred Flash games (thus the name of his blog) but he also creates web/standalone applications, does workshops and other consulting. He loves playing with new technology and he is convinced that the moment you stop learning you die (creatively speaking). Jens is also the Editor of this website.

Get new stories first

Click to follow us on Twitter!

 

Comments


Posted by Thaylin on 09/09 at 07:13 PM

Great tutorial on the beginning use of javascript with flash. But why stop there?!?!?
There’s so much you can do once you’ve learned about the communication of flash and js.
I posted a couple things on my blog that utilize js for various things. One is for creating your own js that you can then embed into your page for use in things such as the facebook js api.

http://thaylin.info/blog/2009/05/01/javascript-injection-via-as3-to-embed-external-libraries/

And this one is the source files for a presentation I did at Flash Coders NY on the use of externalInterface and communication between the page and the flash. The source files are pretty well documented so it isn’t too hard to follow.

http://thaylin.info/blog/2009/05/21/the-down-lo-on-externalinterface-and-javascript-injection-via-actionscript-3/


Posted by Jens C Brynildsen on 09/10 at 09:18 AM

Great stuff Thaylin! If you’d like to write a follow-up tutorial that takes this further, you’re very welcome to do so.


Posted by Jeremy on 10/27 at 07:43 AM

Hi Jens, great tutorial. I really appreciate the three different steps as I am creating a menu very similar to what you have explained. One thing I would like to do is filter the parameters, keeping values intact for some but removing others. For instance, if the URL was…

www.-sitegoeshere-.com?aa=1&bb=29&cc=183

I would like to keep the values for ‘aa’ and ‘cc’ and insert them back into the URL, but remove ‘bb’ completely from the string. So in other words, add a script that recognises if there is a ‘bb’ parameter and remove it completely if present.

Apologies if this sounds like a simple question; I’m relatively new to this stuff!

-Jeremy


Posted by Jens C Brynildsen on 11/03 at 10:29 AM

Hi Jeremy,
You can do this easily by just building up a new URL with the parameters you want (using a little string parsing) and then just load that URL using navigateToURL. This will do a reload of the SWF and since all elements are cached, it’ll hardly be noticeable to the end user.

This will work alright, but it’ll also hamper the Back-button functionality a bit so it’s not an ideal solution. I don’t think it’s a better way though?

J


Posted by dduron on 01/07 at 11:04 PM

I was wondering if it’s possible to set this up to work with AS2. When I try to recreate the files it only works with AS3.

Any help would be greatly appreciated. My AS3 isn’t very good and I’m looking for a quick solution to beat the clock.


Posted by Jens C Brynildsen on 01/29 at 10:14 AM

@dduron Sorry for replying so late. I assume you’ve already found a solution since it was urgent?

Anyway - in AS2, the Flashvars can be found straight on the main timeline (not in the LoaderInfo object). You’ll access these directly using something like _root.myVariable and not a try/catch block since this is AS3 only.

Here’s a tutorial that has an example: http://www.hosfordusa.com/?p000100000181000000 The SWFObject/Javascript part should be identical except that you’ll need to change the SWF version number to the version you are targeting.

Regarding AS2 vs AS3, you might as well get started with AS3. It’s so much easier to work with if you only make the leap. All those I know that learned AS3 now refuse to do AS2 work. It’s really that much of a difference in coding comfort! It’s not hard either. What is hard is actually to not try to do things the AS2 way. Start here at Senoculars AS3 tip of the day. If you read your way through that, you’re an AS3 expert! http://www.kirupa.com/forum/showthread.php?t=223798

J


Posted by camelic on 05/19 at 04:44 PM

There is another way to do this.  And I feel that it’s easier.  By using swfobject.  Here is a simple tutorial on connect 2 flash players with javascript.  SOURCE CODE is included.

http://www.greeneggsandcam.com/tutorials/connect-2-swfs

Enjoy!

Submit a comment

Only registered members can comment. Click here to login or here to register