Archive for the ‘saving’ Tag
More on saving images out of Flash
I posted previously on generating a bitmap image of a MovieClip and writing it from Flash to a remote server. However, that previous post was a very early. Now that I’ve implemented the process within an actual project scenario, I’ll follow up here with some revised code that streamlines the task with greater efficiency.
1) Server-side. First thing first: you’ll need a PHP script (or other server-side flavor) to receive binary image data and write it to a file. This revised PHP script is even simpler than before; just save this to a PHP file and place it on a PHP enabled server:
<?php $file = $_GET['file']; $fp = fopen( $file, 'wb' ); fwrite( $fp, $GLOBALS[ 'HTTP_RAW_POST_DATA' ] ); fclose( $fp ); echo $file; ?>
2) Image encoders. Next, you’ll need the Adobe AS3 corelib which has a collection of classes for JPG and PNG image encoding. Download and extract the corelib’s source library into your main class library. The following image service classes will build upon these image encoders.
3) Image services. Assemble the following three classes into a library. These classes will take care of capturing a DisplayObject’s image and then sending it to your server to be saved. Note: you’ll need to update the ImageCaptureService class member “serverPath” to point to your image service PHP file (from step #1).
3.a) Save this class as: com/gmacwilliam/images/ImageCaptureService.as
package com.gmacwilliam.images
{
import flash.events.EventDispatcher;
import flash.events.Event;
import flash.utils.ByteArray;
import flash.net.URLLoader;
import flash.net.URLRequest;
import flash.net.URLRequestMethod;
import flash.net.URLVariables;
public class ImageCaptureService extends EventDispatcher
{
public static const FILE_WRITE_COMPLETE_EVENT:String = "ImageFileWriteComplete";
// UPDATE THIS...
public static var servicePath:String = "http://www.yourServerHere.com/save_image.php";
public function ImageCaptureService():void
{
super();
}
/* write
* @desc: Writes image data to file.
* @param: image data byte array.
* @param: path/name of file to write.
*/
protected function write(img:ByteArray, filename:String):void
{
// configure data to send
var req:URLRequest = new URLRequest(ImageCaptureService.servicePath +"?file="+ filename);
req.contentType = "application/octet-stream";
req.method = URLRequestMethod.POST;
req.data = img;
// send data to file service
var write:URLLoader = new URLLoader();
write.addEventListener(Event.COMPLETE, this.onWriteComplete);
write.load(req);
}
private function onWriteComplete(evt:Event):void
{
// cleanup write operation
var write:URLLoader = evt.target as URLLoader;
write.removeEventListener(Event.COMPLETE, this.onWriteComplete);
dispatchEvent(new Event(ImageCaptureService.FILE_WRITE_COMPLETE_EVENT));
}
}
}
3.b) Save this class as: com/gmacwilliam/images/JPGCapture.as
package com.gmacwilliam.images
{
import flash.display.DisplayObject;
import flash.display.BitmapData;
import com.adobe.images.JPGEncoder;
public final class JPGCapture extends ImageCaptureService
{
public function JPGCapture(clip:DisplayObject, filePath:String="", quality:int=50):void
{
super();
var jpg:JPGEncoder = new JPGEncoder(quality);
var bmp:BitmapData = new BitmapData(clip.width, clip.height, false, 0xFFFFFF);
bmp.draw(clip);
write(jpg.encode(bmp), filePath);
}
}
}
3.c) Save this class as: com/gmacwilliam/images/PNGCapture.as
package com.gmacwilliam.images
{
import flash.display.DisplayObject;
import flash.display.BitmapData;
import com.adobe.images.PNGEncoder;
public final class PNGCapture extends ImageCaptureService
{
public function PNGCapture(clip:DisplayObject, filePath:String=""):void
{
super();
var bmp:BitmapData = new BitmapData(clip.width, clip.height, true, 0x00000000);
bmp.draw(clip);
write(PNGEncoder.encode(bmp), filePath);
}
}
}
4) Instantiation. These services are extremely easy to use… Just instantiate them with a reference to a DisplayObject and a server path at which to write the image file. Also, the JPGCapture class will accept an optional quality setting (a number between 0 and 100).
var saveJPG:JPGCapture = new JPGCapture(myDisplayObject, "images/flashimg.jpg", 85); var savePNG:PNGCapture = new PNGCapture(myDisplayObject, "images/flashimg.png");
You can listen to boh object for an “ImageCaptureService.FILE_WRITE_COMPLETE_EVENT” event to know when the image data has finished getting sent to the server.
While these image services are very similar to the ones in my last post, there has been an important change: they now send both binary and text data to the server in a single server call, rather than breaking the two formats out into seperate calls. This was achieved by dropping the text data (the filename) into GET variables so that POST could be allocated entirely to binary image data.
Comments (6)