Showing posts with label pentomino. Show all posts
Showing posts with label pentomino. Show all posts

Saturday, January 31, 2015

Creating a Pentomino game using AS3 Part 15

In this tutorial well add the ability to set canvas size in the level editor.

Go to your Flash project and create a new MovieClip based on win_screen. Give the new MC a class path of new_edit_screen. Inside of it we need to include 4 objects at least - two text field inputs tWidth and tHeight (max chars - 2), a button btn_continue and an error message turned into a movie clip with id "incorrect".

Delete it from stage and just keep it in the library. Now return to pentomino_editor.as script file. Inside the constructor, delete all the lines that declare and create the map. Add a listener for btn_reset button and set its click event handler to a function that calls newLevel(). Call newLevel() from the constructor too.

public function pentomino_editor() 
{
// add shape buttons
for (var i:int = 0; i < 4; i++) {
for (var u:int = 0; u < 3; u++) {
var shapeButton:MovieClip = new edit_shape();
shapeButton.x = 528 + u * 62;
shapeButton.y = 15 + i * 84;
addChild(shapeButton);
shapeButton.bg.alpha = 0.3;
shapeButton.shape.gotoAndStop(3 * i + u + 1);
shapeButtons.push(shapeButton);
shapeButton.addEventListener(MouseEvent.ROLL_OVER, buttonOver);
shapeButton.addEventListener(MouseEvent.ROLL_OUT, buttonOut);
}
}

// buttons
btn_mainmenu.addEventListener(MouseEvent.CLICK, doMainmenu);
btn_reset.addEventListener(MouseEvent.CLICK, function():void{newLevel()});

// new level
newLevel();
}

Now create the newLevel() function.

First thing we do here is add an instance of new_edit_screen to the stage.

var newScreen:MovieClip = new new_edit_screen();
addChild(newScreen);

Add lines that only allow numeric values in tWidth and tHeight, also set their default values:

newScreen.tWidth.restrict = "0-9";
newScreen.tHeight.restrict = "0-9";
newScreen.tWidth.text = 10;
newScreen.tHeight.text = 6;

Set incorrects alpha to 0 (since there was no error yet):

newScreen.incorrect.alpha = 0;

Add a click event listener to btn_continue, set its handler to an internal function editContinue:

newScreen.btn_continue.addEventListener(MouseEvent.CLICK, editContinue);

Create the editContinue() function inside newLevel(). First thing we do is check if the specified width and height is correct:

if (newScreen.tWidth.text == "" || newScreen.tHeight.text == "" || newScreen.tWidth.text == "0" || newScreen.tHeight.text == "0") {
newScreen.incorrect.alpha = 1;
return;
}

If it is correct, we delete the newScreen object from stage, set mapGrid to an empty array and declare width and height variables:

newScreen.parent.removeChild(newScreen);
mapGrid = [];
var width:int = newScreen.tWidth.text;
var height:int = newScreen.tHeight.text;

Add two loops that add values to mapGrid based on width and height:

for (var i:int = 0; i < height; i++) {
mapGrid[i] = [];
for (var u:int = 0; u < width; u++) {
mapGrid[i][u] = 1;
}
}

Then calculate grid values and draw the grid:

// grid settings
calculateGrid();
addChild(gridShape);
gridShape.x = gridStartX;
gridShape.y = gridStartY;

// draw tiles
drawGrid();

Full newLevel() function:

private function newLevel():void {
var newScreen:MovieClip = new new_edit_screen();
addChild(newScreen);
newScreen.tWidth.restrict = "0-9";
newScreen.tHeight.restrict = "0-9";
newScreen.tWidth.text = 10;
newScreen.tHeight.text = 6;
newScreen.incorrect.alpha = 0;
newScreen.btn_continue.addEventListener(MouseEvent.CLICK, editContinue);

function editContinue(evt:MouseEvent):void {
if (newScreen.tWidth.text == "" || newScreen.tHeight.text == "" || newScreen.tWidth.text == "0" || newScreen.tHeight.text == "0") {
newScreen.incorrect.alpha = 1;
return;
}
newScreen.parent.removeChild(newScreen);
mapGrid = [];
var width:int = newScreen.tWidth.text;
var height:int = newScreen.tHeight.text;
for (var i:int = 0; i < height; i++) {
mapGrid[i] = [];
for (var u:int = 0; u < width; u++) {
mapGrid[i][u] = 1;
}
}
// grid settings
calculateGrid();
addChild(gridShape);
gridShape.x = gridStartX;
gridShape.y = gridStartY;

// draw tiles
drawGrid();
}
}

