• Dear Cerberus X User!

    As we prepare to transition the forum ownership from Mike to Phil (TripleHead GmbH), we need your explicit consent to transfer your user data in accordance with our amended Terms and Rules in order to be compliant with data protection laws.

    Important: If you accept the amended Terms and Rules, you agree to the transfer of your user data to the future forum owner!

    Please read the new Terms and Rules below, check the box to agree, and click "Accept" to continue enjoying your Cerberus X Forum experience. The deadline for consent is April 5, 2024.

    Do not accept the amended Terms and Rules if you do not wish your personal data to be transferred to the future forum owner!

    Accepting ensures:

    - Continued access to your account with a short break for the actual transfer.

    - Retention of your data under the same terms.

    Without consent:

    - You don't have further access to your forum user account.

    - Your account and personal data will be deleted after April 5, 2024.

    - Public posts remain, but usernames indicating real identity will be anonymized. If you disagree with a fictitious name you have the option to contact us so we can find a name that is acceptable to you.

    We hope to keep you in our community and see you on the forum soon!

    All the best

    Your Cerberus X Team

Collisions.

12wwood

New member
Joined
Mar 5, 2019
Messages
10
Hey guys, im trying to create code that when a bullet in the bullet list collides with one of the swarm objects, they both delete from the list. I have tried many ways of tackling this problem but i can never get it right. could someone give me a hand?
Cerberus:
Import mojo


Class MyGame Extends App
    Global GameState:String = "Menu"
    Global PlayerLife:Int
    Global PlayerScore:Int
    Global HiScore:Int
    Global GameTime:Int
    Field EndGameTime:Int
    Field Accuracy:Int
    Field PlaneShootNum:Int
    Field Menu:Image
    Field Instruction1:Image
    Field Instruction2:Image
    Field Background:Image
    Field Paused:Image
    Field Player:Plane
    Field Swarm_List:List<Swarm>
    Field Bullet_List:List<Bullet>
    

    

    Method OnUpdate()
    
        Select GameState
            Case "Menu"
                If KeyHit (KEY_1) Then GameState = "Initialise"
                If KeyHit (KEY_2) Then GameState = "Instruction1"
                If KeyHit (KEY_3) Then GameState = "Scoreboard"
                If KeyHit (KEY_4) Then GameState = "Exit"
            Case "Exit"
                Error("you have exited")
            Case "Initialise"
                GameState = "Playing"
            Case "Playing"
                If KeyHit(KEY_P) Then GameState = "Paused"
                If KeyHit(KEY_ENTER) Then GameState = "EndScore"
                If KeyHit(KEY_SPACE) Then Bullet_List.AddLast(New Bullet(Player.X,Player.Y))
                If KeyDown(KEY_A) Then Player.Movement(-6,0)
                If KeyDown(KEY_D) Then Player.Movement(6,0)
                If KeyDown(KEY_W) Then Player.Movement(0,-5)
                If KeyDown(KEY_S) Then Player.Movement(0,5)
                For Local Bullet:=Eachin Bullet_List
                    Bullet.Move(10)
                    If Bullet.Y < 5 Then Bullet_List.Remove Bullet
                Next
            Case "EndScore"
                If KeyHit(KEY_ENTER) Then GameState = "Scoreboard"
            Case "Scoreboard"
                If KeyHit(KEY_ENTER) Then GameState = "Menu"
            Case "Instruction1"
                If KeyHit(KEY_ENTER) Then GameState = "Instruction2"
            Case "Instruction2"
                If KeyHit(KEY_ENTER) Then GameState = "Menu"
            Case "Paused"
                If KeyHit(KEY_2) Then GameState = "Playing"
                If KeyHit(KEY_1) Then GameState = "Menu"
        End       
            
    End
    
    
    Method OnCreate()
        Bullet_List = New List<Bullet>
        Swarm_List = New List<Swarm>
        Swarm_List.AddLast(new Swarm(320,160))
        SetUpdateRate(60)
        Player = New Plane
        Menu = LoadImage("MenuScreen.png")
        Instruction1 = LoadImage("Instruction1.png")
        Instruction2 = LoadImage("Instruction2.png")
        Background = LoadImage("sea_background.png")
        Paused = LoadImage("PausedMenu.png")
    End
    
    
    Method OnRender()
        Cls(0,0,0)
        Select GameState
            Case "Menu"
                DrawImage(Menu,0,0)
            Case "Playing"
                DrawImage(Background,0,0)
                For Local Bullet:= Eachin Bullet_List
                    DrawImage(Bullet.BulletImage,Bullet.X,Bullet.Y)
                Next
                DrawImage(Player.PlayerImage,Player.X,Player.Y)
                For Local enemy:=Eachin Swarm_List
                    DrawImage (enemy.SwarmImage,enemy.X,enemy.Y)
                Next
                DrawText("SCORE"+" "+PlayerScore,8,15,0,0.5)
                DrawText("HI-SCORE"+" "+ HiScore, 320,15,0.5,0.5)
                DrawText("LIVES"+" "+PlayerLife,610,15,0.5,0.5)
            Case "EndScore"
                DrawText("GAME OVER",320,160,0.5,0.5)
                DrawText("SCORE"+" "+PlayerScore, 320,200,0.5,0.5)
                DrawText("HI-SCORE"+" "+HiScore,320,220,0.5,0.5)
                DrawText("PLANES SHOT DOWN"+" "+PlaneShootNum,320,240,0.5,0.5)
                DrawText("% ACCURACY"+" "+Accuracy+"%",320,260,0.5,0.5)
                DrawText("GAME TIME"+" "+EndGameTime,320,280,0.5,0.5)
            Case "Scoreboard"
                DrawText("This Is ScoreBoard",320,240,0.5,0.5)
            Case "Instruction1"
                DrawImage(Instruction1,0,0)
            Case "Instruction2"
                DrawImage(Instruction2,0,0)
            Case "Paused"
            DrawImage(Paused,0,0)
        End
    End
