플래시 게임 - SlidingPuzzle 슬라이더 퍼 즐 게임

더 읽 기
최근 플래시 게임 의 알고리즘 을 연구 한 결과 같은 게임 에 여러 가지 알고리즘 이 있 는 것 을 발 견 했 습 니 다. 저 는 대상 과 사건 알림 방식 을 대상 으로 하 는 알고리즘 을 좋아 하고 시원 한 프로그램 구 조 를 좋아 합 니 다.
[운행 효과]
[FLASH=550,400,True]upload/SlidingPuzzle.swf[/FLASH]
[주 프로그램 클래스]
package {
	import com.klstudio.puzzles.slider.PuzzleBoard;

	import flash.display.Sprite;

	/**
	 * SlidingPuzzle
	 * @author Kinglong([email protected])
	 * @since:2010-9-13
	 */
	public class SlidingPuzzle extends Sprite {
		[Embed(source="image.jpg")]
		private var embeddedImage : Class;
		
		private var _board:PuzzleBoard;
		public function SlidingPuzzle() {
			_board = new PuzzleBoard(300,300,4);
			addChild(_board);
			
			_board.createPuzzle(new embeddedImage());
			
			_board.startGame();
		}
	}
}

[퍼 즐 보드 클래스]

package com.klstudio.puzzles.slider {
	import flash.geom.Point;
	import flash.geom.Rectangle;
	import flash.display.Bitmap;
	import flash.geom.Matrix;
	import flash.display.BitmapData;
	import flash.display.Sprite;

	/**
	 * PuzzleBoard
	 * @author Kinglong([email protected])
	 * @since:2010-9-13
	 */	

	public class PuzzleBoard extends Sprite {
		private var _pieces : Array;
		private var _moving : Boolean;
		private var _boardWidth : int;
		private var _boardHeight : int;
		private var _pieceWidth : Number;
		private var _pieceHeight : Number;
		private var _subdivisions : uint;
		private var _space : uint;
		private var _padding : uint;

		public function PuzzleBoard(width : uint,height : uint,subdivisions : uint = 3,padding : uint = 1,space : int = -1) {
			_pieces = [];
			_moving = true;
			
			_boardWidth = width;
			_boardHeight = height;
			_subdivisions = subdivisions = (subdivisions < 3) ? 3 : subdivisions;
			_space = (space < subdivisions * subdivisions && space > -1) ? space : subdivisions - 1; 
			_padding = padding;
			
			_pieceWidth = _boardWidth / subdivisions;
			_pieceHeight = _boardHeight / subdivisions;
		}

		public function get subdivisions() : uint {
			return _subdivisions;
		}

		public function get padding() : uint {
			return _padding;
		}

		private function scaleImage(bitmap : Bitmap) : BitmapData {
			var bd : BitmapData = new BitmapData(_boardWidth, _boardHeight);
			var bRate : Number = _boardWidth / _boardHeight;
			var iRate : Number = bitmap.width / bitmap.height;
			var matrix : Matrix = new Matrix();
			if(bRate < iRate) {
				matrix.scale(_boardHeight * iRate / bitmap.width, _boardHeight / bitmap.height);
			} else {
				matrix.scale(_boardWidth / bitmap.width, _boardWidth / iRate / bitmap.height);
			}
			bd.draw(bitmap, matrix, null, null, null, true);			
			return bd;
		}

		public function createPuzzle(bitmap : Bitmap) : void {
			clearBoard();
			var bd : BitmapData = scaleImage(bitmap);
			var pbd : BitmapData;
			var len : uint = subdivisions * subdivisions;
			var rect : Rectangle = new Rectangle(0, 0, _pieceWidth, _pieceHeight);
			var point : Point = new Point();
			for(var i : uint = 0;i < len;i++) {
				if(i == _space) {
					continue;
				}
				rect.x = (i % subdivisions) * _pieceWidth;
				rect.y = Math.floor(i / subdivisions) * _pieceHeight;
				pbd = new BitmapData(_pieceWidth, _pieceHeight);				
				pbd.copyPixels(bd, rect, point);				
				var piece : PuzzlePiece = new PuzzlePiece(pbd, new Point(i % subdivisions, Math.floor(i / subdivisions)), padding);
				piece.addEventListener(PuzzleEvent.CLICK, clickHandler);
				piece.addEventListener(PuzzleEvent.MOVE, moveHandler);
				piece.addEventListener(PuzzleEvent.READY, moveHandler);
				addChild(piece);
				_pieces.push(piece);
			}
		}

		public function startGame() : void {
			var count : uint = 0;
			var piece : PuzzlePiece;
			var position : int;
			while (count < 100) {                
				do {                    
					piece = _pieces[int(Math.random() * _pieces.length - 1)];
					position = checkNeighbours(piece);
				}while (position == -1);
				piece.move(position, false);
				count++;
			}
			_moving = false;
		}

		private function clickHandler(event : PuzzleEvent) : void {
			if(_moving) {
				return;
			}
			var position : int = checkNeighbours(event.piece);
			if(position > -1) {
				event.piece.move(position);
			}
		}

		private function moveHandler(event : PuzzleEvent) : void {
			switch(event.type) {
				case PuzzleEvent.READY:
					_moving = false;
					break;
				case PuzzleEvent.MOVE:
					_moving = true;
					break;
			}
		}

		private function clearBoard() : void {
			if(_pieces.length == 0) {
				return;
			}
			for each(var piece:PuzzlePiece in _pieces) {
				piece.removeEventListener(PuzzleEvent.CLICK, clickHandler);
				piece.removeEventListener(PuzzleEvent.READY, moveHandler);
				piece.removeEventListener(PuzzleEvent.MOVE, moveHandler);
				removeChild(piece);
			}
			_pieces = [];
		}

		private function isEmptySpace(x : int,y : int) : Boolean {            
			for each (var piece:PuzzlePiece in _pieces) {
				if(piece.point.x == x && piece.point.y == y) {
					return false;
				}
			}
			return true;
		}

		private function checkNeighbours(piece : PuzzlePiece) : int {
			if (piece.point.x > 0 && isEmptySpace(piece.point.x - 1, piece.point.y)) {				
				return PuzzlePiece.LEFT;
			}
			if (piece.point.x < subdivisions - 1 && isEmptySpace(piece.point.x + 1, piece.point.y)) {				
				return PuzzlePiece.RIGHT;
			}
			if (piece.point.y > 0 && isEmptySpace(piece.point.x, piece.point.y - 1)) {				
				return PuzzlePiece.UP;
			}
			if (piece.point.y < subdivisions - 1 && isEmptySpace(piece.point.x, piece.point.y + 1)) {				
				return PuzzlePiece.DOWN;
			}			
			return -1;
		}
	}
}

