AS3 example Drag and Drop: Difference between revisions
m (→Walkthrough) |
|||
Line 210: | Line 210: | ||
closing the class definition and the package delcaration. | closing the class definition and the package delcaration. | ||
--- | --- | ||
== Variants == | == Variants == | ||
(to provide) | (to provide) |
Revision as of 13:08, 5 November 2007
<pageby nominor="false" comments="false"/>
ActionScript Program
Note: For now, the drag and drop works when you click anywhere on the tile but the letter itself. We keep things simple and won't provide a workaround.
package {
import flash.display.Sprite; import flash.events.Event; import flash.events.MouseEvent; import flash.text.TextField; public class AnagramDragDrop extends Sprite { private var dragTarget:Sprite; public function AnagramDragDrop() { var board:Sprite = new Sprite(); var letters:Array = new Array("d","i","r","t","y","r","o","o","m") var l:String; var xPos:uint = 50 var yPos:uint = 100 for each (l in letters) { var tile:Sprite = new Sprite(); tile = createLetterTile(l as String) // size, color yellow tile.x = xPos; tile.y = yPos; xPos += 50; board.addChild(tile); tile.addEventListener(MouseEvent.MOUSE_DOWN, dragStarter, false); tile.addEventListener(MouseEvent.MOUSE_UP, dragStopper); } addChild(board) instructions.text = "Re-order the letters to form another word." instructions.x = 20 instructions.y = 20 instructions.width = 300; addChild(instructions) } private function dragStarter(event:MouseEvent):void { if (event.target is Sprite) { dragTarget = event.target as Sprite; dragTarget.startDrag(); } } private function dragStopper(event:MouseEvent):void { dragTarget.stopDrag(); } private function createLetterTile(txt:String):Sprite { var s:Sprite = new Sprite(); var letter:TextField = new TextField(); var tileBackColor:uint = 0xDBD9A6; var tileShadowColor:uint = 0x676420; var tileBorderColor:uint = 0x000000; s.graphics.beginFill(tileShadowColor); s.graphics.drawRect(-2, 2, 40, 40); s.graphics.endFill(); s.graphics.beginFill(tileBackColor); s.graphics.drawRect(0, 0, 40, 40); s.graphics.endFill(); s.graphics.lineStyle(1, tileBorderColor, 100); s.graphics.drawRect(0, 0, 40, 40); letter.text = txt letter.selectable = false; letter.x = 14 letter.y = 14 letter.width = 14 letter.height = 16 s.addChild(letter) return s; } } }
Walkthrough
---
package { import flash.display.Sprite; import flash.events.Event; import flash.events.MouseEvent; import flash.text.TextField; public class AnagramDragDrop extends Sprite {
Package declaration, import statements, class definition. ---
private var dragTarget:Sprite;
Declaration of all variables that will be used in more than one functions. We store in a variable information about the sprite object that was the target of the drag. When the mouse gets up, we want the drag action to stop, whether the mouse is over that object or not.
---
public function AnagramDragDrop() { var board:Sprite = new Sprite(); var letters:Array = new Array("d","i","r","t","y","r","o","o","m") var l:String; var xPos:uint = 50 var yPos:uint = 100 for each (l in letters) { var tile:Sprite = new Sprite(); tile = createLetterTile(l as String) // size, color yellow tile.x = xPos; tile.y = yPos; xPos += 50; board.addChild(tile); tile.addEventListener(MouseEvent.MOUSE_DOWN, dragStarter); tile.addEventListener(MouseEvent.MOUSE_UP, dragStopper); } addChild(board) instructions.text = "Re-order the letters to form another word." instructions.x = 20 instructions.y = 20 instructions.width = 300; addChild(instructions) }
Rather than draw a single object on the screen to be dragged and dropped, we spice things up a bit. We will draw a number of tiles letters.
It would be quite tedious to have something of the like:
var tile1:Sprite = createLetterTile("d") tile1.x = 50 tile1.y = 50 addChild(tile1) var tile2:Sprite = createLetterTile("i") tile2.x = 50+30 tile2.y = 50 addChild(tile2) var tile3:Sprite = createLetterTile("r") tile3.x = 50+(30*2) tile3.y = 50 addChild(tile3)
What if we were to decide to change to offset all times by 10 pixels? What if we wanted to change the anagram to appear on the screen. This would be a very slow, tedious process, and error prone process.
We opt for a more efficient of coding this. We put the letters in an array and we use Flash built in for each (value in array) to rapidly loop across the items with in this array.
We also define a point of origin (x=50, y=100), where the first tile will appear. Within the for each loop, we add 50 pixels to the x position, causing the tiles to appear one on the right of the other.
Because all tiles are to look the same except for the letter in the middle, we delegate the creation of each tile to a function. This way, we are free to change the look and feel of a tile later on.
For convenience reasons, we create a board object to store all sprites. This way, we can treat the tiles as component and position it on its own.
Finally, we add two mouseEvent listener, one to trigger a function whenever a mousedown event occurs, another one to trigger another function whenever a mouseup event occurs. They will be used to trigger start drag and stop drag actions, respectively.
---
private function dragStarter(event:MouseEvent):void { dragTarget = event.target as Sprite; dragTarget.startDrag(); }
private function dragStopper(event:MouseEvent):void { dragTarget.stopDrag(); }
whenever a mousedown event occurs anywhere on the interface, the event is forwarded to the function specified as parameter to the addListener function. In this program, it is the dragStarter function.
The function is called and the information about the event that toke place passed as a parameter to this function. We therefore create a parameter event, of type MouseEvent, to be able to access information about the event from within our function.
Different information become available, the target, the mouse location and others. These information vary slightly from mouseevent to mouseevent. Detailed information about event information can be obtained on the MouseEvent entry in the Actionscript Language Reference.
Here, we are only interested in the target property. This holds information on the on-screen object that was the target of the event. We store this information in a variable because we want a mouse up action to interrupt the dragging of the object on which a dragging action was initiated rather than the object currently under the mouse.
---
private function createLetterTile(txt:String):Sprite { var s:Sprite = new Sprite(); var letter:TextField = new TextField(); var tileBackColor:uint = 0xDBD9A6; var tileShadowColor:uint = 0x676420; var tileBorderColor:uint = 0x000000; s.graphics.beginFill(tileShadowColor); s.graphics.drawRect(-2, 2, 40, 40); s.graphics.endFill(); s.graphics.beginFill(tileBackColor); s.graphics.drawRect(0, 0, 40, 40); s.graphics.endFill(); s.graphics.lineStyle(1, tileBorderColor, 100); s.graphics.drawRect(0, 0, 40, 40); letter.text = txt letter.selectable = false; letter.x = 14 letter.y = 14 letter.width = 14 letter.height = 16 s.addChild(letter) return s; }
Function to create a given tile object. ---
} }
closing the class definition and the package delcaration. ---
Variants
(to provide)
- Fridge Magnets
- Put this code in the write order
Challenge
(to provide)
- simplistic Hanoi tower problem.
- Domino game.