End


Class Plane
    Field PlayerImage:Image = LoadImage("Player.png")
    Field X:Int = 265
    Field Y:Int = 320
    
    Method Movement(X_distance:Int,Y_distance:Int)
    X = X + X_distance
    Y = Y + Y_distance
    If X <= -15 Then X = -15
    If X >= 535 Then X = 535
    If Y <=  60 Then Y = 60
    If Y >= 410 Then Y = 410
    End
End


Class Swarm
    Field SwarmImage:Image = LoadImage("SwarmPlane.png")
    Field X:Int
    Field Y:Int
    
    Method New(X_spawn:Int,Y_spawn:Int)
        X = X_spawn
        Y = Y_spawn
    End
End


Class Bullet
    Field X:Int
    Field Y:Int
    Field BulletImage:Image = LoadImage("Bullet.png",Image.MidHandle)
    
    Method New(X_spawn:Int,Y_spawn:Int)
    X = X_spawn + 37
    Y = Y_spawn - 5
    End
    
    Method Move(Y_distance:Int)
    Y = Y - Y_distance
    End
End


Function Main()
    New MyGame
End
 
Basically:

You'll need two nested loops that check all bullets against all swarms, pseudocode:
Cerberus:
For Local bullet := Eachin bullets
    For Local swarm := Eachin swarms
        If bullet.CollidesWithSwarm( swarm ) Then
            swarms.Remove( swarm )
        Endif
    Next
Next

Next up, you need to implement the CollidesWithSwarm( coll:Swarm ) method that takes a swarm and returns true if they collide. How you check for collision depends on your requirements. You can:
  • do a rectangle-overlap check, by checking if the right edge of the bullet is right of the left edge of the swarm, the left edge of the bullet left of the right edge of the swarm and so on.
  • do a distance check, by calculating the distance between the two objects using Pythagoras and comparing it against the sum of the two objects' radii
  • do some sort of polygon-overlap check

I usually go for the the Pythagoras approach. If your objects are very un-round, you can't use that. But for the start, go with that ;) for simplicity:
Cerberus:
Local dx := x - coll.x
Local dy := y - coll.y
Local dist := Sqrt( dx*dx + dy*dy )
If dist < SAVEDISTANCE Then Return True


Advanced:

Make a base class for all your object that can potentially collide with each other in the same way. This class has to provide fields for the position and collision radius. And the CollidesWith( coll:MyBaseClass ) method. Then all your Swarms and Bullets extend that base class and if you want to add a new class that must be able to collide with the other objects, that one too extends the base class.
 
Basically:

You'll need two nested loops that check all bullets against all swarms, pseudocode:
Cerberus:
For Local bullet := Eachin bullets
    For Local swarm := Eachin swarms
        If bullet.CollidesWithSwarm( swarm ) Then
            swarms.Remove( swarm )
        Endif
    Next
Next

Next up, you need to implement the CollidesWithSwarm( coll:Swarm ) method that takes a swarm and returns true if they collide. How you check for collision depends on your requirements. You can:
  • do a rectangle-overlap check, by checking if the right edge of the bullet is right of the left edge of the swarm, the left edge of the bullet left of the right edge of the swarm and so on.
  • do a distance check, by calculating the distance between the two objects using Pythagoras and comparing it against the sum of the two objects' radii
  • do some sort of polygon-overlap check

I usually go for the the Pythagoras approach. If your objects are very un-round, you can't use that. But for the start, go with that ;) for simplicity:
Cerberus:
Local dx := x - coll.x
Local dy := y - coll.y
Local dist := Sqrt( dx*dx + dy*dy )
If dist < SAVEDISTANCE Then Return True


Advanced:

Make a base class for all your object that can potentially collide with each other in the same way. This class has to provide fields for the position and collision radius. And the CollidesWith( coll:MyBaseClass ) method. Then all your Swarms and Bullets extend that base class and if you want to add a new class that must be able to collide with the other objects, that one too extends the base class.

Thanks man, I literally just coded it and it worked perfectly with a couple tweaks to fit my code. you were a massive help.
 
Back
Top Bottom