2048 M * N
it's my coursera class assignment pyton code moved to actionscript. I newly wrote about graphics.
/**
* Copyright greentec ( http://wonderfl.net/user/greentec )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/dxIW
*/
package
{
import com.bit101.components.ColorChooser;
import com.bit101.components.Label;
import com.bit101.components.PushButton;
import com.bit101.components.Style;
import flash.display.Bitmap;
import flash.display.BitmapData;
import flash.display.Sprite;
import flash.events.Event;
import flash.events.KeyboardEvent;
import flash.geom.ColorTransform;
import flash.geom.Rectangle;
import flash.text.TextField;
import flash.text.TextFormat;
import flash.text.TextFieldAutoSize;
import flash.text.TextFormatAlign;
import flash.utils.Dictionary;
import flash.utils.ByteArray;
/**
* ...
* @author ypc
*/
[SWF(width = "465", height = "465")]
public class Main extends Sprite
{
public var boardBitmapData:BitmapData;
public var boardBitmap:Bitmap;
public var rowMax:int = 8;
public var colMax:int = 8;
public var rowMin:int = 3;
public var colMin:int = 3;
public var labelArray:Array;
public var rowNow:int = 3;
public var colNow:int = 8;
public var rowNext:int = 3;
public var colNext:int = 8;
public var boardSize:int = 360;
public var boardStartX:Number;
public var boardStartY:Number;
public var tileArray:Array;
public var rowButtonArray:Array;
public var colButtonArray:Array;
public var maxLineNum:int;
public var indent:Number;
public var cellSize:Number;
public const colorDict:Object = {
BACK : 0xFCFDEB,
BORDER : 0xBCAC9F,
0 : 0xCCC0B2,
2 : 0xEEE4D9,
4 : 0xECE0C8,
8 : 0xF3AE78,
16 : 0xF59362,
32 : 0xF57B5F,
64 : 0xF55C37,
128 : 0xEDCD70,
256 : 0xEDCB61,
512 : 0xEBC750,
1024 : 0xE8C03C,
2048 : 0xE8C03C,
4096 : 0x3A3B33,
LOWNUMBER : 0x797066,
HIGHNUMBER : 0xF4F6F3
};
//public const var directions:Object = {
//UP : 1,
//DOWN : 2,
//LEFT : 3,
//RIGHT : 4
//}
//
//public const var OFFSETS:Object = {
//UP: [1, 0],
//DOWN: [-1, 0],
//LEFT: [0, 1],
//RIGHT: [0, -1]
//};
public const OFFSETS_NUM:Array = [ [], [1, 0], [ -1, 0], [0, 1], [0, -1] ];
public const START_MOVE_OFFSETS:Array = [ [], [0, 1], [0, 1], [1, 0], [1, 0] ];
public const START_OFFSETS:Array = [ [], [0, 0], [1, 0], [0, 0], [0, 1] ];
public var gameOverLabel:TextField;
public function Main():void
{
if (stage) init();
else addEventListener(Event.ADDED_TO_STAGE, init);
}
private function init(e:Event = null):void
{
removeEventListener(Event.ADDED_TO_STAGE, init);
// entry point
//Style.fontName = "Fixedsys";
//Style.BUTTON_DOWN = 0x24A198;
boardBitmapData = new BitmapData(465, 465, false, colorDict.BACK);
boardBitmap = new Bitmap(boardBitmapData);
addChild(boardBitmap);
initGraphics();
resetGraphics();
resetTiles();
drawTiles();
stage.addEventListener(KeyboardEvent.KEY_DOWN, onKeyDown);
//var a:Array = [1, 2, 3];
//trace(String(a) == String([1, 2, 3]));
}
private function drawTiles():void
{
var i:int, j:int;
var value:int;
var label:TextField;
//var colT:ColorTransform = new ColorTransform();
var format:TextFormat = new TextFormat();
for (i = 0; i < rowNow; i += 1)
{
for (j = 0; j < colNow; j += 1)
{
value = tileArray[i * colNow + j];
if (value != 0)
{
if (value <= 2048)
{
boardBitmapData.fillRect(new Rectangle(boardStartX + (j + 1) * indent + j * cellSize,
boardStartY + (i + 1) * indent + i * cellSize,
cellSize,
cellSize),
colorDict[String(value)]);
}
else
{
boardBitmapData.fillRect(new Rectangle(boardStartX + (j + 1) * indent + j * cellSize,
boardStartY + (i + 1) * indent + i * cellSize,
cellSize,
cellSize),
colorDict["4096"]);
}
label = labelArray[i * colNow + j];
label.text = String(value);
label.x = boardStartX + (j + 1) * indent + j * cellSize + cellSize / 2 - label.width / 2;
label.y = boardStartY + (i + 1) * indent + i * cellSize + cellSize / 2 - label.height / 2;
if (value <= 4)
{
format.color = colorDict.LOWNUMBER;
//colT.color = colorDict.LOWNUMBER;
}
else
{
format.color = colorDict.HIGHNUMBER;
//colT.color = colorDict.HIGHNUMBER;
}
label.setTextFormat(format);
//label.transform.colorTransform = colT;
}
}
}
}
private function resetTiles():void
{
tileArray = [];
var i:int, j:int;
for (i = 0; i < rowNow; i += 1)
{
for (j = 0; j < colNow; j += 1)
{
tileArray.push(0);
}
}
addNewTile(2);
}
private function addNewTile(count:int):void
{
var i:int, j:int;
var c:int = 0;
while (c < count)
{
i = int(Math.random() * rowNow);
j = int(Math.random() * colNow);
if (tileArray[i * colNow + j] == 0)
{
if (Math.random() < 0.9)
{
tileArray[i * colNow + j] = 2;
}
else
{
tileArray[i * colNow + j] = 4;
}
c += 1;
}
}
}
private function resetGraphics():void
{
boardBitmapData.fillRect(new Rectangle(boardStartX, boardStartY, boardSize, boardSize), colorDict.BORDER);
maxLineNum = Math.max(rowNow, colNow);
indent = Number(boardSize) / (maxLineNum + 1) / (maxLineNum + 1);
cellSize = Number(boardSize) / (maxLineNum + 1);
var i:int, j:int;
var rect:Rectangle;
var label:TextField;
for (i = 0; i < rowMax; i += 1)
{
for (j = 0; j < colMax; j += 1)
{
label = labelArray[i * colMax + j];
label.text = "";
}
}
var colT:ColorTransform = new ColorTransform();
colT.color = colorDict.LOWNUMBER;
for (i = 0; i < rowNow; i += 1)
{
for (j = 0; j < colNow; j += 1)
{
boardBitmapData.fillRect(new Rectangle(boardStartX + (j + 1) * indent + j * cellSize,
boardStartY + (i + 1) * indent + i * cellSize,
cellSize,
cellSize),
colorDict["0"]);
//label = labelArray[i * colNow + j];
//label.text = "0";
//label.x = boardStartX + (j + 1) * indent + j * cellSize + cellSize / 2 - label.width / 2;
//label.y = boardStartY + (i + 1) * indent + i * cellSize + cellSize / 2 - label.height / 2;
//label.transform.colorTransform = colT;
}
}
}
private function initGraphics():void
{
boardStartX = (465 - boardSize) / 2;
boardStartY = (465 - boardSize) / 2 + 35;
labelArray = [];
var i:int, j:int;
var label:TextField;
var labelFormat:TextFormat;
labelFormat = new TextFormat();
labelFormat.font = "Helvetica";
labelFormat.size = 20;
labelFormat.align = TextFormatAlign.CENTER;
labelFormat.bold = true;
for (i = 0; i < rowMax; i += 1)
{
for (j = 0; j < colMax; j += 1)
{
label = new TextField();
label.autoSize = TextFieldAutoSize.CENTER;
label.mouseEnabled = false;
label.defaultTextFormat = labelFormat;
label.setTextFormat(labelFormat);
//label = new Label(this, 0, 0, "");
//label.mouseEnabled = false;
//label.mouseChildren = false;
//label.scaleX = 2;
//label.scaleY = 2;
labelArray.push(label);
addChild(label);
}
}
boardBitmapData.fillRect(new Rectangle(22.5, 22.5, 100, 50), colorDict["1024"]);
//var _label:Label = new Label(this, 22.5, 22.5, "2048");
//_label.scaleX = 2;
//_label.scaleY = 2;
//_label.x += (100 - 22.5) / 2 - label.width / 2;
//_label.y += (50 - 22.5) / 2 - label.height / 2;
label = new TextField();
label.autoSize = TextFieldAutoSize.CENTER;
label.mouseEnabled = false;
labelFormat.size = 36;
labelFormat.color = colorDict.HIGHNUMBER;
label.defaultTextFormat = labelFormat;
label.setTextFormat(labelFormat);
label.text = "2048";
//label.borderColor = 0xff0000;
//label.border = true;
//label.background = true;
//trace(label.getLineMetrics(0));
//trace(label.width, label.height, label.textWidth, label.textHeight);
label.x = 22.5 + 100 / 2 - label.width / 2;
label.y = 22.5 + 50 / 2 - label.height / 2;
//trace(label.x, label.y);
addChild(label);
//var colT:ColorTransform = new ColorTransform();
//colT.color = colorDict.HIGHNUMBER;
//label.transform.colorTransform = colT;
var _label:Label;
_label = new Label(this, 150, 22.5, "BOARD WIDTH -> ");
_label = new Label(this, 150, 50, "BOARD HEIGHT-> ");
var button:PushButton;
rowButtonArray = [];
for (i = rowMin; i < rowMax + 1; i += 1)
{
button = new PushButton(this, 230 + (i - rowMin) * 20, 22.5, String(i), onRowButtonClicked);
button.width = 20;
button.name = String(i);
button.toggle = true;
rowButtonArray.push(button);
}
//rowButtonArray[rowButtonArray.length - 1].selected = true;
rowButtonArray[0].selected = true;
colButtonArray = [];
for (i = colMin; i < colMax + 1; i += 1)
{
button = new PushButton(this, 230 + (i - colMin) * 20, 50, String(i), onColButtonClicked);
button.width = 20;
button.name = String(i);
button.toggle = true;
colButtonArray.push(button);
}
colButtonArray[colButtonArray.length - 1].selected = true;
button = new PushButton(this, 465 - 102.5, 22.5, "RESET", onReset);
button.width = 80;
button.height = colButtonArray[0].y + colButtonArray[0].height - rowButtonArray[0].y;
gameOverLabel = new TextField();
gameOverLabel.text = "Game Over";
gameOverLabel.autoSize = TextFieldAutoSize.CENTER;
gameOverLabel.mouseEnabled = false;
labelFormat.size = 60;
labelFormat.color = 0xdd00dd;
gameOverLabel.setTextFormat(labelFormat);
gameOverLabel.defaultTextFormat = labelFormat;
gameOverLabel.x = 465 / 2 - gameOverLabel.width / 2;
gameOverLabel.y = 465 / 2 - gameOverLabel.height / 2;
gameOverLabel.visible = false;
addChild(gameOverLabel);
}
private function onReset(e:Event):void
{
rowNow = rowNext;
colNow = colNext;
gameOverLabel.visible = false;
resetGraphics();
resetTiles();
drawTiles();
}
private function onRowButtonClicked(e:Event):void
{
var i:int;
var str:String = e.target.name;
rowNext = parseInt(str);
for (i = 0; i < rowButtonArray.length; i += 1)
{
if (rowButtonArray[i].name != str)
{
rowButtonArray[i].selected = false;
}
else
{
if (rowButtonArray[i].selected == false)
{
rowButtonArray[i].selected = true;
}
}
}
}
private function onColButtonClicked(e:Event):void
{
var i:int;
var str:String = e.target.name;
colNext = parseInt(str);
for (i = 0; i < colButtonArray.length; i += 1)
{
if (colButtonArray[i].name != str)
{
colButtonArray[i].selected = false;
}
else
{
if (colButtonArray[i].selected == false)
{
colButtonArray[i].selected = true;
}
}
}
}
private function onKeyDown(e:KeyboardEvent):void
{
switch(e.keyCode)
{
case 38: //Up
case 87: //W
makeTurn(1);
break;
case 37: //Left
case 65: //A
makeTurn(3);
break;
case 40: //Down
case 83: //S
makeTurn(2);
break;
case 39: //Right
case 68: //D
makeTurn(4);
break;
}
}
private function makeTurn(direction:int):void
{
var empty_tile_found:Boolean;
var moveNotPossible:Boolean;
var i:int;
tileArray = move(direction);
empty_tile_found = find_empty_tile();
if (empty_tile_found)
{
addNewTile(1);
}
else
{
//game over check
moveNotPossible = true;
for (i = 1; i <= 4; i += 1)
{
if (String(tileArray) != String(move(i)))
{
moveNotPossible = false;
break;
}
}
if (moveNotPossible == true)
{
gameOverLabel.visible = true;
}
}
resetGraphics();
drawTiles();
}
private function move(direction:int):Array
{
var line_num:int = 0;
var line_max:int = 0;
var start_row:int;
var start_col:int;
var temp_line:Array;
var now_r:int;
var now_c:int;
var i:int, j:int;
var copyTileArray:Array = clone(tileArray);
if (direction == 1 || direction == 2)
{
line_num = colNow;
line_max = rowNow;
}
else //direction == 3 or 4
{
line_num = rowNow;
line_max = colNow;
}
start_row = START_OFFSETS[direction][0] * (rowNow - 1);
start_col = START_OFFSETS[direction][1] * (colNow - 1);
for (i = 0; i < line_num; i += 1)
{
temp_line = [];
for (j = 0; j < line_max; j += 1)
{
now_r = start_row + j * OFFSETS_NUM[direction][0];
now_c = start_col + j * OFFSETS_NUM[direction][1];
temp_line.push(copyTileArray[now_r * colNow + now_c]);
}
temp_line = merge(temp_line);
for (j = 0; j < line_max; j += 1)
{
now_r = start_row + j * OFFSETS_NUM[direction][0];
now_c = start_col + j * OFFSETS_NUM[direction][1];
copyTileArray[now_r * colNow + now_c] = temp_line[j];
}
start_row += START_MOVE_OFFSETS[direction][0];
start_col += START_MOVE_OFFSETS[direction][1];
}
return copyTileArray;
}
private function find_empty_tile():Boolean
{
var i:int;
var j:int;
for (i = 0; i < rowNow; i += 1)
{
for (j = 0; j < colNow; j += 1)
{
if (tileArray[i * colNow + j] == 0)
{
return true;
}
}
}
return false;
}
private function merge(line:Array):Array
{
if (line.length == 1)
{
return line;
}
var sum_switch:Array = [];
var copy_line:Array = clone(line);
var i:int, j:int;
var temp:int;
for (i = 0; i < line.length; i += 1)
{
sum_switch.push(false);
}
for (i = 0; i < line.length - 1; i += 1) //add
{
for (j = i + 1; j < line.length; j += 1)
{
if (copy_line[i] != copy_line[j])
{
if (copy_line[j] == 0)
{
continue;
}
else
{
break;
}
}
if (copy_line[i] == copy_line[j] && sum_switch[i] == false && sum_switch[j] == false)
{
sum_switch[i] = true;
sum_switch[j] = true;
copy_line[i] *= 2;
copy_line[j] = 0;
}
}
}
for (i = 1; i < line.length; i += 1) //move other block to empty block
{
if (copy_line[i] != 0)
{
j = i - 1;
while (j >= 0)
{
if (copy_line[j] == 0)
{
temp = copy_line[j + 1];
copy_line[j + 1] = copy_line[j];
copy_line[j] = temp;
j -= 1;
}
else
{
break;
}
}
}
}
return copy_line;
}
public function clone(source:Object):*
{
var myBA:ByteArray = new ByteArray();
myBA.writeObject(source);
myBA.position = 0;
return(myBA.readObject());
}
}
}