Hit Detection on array

Copy link to clipboard
Copied
Hi i have a snake game, that after time loads sprites in an array to make the snake grow. Just wondering how i would go about adding a hit so when the head of the snake hits the body something happens. Below is the full document class code. Any pointers to what type of code would be massively helpful.
<code>
package {
import flash.display.Sprite;
import flash.events.KeyboardEvent;
import flash.events.TimerEvent;
import flash.ui.Keyboard;
import flash.utils.Timer;
import flash.display.MovieClip;
import flash.utils.getTimer;
import flash.text.TextField;
import flash.events.Event;
[SWF(width='430', height='430', frameRate='30')]
public class Snake extends MovieClip{
private const SPEED :uint = 25;//lower = faster
private const snakeAttach :uint = 400;//lower = faster
private const count: uint = 10;
private const DIM :int = 50; //keep this number uneven to have the snake starting in the middle
private const INITIAL_SIZE :int = 3; //keep this lower then DIM/2
private var stopped :Boolean;
private var left :Boolean;
private var right :Boolean;
private var up :Boolean;
private var down :Boolean;
private var size :Number;
private var food :Sprite;
private var tmr :Timer;
private var count1 :Timer;
private var addSnake :Timer;
private var curI :Number;
private var curJ :Number;
private var snake :Array;
private var grid :Array;
private var sp :Sprite;
private var _start:uint;
public var myTextBox:TextField = new TextField();
public function Snake(){
addEventListener(Event.ADDED_TO_STAGE, onAddedToStage);
}
private function onAddedToStage(event:Event):void {
removeEventListener(Event.ADDED_TO_STAGE, onAddedToStage);
stage.addEventListener(KeyboardEvent.KEY_DOWN,changeDir);
size = stage.stageWidth / DIM; //change grid size
curI = curJ = Math.floor(DIM * 0.5); //change grid size
initSnake();
fillGrid();
addTimer();
addChild(myTextBox);
count1 = new Timer(count);
count1.addEventListener(TimerEvent.TIMER,stopWatch);
count1.start();
addSnake = new Timer(snakeAttach);
addSnake.addEventListener(TimerEvent.TIMER,placeFood);
addSnake.start();
tmr = new Timer(SPEED);
tmr.addEventListener(TimerEvent.TIMER,move);
tmr.start();
}
private function stopWatch(event:TimerEvent):void{
myTextBox.text = (count1.currentCount / 100).toString();
}
public function addTimer():void{ //timer
var myTextBox:TextField = new TextField();
addChild(myTextBox);
}
private function fillGrid():void{ //grid
grid = Make2DArray();
for (var i:uint = 0; i < DIM; i++){
for (var j:uint = 0; j < DIM; j++){
var sp:Sprite = new Sprite();
sp.graphics.beginFill(0xD7E0FC);
sp.graphics.lineStyle(1,0xF5F5F5);
sp.graphics.drawRect(0, 0, size - 1, size - 1);
sp.x = i * size;
sp.y = j * size;
addChild(sp);
grid
}
}
}
private function Make2DArray():Array{ //for the grid
var a:Array = new Array(DIM);
for(var i:uint = 0; i < a.length; i++){
a = new Array(DIM);
}
return a;
}
private function initSnake():void{ //initialises the snake
var center:Number = Math.floor(DIM * 0.5) * size;
snake = new Array(INITIAL_SIZE);
for (var i:uint = 0; i < INITIAL_SIZE; i++){
var sp:Sprite = makeItem(); //adds a body part of makeItem
sp.x = center;
sp.y = center + i * size;
addChild(sp); //adds to the stage
snake = sp; //sets the index to one
}
snake.reverse();
}
private function makeItem(c:uint = 0):Sprite{ //graphics for item
var s:Sprite = new Sprite();
s.graphics.beginFill(c);
s.graphics.lineStyle(2,0x3800E0);
s.graphics.drawRect(0, 0, size, size);
return s;
}
private function placeFood(event:TimerEvent):void{
var rndI:uint = Math.floor(Math.random() * DIM); //sets a random integer based on the the floor
var rndJ:uint = Math.floor(Math.random() * DIM);
var rndX:Number = grid[rndI][rndJ].x; // sets a grid position for the food item to go
var rndY:Number = grid[rndI][rndJ].y;
if (food != null) removeChild(food); //if there is food on the grid removes the food from the board
food = makeItem(Math.random() * 0xFFFFFF);// random color
food.x = rndX;
food.y = rndY;
addChild(food); //adds the food to the board
for (var i:uint = 0; i < snake.length; i++){
if (rndY == snake.y && rndX == snake.x){
}
}
}
private function move(e:TimerEvent):void{
if (left){
curI -= 1;
}else if (right){
curI += 1;
}
if (up){
curJ -= 1;
}else if (down){
curJ += 1;
}
if (left || right || up || down){
var s:Sprite = makeItem();
if (curI > DIM - 1) curI = 0;
if (curJ > DIM - 1) curJ = 0;
if (curI < 0) curI = DIM - 1;
if (curJ < 0) curJ = DIM - 1;
s.x = grid[curI][curJ].x;
s.y = grid[curI][curJ].y;
addChild(s);
snake.push(s);
if (Math.floor(s.x) == Math.floor(food.x) && Math.floor(s.y) == Math.floor(food.y) ){
}
else if((tmr.currentCount % 3) > 0) { removeChild(snake[0]); snake.shift(); }
}
}
private function changeDir(e:KeyboardEvent):void{
if(e.keyCode == Keyboard.LEFT) {if (!right){left = true; up = false; down = false; right = false;}}
if(e.keyCode == Keyboard.UP) {if (!down) {left = false; up = true; down = false; right = false;}}
if(e.keyCode == Keyboard.RIGHT) {if (!left) {left = false; up = false; down = false; right = true;}}
if(e.keyCode == Keyboard.DOWN) {if (!up) {left = false; up = false; down = true; right = false;}}
}
}
} </code>
thanks
Copy link to clipboard
Copied
assuming snake[0] is the head, in move():
for(var i:int=1;i<snake.length;i++){
if(snake[0].hitTestObject(snake)){
// do whatever
}
}

