// forked from checkmate's colin challenge for professionals /** * やっぱネットワークするならゲームだろ! * ということで前のSnake Game「http://wonderfl.net/code/7f8f78663b1487a4dda53dcc7be1fc81ae6706f4」のリベンジ * * Tweetでtwitterで「仲間を呼ぶ」ボタン * 勝手に「http://wonderfl.net/code/7bc146049d06410fea6c857e542597666671d1e6」を参考に追加した。 * * ローカル部分(Main)とネットワーク部分(UnionRamen)と完全に切り離せるのがウリ。 * @author coppieee */ package { import com.bit101.components.PushButton; import flash.display.Sprite; import flash.events.KeyboardEvent; import flash.events.MouseEvent; import flash.net.navigateToURL; import flash.net.URLRequest; import flash.text.TextField; import flash.ui.Keyboard; import flash.utils.escapeMultiByte; import net.user1.reactor.*; import net.user1.logger.Logger; public class UnionRamen extends Sprite { protected var _reactor:Reactor; protected var _room:Room; private var _main:Main; public function UnionRamen () { _main = new Main(); _main.x = (465 -_main.width) / 2; addChild(_main); var twitButton:PushButton = new PushButton(this); twitButton.label = "Tweet"; twitButton.x = (465 - twitButton.width) / 2; twitButton.y = (465 - twitButton.height); twitButton.addEventListener(MouseEvent.CLICK, function(e:MouseEvent):void { navigateToURL(new URLRequest("http://twitter.com/home/?status=" + escapeMultiByte("Let's Snake Game! http://wonderfl.net/code/912e5bbfb8bfc055345361cee2b222d2c8a182a8") )); }); _reactor = new Reactor(); _reactor.addEventListener(ReactorEvent.READY, onReady); _reactor.connect("tryunion.com", 9100); //_reactor.getLog().setLevel(Logger.DEBUG); Wonderfl.capture_delay( 15 ); } private function onReady(e:ReactorEvent):void { _main.addEventListener(PixelChangeEvent.PIXEL_CHANGE, function(e:PixelChangeEvent):void { _room.sendMessage("PICEL_GANGE", false, null, e.toDataString()); }); _main.addEventListener(PixelChangeEvent.PIXEL_CLEAR, function(e:PixelChangeEvent):void { _room.sendMessage("PICEL_CLEAR", false, null, e.toDataString()); }); _room = _reactor.getRoomManager().createRoom("wonderfl.coppieee.MultiSnakeGame"); //_room.addMessageListener("ADD_NARUTO", addNarutoListener); _room.addMessageListener("PICEL_GANGE", onPixelChangeMessage); _room.addMessageListener("PICEL_CLEAR", onPixelClearMessage); _room.join(); } private function onPixelChangeMessage(from:IClient,data:String):void { trace(data); var buffer:/*String*/Array = data.split(","); var row:int = int(buffer[0]); var column:int = int(buffer[1]); var color:uint = uint(buffer[2]); trace(row, column, color); _main.setPixel(new Position(row, column), color); } private function onPixelClearMessage(from:IClient, data:String):void { var buffer:/*String*/Array = data.split(","); var row:int = int(buffer[0]); var column:int = int(buffer[1]); var color:uint = uint(buffer[2]); _main.clearPixel(new Position(row,column), color); } } } //pakage{ import flash.display.Bitmap; import flash.display.BitmapData; import flash.display.Sprite; import flash.events.Event; import flash.events.KeyboardEvent; import flash.ui.Keyboard; import frocessing.color.ColorHSV; class Main extends Sprite { private var _bitmapData:BitmapData; public static const LENGTH:int = 16; private static const BACKGROUND_COLOR:uint = 0x000000; private static const FOOD_COLOR:uint = 0xFFFFFF; private var _snake:Snake; private var _food:Position; public function Main():void { _bitmapData = new BitmapData(LENGTH, LENGTH, false, BACKGROUND_COLOR); var bitmap:Bitmap = new Bitmap(_bitmapData); bitmap.width = 16 * 27; bitmap.height = 16 * 27; addChild(bitmap); _snake = new Snake(Position.createRamdom()); _food = Position.createRamdom(); addEventListener(Event.ENTER_FRAME, onEnterFrame); addEventListener(KeyboardEvent.KEY_DOWN, onKeyDown); } private function onKeyDown(e:KeyboardEvent):void { var angle:Angle = Angle.keyCodeToAngle(e.keyCode); if (!angle) { return; } _snake.nextAngle = angle; } private var _count:int = 0; private function onEnterFrame(e:Event):void { stage.focus = this; if (_count > 5) { _count = 0; var data:SnakeUpdateData = _snake.update(); var nextColor:uint = getPixel(data.createPosition); if (data.deletePosition) { clearPixel(data.deletePosition, _snake.color); dispatchEvent(new PixelChangeEvent(PixelChangeEvent.PIXEL_CLEAR, data.deletePosition, _snake.color)); } if (nextColor == FOOD_COLOR) { _snake.grow(); } else if (nextColor != BACKGROUND_COLOR) { for each(var index:Position in _snake.indexs) { clearPixel(index, _snake.color); dispatchEvent(new PixelChangeEvent(PixelChangeEvent.PIXEL_CLEAR, index, _snake.color)); } _snake = new Snake(Position.createRamdom()); return; } dispatchEvent(new PixelChangeEvent(PixelChangeEvent.PIXEL_CHANGE, data.createPosition, _snake.color)); setPixel(data.createPosition, _snake.color); } _count ++; if (getPixel(_food) != FOOD_COLOR) { _food = Position.createRamdom(); setPixel(_food, FOOD_COLOR); dispatchEvent(new PixelChangeEvent(PixelChangeEvent.PIXEL_CHANGE, _food, FOOD_COLOR)); } } public function clearPixel(p:Position, color:uint):void { if (getPixel(p) != color) { return; } _bitmapData.setPixel(p.column, p.row, BACKGROUND_COLOR); } public function getPixel(p:Position):uint { return _bitmapData.getPixel(p.column, p.row); } public function setPixel(p:Position, color:uint):void { _bitmapData.setPixel(p.column, p.row, color); } } //} import flash.geom.Point; import flash.utils.Dictionary; import flash.ui.Keyboard; import frocessing.color.ColorHSV; import flash.events.Event; class Snake { private static const COLOR:uint = new ColorHSV(Math.random() * 360).value; public function get nextAngle():Angle { return _nextAngle; } public function set nextAngle(value:Angle):void { if ((value.row + _prevAngle.row) == 0 && (value.column + _prevAngle.column) == 0) { return; } _nextAngle = value; } private var _nextAngle:Angle = Angle.RIGHT; private var _prevAngle:Angle = Angle.RIGHT; public var indexs:/*Position*/Array; public const color:uint = COLOR; public function Snake(position:Position) { indexs = []; indexs.push(position); } public function update():SnakeUpdateData { _prevAngle = nextAngle; var nextHead:Position = nextAngle.add(indexs[indexs.length - 1]); indexs.push(nextHead); var data:SnakeUpdateData = new SnakeUpdateData(); data.createPosition = nextHead; if (_isGrowed) { _isGrowed = false; return data; } var tail:Position = indexs[0]; indexs.shift(); data.deletePosition = tail; return data; } private var _isGrowed:Boolean = false; public function grow():void { _isGrowed = true; } } class SnakeUpdateData { public var createPosition:Position; public var deletePosition:Position; public function SnakeUpdateData(){} } class PixelChangeEvent extends Event { public static const PIXEL_CHANGE:String = "pixelChange"; public static const PIXEL_CLEAR:String = "pixelClear"; public function toDataString():Object { return position.row+","+position.column+","+color; } public var position:Position; public var color:uint; public function PixelChangeEvent(type:String,position:Position,color:uint) { super(type); this.position = position; this.color = color; } } class Position { public static function createRamdom():Position { return new Position(Main.LENGTH * Math.random(),Main.LENGTH *Math.random()); } public function get row():int { return _row; } public function set row(value:int):void { _row = value % Main.LENGTH; if (_row < 0) { _row += Main.LENGTH; } } public var _row:int; public function get column():int { return _column; } public function set column(value:int):void { _column = value % Main.LENGTH; if (_column < 0) { _column += Main.LENGTH; } } public var _column:int; public function Position(row:int,column:int) { this.row = row; this.column = column; } } class Angle { public static const LEFT:Angle = new Angle( 0, -1); public static const RIGHT:Angle = new Angle(0, 1); public static const UP:Angle = new Angle( -1, 0); public static const DOWN:Angle = new Angle(1, 0); public static function keyCodeToAngle(keyCode:int):Angle { return _angles[keyCode]; } private static var _angles:Dictionary; //static initializer { _angles = new Dictionary(); _angles[Keyboard.LEFT] = LEFT; _angles[Keyboard.RIGHT] = RIGHT; _angles[Keyboard.UP] = UP; _angles[Keyboard.DOWN] = DOWN; } public function get row():int { return _row; } private var _row:int; public function get column():int { return _column; } private var _column:int; public function Angle(row:int, column:int) { _row = row; _column = column; } public function add(p:Position):Position { return new Position(p.row + this.row, p.column + this.column); } public function toString():String { return "[Angle " + row + "," + column + "]"; return "[Angle row:" + row + ",column:" + column + "]"; } } MultiSnakeGame