A Magnifier – Using Flex/AS3
The logic is pretty simple. Capture the Bitmap data in a defined area and display it. I added a MouseWheel zoom for ease of use. Drag the Magnifier tile around and have fun!
Click here for the demo.
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute">
<mx:Script>
<![CDATA[
private var bitmapData:BitmapData;
private function update(e:Event):void {
var matrix:Matrix = new Matrix(1,0,0,1,-Math.abs(mag.x),-Math.abs(mag.y));
bitmapData = new BitmapData(Math.abs(mag.width),Math.abs(mag.height),false,0x000000);
bitmapData.draw(container,matrix);
mag_img.source = new Bitmap(bitmapData);
}
private function zoom(e:MouseEvent):void {
if(e.delta > 0) {
if(mag_img.scaleX <= 10) {
mag_img.scaleX += 0.1;
mag_img.scaleY += 0.1;
}
} else {
if(mag_img.scaleX > 1) {
mag_img.scaleX -= 0.1;
mag_img.scaleY -= 0.1;
}
}
}
]]>
</mx:Script>
<mx:Canvas id="container" left="0" top="0" right="0" bottom="0">
<mx:Image horizontalCenter="0" verticalCenter="0" source="Clown Fish.jpg"
width="100%" height="100%" verticalAlign="middle" horizontalAlign="center"/>
<mx:DateChooser right="100" bottom="60"/>
<mx:Button label="Button 1" right="165" top="52"/>
<mx:Button label="Button 2" right="210" top="82"/>
<mx:Button label="Button 3" right="165" top="112"/>
<mx:TextArea width="219" height="78" right="210" top="174" text="Some controls to play around with!&amp;amp;amp;amp;amp;#xa;&amp;amp;amp;amp;amp;#xa;Try to edit this text when viewing its magnified image..."/>
</mx:Canvas>
<mx:Canvas id="mag" x="105" y="39" width="200" height="200"
borderStyle="solid" verticalScrollPolicy="off" horizontalScrollPolicy="off"
mouseWheel="{zoom(event)}" mouseWheelOutside="{zoom(event)}">
<mx:creationComplete>
<![CDATA[
mag.addEventListener(Event.ENTER_FRAME, update);
]]>
</mx:creationComplete>
<mx:mouseDown>
<![CDATA[
mag.addEventListener(MouseEvent.MOUSE_MOVE, update);
mag.startDrag();
]]>
</mx:mouseDown>
<mx:mouseUp>
<![CDATA[
mag.removeEventListener(MouseEvent.MOUSE_MOVE, update);
mag.stopDrag();
]]>
</mx:mouseUp>
<mx:Image id="mag_img" width="200" height="200" verticalCenter="0" horizontalCenter="0" scaleY="2" scaleX="2"/>
</mx:Canvas>
</mx:Application>
UPDATE: As Ian Fuller pointed out, the magnifier was not zooming from the center, but from the top-left corner. I’ve updated the code to zoom from the center. Here is a direct link to the demo, in case you want to try the zooming with the mouse-wheel without having the entire page scroll.
Thanks Ian.
Adobe riathon 08
The theme for my app was “create and collaborate”. Anyways…Here is a demo of it. Its called Stickies-in-sync, an affinity diagram building tool. It leaverages the power of CoCoMo to bring a collaborative experience when building affinity diagrams. Check it out… (The demo is a little buggy at times)
More posts on this app, CoCoMo and the source, coming soon…
What keeping me busy?
Well, I’m working on a TextFlow-Container control. Yup. I am using the new and awesome Text Layout Framework of Flash player 10. Adobe’s demo was really mind-blowing. But the TextFlow class isn’t that easy to use, especially for noobs. I know, its not the final build and adobe is still working on it and everything. But hey, thats not good enough for me. So i’m mashing up a little something on my own. A TextFlow control which is as easy to use as a TextArea control. I’ll be posting more about that really soon.
Also on my list of new-cool-things-to-fool-aroud-with is Cocomo. I have a decent experience with weborb for .net Messaging. I was kinda sceptical for a second on how Cocomo could make things any better. Well it didnt disappoint me. I love the code part. Cocomo packs a bunch of components from Adobe Acrobat Connect like Video,Text, Voice Chat, WhiteBoard and more. There is even a FilePublisher, meaning two people can share files using cocomo apps. Cool. But how? Well, Cocomo uses the new Real Time Media Transfer Protocol(RTMTP) which, according to Adobe, is C2C (whatever the hell that is). Well its actually P2P (thats right, Peer to Peer), and Adobe is safely avoiding that name. Crazy!
Setting programming aside, I’m currently playing Gears of War. Boy, does it feel good to chain saw a locust. Also i’m on the look out for Left4Dead. Can’t wait to try that with its superb co-op mode. GTA 4 for PC is also on my Christmas wish list.
So thats it. I’ll be posting more on the TextLayout Framework. So look out for that really soon.
Flex Selection Rectangle
Click anywhere on the demo and drag to see the selection rectangle. On the top right, the number of items selected is displayed. Like it? Lets look at the code.
FlexSelectionRectangle.mxml
<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
layout="absolute"
creationComplete="{init()}"
backgroundGradientAlphas="[1.0, 1.0]"
backgroundGradientColors="[#FFFFFF, #FFFFFF]" width="800" height="600">
<mx:Style>
.selectionRectangleStyle {
backgroundAlpha: 0.3;
backgroundColor: #067EE3;
borderColor: #FFFFFF;
borderStyle: inset;
borderThickness: 2;
cornerRadius: 0;
}
</mx:Style>
<mx:Script source="script.as"/>
<!-- A bunch of controls to play with -->
<mx:Button label="Button" horizontalCenter="26" verticalCenter="3"/>
<mx:Button label="Button" horizontalCenter="-197" verticalCenter="-193"/>
<mx:CheckBox label="Checkbox" horizontalCenter="166" verticalCenter="-218"/>
<mx:DataGrid horizontalCenter="219" verticalCenter="111">
<mx:columns>
<mx:DataGridColumn headerText="Column 1" dataField="col1"/>
<mx:DataGridColumn headerText="Column 2" dataField="col2"/>
<mx:DataGridColumn headerText="Column 3" dataField="col3"/>
</mx:columns>
</mx:DataGrid>
<mx:DateChooser horizontalCenter="-284" verticalCenter="6"/>
<mx:RadioButton label="Radio" horizontalCenter="155" verticalCenter="-157"/>
<mx:TextArea horizontalCenter="-39" verticalCenter="-181"/>
<mx:Label text="Click and drag to see a selection rectangle" fontSize="16"
horizontalCenter="3" verticalCenter="-72"/>
<mx:DateField horizontalCenter="-115" verticalCenter="36"/>
<mx:LinkButton label="LinkButton" horizontalCenter="-330" verticalCenter="-133"/>
<!-- To display some output -->
<mx:Label
id="output_txt"
right="10" top="10"
fontSize="14"
color="#00AED3" fontWeight="bold"/>
</mx:Application>
script.as
import mx.containers.Canvas;</span></span>
/* This canvas will act as the selection rectangle. */
private var selectionRectangle:Canvas;
/* A reference rectangle object to size my selection canvas */
private var r:Rectangle;
[Bindable] private var selectedItems:Array = new Array();
private function init():void {
/* Set the event listeners */
this.addEventListener(MouseEvent.MOUSE_DOWN, onMouseDown);
this.addEventListener(MouseEvent.MOUSE_UP, onMouseUp);
this.addEventListener(MouseEvent.MOUSE_MOVE, onMouseMove);
selectionRectangle = new Canvas();
selectionRectangle.setStyle("styleName", "selectionRectangleStyle");
r = new Rectangle(0,0,0,0);
}
private function onMouseDown(e:MouseEvent):void {
/* Instantiate the referece rectangle at the mouse-downed coordinates*/
r = new Rectangle(Number(e.stageX),Number(e.stageY),0,0);
//Apply the x,y,width and height properties to the canvas
selectionRectangle.x = r.x;
selectionRectangle.y = r.y;
selectionRectangle.width = r.width;
selectionRectangle.height = r.height;
//Add to stage
addChild(selectionRectangle);
}
private function onMouseUp(e:MouseEvent):void {
//Get an array of items on stage
var children:Array = this.getChildren();
selectedItems = new Array();
/* Find items that intersect with the selection rectangle */
for(var i:uint = 0; i< children.length; i++) {
if((children[i] as DisplayObject) != selectionRectangle)
if(selectionRectangle.getRect(this).intersects((children[i] as DisplayObject).getRect(this)))
selectedItems.push(children[i]);
}
//Remove the selection rectangle
removeChild(selectionRectangle);
//Show output
output_txt.text = selectedItems.length + " items selected";
}
private function onMouseMove(e:MouseEvent):void {
//Keep resizing the Rectangle object and the canva
r.bottomRight = new Point(e.stageX, e.stageY);
selectionRectangle.x = r.x;
selectionRectangle.y = r.y;
selectionRectangle.width = r.width;
selectionRectangle.height = r.height;
}
Lets start from the beginning. First, i set the event listeners for the MouseDown, MouseUp and MouseMove event. I’m using a Canvas object as the selection rectangle. It can be replaced with any custom component. And finally i have a Rectangle object.
On MouseDown, I instantiate the Rectangle object to the current mouse x and y co-ordinates. Then set the x, y, width and height of the canvas object to that of the rectangle object. Why am i doing this? Well you can try to do this without having a rectangle object. Try setting the Canvas’ properties directly from the MouseEvent.stageX and MouseEvent.localX values. It wont work. Try it out.
On MouseMove, the Rectangle object is resized and the values are reflected on the Canvas object.
On MouseDown, the selectedItems array is populated with all the children which came under the selection. Its done using the intersects() function of the Rectangle class. From here any function that implements some action to be taken on selection, can be called. The code might be kinda rough. I intend to polish it a bit and make it into a reusable component soon.
So there it is. Flex Selection Rectangle!
