Assembleeze Screen

Dynamic User-Controlled Print System for Customized Kodak Paper Forms

March 21, 2012

Wilen Direct printing companies wanted to create a system that would allow users to customize content like photos, illustrations, text and backgrounds including cutting out shapes (e.g. photo uploaded heads) to decorate pre-perforated forms to allow users to create their own paper products, from pop-up business cards to paper toy folding cars, to dimensional artwork suitable for framing, all customizable using the online system, and intended to be used with new Kodak paper forms to be produced.

I coded the system using Actionscript 3 (Flash) using a cascading series of classes that allowed precise control over each element to be printed on the form, including placement, rotation, scaling, fonts, colors, images etc. in an advanced graphical user interface.  This allowed a high degree of customization, and users could save their pre-created content into libraries accessible upon log in. Example forms that I created to supplement the user-built libraries were for a folding paper toy car and a folding paper holiday ornament with user uploaded photos dynamically positioned.

Example code showing class used to display certain types of images within system:


package
{
	import flash.display.*;
	import flash.events.*;
	import flash.net.URLRequest;

	public class SwfObj extends MovieClipXtended
	{
		public var mySwfs:Array = new (Array);

		public var imageWid:Number;
		public var imageHei:Number;
		public var panelWid:Number;
		public var panelHei:Number;
		public var picRatio:Number;
		public var panelRatio:Number;
		public var imageXML:XML;
		public var i:uint;
		public var myI:uint;

		//Mask/upload head data
		public var hasMask:Boolean;   // if this particular SWF has mask

		var currHeadNum:String = "";
		var pcount:int;

		public function SwfObj()
		{
		}
		public function PopulateSwfObj(myXML, i):void
		{
			/// NEW CODE BELOW
			var updata = myXML.swfs.swf[i].uploadphoto;  // this is the attribute (XML string) holding all the upload info for all photos/heads/etc
			var numUploads:Number = updata.length();  // NOTE: in this system, with one head per SWF this should always = 1, but play it safe with multi-capability

			var currUpload:XML = new XML;
			// this sends to child head SWF *which* head it is, which upload id number
			trace ("CURRHEADNUM = "+currHeadNum);

			var count:int;

			for (count=1;countpanelRatio) {
						loader.x = 0;
						loader.width = Number(imageXML.@width);
						loader.height = Number(imageXML.@width)/picRatio;
						loader.y = ( Number(imageXML.@height)-loader.height)/2;
					} else {
						loader.y = 0;
						loader.height = Number(imageXML.@height);
						loader.width = Number(imageXML.@height)/picRatio;
						loader.x = (Number(imageXML.@width)-loader.width)/2;
					}
					trace ("FIT");
				break;

				case "fill":  //scale proportional to barely fill panel
					picRatio =  Number(imageXML.swfs.swf[myI].@width)/ Number(imageXML.swfs.swf[myI].@height);
					panelRatio = Number(imageXML.@width)/ Number(imageXML.@height);
					if (picRatio>panelRatio) {
						loader.y = 0;
						loader.height = Number(imageXML.@height);

						loader.width = Number(imageXML.@height)*picRatio;
						loader.x = -( Number(imageXML.@width)-loader.width)/2;
					} else {
						loader.x = 0;
						loader.width = Number(imageXML.@width);
						loader.height = Number(imageXML.@height)*picRatio;
						loader.y = -(Number(imageXML.@height)-loader.height)/2;
					}
					trace ("FILL");
				break;

				case "percentage": //using wid and hei as PERCENTAGE number, then offset x and y
				loader.width = Number(imageXML.swfs.swf[myI].@width)/100*Number(imageXML.@width);
				loader.height = Number(imageXML.swfs.swf[myI].@height)/100*Number(imageXML.@height);
				trace ("%%%%%%%%%%%%%%% HIT THIS POINT - PERCENTAGE!");
				break;

				default:  //defaults to "Manual" mode
				loader.width = Number(imageXML.swfs.swf[myI].@width);
				loader.height = Number(imageXML.swfs.swf[myI].@height);
			}

			// send Event to let system know that this SWF image is fully loaded already
			//dispatchEvent (new Event(MovieClipXtended.LOAD_DONE));
			LoadComplete.arg = "test";
			LoadComplete.caller = this;

			SelfLoaded = true;
			dispatchEvent(LoadComplete);

        }

        private function ioErrorHandler(event:IOErrorEvent):void {
            //trace("ioErrorHandler: " + event);
        }

	}

}

Leave a Comment