php[architect] logo

Want to check out an issue? Sign up to receive a special offer.

Saving Images in AIR Applications

Posted by on March 1, 2010

I’ve started a series of Flex 3 posts ([1] and [2]) over on my blog but decided to continue them here, where hopefully they will be of interest to our php|architect visitors. Flex is a fascinating subject—one that a lot of PHP developers could benefit from if only they knew it a bit better.

On to my project! I’ve been assembling a program that dynamically generates graphics that I want to be able to use in other applications, so the final step, after dynamically generating the image, is to save it.

Adobe AIR, unlike Flash movies embedded in a web page, has access to the file system because it resides outside of the normal web-based sandbox, so the only real questions were how do I output the file, and in which format.

The first question I dealt with was the format. Flex makes it very easy to encode different graphic formats for output, but I chose to only support jpegs and pngs for simplicity. Regardless of the final output format, though, you need a BitmapData to work with:

var bmpd:BitmapData = new BitmapData(qrCode.width,qrCode.height);
bmpd.draw(qrCode);

var imgByteArray:ByteArray = null;
var fileName:String  = "";

The other thing that varies with format is the file name. I’ve created a string to hold the suggested file name that will be populate after encoding.

The actual encoding is simple:

if (grpImageType.selectedValue=="PNG") {
	var pngenc:PNGEncoder = new PNGEncoder();
	imgByteArray = pngenc.encode(bmpd);
	fileName = "qrCode.png";
} else {
	var jpgenc:JPEGEncoder = new JPEGEncoder(80);
	imgByteArray = jpgenc.encode(bmpd);
	fileName = "qrCode.jpg";
} // if (grpImageType.selectedValue=="PNG")

Whichever format is selected, we create an encoder for that format and then use it to generate the actual name of our newly created BitmapData into it. The one difference is that the JPG encoder takes a quality value—the smaller the value, the smaller the file size (and the lower its quality). In both cases you call encode(bmpd) on the encoder to get the ByteArray that can be saved.

Once you have a ByteArray and a default file name, we can write the image out to the file system.

var file:FileReference = new FileReference();
file.save(imgByteArray, fileName);

Calling save() on the FileReference class will open a Save As dialog, allowing you to specify where to save the file and change its name if desired.

That’s all there is to it. As with most tasks in this project, Flex makes saving custom graphics for later use very easy.

My little application is now functionally complete—you can find information on its other parts on my blog. It is now in the hands of the lovely and talented Kathy to make it look as good as it works. All in all, given that this was my first AIR application, I will say that I was pleasantly surprised at how easy it is to work with Flex. For someone who is an avowed Eclipse hater, working with Flex Builder was a positive experience. Once I got used to dealing with an event driven programming environment again, things started to come together without much in the way of sweat, blood and tears. Now, if they could just make an Eclipse plugin capable of magically making my interfaces user friendly…


Cal Evans is a veteran of the browser wars. (BW-I, the big one) He has been programming for more years than he likes to remember but for the past [redacted] years he's been working strictly with PHP, MySQL and their friends. Cal regularly speaks at PHP users groups and conferences, writes articles and wanders the net looking for trouble to cause. He blogs on an "as he feels like it" basis at Postcards from my life.
Tags: , , , , ,
 

Leave a comment

Use the form below to leave a comment: