There are some challenges in Flash that are addressed with such regularity that it can be surprising that no uniform way of accomplishing these tasks has emerged. One of these challenges is dynamic flash movie resizing through JavaScript. While websites have been doing this for years and the techniques involved are simple, there are enough moving parts involved to make it a chore to recode and deploy every time you launch a new site. BrowserCanvas bundles all of the code necessary to do Flash resizing into a single ActionScript file which is easy to deploy and reuse. It takes care of a lot of the maintenance work necessary to do Flash JavaScript resizing so that it can be deployed with minimal effort.
The best part of BrowserCanvas is that it requires no external JavaScript in the page to function. Deployment involves putting a single Actionscript class into your classpath and adding a couple lines of code to your project. That’s it. There is no messing around with JavaScript imports, there are no extensive Actionscript libraries. It is as clean and simple as possible.
The following example shows you everything you need to do to randomly resize a flash movie every time the stage is clicked.
package {
import flash.display.Sprite;
import flash.events.MouseEvent;
import com.dncompute.canvas.BrowserCanvas;
public class DemoMain extends Sprite {
private var canvas:BrowserCanvas;
public function DemoMain() {
canvas = new BrowserCanvas(stage);
stage.addEventListener(MouseEvent.CLICK,randomSize);
}
public function randomSize(event:MouseEvent=null):void {
canvas.width = String( Math.random()*500 + 200);
canvas.height = String( Math.random()*500 + 200);
}
}
}
Below are links to different examples of BrowserCanvas in action. All of these examples are included in the browser canvas download file at the end of this post. You will note that none of these examples have additional javascript code embedded in them, all of the code is embedded in the Flash movie.
While using BrowserCanvas is really simple, the code itself does have a little bit of complexity to it. Unfortunately, simple and cross-browser are rarely in the same sentence.
I’ve tested BrowserCanvas in a variety of modern browsers on both OSX and Windows. I have not tested BrowserCanvas in any of the golden oldies (IE 5.5 or less, Firefox 1.5 or less, Netscape anything, Safari 2.0 or less, Opera 8 or less) and don’t plan to add support for them.
The execution speed seems to be incredibly slow in Safari, and min/max behavior in Safari seems to only work in the SWF Object version of my demos. For most applications this shouldn’t be an issue, but I plan to investigate this further if I find the time.
I also have not tested BrowserCanvas in sites with complicated CSS layouts and AJAX interaction. If you have issues in any current browser, I’d be eager to hear about them. BrowserCanvas attempts to do a bunch of clever things in JavaScript, but I wouldn’t be surprised if some of these tricks don’t work in a few fringe cases. You can turn the browser specific hacks off, this is discussed in the comments for the BrowserCanvas class.
Also note that if you want to run the examples locally, you may need to make changes to the Flash Player security settings. You can find instructions on how to do this half way down this article from Adobe . You can access the Global Security Settings Panel by doing the following:
Right Click Any Flash Movie > Settings > Privacy (Tab) > Advanced (Button) > Global Security Settings Panel (Link)
Packaging up Flash based components for use across a large variety of websites is a regular challenge for professional Actionscript developers. With the release of Flash 9, Adobe has made this easier to accomplish with innovations such as SWC Actionscript libraries. SWC libraries work well when you are deploying components which are self contained, but don’t cover situations where a component requires external elements such as JavaScript libraries. Documenting and deploying all of the various pieces necessary for a component like this can be an onerous task. I’ve often longed for a way to package all of a component’s various pieces together into a single, easy to deploy package.
One way to do this is to insert the JavaScript directly from Flash, rather than embedding it in the HTML page. I spent some time when Flash 9 was first released looking into ways to accomplish this. My understanding at the time was that ExternalInterface only worked to call existing JavaScript functions on the page, so I focused my JavaScript code insertion efforts on the use of navigateToURL("javascript:XXX"). While this technique works to a limited degree, I abandoned my efforts because I found the results incredibly unwieldy to use with large codebases.
However, I recently discovered an article devoted to JavaScript injection by Peter McBride. Mr. McBride has dispelled many of my misconceptions surrounding ExternalInterface. He also demonstrates some clever techniques for embedding JavaScript into your Actionscript code. I highly recommend Mr. McBride’s article, it is a thorough and easy to follow introduction to the JavaScript injection techniques used in BrowserCanvas.
Joe says:
Thanks, for sharing. I’ll check it out.
OpenRIA » Blog Archive » 在HTML页面中动态缩放flash的最佳方法 says:
[...] 以前曾经尝试过在html页面中让整个flash自己缩放自己,方法是利用javascript改变flash的所在的div宽度和高度,方法虽然可行,但是比较麻烦;现在终于发现了这个国外同行提供的解决方案,无需在html页面中写一行js代码,只需在flash中引入一个AS类即可,超级简单,超级强大,其原理是利用了javascript在actionscript中的代码注入功能,简单来说就是将js嵌入as中使用,实现了js和as的完美的契合! [...]
nant says:
thanks for sharing ,but when property “allowScriptAccess ” is set “never”,it will not work any more.
Noel says:
@nant - That is correct, thanks for clarifying this point.
Setting “allowScriptAccess” to “never” explicitly prevents Flash movies from being able to communicate with the browser, thereby preventing BrowserCanvas from making any changes to the Flash movie’s size.
Rob says:
In regards to the slow performance, have you tried wrapping the js calls in setTimeout(call, 0)? It effectively decouples the two runtimes and lets js run the call in a seperate thread so Flash doesnt lock up.
Pat says:
Hey thanks for the great example. Even though it wasn’t quite what I was looking for, I did learn quite a bit - thanks!
What I WAS looking for was a way to resize the elements inside the flash movie as I resize the browser. Ie: I have a full screen flash app that displays a large # (say for example the current time) I want it to be as large as possible, so if I maximize it takes up the whole screen. Any good URLs you can point me to to read? Thanks
Rob says:
@pat: http://board.flashkit.com/board/showthread.php?t=768235&highlight=stage
Noel says:
@Rob:
I did not try that, but I can see how that could be a great trick for making fast ExternalInterface calls where you either don’t care about the response or don’t need it immediately. Thanks for the tip.
@Pat:
All of the live examples you see on this site have “stage.scaleMode = StageScaleMode.NO_SCALE;” and “stage.align = StageAlign.TOP_LEFT;” set, which prevents the flash movie from scaling. If you comment the scaleMode line out, everything in the flash movie will start scaling out, which should make it behave in a manner similar to what you are requesting. I personally find the coordinate systems easier to work with when scaling is off (as well as avoiding half pixel issues) and if needed, I prefer to scale up in code.
If you only need to scale the movie full screen, and do not need to resize the movie at runtime, BrowserCanvas is probably overkill. You can make the Flash movie full screen through a few CSS/Object/Embed/SWFObject params, and all scaling/centering issues can be handled internally to Flash. BrowserCanvas is primarily aimed at those wishing to change SWF size during runtime.
deviation.de | Christian Klotz › BrowserCanvas says:
[...] light on BrowserCanvas yesterday. A really nice way to resize flash content dynamically via Actionscript. Give it a [...]
Miller Medeiros says:
very nice solution.. i didn’t tried to use it yet but it seems to be very nice.. principally because you can set the new size “on the go”..
i’ve made a solution for “full bleed” and “min/max size” based on javascript.. it’s called SWFFIT ( http://swffit.millermedeiros.com/ ) check it out later.. it’s not intended to work like your solution.. (i’ve made it to work only with 100% wid/hei flash movies..)
cheers and keep your good work..
doesnotcompute » BrowserUtil. An Actionscript Method for Getting the Value of an Object/Embed’s Id Attribute says:
[...] HTML page, there is no easy way to tell if you have the right one. In one of my previous projects, BrowserCanvas, I looked at the root URL in Flash and compared it to the URL assigned in the object/embed tag. [...]
Jim says:
license of source?
Noel says:
BrowserCanvas is under the MIT license. I believe it’s in the code itself, but I’ll add it into the post as well so it’s more clear.
2008/08/04 Daily Catch | 1983 | Catching design, since 1983 says:
[...] BrowserCanvas Dynamically resize your Flash canvas. [...]
Romu says:
Exactly what I needed for a special project. Very nice integration with SWFObject.
Thanks for sharing.
Romu