Full code so far:

package  
{
import flash.display.MovieClip;
import flash.display.Sprite;
import flash.events.Event;
import flash.events.KeyboardEvent;
import flash.events.MouseEvent;
import flash.geom.Point;
import flash.sampler.NewObjectSample;
import flash.utils.ByteArray;

/**
* Open-source pentomino game engine
* @author Kirill Poletaev
*/

public class pentomino_editor extends MovieClip
{
private var mapGrid:Array = [];
private var shapeButtons:Array = [];

private var gridShape:Sprite = new Sprite();
private var canPutShape:Sprite = new Sprite();
private var gridStartX:int;
private var gridStartY:int;
private var gridCellWidth:int;

public function pentomino_editor()
{
// add shape buttons
for (var i:int = 0; i < 4; i++) {
for (var u:int = 0; u < 3; u++) {
var shapeButton:MovieClip = new edit_shape();
shapeButton.x = 528 + u * 62;
shapeButton.y = 15 + i * 84;
addChild(shapeButton);
shapeButton.bg.alpha = 0.3;
shapeButton.shape.gotoAndStop(3 * i + u + 1);
shapeButtons.push(shapeButton);
shapeButton.addEventListener(MouseEvent.ROLL_OVER, buttonOver);
shapeButton.addEventListener(MouseEvent.ROLL_OUT, buttonOut);
}
}

// buttons
btn_mainmenu.addEventListener(MouseEvent.CLICK, doMainmenu);
btn_reset.addEventListener(MouseEvent.CLICK, function():void{newLevel()});

// new level
newLevel();
}

private function newLevel():void {
var newScreen:MovieClip = new new_edit_screen();
addChild(newScreen);
newScreen.tWidth.restrict = "0-9";
newScreen.tHeight.restrict = "0-9";
newScreen.tWidth.text = 10;
newScreen.tHeight.text = 6;
newScreen.incorrect.alpha = 0;
newScreen.btn_continue.addEventListener(MouseEvent.CLICK, editContinue);

function editContinue(evt:MouseEvent):void {
if (newScreen.tWidth.text == "" || newScreen.tHeight.text == "" || newScreen.tWidth.text == "0" || newScreen.tHeight.text == "0") {
newScreen.incorrect.alpha = 1;
return;
}
newScreen.parent.removeChild(newScreen);
mapGrid = [];
var width:int = newScreen.tWidth.text;
var height:int = newScreen.tHeight.text;
for (var i:int = 0; i < height; i++) {
mapGrid[i] = [];
for (var u:int = 0; u < width; u++) {
mapGrid[i][u] = 1;
}
}
// grid settings
calculateGrid();
addChild(gridShape);
gridShape.x = gridStartX;
gridShape.y = gridStartY;

// draw tiles
drawGrid();
}
}

private function calculateGrid():void {
var columns:int = mapGrid[0].length;
var rows:int = mapGrid.length;

// free size: 520x460
// fit in: 510x450

// calculate width of a cell:
gridCellWidth = Math.round(510 / columns);

var width:int = columns * gridCellWidth;
var height:int = rows * gridCellWidth;

// calculate side margin
gridStartX = (520 - width) / 2;

if (height < 450) {
gridStartY = (450 - height) / 2;
}
if (height >= 450) {
gridCellWidth = Math.round(450 / rows);
height = rows * gridCellWidth;
width = columns * gridCellWidth;
gridStartY = (460 - height) / 2;
gridStartX = (520 - width) / 2;
}
}

private function drawGrid():void {
gridShape.graphics.clear();
var width:int = mapGrid[0].length;
var height:int = mapGrid.length;

var i:int;
var u:int;

// draw background
for (i = 0; i < height; i++) {
for (u = 0; u < width; u++) {
if (mapGrid[i][u] == 1) drawCell(u, i, 0xffffff, 1, 0x999999);
}
}
}

private function drawCell(width:int, height:int, fill:uint, thick:Number, line:uint):void {
gridShape.graphics.beginFill(fill);
gridShape.graphics.lineStyle(thick, line);
gridShape.graphics.drawRect(width * gridCellWidth, height * gridCellWidth, gridCellWidth, gridCellWidth);
}

private function buttonOver(evt:MouseEvent):void {
evt.currentTarget.bg.alpha = 1;
}

private function buttonOut(evt:MouseEvent):void {
evt.currentTarget.bg.alpha = 0.3;
}

private function doMainmenu(evt:MouseEvent):void {
(root as MovieClip).gotoAndStop(1);
}
}

}