Copy link to clipboard
Copied
ive added it to the move function and called it in but im getting this error :
TypeError: Error #2007: Parameter child must be non-null.
at flash.display::DisplayObjectContainer/removeChild()
at Snake/move()
at flash.utils::Timer/_timerDispatch()
at flash.utils::Timer/tick()
Heres the code that ive changed -
private function move(e:TimerEvent):void{
if (left){
curI -= 1;
}else if (right){
curI += 1;
}
if (up){
curJ -= 1;
}else if (down){
curJ += 1;
}
if (left || right || up || down){
var s:Sprite = makeItem();
if (curI > DIM - 1) curI = 0;
if (curJ > DIM - 1) curJ = 0;
if (curI < 0) curI = DIM - 1;
if (curJ < 0) curJ = DIM - 1;
s.x = grid[curI][curJ].x;
s.y = grid[curI][curJ].y;
addChild(s);
checkForHits();
if (Math.floor(s.x) == Math.floor(food.x) && Math.floor(s.y) == Math.floor(food.y) ){
}
else if((tmr.currentCount % 3) > 0) { removeChild(snake[0]); snake.shift(); }
}
}
private function checkForHits():void {
for(var i:int=1;i<snake.length;i++){
if(snake[0].hitTestObject(snake)){
trace("hit")
}
}
}
Copy link to clipboard
Copied
that error's not from the code i suggested. it's from:
0) { removeChild(snake[0]); snake.shift(); }

Copy link to clipboard
Copied
ahh i see yes i fixed the error. However all it does is just trace the word "hit" as soon as the snake moves?
Copy link to clipboard
Copied
1. is snake[0] the snake's head and the rest of snake the body?
2. does the bounding box of snake[0] contact the bounding box of any of the rest of snake?

