AS3 Tile Collision platformer

281 views Asked by At

I am new to AS3 and have to make a tile platformer for school, sadly my teachers aren't that much of a help. I do not have the slightest clue on how to get collision on my game. I've been searching the internet for a while now and really can't find a solution. If you know anything that could help me progress then please leave a comment!

package  {

    import flash.display.*;
    import flash.events.*;
    import flash.utils.Timer;
    import flash.events.TimerEvent;
    import flash.geom.Rectangle;
    import flashx.textLayout.formats.BlockProgression;
    import flashx.textLayout.formats.BackgroundColor;


    public class jump extends MovieClip {

        //Var player
        var persoon:testSubject = new testSubject();
        var grond:Ground = new Ground();
        var backGround:Background = new Background();
        var health:Health = new Health();

        var mapWidth = 10;
        var mapHeight = 10;
        var tileSide = 50;
        var totalTiles = mapWidth * mapHeight;

        var accel:Number = 2;
        var speed:Number = 5;
        var jumpSpeed:Number = 0;
        var gravity:Number = 5; 

        var ground:Number = 745 - persoon.height;

        var nr:Number = 3;

        var sprint:Boolean = true;
        var shiftButton:Boolean = false;
        var leftButton:Boolean = false;
        var rightButton:Boolean = false;
        var upButton:Boolean = false;
        var downButton:Boolean = false;
        var isJumping:Boolean = true;

        //Array map
        var myMap:Array = [
           [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1],
           [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,1,1,1,1,1,1,1,1,0,0,0,1,3,2,4,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,1,0,0,0,1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,0,0,0,0,0,0,0,0,0,1,0,0,0,1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
           [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1]
           ];

        public function jump() {
            //Event listener up key
            stage.addEventListener(KeyboardEvent.KEY_DOWN, upKeyDown);
            stage.addEventListener(KeyboardEvent.KEY_UP, upKeyUp);
            stage.addEventListener(Event.ENTER_FRAME, moveChar);

            //backGround
            backGround.x = -1000;
            backGround.y = -1000;
            backGround.height = 2000;
            backGround.width = 6000;
            addChild(backGround);

            //Map
            for (var i:int=0; i<13; i++)
            {
             for (var u:int=0; u<36; u++){
              var cell:MovieClip = new tile();
              cell.gotoAndStop(myMap[i][u]+1);
              cell.x=tileSide*u
              cell.y=tileSide*i
              addChild(cell);
             }
            }

            //Player
            persoon.x = 450;
            persoon.y = 490;
            persoon.width = 50;
            persoon.height = 60;
            addChild(persoon);

            //Healthbar
            health.x = 10;
            health.y = 65;
            health.gotoAndStop(4);
            addChild(health);
        }

        //Spring function when key is pressed
        public function upKeyDown(e:KeyboardEvent):void {
            //Buttons  Left - Up - Right - Down - Shift
            if ( e.keyCode == 37 || e.keyCode == 65 ) {
                leftButton = true;
                trace(persoon.y);
            }
            if ( e.keyCode == 38 || e.keyCode == 87 ) {
                upButton = true;
                    if(!isJumping) {  
                        jumpSpeed = 31;  
                        isJumping = true;  
                    }
            }
            if ( e.keyCode == 39 || e.keyCode == 68 ) {
                rightButton = true;
            }
            if ( e.keyCode == 40 || e.keyCode == 83 ) {
                downButton = true;
            }
            if ( e.keyCode == 16 ) {
                shiftButton = true;
                if ( sprint == true ) {
                    speed = speed * accel;
                    sprint = false;
                }
            }
        }

        //Spring function when key is released
        public function upKeyUp(e:KeyboardEvent):void {
            //Buttons  Left - Up - Right - Down - Shift
            if ( e.keyCode == 37 || e.keyCode == 65 ) {
                leftButton = false;
            }
            if ( e.keyCode == 38 || e.keyCode == 87 ) {
                upButton = false;
            }
            if ( e.keyCode == 39 || e.keyCode == 68 ) {
                rightButton = false;
            }
            if ( e.keyCode == 40 || e.keyCode == 83 ) {
                downButton = false;
            }
            if ( e.keyCode == 16 ) {
                shiftButton = false;
                speed = 5;
                sprint = true;
            }
        }

        //Character Movement
        public function moveChar(event:Event):void {
            //Collision


            //Walk Left & Right
            if ( leftButton == true ) {
                if (persoon.x > 78) {
                    persoon.x -= speed;
                    health.x = persoon.x - 440;
                }
            } else if ( rightButton == true ) {
                if ( persoon.x < 1722 ) {
                    persoon.x += speed;
                    health.x = persoon.x - 440;
                }
            }

            //Jump
            if(isJumping) {
                health.y -= jumpSpeed;
                persoon.y -= jumpSpeed;  
                jumpSpeed -= 2;
            }

            if (persoon.y + gravity < ground) {
                persoon.y += gravity; 
                health.y += gravity;
                trace(persoon.y);
            } else {
                health.y = ground - 420;
                persoon.y = ground;  
                isJumping = false;
            }

            //Camera
            root.scrollRect = new Rectangle ( persoon.x - stage.stageWidth/2, persoon.y - 430, stage.stageWidth, stage.stageHeight );
        }
    }
}
3

There are 3 answers

0
CyanAngel On

hitTestObject() is a function available on anything that extends the DisplayObject class. It allows you to detect if two objects are touching or intersecting.

It's implementation is fair straight forward:

if (obj1.hitTestObject(obj2) == true)
{
    //hit
}

Depending on how your onscreen assets are implemented you could also use BitmapData.hitTest() to detect if two bit maps have collided. This is more precise as it allows you to declare alph channels. You can find a good tutorial on that here

0
philipp On

If you want to have real good collisions (physics), than you definitively need a Physics engine like Box2D! But to come into it you will have to master a little learning curve, but I promise its absolutely worth digging into it.

Please note: Box2D was originally developed in C++, but there are many ports to different Languages like AS3, Javascript, Java and so on. That's why you sometimes have to refer to the original documentation, whereby the docs for the flash port are very good.

Some good tutorials are here:

Since you are building a tiled platformer, have a look at tiled, it will serve you from writing your map by hand. Additionally I can recommend you to have a look at melonjs a nice tile-based platformer game engine for Javascript. The tutorials can show you the workflow, what should be quite similar for you with flash. If you need a browsergame and are not bound to flash, I would recommend you to switch to HTML5 and use melonjs…

Good Luck!

0
mitim On

For very simple collision detection in your case, I'll assume that your tiles can be represented by squares and that the player is a rectangle. Given these two points, the main bit of new code you'll need to write will be to find the intersection amount of 2 generic rectangles (since the square is also a rectangle). There are built in methods you can use within the rectangle class if you desire or you can write your own (it's not too complex).

Next, within your player movement, instead of applying the movement right away to the player, you can store it and using the rectangle vs rectangle intersection method above, check to see if a player would run in to a solid tile. If they do, then stop/limit the player from running in to it by limiting the amount at which they are allowed to move, then applying it to the player.

This is just one of many ways and even what I've described here can be improved as well.