#### Howdy, Stranger!

We are about to switch to a new forum software. Until then we have removed the registration on this forum.

# How to make a projectile get thrown by your character like it was thrown by a slingshot?

edited January 2017

Hello, I'm new here so excuse me if i do anything wrong. I'm trying to program a "Worms" like game, where you have a character in one side and you want to hit the other player in the other side of the map. I was trying to throw a projectile by clicking on my player1 body and then dragging the mouse back and releasing it so the projectile had a different angle and velocity depending on the position of the mouse in relation to the player 1 body. I'm using the box2D physiscs library in my project. If anyone could help me trying to understand how this would work i really appreciate it. Thank you.

Tagged:

• edited January 2017

Get the point of your first click on the character with mousePressed() and save the mouse coordinates(mouseX and mouseY) and then capture the point of release with mouseReleased(). By subtracting the former values from the latter you get the changes in x and y and can set the projectile speed accordingly.

• This might be a stupid question, but how can i save the mouse coordinates of the point when i use the mousePressed()? I'm still beggining so i lack a lot of basic knowlegde.

• Hello @andrecota

So,

o what angle would you apply for each thrown, is basic, that way you could try more attempts in the same place. o what initial speed would you apply for each thrown

If you have some code it'd be good in order to give some solutions

• edited January 2017
``````class Projectile {

Body body;

boolean overBox = false;
boolean locked = false;
float posx, posy;
float r;
Projectile(float x, float y, float r_, boolean fixed) {
r = r_;
x=posx;
y=posy;

BodyDef bd = new BodyDef();
if (fixed) bd.type= BodyType.STATIC;
else bd.type = BodyType.DYNAMIC;

bd.position = box2d.coordPixelsToWorld(x, y);
body = box2d.world.createBody(bd);

CircleShape cs = new CircleShape();

FixtureDef fd = new FixtureDef();
fd.shape = cs;

fd.density= 1;
fd.friction = 0.3;
fd.restitution = 0.5;

body.createFixture(fd);

body.setUserData(this);
}

void killBody() {
box2d.destroyBody(body);
}
boolean done() {
Vec2 pos = box2d.getBodyPixelCoord(body);
if ( pos.y > height+r*2) {
killBody();
return true;
}
if (pos.x > width+r*2) {
killBody();
return true;
}
return false;
}

void display() {
Vec2 pos = box2d.getBodyPixelCoord(body);
float a  = body.getAngle();
pushMatrix();
translate(pos.x, pos.y);
rotate(a);
stroke(0);
strokeWeight(1);
ellipse(0, 0, r*2, r*2);
popMatrix();
}

void mousePressed() {
Vec2 pos= box2d.getBodyPixelCoord(body);
}
void mouseDragged() {
//display projectil
}
void mouseReleased() {
//Vec2 imp = new Vec2
}

void shoot() {
Vec2 pos= box2d.getBodyPixelCoord(body);
Vec2 imp = new Vec2 (-mouseX-posx, -mouseY-posy);
imp.normalize();
imp.mulLocal(2);
body.applyLinearImpulse(imp, body.getWorldCenter(), true);
}
}
``````

And the player class:

``````class Player1 {

Body body;

float w;
float h;
boolean isPlayer1;
boolean active = true;

Player1(float x_, float y_) {
float x = x_;
float y = y_;
w = 25;
h = 35;

BodyDef bd = new BodyDef();

bd.type = BodyType.DYNAMIC;
bd.position.set(box2d.coordPixelsToWorld(x_, y_));

body = box2d.createBody(bd);

PolygonShape ps = new PolygonShape();
float box2Dw = box2d.scalarPixelsToWorld(w/2);
float box2Dh = box2d.scalarPixelsToWorld(h/2);
ps.setAsBox(box2Dw, box2Dh);

FixtureDef fd = new FixtureDef();
fd.shape = ps;

fd.density = 1;
fd.friction = 0.01;
fd.restitution = 0.3;

body.createFixture(fd);

body.setUserData(this);
}
void keyPressed() {
if(active == false){
return;
}
if (isPlayer1) {
switch (key) {
case('A'):
case('a'):
body.setLinearVelocity(new Vec2(-10, 0));
break;
case('d'):
case('D'):
body.setLinearVelocity(new Vec2(10, 0));
break;
case('S'):
case('s'):
body.setLinearVelocity(new Vec2(0, 0));
break;
case('W'):
case('w'):
body.setLinearVelocity(new Vec2(0, 30));
}
break;
}
} else {
switch (key) {
case('A'):
case('a'):
body.setLinearVelocity(new Vec2(-10, 0));
break;
case('d'):
case('D'):
body.setLinearVelocity(new Vec2(10, 0));
break;
case('S'):
case('s'):
body.setLinearVelocity(new Vec2(0, 0));
break;
case('W'):
case('w'):
body.setLinearVelocity(new Vec2(0, 30));
}
break;
}
}
}

void display() {
Vec2 pos = box2d.getBodyPixelCoord(body);
// float a = body.getAngle();
pushMatrix();
//rotate(-a);
translate(pos.x, pos.y);
fill(127);
stroke(0);
strokeWeight(2);
rectMode(CENTER);
rect(0, 0, w, h);
popMatrix();
}
void displaynew() {
body.setLinearVelocity(new Vec2(X, Y));
}
}
``````

But i havent implemented anything sucessfully in the main tab.

You could do something like this

``````int mouseXPrevious;
int mouseYPrevious;

void MousePressed() {
mouseXPrevious = mouseX;
mouseYPrevious = mouseY;
}
void mouseReleased() {
xChange = mouseX - mouseXPrevious;
yChange = mouseY - mouseYPrevious;
}
``````
• @andrecota Please format your code. Edit post, select code and hit ctrl+o. Ensure there is an empty line above and below your code.

@Sayid Your example is valid. To clarify, there are processing variables already tracking previous mouse coordinates: pmouseX and pmouseY:

Kf

• Ok i formated it

• You need to provide a minimum running code showing your challenge. In addition, there are classes definitions missing in the code you provided: Body and Vec2.

Kf

• To clarify, there are processing variables already tracking previous mouse coordinates: pmouseX and pmouseY.

I don't see the use of that - pmouseX and pmouseY change every time in draw (at least they will if they can), and also each time a mouse event is called.