A Flash Developer Resource Site

Results 1 to 2 of 2

Thread: Vector collision detection for heroMc

  1. #1
    Junior Member
    Join Date
    Feb 2006
    Posts
    11

    Vector collision detection for heroMc

    Calculate the _y collision and previous _y and subtract them and add to the previous _y and place heroMc there.

  2. #2
    Junior Member
    Join Date
    Jan 2021
    Posts
    16
    Before we begin, we must understand what a vector is and how it works. A vector has two properties: a direction and a magnitude, and can be illustrated by drawing an arrow from point A to point B.
    The direction as you might have already guessed, is indicated by cheat here where the arrow is pointing. The length of the arrow is called its magnitude.
    For example, if we have an arrow pointing clockwise at a 45-degree angle of length 5 units, we say that its direction is northeast and it has a magnitude of 5. Each vector defines its location using x and y coordinates, and in a 3D space, we also have the element of depth: the z-axis.
    Through vectors, we can program and simulate motion.
    The location of an object on screen is a vector from the origin (0, 0) to its actual position in the physical or virtual space. Velocity is another vector that tells the object how to move from one point to another in a specific direction e.g. “move 3 units to the right and 5 units upwards” (3, -5).


    The algorithm for motion is simply adding the location and velocity vectors together!
    In Processing, we have the PVector data structure that has two floating-point properties: x and y. There is also the optional z property for 3D simulation. In its essence, it is just a convenient way to store two or three coordinate values.
    class PVector { float x;
    float y; PVector(float x, float y) {
    this.x = x;
    this.y = y;
    }}
    So let’s imagine that we have an object at (2, 5) on screen. And we want to move it to the right at a speed of 3 units. We can simply write it in this way.
    PVector location = new PVector(2, 5);
    PVector velocity = new PVector(3, 0);location.add(velocity); // new location is (5, 5)
    Vector addition simply adds the x-coordinates of both vectors together and does the same with the y-coordinates.


    An example of vector addition. As seen in The Nature of Code.
    Detecting Collisions
    Now that you know what a vector is and how motion works, we can look at how to detect a collision. After all, the whole point of this article is to create a colliding object.
    By default, an object cannot know if it has collided with something — even if it touches the bounds of our screen. Let us imagine that we want to turn our window into a collider. How can we do that?
    So far, we know that we can track an object’s position on screen using the location vector. And any pixel on screen has a location vector. Because technically, each pixel that makes up the window is an object!
    For example, if we wanted to get the location vector at the bottom right point of a window of size 640 by 360, we can express it as (640, 360). In a simple rectangular space, we have four conditions at which a collision can occur.
    1. The x-coordinate of our object is less than the starting point of our window. The object is at (x < 0, y).
    2. The y-coordinate of our object is less than the starting point of our window. The object is at (x, y < 0).
    3. The x-coordinate of our object is greater than the width of our window. The object is at (x > 640, y).
    4. The y-coordinate of our object is greater than the height of our window. The object is at (x, y > 360).
    In Processing, we can access the width and height of the screen using the global variables width and height respectively.
    Before we look at how this can be written in code, we need to define what goes on when the object detects a collision. For simplicity, we will model a simple bouncing ball without calculating real world factors such as gravity, friction and acceleration.
    Therefore, we can say that on collision, the object will bounce back in uniform fashion. To achieve this, we need to invert the direction at which the ball is travelling by multiplying the corresponding axis on the velocity vector by -1.
    void detectCollisions() { if (location.x < 0 || location.x > width) {
    velocity.x = velocity.x * -1;
    // ball now moves in opposite horizontal direction
    } if (location.y < 0 || location.y > height) {
    velocity.y = velocity.y * -1;
    // ball now moves in opposite vertical direction
    }}
    Now that we’ve had an overview on vectors and got an idea of how to simulate a collision, we are ready to create the real thing.
    Creating The Simulation
    Let’s look at the two main components we want to create in this program: a collider and a moving object.
    We want this to be a bit cooler than the ideas we’ve worked with so far so we will work in 3D space. For our collider, we’ll use a cube and our object will be a sphere.
    Processing has two main built-in methods, setup and draw. Inside the setup method, we usually initialise the variables we want to work with. During the lifecycle of our simulation, it will be called only once. On the other hand, the draw method gets called every frame, as it repaints the entire scene. Change in location and velocity must happen inside draw.
    Step 1: Creating The Collider Class
    First we’ll position the collider in the middle of our 3D workspace.
    class Box {
    private float _size;

    Box(float size) {
    _size = size;
    }

    float getRadius() {
    return _size / 2;
    }

    void drawBox() {
    translate(width/2, height/2, _size);
    rotateY(QUARTER_PI);

    noFill();
    stroke(255);

    box(_size);
    }
    }
    As we can see in the code snippet above, there are many things going on here. The Box has a property called size, which is used to define how big it is. It also has a getRadius getter method, which we will come into play during collision detection.
    The main method in this class is drawBox. Since we want to position it in the middle of our screen, we will set the x-axis to be half the width and the y-axis to be half the height.
    After that, we rotate by 45°, referenced by the global variable QUARTER_PI, on the y-axis to emphasise the 3D effect. This is entirely optional and can be omitted. Finally, we draw a transparent box with a white (255) outline and the size assigned in the constructor.
    Step 2: Creating The Moving Object
    The word “moving” should tell you enough. Vectors are coming into the mix here. This class will also handle the collision detection functionality we saw before.
    class Ball {
    private float _size;
    private PVector _location;

    Ball(float size) {
    _size = size;
    _location = new PVector();
    }

    void move(PVector velocity, float colliderSize) {
    _location.add(velocity); if (checkBounce(_location.x, colliderSize)) {
    velocity.x = velocity.x * -1;
    }

    if (checkBounce(_location.y, colliderSize)) {
    velocity.y = velocity.y * -1;
    }

    if (checkBounce(_location.z, colliderSize)) {
    velocity.z = velocity.z * -1;
    }
    }

    void drawBall() {
    translate(_location.x, _location.y, _location.z);

    fill(255);
    noStroke(); sphere(_size);
    }

    private boolean checkBounce(float coord, float colliderSize) {
    return
    coord > colliderSize - _size ||
    coord < _size - colliderSize;
    }
    }
    Our moving object has two properties: size and a location vector. Just like our collider, it needs to paint itself, but also move.
    The move method is familiar to us, because it includes the logic we’ve already explored to get an understanding of motion and collisions. Note that we’re also checking for collisions on the z-axis this time, since we’re in 3D.
    However, in this scenario, the collision bounds are the facets of the box, not the dimensions of the window. There are also two important points we need to keep in mind here that keep things simple.
    1. The moving object is starting from the middle of the screen.
    2. The colliding area is a cube, and thus we can assume that the radius is the same for all axes. This is the colliderSize in the code shown.
    Therefore, the collision conditions are:
    • The x/y/z-coordinate of the ball is less than the radius of the box minus the size of the ball.
    • The x/y/z-coordinate of the ball is greater than the radius of the box minus the size of the ball.
    Step 3: Putting It All Together
    Now we will take a look at the code that ties everything together.
    Box box;
    Ball ball;PVector velocity;void setup() {
    size(600, 600, P3D); box = new Box(200);
    ball = new Ball(20);

    velocity = new PVector(10, 5, 2);
    }void draw() {
    background(0); lights();
    ambientLight(255, 0, 0); box.drawBox(); ball.move(velocity, box.getRadius());
    ball.drawBall();
    }
    We start by declaring the size of the screen with a 3D space and initialise our collider and moving object. Additionally, we set a starting velocity vector.
    On each frame render, we repaint the background and lights. Next, we draw our collider, update the location of the ball by adding the velocity vector to the its location and check for collisions based on the collider’s radius. And finally, we draw the ball in its current location.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  




Click Here to Expand Forum to Full Width

HTML5 Development Center