Thanks for reading!

Results:

Read more »

Thursday, January 22, 2015

Creating a Pentomino game using AS3 Part 29

In this tutorial we will add the ability to edit saved levels.

Firstly go to saved_levels.as constructor and add click event handlers for btn_edit objects of item1, item2 and item3. Set their handlers to anonymous inline functions that call editLevel() method of the root class. Pass the current levels data object from the SharedObject as the only parameter:

public function saved_levels() 
{
savedLevels = SharedObject.getLocal("myLevels");
btn_back.addEventListener(MouseEvent.CLICK, doBack);
if (savedLevels.data.levels != null) levels = savedLevels.data.levels;
tInfo.text = levels.length + " levels (" + savedLevels.size + "B)";
pages = Math.floor(levels.length / 3) + 1;
goPage(1);
btn_previous.addEventListener(MouseEvent.CLICK, function() { goPage(currentPage - 1) } );
btn_next.addEventListener(MouseEvent.CLICK, function() { goPage(currentPage + 1) } );
item1.btn_play.addEventListener(MouseEvent.CLICK, function () { (root as MovieClip).playLevel(levels[3 * (currentPage-1)].grid, levels[3 * (currentPage-1)].shapes); savedLevels.data.levels[3 * (currentPage-1)].played++ } );
item2.btn_play.addEventListener(MouseEvent.CLICK, function () { (root as MovieClip).playLevel(levels[3 * (currentPage-1) + 1].grid, levels[3 * (currentPage-1) + 1].shapes); savedLevels.data.levels[3 * (currentPage-1)+1].played++} );
item3.btn_play.addEventListener(MouseEvent.CLICK, function () { (root as MovieClip).playLevel(levels[3 * (currentPage-1) + 2].grid, levels[3 * (currentPage-1) + 2].shapes); savedLevels.data.levels[3 * (currentPage-1) + 2].played++ } );
item1.btn_edit.addEventListener(MouseEvent.CLICK, function () { (root as MovieClip).editLevel(levels[3 * (currentPage-1)])} );
item2.btn_edit.addEventListener(MouseEvent.CLICK, function () { (root as MovieClip).editLevel(levels[3 * (currentPage-1) + 1])} );
item3.btn_edit.addEventListener(MouseEvent.CLICK, function () { (root as MovieClip).editLevel(levels[3 * (currentPage-1) + 2])} );
}

Open your project in Flash and go to the thrid frame (where the pentomino_edit instance is located). Give the pentomino_edit instance an id of "edit".

Then go to main.as class and declare a new public variable alreadyExists, set its default value to false.

Create a function called editLevel(). Here we receive levelItem object, set alreadyExists to true, go to the third frame, set levelName and mapGrid variables of the "edit" object to levelItem.name nad levelItem.edit and call that objects calculateAndDraw() and setShapes() methods as shown below:

package  
{
import flash.display.MovieClip;
import flash.net.SharedObject;

/**
* Open-source pentomino game engine
* @author Kirill Poletaev
*/

public class main extends MovieClip
{
public var alreadyExists:Boolean = false;

public function main()
{
}

public function playLevel(grid:Array, shapes:Array):void {
gotoAndStop(2);
game.playLevel(grid, shapes);
}

public function editLevel(levelItem:Object):void {
alreadyExists = true;
gotoAndStop(3);
edit.levelName = levelItem.name;
edit.mapGrid = levelItem.grid;
edit.calculateAndDraw();
edit.setShapes(levelItem.shapes);
}

public function saveLevelLocal(grid:Array, shapes:Array, levelName:String):void {
var sharedObject:SharedObject = SharedObject.getLocal("myLevels");
if (sharedObject.data.levels == null) sharedObject.data.levels = [];
var levelObject:Object = new Object;
levelObject.grid = grid;
levelObject.shapes = shapes;
levelObject.name = levelName;
levelObject.played = 0;
sharedObject.data.levels.push(levelObject);
sharedObject.flush();
}

}

}