[퍼 즐 이벤트 클래스]

package com.klstudio.puzzles.slider {
	import flash.events.Event;

	/**
	 * PuzzleEvent
	 * @author Kinglong([email protected])
	 * @since:2010-9-13
	 */	

	public class PuzzleEvent extends Event {
		private var _piece : PuzzlePiece;
		public static const MOVE : String = "MOVE";
		public static const READY : String = "READY";
		public static const CLICK : String = "CLICK";

		public function PuzzleEvent(type : String, piece : PuzzlePiece = null) {
			super(type);
			_piece = piece;
		}

		public function get piece() : PuzzlePiece {
			return _piece;
		}

		override public function clone() : Event {
			return new PuzzleEvent(type, piece);
		}
	}
}

[PuzzlePiece 류]

package com.klstudio.puzzles.slider {
	import flash.filters.GradientBevelFilter;
	import flash.filters.BitmapFilter;
	import flash.filters.BitmapFilterType;
	import flash.filters.BitmapFilterQuality;
	import flash.events.MouseEvent;

	import gs.TweenLite;
	import gs.easing.Circ;

	import flash.display.Bitmap;
	import flash.display.Shape;
	import flash.geom.Point;
	import flash.display.BitmapData;
	import flash.display.Sprite;

	/**
	 * PuzzlePiece
	 * @author Kinglong([email protected])
	 * @since:2010-9-13
	 */	

	public class PuzzlePiece extends Sprite {
		public static const DOWN : int = 3;
		public static const LEFT : int = 1;
		public static const UP : int = 4;
		public static const RIGHT : int = 2;

		private var _padding : uint;
		private var _ease : Function;
		private var _point : Point;
		private var _oPoint : Point;
		private var _bmp : Bitmap;
		private var _mask : Shape;

		public function PuzzlePiece(bitmapData : BitmapData,point : Point,padding : uint = 1) {
			mouseChildren = false;			
			_ease = Circ.easeInOut;
			_padding = padding;
			_oPoint = point.clone();
			_point = point.clone();
			
			_bmp = new Bitmap(bitmapData);
			addChild(_bmp);			
			
			_mask = new Shape();
			_mask.graphics.beginFill(0xFF0000);
			_mask.graphics.drawRoundRect(_padding, _padding, _bmp.width - _padding * 2, _bmp.height - _padding * 2, 8, 8);
			_mask.graphics.endFill();
			addChild(_mask);
			_bmp.mask = _mask;	
			
			x = point.x * _bmp.width;
			y = point.y * _bmp.height;
			
			addEventListener(MouseEvent.CLICK, clickHandler);		
			
			_bmp.filters = [getBitmapFilter()];
		}

		public function move(position : int,tweened : Boolean = true) : void {
			var params : Object = {ease:_ease, onComplete:tweenCompleteHandler};
			var duration : Number = 0.4;
			switch(position) {
				case LEFT:
					updatePoint(point.x - 1, point.y);
					if(tweened) {
						params["x"] = point.x * _bmp.width;
						TweenLite.to(this, duration, params);
						dispatchEvent(new PuzzleEvent(PuzzleEvent.MOVE));
					} else {
						x = point.x * _bmp.width;
					}
					break;
				case RIGHT:	
					updatePoint(point.x + 1, point.y);	
					if(tweened) {
						params["x"] = point.x * _bmp.width;
						TweenLite.to(this, duration, params);
						dispatchEvent(new PuzzleEvent(PuzzleEvent.MOVE));
					} else {
						x = point.x * _bmp.width;
					}			
					break;
				case UP:	
					updatePoint(point.x, point.y - 1);
					if(tweened) {
						params["y"] = point.y * _bmp.height;
						TweenLite.to(this, duration, params);
						dispatchEvent(new PuzzleEvent(PuzzleEvent.MOVE));
					} else {
						y = point.y * _bmp.height;
					}				
					break;
				case DOWN:	
					updatePoint(point.x, point.y + 1);
					if(tweened) {
						params["y"] = point.y * _bmp.height;
						TweenLite.to(this, duration, params);
						dispatchEvent(new PuzzleEvent(PuzzleEvent.MOVE));
					} else {
						y = point.y * _bmp.height;
					}				
					break;				
			}		
		}

		public function get point() : Point {
			return _point;
		}

		public function reset() : void {
			updatePoint(_oPoint.x, _oPoint.y);
			x = point.x * _bmp.width;
			y = point.y * _bmp.height;						
		}

		private function updatePoint(x : int,y : int) : void {
			_point.x = x;
			_point.y = y;
			if(hasCompleted()) {
				_bmp.filters = null;
			}else{
				_bmp.filters = [getBitmapFilter()];
			}
		}

		private function getBitmapFilter() : BitmapFilter {
			return new GradientBevelFilter(5, 225, [16777215, 13421772, 0], [0.4, 0, 0.4], [0, 128, 255], 8, 8, 2, BitmapFilterQuality.HIGH, BitmapFilterType.INNER, false);
		}

		public function hasCompleted() : Boolean {
			return _point.equals(_oPoint);
		}

		private function clickHandler(event : MouseEvent) : void {
			dispatchEvent(new PuzzleEvent(PuzzleEvent.CLICK, this));
		}

		private function tweenCompleteHandler() : void {
			dispatchEvent(new PuzzleEvent(PuzzleEvent.READY));
		}
	}
}
  • SlidingPuzzle.swf (194.6 KB)
  • 다운로드 횟수: 7
  • 좋은 웹페이지 즐겨찾기