<?xml version="1.0" encoding="utf-8"?>
<mx:Application 
                xmlns:mx            ="http://www.adobe.com/2006/mxml"
                layout                ="absolute" 
                applicationComplete    ="initApp()" 
                backgroundColor     ="0x444444"
                viewSourceURL        ="srcview/index.html"
                > 
    <!-- by Petri Leskinen, Espoo, Finland, April 2011  -->
    
    <mx:Script>
        <![CDATA[ 
            import filter.ComplexPatternFilter;
            
            import flash.display.Bitmap;
            import flash.display.BitmapData;
            import flash.display.Sprite;
            import flash.events.Event;
            
            import mx.controls.HSlider;
            import mx.controls.Label;
            import mx.controls.Spacer;
            import mx.controls.TextArea;
            import mx.controls.sliderClasses.Slider;
            import mx.core.UIComponent;
            import mx.events.SliderEvent;
            
            import net.*;
            
            
            
            /**    the shader class */
            protected var pattern:ComplexPatternFilter = new ComplexPatternFilter(null,null);
            
            /**    image area on the stage */
            protected var canvas:BitmapData;
            
            /**    initializes the application */
            protected function initApp():void {
                canvas = new BitmapData(800,600,true,0);
                UIRef.addChild(new Bitmap(canvas));
                
                var gripA:GripBox = new GripBox(100,200),
                    gripB:GripBox = new GripBox(700,200),
                    gripC:GripBox = new GripBox(400,400);
                
                UIRef.addChild(gripA);
                UIRef.addChild(gripB);
                UIRef.addChild(gripC);
                
                gripA.addEventListener(GripBox.EDITED, editedA);
                gripB.addEventListener(GripBox.EDITED, editedB);
                gripC.addEventListener(GripBox.EDITED, editedC);
                
                pattern.center = {x:canvas.width/2, y:canvas.height/2};
                pattern.scale = 300;
                pattern.pointA = gripA;
                pattern.pointB = gripB;
                pattern.pointC = gripC;
                
                changeImage();
            }
            
            
            protected function editedA(e:Event):void {
                this.pattern.pointA=e.target; // {x:e.target.x, y:e.target.y};
            }
            protected function editedB(e:Event):void {
                this.pattern.pointB=e.target;
            }
            protected function editedC(e:Event):void {
                this.pattern.pointC=e.target;
            }
            
            
            /**    change the source image */
            protected function initSource(bmd:BitmapData):void {
                //    set filter's input and output
                pattern.input    =bmd;
                pattern.output    =canvas;
                
                //    render the filter 
                pattern.render();
                
                //    update preview thumbnail on controls
                sourcePreview.source = new Bitmap(bmd);
            }
            
            
            /**    change pattern's base point on mouse click */
            protected function clicked(e:MouseEvent):void {
                var p:Object = {x:e.localX, y:e.localY},
                    a:Object = pattern.pointA,
                    b:Object = pattern.pointB,
                    c:Object = pattern.pointC,
                    tmp:Number;
                
                var    da:Number = (tmp=p.x-a.x)*tmp+(tmp=p.y-a.y)*tmp,
                    db:Number = (tmp=p.x-b.x)*tmp+(tmp=p.y-b.y)*tmp,
                    dc:Number = (tmp=p.x-c.x)*tmp+(tmp=p.y-c.y)*tmp;
                
                if (da<db && da<dc) {
                    pattern.pointA=p;
                } else if (db<da && db<dc) {
                    pattern.pointB=p;    
                } else     pattern.pointC=p; 
                
                this.laabeli.text="x:"+p.x;
            }
            
            protected function set autoRotate(value:Boolean):void {
                if (value) {
                    this.addEventListener(Event.ENTER_FRAME, enterFrame);
                } else {
                    this.removeEventListener(Event.ENTER_FRAME, enterFrame);
                }
            }
            
            [Bindable]protected var rotationAngle:Number=0.0;
            
            protected function enterFrame(e:Event):void {
                this.rotationAngle+=0.025;
                if (this.rotationAngle>Math.PI) this.rotationAngle -= 2*Math.PI;
                this.pattern.rotation=rotationAngle;
            }
            
            /**    upload an image from local computer */
            private function uploadImage():void {
                //    initSource as parameter is the function to call when upload is ready
                new ImageFormatImporter(initSource);
            }
            
            /**    save .png to local computer */
            private function savePNG():void {
                new PngFormatExporter(pattern.output, "ComplexPattern.png");
            }
            
            /**    save .jpg to local computer */
            private function saveJPG():void {
                new JpgFormatExporter(pattern.output, "ComplexPattern.jpg");
            }
            
            
            /** embedded images */
            [Embed( '../assets/sinebrychoff.jpg')]
            protected var Picture3:Class;
            
            [Embed( '../assets/bouquet.jpg')]
            protected var Picture2:Class;
            
            [Embed( '../assets/blueCar.jpg')]
            protected var Picture4:Class;
            
            
            /**    change to the image selected in ComboBox */
            protected function changeImage():void {
                var bmd:BitmapData;
                switch (imageSelected.selectedLabel) {
                    
                    case "Bouquet":
                        bmd = Bitmap(new Picture2).bitmapData; 
                        break;
                    
                    case "Sinebrychoff":
                        bmd = Bitmap(new Picture3).bitmapData; 
                        break;
                    
                    case "Blue Car":
                        bmd = Bitmap(new Picture4).bitmapData; 
                        break;
                    
                    
                    case "Solid Black": 
                        bmd = new BitmapData(16,12,false,0);
                        break;
                    
                    case "Solid White": 
                        bmd = new BitmapData(16,12,false,0xFFFFFF);
                        break;
                }
                initSource(bmd);
            }
        ]]>
        
    </mx:Script>
    
    <mx:HBox x="50" y="35">
        <mx:VBox id="controls" x="20" y="0" width="170" height="600" horizontalAlign="center" verticalGap="5" backgroundColor="0x808080">
            
            <mx:Spacer height="10" />
            <mx:Label id="laabeli" text="Source Image"/>
            
            <mx:ComboBox 
                id="imageSelected" width="150" 
                change="changeImage()" > 
                <mx:ArrayCollection>
                    <mx:Object label="Sinebrychoff" />
                    <mx:Object label="Bouquet" />
                <!-- <mx:Object label="Dice" /> -->
                    <mx:Object label="Blue Car" />
                    <mx:Object label="Solid Black" />
                    <mx:Object label="Solid White" />
                    
                </mx:ArrayCollection>
            </mx:ComboBox>
            
            <mx:Spacer height="3" /> 
            <mx:Image id="sourcePreview" width="120" height="80" />
            
            <mx:Spacer height="3" /> 
            <mx:Button label="Upload an Image" width="150" click="uploadImage();" />
            
            <mx:Spacer height="10" /> 
            <mx:HSlider value="200" minimum="1" maximum="1000" width="150"
                        change="pattern.scale=event.value;" 
                        labels="['','Scale','']" labelOffset="0"
                        liveDragging="true" />
            
            <mx:HSlider value="0.2" minimum="0.03" maximum="0.4" width="150"
                        change="pattern.fill=event.value;" 
                        labels="['','Fill','']" labelOffset="0"
                        liveDragging="true" />
            
            <mx:HSlider value="0" minimum="-1" maximum="2" width="150"
                        change="pattern.focus=event.value;" 
                        labels="['','Focus','']" labelOffset="0"
                        liveDragging="true" />
            
            <mx:Spacer height="10" />
            <mx:HSlider value="3.0" minimum="0.5" maximum="7.0" width="150"
                        change="pattern.distortX=event.value;" 
                        labels="['','Shape Distort','']" labelOffset="0"
                        liveDragging="true" />
            <mx:HSlider value="1.732" minimum="0.5" maximum="7.0" width="150"
                        change="pattern.distortY=event.value;" 
                        liveDragging="true" />
            
            <mx:Spacer height="15" />
            <mx:HBox>
                <mx:Label text="Rotation" />
                <mx:Label text="Auto" />
                <mx:CheckBox selected="false" id="autoRotateCB" click="this.autoRotate=autoRotateCB.selected"/>
            </mx:HBox>
        
            
            <mx:HSlider value="@{this.rotationAngle}" minimum="-3.14" maximum="3.14" width="150"
                        change="pattern.rotation=event.value;" 
                        liveDragging="true" />
            <mx:Spacer height="8" />
            
            
            <mx:HBox>
                <mx:Label text="Background Color" />
                <mx:ColorPicker change="pattern.bgcolor=event.color | 0xFF000000;" 
                                selectedColor="0" addedToStage="pattern.bgcolor=0x000000;"/>
            </mx:HBox>
            <mx:Spacer height="8" />
            
            
            <mx:HBox>
                <mx:Label text="Motion Blur" />
                <mx:CheckBox id="mblurCB" change="pattern.bgcolor=0;pattern.motionBlur=mblurCB.selected;" />
            </mx:HBox>
            <mx:Spacer height="20" />
            
            <mx:HBox>
                <mx:Button label="Save as .png" width="96" click="savePNG();" />
                <mx:Button label=".jpg" width="45" click="saveJPG()" />
            </mx:HBox>
            
        </mx:VBox>
        <mx:Spacer width="25" />
        <!--    UIRef: the container for image -->
        <mx:UIComponent id="UIRef" >
        </mx:UIComponent>
    </mx:HBox>
    
</mx:Application>