The alreadyExists variable is used to tell pentomino_edit whether or not it should display the "Create new level" window in the beginning. The levelName variable sets the default name for the level thats being saved. Since we are editing an existing level, we want to use the same name, but still give the user the ability to change the name if they wish. The mapGrid variable is used to draw and manage the grid, we just apply our existing grid array to this variable. The calculateAndDraw() and setShapes() methods are new, I will explain them as I add them to pentomino_editor.as. For now, jsut rememebr to pass levelItem.shapes as parameter for setShapes().

Go to pentomino_editor.as, set mapGrid to public and declare a new public varaible levelName:

public var mapGrid:Array = [];
public var levelName:String = "My Level"

In the constructor find the line that calls newLevel(). Here we check if Pentominos alreadyExists value is false before calling the method. If it is true, dont call newLevel() and reset alreadyExists to false.

// new level
if (!Pentomino.alreadyExists) {
newLevel();
}
if (Pentomino.alreadyExists) {
Pentomino.alreadyExists = false;
}

Now go to newLevel() function. In its internal editContinue() function, right after mapGrid values are set, call a function calculateAndDraw() instead of all the rest code:

private function newLevel():void {
canDraw = false;

var newScreen:MovieClip = new new_edit_screen();
addChild(newScreen);
newScreen.tWidth.restrict = "0-9";
newScreen.tHeight.restrict = "0-9";
newScreen.tWidth.text = 10;
newScreen.tHeight.text = 6;
newScreen.incorrect.alpha = 0;
newScreen.btn_continue.addEventListener(MouseEvent.CLICK, editContinue);

function editContinue(evt:MouseEvent):void {
if (newScreen.tWidth.text == "" || newScreen.tHeight.text == "" || newScreen.tWidth.text == "0" || newScreen.tHeight.text == "0") {
newScreen.incorrect.alpha = 1;
return;
}
newScreen.parent.removeChild(newScreen);
mapGrid = [];
var height:int = newScreen.tHeight.text;
var width:int = newScreen.tWidth.text;
for (var i:int = 0; i < height; i++) {
mapGrid[i] = [];
for (var u:int = 0; u < width; u++) {
mapGrid[i][u] = 1;
}
}
calculateAndDraw();
}
}

Now declare this public function:

public function calculateAndDraw():void {
// grid settings
calculateGrid();
gridShape.x = gridStartX;
gridShape.y = gridStartY;

// draw tiles
drawGrid();

// canPutShape settings
canPutShape.graphics.clear();
canPutShape.graphics.lineStyle(2, 0xff0000);
canPutShape.graphics.drawRect(0, 0, gridCellWidth, gridCellWidth);
canPutShape.alpha = 0;

canDraw = true;
}

You can see the code is all the same, but because we turned it all into a public function it is now reusable.

Finally, add a function setShapes() that receives an array and applies its values to shapeButtons count values:

public function setShapes(sh:Array):void {
for (var i:int = 0; i < shapeButtons.length; i++) {
shapeButtons[i].count.value = sh[i];
}
}

Now we can load the saved levels in the editor and save them. However, overwriting isnt possible right now, and nor is deleting saved levels, but well work on that in the future tutorials.

Heres full pentomino_editor.as code so far:

package  
{
import flash.display.MovieClip;
import flash.display.Sprite;
import flash.events.Event;
import flash.events.KeyboardEvent;
import flash.events.MouseEvent;
import flash.geom.Point;
import flash.sampler.NewObjectSample;
import flash.utils.ByteArray;

/**
* Open-source pentomino game engine
* @author Kirill Poletaev
*/

public class pentomino_editor extends MovieClip
{
public var mapGrid:Array = [];
public var levelName:String = "My Level"
private var shapeButtons:Array = [];

private var gridShape:Sprite = new Sprite();
private var canPutShape:Sprite = new Sprite();
private var gridStartX:int;
private var gridStartY:int;
private var gridCellWidth:int;
private var canDraw:Boolean = false;
private var mouseDown:Boolean = false;
private var currentCell:Point = new Point( -1, -1);

private static var Pentomino:MovieClip;

public function pentomino_editor()
{
Pentomino = (root as MovieClip);
addEventListener(MouseEvent.MOUSE_MOVE, onMouseMove);
addEventListener(MouseEvent.MOUSE_DOWN, onMouseDown);
addEventListener(MouseEvent.MOUSE_UP, onMouseUp);
addEventListener(Event.ENTER_FRAME, onEnterFrame);

// add shape buttons
for (var i:int = 0; i < 4; i++) {
for (var u:int = 0; u < 3; u++) {
var shapeButton:MovieClip = new edit_shape();
shapeButton.x = 528 + u * 62;
shapeButton.y = 15 + i * 84;
addChild(shapeButton);
shapeButton.bg.alpha = 0.3;
shapeButton.shape.gotoAndStop(3 * i + u + 1);
shapeButton.count.minimum = 0;
shapeButton.count.maximum = 100;
shapeButtons.push(shapeButton);
shapeButton.addEventListener(MouseEvent.ROLL_OVER, buttonOver);
shapeButton.addEventListener(MouseEvent.ROLL_OUT, buttonOut);
}
}

// buttons
btn_mainmenu.addEventListener(MouseEvent.CLICK, doMainmenu);
btn_reset.addEventListener(MouseEvent.CLICK, function():void { newLevel() } );
btn_save.addEventListener(MouseEvent.CLICK, doSave);
stat_display.addEventListener(MouseEvent.MOUSE_OVER, function() { stat_display.alpha = 0 } );
stat_display.addEventListener(MouseEvent.MOUSE_OUT, function() { stat_display.alpha = 1 } );

// new level
if (!Pentomino.alreadyExists) {
newLevel();
}
if (Pentomino.alreadyExists) {
Pentomino.alreadyExists = false;
}

addChild(gridShape);
addChild(canPutShape);
stat_display.parent.setChildIndex(stat_display, stat_display.parent.numChildren - 1);
canPutShape.mouseEnabled = false;
canPutShape.mouseChildren = false;
}

private function onMouseMove(evt:MouseEvent):void {
if(mapGrid.length>0){
var mousePos:Point = new Point(Math.floor((mouseX - gridStartX) / gridCellWidth), Math.floor((mouseY - gridStartY) / gridCellWidth));
canPutShape.x = mousePos.x * gridCellWidth + gridStartX;
canPutShape.y = mousePos.y * gridCellWidth + gridStartY;
if (mousePos.x < mapGrid[0].length && mousePos.y < mapGrid.length && mousePos.x >= 0 && mousePos.y >= 0) {
canPutShape.alpha = 1;
}else {
canPutShape.alpha = 0;
}
}
}

private function newLevel():void {
canDraw = false;

var newScreen:MovieClip = new new_edit_screen();
addChild(newScreen);
newScreen.tWidth.restrict = "0-9";
newScreen.tHeight.restrict = "0-9";
newScreen.tWidth.text = 10;
newScreen.tHeight.text = 6;
newScreen.incorrect.alpha = 0;
newScreen.btn_continue.addEventListener(MouseEvent.CLICK, editContinue);

function editContinue(evt:MouseEvent):void {
if (newScreen.tWidth.text == "" || newScreen.tHeight.text == "" || newScreen.tWidth.text == "0" || newScreen.tHeight.text == "0") {
newScreen.incorrect.alpha = 1;
return;
}
newScreen.parent.removeChild(newScreen);
mapGrid = [];
var height:int = newScreen.tHeight.text;
var width:int = newScreen.tWidth.text;
for (var i:int = 0; i < height; i++) {
mapGrid[i] = [];
for (var u:int = 0; u < width; u++) {
mapGrid[i][u] = 1;
}
}
calculateAndDraw();
}
}

public function calculateAndDraw():void {
// grid settings
calculateGrid();
gridShape.x = gridStartX;
gridShape.y = gridStartY;

// draw tiles
drawGrid();

// canPutShape settings
canPutShape.graphics.clear();
canPutShape.graphics.lineStyle(2, 0xff0000);
canPutShape.graphics.drawRect(0, 0, gridCellWidth, gridCellWidth);
canPutShape.alpha = 0;

canDraw = true;
}

private function calculateGrid():void {
var columns:int = mapGrid[0].length;
var rows:int = mapGrid.length;

// free size: 520x460
// fit in: 510x450

// calculate width of a cell:
gridCellWidth = Math.round(510 / columns);

var width:int = columns * gridCellWidth;
var height:int = rows * gridCellWidth;

// calculate side margin
gridStartX = (520 - width) / 2;

if (height < 450) {
gridStartY = (450 - height) / 2;
}
if (height >= 450) {
gridCellWidth = Math.round(450 / rows);
height = rows * gridCellWidth;
width = columns * gridCellWidth;
gridStartY = (460 - height) / 2;
gridStartX = (520 - width) / 2;
}
}

private function drawGrid():void {
gridShape.graphics.clear();
var width:int = mapGrid[0].length;
var height:int = mapGrid.length;

var i:int;
var u:int;

// draw background
for (i = 0; i < height; i++) {
for (u = 0; u < width; u++) {
if (mapGrid[i][u] == 1) drawCell(u, i, 0xffffff, 1, 0x999999);
}
}
displayTotalCells();
}

private function drawCell(width:int, height:int, fill:uint, thick:Number, line:uint):void {
gridShape.graphics.beginFill(fill);
gridShape.graphics.lineStyle(thick, line);
gridShape.graphics.drawRect(width * gridCellWidth, height * gridCellWidth, gridCellWidth, gridCellWidth);
}

private function buttonOver(evt:MouseEvent):void {
evt.currentTarget.bg.alpha = 1;
}

private function buttonOut(evt:MouseEvent):void {
evt.currentTarget.bg.alpha = 0.3;
}

private function doMainmenu(evt:MouseEvent):void {
Pentomino.gotoAndStop(1);
}

private function onMouseDown(evt:MouseEvent):void {
mouseDown = true;
}

private function onMouseUp(evt:MouseEvent):void {
mouseDown = false;
currentCell = new Point(-1, -1)
}

private function onEnterFrame(evt:Event):void {
// if drawing is allowed and mouse is down
if (canDraw && mouseDown) {
var mousePos:Point = new Point(Math.floor((mouseX - gridStartX) / gridCellWidth), Math.floor((mouseY - gridStartY) / gridCellWidth));
// if valid coordinates
if (mousePos.x < mapGrid[0].length && mousePos.y < mapGrid.length && mousePos.x >= 0 && mousePos.y >= 0) {
// if the cell is not "current cell"
if (mousePos.x != currentCell.x || mousePos.y != currentCell.y) {
currentCell.x = mousePos.x;
currentCell.y = mousePos.y;
if (mapGrid[mousePos.y][mousePos.x] == 1) {
mapGrid[mousePos.y][mousePos.x] = 0;
}else {
mapGrid[mousePos.y][mousePos.x] = 1;
}
drawGrid();
}
}
}
}

public function setShapes(sh:Array):void {
for (var i:int = 0; i < shapeButtons.length; i++) {
shapeButtons[i].count.value = sh[i];
}
}

private function doSave(evt:MouseEvent):void {
if (checkSave()) {
var shapes:Array = [];
for (var i:int = 0; i < shapeButtons.length; i++) {
shapes.push(shapeButtons[i].count.value);
}
var saveScreen:MovieClip = new save_screen(Pentomino, mapGrid, shapes, alertClose);
addChild(saveScreen);
canDraw = false;
}
}

private function displayTotalCells():void {
var totalCells:int = 0;
var i:int;
var u:int;
var width:int = mapGrid[0].length;
var height:int = mapGrid.length;

for (i = 0; i < height; i++) {
for (u = 0; u < width; u++) {
if (mapGrid[i][u] == 1) totalCells++;
}
}
stat_display.tCells.text = totalCells;

if (totalCells / 5 != Math.round(totalCells / 5)) {
stat_display.tCells.textColor = 0xFF0000;
}else {
stat_display.tCells.textColor = 0x009900;
}
}

private function checkSave():Boolean {
// count total cells
var totalCells:int = 0;
var i:int;
var u:int;
var width:int = mapGrid[0].length;
var height:int = mapGrid.length;

for (i = 0; i < height; i++) {
for (u = 0; u < width; u++) {
if (mapGrid[i][u] == 1) totalCells++;
}
}

// check if total cells can be divided by 5
if (totalCells / 5 != Math.round(totalCells / 5)) {
alert("Error!
Incorrect cell count: " + totalCells + ", number must be divideable by 5.");
return false;
}

// count total available shape count
var totalShapes:int = 0;

for (i = 0; i < shapeButtons.length; i++) {
totalShapes += shapeButtons[i].count.value;
}

// check if there are enough shapes available
if (totalCells > totalShapes * 5) {
alert("Error!
Not enough shapes available: " + totalShapes + " out of " + totalCells/5);
return false;
}

return true;
}

private function alert(message:String):void {
var alertWindow:MovieClip = new alert_screen(message, alertClose);
addChild(alertWindow);
canDraw = false;
}

private function alertClose():void {
canDraw = true;
}

}

}

Thanks for reading!
Read more »