I am new to Box2D. I am just trying to follow a simple tutorial, but trying to integrate it inside my code:
I start creating my Libgdx game:
public void create() {
float w = Gdx.graphics.getWidth();
float h = Gdx.graphics.getHeight();
camera = new OrthographicCamera(w, h, 0);
camera.position.set(camera.viewportWidth * .5f, camera.viewportHeight * .5f, 0f);
camera.update();
batch = new SpriteBatch();
viewSwitcher("GameScreen",null);
}
The call to viewSwitcher, creates a new object, which creates a new Screen:
public GameScreenController(SomeGame t, String id) {
somegame = t;
db = t.getDB();
world = new World(new Vector2(0, -20), true);
screen = new GameScreen(this);
[. . .]
}
Inside the Game Screen (which extends Screen class) I have the render method:
#Override
public void render(float delta) {
debugRenderer.render(world, camera.combined);
world.step(BOX_STEP, BOX_VELOCITY_ITERATIONS, BOX_POSITION_ITERATIONS);
stage.act(delta);
//stage.draw();
}
Finally, a Timer, creates periodically new objects. Inside the constructor of these objects, I have the creation of the bodyDef:
public void createBodyLetter() {
BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyType.DynamicBody;
bodyDef.position.set(200, 200);
Body body = controller.getWorld().createBody(bodyDef);
PolygonShape dynamicBox = new PolygonShape();
dynamicBox.setAsBox(1.0f, 1.0f);
FixtureDef fixtureDef = new FixtureDef();
fixtureDef.shape = dynamicBox;
fixtureDef.density = 1.0f;
fixtureDef.friction = 0.3f;
body.createFixture(fixtureDef);
dynamicBox.dispose();
}
The result when I start the program is just a black screen. Do anyone know where is the problem?
Thank you
initialize camera as
camera = new OrthographicCamera(w, h);
the third parameter you have given is the diamond angle which would be causing problem for you
Check the javadoc on this link
http://libgdx.badlogicgames.com/nightlies/docs/api/com/badlogic/gdx/graphics/OrthographicCamera.html#OrthographicCamera(float, float, float)
Related
I'm a newbie in libgdx and working on a simple 2d game and I want that my box2d world(or background) move with the input touch(move upward when I press the button) but I don't know how to move the world and place my player on the center. I want to know:
How to move my world with the input control.
Place my player in the center.
and also it looks like that my player is moving whenever I play that game, not the world.
if you can just provide an example with your answer.
so, Here is my code
public void show() {
world = new World(new Vector2(0, 25), true);
renderer = new Box2DDebugRenderer();
cam = new OrthographicCamera(Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
/* cam.position.set(Gdx.graphics.getWidth() / 2, Gdx.graphics.getHeight() / 2, 0);
cam.update();*/
shapeRenderer = new ShapeRenderer();
batch = new SpriteBatch();
texture = new Texture("img/imgs.png");
sprite = new Sprite(texture);
sprite.setSize(10, 10);
sprite.setOrigin(sprite.getWidth() / 2, sprite.getHeight() / 2);
sprite.setPosition(Gdx.graphics.getWidth()/2, Gdx.graphics.getHeight()/2);
//sprite.setBounds(200, 200, 64, 64);
//sprite.setPosition(Gdx.graphics.getWidth()/2 -sprite.getWidth()/2, Gdx.graphics.getHeight()/2-sprite.getHeight()/2);
/* //Body definition
BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyDef.BodyType.DynamicBody;
bodyDef.position.set(0, Gdx.graphics.getHeight() / 2 - 250);
box = world.createBody(bodyDef);
//Polygon Shape
PolygonShape shape = new PolygonShape();
shape.setAsBox(10, 20);
//fixture definition
FixtureDef fixtureDef = new FixtureDef();
fixtureDef.shape = shape;
fixtureDef.density = 5f;
fixtureDef.friction = .5f;
box.createFixture(fixtureDef);
box.setUserData(sprite);
shape.dispose();
*/ }
#Override
public void render(float delta) {
Gdx.gl.glClearColor(1, 1, 1, 1);
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
world.step(1 / 60f, 6, 2);
cam.translate(0, 12);
cam.update();
batch.setProjectionMatrix(cam.combined);
if(Gdx.input.isKeyPressed(Input.Keys.A))
spriteY += Gdx.graphics.getDeltaTime() * spriteSpeed;
if(Gdx.input.isKeyPressed(Input.Keys.D))
spriteY += Gdx.graphics.getDeltaTime() * sprite1Speed;
batch.begin();
batch.draw(sprite, spriteX, spriteY);
batch.end();
shapeRenderer.setColor(Color.RED);
shapeRenderer.begin(ShapeRenderer.ShapeType.Filled);
shapeRenderer.rect(0, 200, 50, 50);
shapeRenderer.translate(1, 0, 0);
shapeRenderer.end();
}
#Override
public void resize(int width, int height) {
cam.viewportWidth = width;
cam.viewportHeight = height;
cam.update();
}
#Override
public void pause() {
}
#Override
public void resume() {
}
#Override
public void hide() {
dispose();
}
#Override
public void dispose() {
//world.dispose();
shapeRenderer.dispose();
batch.dispose();
}
}
Sorry, for the mess(I'm a novice) in code and I want that my world moves upwards with input controls and my sprite just placed in the center.
Thank you in advance.
Your question sounds like you want to create a platformer or kinda.
I'll let you know that the best way to build your logic on when creating a (2d) platformer game is your character should always keep it's position the same and the background and other solid objects should move towards the player (based on input controls or automatic) so giving the look like your player is naturally moving and the background & objects appear in his way.
My answer is pretty general as your question is pretty general. If you need code you must provide us code so we know where you're stuck. Good luck :)
Like my question says can someone tell me, why does my circle texture/sprite are acting like a rectangle ?
Code:
`
#Override
public void create() {
batch = new SpriteBatch();
img = new Texture("ball.png");
sprite = new Sprite(img);
sprite.setPosition(-sprite.getWidth()/2,-sprite.getHeight()/2);
world = new World(new Vector2(0, -1f),true);
BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyDef.BodyType.DynamicBody;
bodyDef.position.set((sprite.getX() + sprite.getWidth()/2) /
PIXELS_TO_METERS,
(sprite.getY() + sprite.getHeight()/2) / PIXELS_TO_METERS);
body = world.createBody(bodyDef);
PolygonShape shape = new PolygonShape();
shape.setAsBox(sprite.getWidth()/2 / PIXELS_TO_METERS, sprite.getHeight()
/2 / PIXELS_TO_METERS);
FixtureDef fixtureDef = new FixtureDef();
fixtureDef.shape = shape;
fixtureDef.density = 0.1f;
fixtureDef.restitution = 0.8f;
body.createFixture(fixtureDef);
shape.dispose();
//CONTINUE
// BOTTOM
BodyDef bodyDefBottom = new BodyDef();
bodyDefBottom.type = BodyDef.BodyType.StaticBody;
float w = Gdx.graphics.getWidth()/PIXELS_TO_METERS;
// Set the height to just 50 pixels above the bottom of the screen so we can see the edge in the
// debug renderer
float h = Gdx.graphics.getHeight()/PIXELS_TO_METERS- 50/PIXELS_TO_METERS;
bodyDefBottom.position.set(0,0);
FixtureDef fixtureDef2 = new FixtureDef();
EdgeShape edgeShape = new EdgeShape();
edgeShape.set(-w/2,-h/2,w/2,-h/2);
fixtureDef2.shape = edgeShape;
bodyEdgeScreenBottom = world.createBody(bodyDefBottom);
bodyEdgeScreenBottom.createFixture(fixtureDef2);
edgeShape.dispose();
// TOP
BodyDef bodyDefTop = new BodyDef();
bodyDefTop.type = BodyDef.BodyType.StaticBody;
w = Gdx.graphics.getWidth()/PIXELS_TO_METERS;
// Set the height to just 50 pixels above the bottom of the screen so we can see the edge in the
// debug renderer
h = Gdx.graphics.getHeight()/PIXELS_TO_METERS;
bodyDefTop.position.set(0,0);
fixtureDef2 = new FixtureDef();
edgeShape = new EdgeShape();
edgeShape.set(-w/2,h/2,w/2,h/2);
fixtureDef2.shape = edgeShape;
bodyEdgeScreenTop = world.createBody(bodyDefTop);
bodyEdgeScreenTop.createFixture(fixtureDef2);
edgeShape.dispose();
// LEFT
BodyDef bodyDefLeft = new BodyDef();
bodyDefLeft.type = BodyDef.BodyType.StaticBody;
w = Gdx.graphics.getWidth()/PIXELS_TO_METERS;
// Set the height to just 50 pixels above the bottom of the screen so we can see the edge in the
// debug renderer
h = Gdx.graphics.getHeight()/PIXELS_TO_METERS;
bodyDefLeft.position.set(0,0);
fixtureDef2 = new FixtureDef();
edgeShape = new EdgeShape();
edgeShape.set(w/2,-h/2,w/2,h/2);
fixtureDef2.shape = edgeShape;
bodyEdgeScreenLeft = world.createBody(bodyDefLeft);
bodyEdgeScreenLeft.createFixture(fixtureDef2);
edgeShape.dispose();
// RIGHT
BodyDef bodyDefRight = new BodyDef();
bodyDefRight.type = BodyDef.BodyType.StaticBody;
w = Gdx.graphics.getWidth()/PIXELS_TO_METERS;
// Set the height to just 50 pixels above the bottom of the screen so we can see the edge in the
// debug renderer
h = Gdx.graphics.getHeight()/PIXELS_TO_METERS;
bodyDefRight.position.set(0,0);
fixtureDef2 = new FixtureDef();
edgeShape = new EdgeShape();
edgeShape.set(-w/2,-h/2,-w/2,h/2);
fixtureDef2.shape = edgeShape;
bodyEdgeScreenRight = world.createBody(bodyDefRight);
bodyEdgeScreenRight.createFixture(fixtureDef2);
edgeShape.dispose();
//CONTINUE
Gdx.input.setInputProcessor(this);
//debugRenderer = new Box2DDebugRenderer();
font = new BitmapFont();
font.setColor(Color.BLACK);
camera = new OrthographicCamera(Gdx.graphics.getWidth(),Gdx.graphics.
getHeight());
}
private float elapsed = 0;
#Override
public void render() {
camera.update();
// Step the physics simulation forward at a rate of 60hz
world.step(1f / 60f, 6, 2);
body.applyTorque(torque, true);
sprite.setPosition((body.getPosition().x * PIXELS_TO_METERS) - sprite.
getWidth() / 2,
(body.getPosition().y * PIXELS_TO_METERS) - sprite.getHeight() / 2)
;
sprite.setRotation((float) Math.toDegrees(body.getAngle()));
Gdx.gl.glClearColor(1, 1, 1, 1);
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
batch.setProjectionMatrix(camera.combined);
//debugMatrix = batch.getProjectionMatrix().cpy().scale(PIXELS_TO_METERS,
// PIXELS_TO_METERS, 0);
batch.begin();
if(drawSprite)
batch.draw(sprite, sprite.getX(), sprite.getY(),sprite.getOriginX(),
sprite.getOriginY(),
sprite.getWidth(),sprite.getHeight(),sprite.getScaleX(),sprite.
getScaleY(),sprite.getRotation());
font.draw(batch,
"Restitution: " + body.getFixtureList().first().getRestitution(),
-Gdx.graphics.getWidth()/2,
Gdx.graphics.getHeight()/2 );
batch.end();
//debugRenderer.render(world, debugMatrix);
}
#Override
public void dispose() {
img.dispose();
world.dispose();
}
#Override
public boolean keyDown(int keycode) {
return false;
}
#Override
public boolean keyUp(int keycode) {
return false;
}
#Override
public boolean keyTyped(char character) {
return false;
}
// On touch we apply force from the direction of the users touch.
// This could result in the object "spinning"
#Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {
body.applyForce(1f,1f,screenX,screenY,true);
//body.applyTorque(0.4f,true);
return true;
}
#Override
public boolean touchUp(int screenX, int screenY, int pointer, int button) {
return false;
}
#Override
public boolean touchDragged(int screenX, int screenY, int pointer) {
return false;
}
#Override
public boolean mouseMoved(int screenX, int screenY) {
return false;
}
#Override
public boolean scrolled(int amount) {
return false;
}
`
I have tried searching for other posts but couldn't find anything that explains to me why it is acting like a rectangle and how to resolve this. I have also tried searching for other methods to draw the texture , even using CircleShape but that cannot put inside texture from image. I'm pretty newbie in libgdx, I'm still learning everyday.
I'm little confused... You are creating PolygonShape and expecting it will behave as circle?
PolygonShape shape = new PolygonShape();
shape.setAsBox(...
All you can achieve this way is polygon with ball sprite inside. If you want to have a circle use mentioned by you CircleShape
CircleShape shape = new CircleShape();
shape.setRadius(1); //or anything you need
...
//assing it to the fixture etc
then update it when drawing with its position and angle - that's all
Hy guys,
I am developing a game for android using libgdx. I am completely stuck at the part of detecting collision between two bodies.
I have a player which I create through the function below
public Body createPlayer(String file_path, String fixture_name) {
// 0. Create a loader for the file saved from the editor.
BodyEditorLoader loader = new BodyEditorLoader(Gdx.files.internal(file_path));
// 1. Create a BodyDef, as usual.
BodyDef bd = new BodyDef();
bd.type = BodyDef.BodyType.DynamicBody;
// 2. Create a FixtureDef, as usual.
FixtureDef fd = new FixtureDef();
fd.density = 1;
fd.friction = 0.5f;
fd.restitution = 0.3f;
// 3. Create a Body, as usual.
body= world.createBody(bd);
//body.setBullet(true);
// 4. Create the body fixture automatically by using the loader.
loader.attachFixture(body, fixture_name, fd, 1);
body.setUserData(this);
return body;
}
and an enemy that I create with the same function of the player where I change only the file_path and the fixture_name.
The file_path points to a .json file that I created with box2d editor (site: http://www.aurelienribon.com/blog/projects/physics-body-editor/).
After the creation of the body I draw the player and the enemy with two similar functions ( I only post one):
private void drawPlayer(){
player_sprite = new Sprite(player_TR);
player_sprite.setSize(player.getWidth(), player.getHeight());
player_sprite.setPosition(player.getX(), player.getY());
player_sprite.setOrigin(0, 0);
player_sprite.draw(sb);
}
If I start the game everything is drawn where it should be. Obviously if the player touches the enemy nothing happen.
So i started trying to search how to make the two bodies collides but I don't really understand how to use ContactListener and beginContact.
beginContact wants as input a Contact but what is a Contact?
I have found this code online which appears to solve my problem but I don't know how to use it:
worldbox.setContactListener(new ContactListener() {
#Override
public void beginContact(Contact contact) {
if(contact.getFixtureA().getBody().getUserData()== "body1" &&
contact.getFixtureB().getBody().getUserData()== "body2")
Colliding = true;
System.out.println("Contact detected");
}
Can you help me (if it is possible through some code) to solve my problem?
Thanks in advance,
Francesco
Update of my question
Here is my render method:
public class GameRenderer{
private GameWorld myWorld;
private ShapeRenderer shapeRenderer;
private SpriteBatch sb;
private Camera camera;
private Constants constant;
private Rectangle viewport;
//dichiaro le variabili per caricare gli asset
private Player player;
private ScrollHandler scroller;
private Bordo frontBordoSX_1, backBordoSX_1, frontBordoSX_2, backBordoSX_2;
private Bordo frontBordoDX_1, backBordoDX_1, frontBordoDX_2, backBordoDX_2;
/*
private Ostacolo ob1_sx, ob2_sx, ob3_sx;
private Ostacolo ob4_dx, ob5_dx, ob6_dx;
*/
private TextureRegion player_TR;
private TextureRegion bordoSX_1, bordoSX_2;
private TextureRegion bordoDX_1, bordoDX_2;
private TextureRegion obstacleSX, obstacleSX_flip;
private TextureRegion obstacleDX, obstacleDX_flip;
private TextureRegion enemyS;
private TextureRegion blackBar;
//box2dpart
private World worldbox;
private Sprite fbDx_1,fbDx_2,fbSx_1,fbSx_2;
private Sprite player_sprite;
private Body player_body, bordo_destro;
private MyContactListener contactListener;
public GameRenderer(GameWorld world) {
myWorld = world;
constant = new Constants();
camera = new OrthographicCamera(constant.getWidth(), constant.getHeight());
shapeRenderer = new ShapeRenderer();
shapeRenderer.setProjectionMatrix(camera.combined);
sb = new SpriteBatch();
sb.setProjectionMatrix(camera.combined);
contactListener = new MyContactListener();
worldbox= new World(new Vector2(0,-10),true);
worldbox.setContactListener(contactListener);
//initialize objects and assets
initGameObjects();
initAssets();
}
private void initGameObjects(){
player = myWorld.getPlayer();
scroller = myWorld.getScroller();
frontBordoSX_1 = scroller.getFrontBordoSX_1();
backBordoSX_1 = scroller.getBackBordoSX_1();
frontBordoSX_2 = scroller.getFrontBordoSX_2();
backBordoSX_2 = scroller.getBackBordoSX_2();
frontBordoDX_1 = scroller.getFrontBordoDX_1();
backBordoDX_1 = scroller.getBackBordoDX_1();
frontBordoDX_2 = scroller.getFrontBordoDX_2();
backBordoDX_2 = scroller.getBackBordoDX_2();
/* other objects
ob1_sx = scroller.getOb1_sx();
ob2_sx = scroller.getOb2_sx();
ob3_sx = scroller.getOb3_sx();
ob4_dx = scroller.getOb4_dx();
ob5_dx = scroller.getOb5_dx();
ob6_dx = scroller.getOb6_dx();
*/
}
private void initAssets(){
player_TR = AssetLoader.player;
bordoSX_1 = AssetLoader.bordoSX;
bordoSX_2 = AssetLoader.bordoSX;
bordoDX_1 = AssetLoader.bordoDX;
bordoDX_2 = AssetLoader.bordoDX;
obstacleDX = AssetLoader.obstacleDX;
obstacleSX = AssetLoader.obstacleSX;
obstacleDX_flip = AssetLoader.obstacleDX_flip;
obstacleSX_flip = AssetLoader.obstacleSX_flip;
enemyS = AssetLoader.enemyS;
blackBar = AssetLoader.blackBar;
//box2d part
}
private void drawMargin(){
//bordo SX
/*
sb.draw(bordoSX_1, frontBordoSX_2.getX(), frontBordoSX_2.getY(), frontBordoSX_2.getWidth(),
frontBordoSX_2.getHeight());
sb.draw(bordoSX_2, frontBordoSX_1.getX(), frontBordoSX_1.getY(), frontBordoSX_1.getWidth(),
frontBordoSX_1.getHeight());
*/
fbSx_1 = new Sprite(bordoSX_1);
fbSx_1.setSize(frontBordoSX_1.getWidth(),frontBordoSX_1.getHeight());
fbSx_1.setPosition(frontBordoSX_1.getX(), frontBordoSX_1.getY());
fbSx_1.setOrigin(0, 0);
fbSx_1.draw(sb);
fbSx_2 = new Sprite(bordoSX_2);
fbSx_2.setSize(frontBordoSX_2.getWidth(),frontBordoSX_2.getHeight());
fbSx_2.setPosition(frontBordoSX_2.getX(), frontBordoSX_2.getY());
fbSx_2.setOrigin(0, 0);
fbSx_2.draw(sb);
fbDx_1 = new Sprite(bordoDX_1);
fbDx_1.setSize(frontBordoDX_1.getWidth(),frontBordoDX_1.getHeight());
fbDx_1.setPosition(frontBordoDX_1.getX(), frontBordoDX_1.getY());
fbDx_1.setOrigin(0, 0);
fbDx_1.draw(sb);
fbDx_2 = new Sprite(bordoDX_2);
fbDx_2.setSize(frontBordoDX_2.getWidth(),frontBordoDX_2.getHeight());
fbDx_2.setPosition(frontBordoDX_2.getX(), frontBordoDX_2.getY());
fbDx_2.setOrigin(0, 0);
fbDx_2.draw(sb);
sb.draw(blackBar,-constant.getWidth()/2,-constant.getHeight()/2,
(float) (0.573913)*(constant.getWidth()/6),constant.getHeight());
sb.draw(blackBar,(float)(constant.getWidth()/2-(0.573913)*(constant.getWidth()/6)),-constant.getHeight()/2,
(float)(0.573913)*(constant.getWidth()/6),constant.getHeight());
}
private void drawPlayer(){
player_sprite = new Sprite(player_TR);
player_sprite.setSize(player.getWidth(), player.getHeight());
player_sprite.setPosition(player.getX(), player.getY());
player_sprite.setOrigin(0, 0);
player_sprite.draw(sb);
}
/*
private void drawOstacoli(){
sb.draw(obstacleSX_flip,ob1_sx.getX(),ob1_sx.getY(),ob1_sx.getWidth(),ob1_sx.getHeight());
sb.draw(obstacleSX,ob2_sx.getX(),ob2_sx.getY(),ob2_sx.getWidth(),ob2_sx.getHeight());
sb.draw(obstacleSX_flip,ob3_sx.getX(),ob3_sx.getY(),ob3_sx.getWidth(),ob3_sx.getHeight());
sb.draw(obstacleDX,ob4_dx.getX()+constant.getWidth()/2-ob4_dx.getWidth(),ob4_dx.getY(),ob4_dx.getWidth(),ob4_dx.getHeight());
sb.draw(obstacleDX_flip,ob5_dx.getX()+constant.getWidth()/2-ob5_dx.getWidth(),ob5_dx.getY(),ob5_dx.getWidth(),ob5_dx.getHeight());
sb.draw(obstacleDX,ob6_dx.getX()+constant.getWidth()/2-ob6_dx.getWidth(),ob6_dx.getY(),ob6_dx.getWidth(),ob6_dx.getHeight());
}
*/
public void render(float runTime) {
Box2D.init();
int width = constant.getWidth();
int height = constant.getHeight();
float ratio = constant.getRatio();
//viewport
float aspectRatio = (float) width / (float) height;
float scale = 1f;
Vector2 crop = new Vector2(0f, 0f);
if(aspectRatio > ratio)
{
scale = (float)height/(float)height;
crop.x = (width - width * scale) / 2f;
} else if (aspectRatio < ratio) {
scale = (float)width/(float)width;
crop.y = (height - height*scale)/2f;
}
else
{
scale = (float) width / (float) width;
}
float w = (float) width * scale;
float h = (float) height * scale;
viewport = new Rectangle(crop.x, crop.y, w, h);
// update camera
camera.update();
// clear previous frame
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
shapeRenderer.begin(ShapeRenderer.ShapeType.Filled);
// Draw Background color
shapeRenderer.setColor(255 / 255.0f, 255 / 255.0f, 250 / 255.0f, 1);
shapeRenderer.rect(-constant.getWidth() / 2, -constant.getHeight() / 2, constant.getWidth(),
constant.getHeight());
// End ShapeRenderer
shapeRenderer.end();
// set viewport
Gdx.gl.glViewport((int) viewport.x, (int) viewport.y,
(int) viewport.width, (int) viewport.height);
// Begin SpriteBatch
sb.begin();
// The player needs transparency, so we enable that again.
sb.enableBlending();
// Draw player at its coordinates.
drawPlayer();
//draw right and left side
drawMargin();
// End SpriteBatch
sb.end();
worldbox.step(1 / 60f, 6, 2);
}
}
And if I start the program my view is my player in the middle and to margins ,one on the left and one on the right. (unfortunatly I cannot post images of my view because I don't have enough rep).
Everithing is fine. I move my player with the accelerometer and it works fine without any problem. The only problem is that if I move the player near the margin the two entities overlap instead of colliding and I don't understand why.
I also fixed the line:
loader.attachFixture(body, fixture_name, fd, 1);
to
loader.attachFixture(body, fixture_name, fd, player_width);
but nothing changes.
First, from here, the object Contact manages contact between two shapes, and from here, the listener ContactListener will be called when two fixtures begin to touch.
So, to make your code work, you should set a custom object to your bodies with the method: setUserData(Object userData). Usually this method is used to link the sprite or the actor with the physic body, but for example purpose you could just send a simple ID (like a string).
So in this part:
// 3. Create a Body, as usual.
body= world.createBody(bd);
//body.setBullet(true);
You could add an identificator to your object like this:
body.setUserData("player");
to idenfity your object, and then, when the listener get fired, you could retrieve this value:
#Override
public void beginContact(Contact contact) {
String userDataA = contact.getFixtureA().getBody().getUserData().toString();
String userDataB = contact.getFixtureB().getBody().getUserData().toString();
if(userDataA.equals("player") && userDataB.equals("otherEntity")){
colliding = true;
//do stuffs when collision has started
} else if(userDataB.equals("player") && userDataA.equals("otherEntity")){
colliding = true;
//do stuffs when collision has started
}
System.out.println("Contact detected");
}
After that, you could be able to do whatever you want to do with this collision.
Hope you find this useful!
i'm fairly new to libgdx in general. Basically I have the ball bouncing world and i am just experimenting with it. Before I had a fixed camera position as such:
http://prntscr.com/567hvo
After I have putted the following line in the render method so the camera keeps following the player (which is the circle) :
camera.position.set(player.getPosition().x, player.getPosition().y, 0);
The player is a Body type.
So when I do this it does follow the player, but the shape renderer acts weird now. Look at what happens:
http://prntscr.com/567i9a
Even though I am referring to the same x and y position of the player to the camera and the shape renderer, they are not in the same position.
Here is my code:
public class Game extends ApplicationAdapter {
World world = new World(new Vector2(0, -9.8f), true);
Box2DDebugRenderer debugRenderer;
OrthographicCamera camera;
static final int PPM = 100;
static float height,width;
Body player;
RayHandler handler;
PointLight l1;
ShapeRenderer shapeRenderer;
#Override
public void create() {
shapeRenderer = new ShapeRenderer();
height = Gdx.graphics.getHeight();
width = Gdx.graphics.getWidth();
//set camera
camera = new OrthographicCamera();
camera.setToOrtho(false, (width)/PPM/2, (height)/PPM/2);
camera.update();
//Ground body
BodyDef groundBodyDef =new BodyDef();
groundBodyDef.position.set(new Vector2(width/PPM/2/2, 0));
Body groundBody = world.createBody(groundBodyDef);
PolygonShape groundBox = new PolygonShape();
groundBox.setAsBox((width/PPM/2/2), 0.1f);
groundBody.createFixture(groundBox, 0.0f);
//wall left
BodyDef wallLeftDef = new BodyDef();
wallLeftDef.position.set(0, 0f);
Body wallLeftBody = world.createBody(wallLeftDef);
PolygonShape wallLeft = new PolygonShape();
wallLeft.setAsBox(width/PPM/20/2, height/PPM/2);
wallLeftBody.createFixture(wallLeft,0.0f);
//wall right
BodyDef wallRightDef = new BodyDef();
wallRightDef.position.set((width/PPM)/2, 0f);
Body wallRightBody = world.createBody(wallRightDef);
PolygonShape wallRight = new PolygonShape();
wallRight.setAsBox(width/PPM/20/2, height/PPM/2);
wallRightBody.createFixture(wallRight,0.0f);
//Dynamic Body
BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyType.DynamicBody;
bodyDef.position.set((width/PPM)/2/2, (height / PPM)/2/2);
player = world.createBody(bodyDef);
CircleShape dynamicCircle = new CircleShape();
dynamicCircle.setRadius(5f/PPM);
FixtureDef fixtureDef = new FixtureDef();
fixtureDef.shape = dynamicCircle;
fixtureDef.density = 0.4f;
fixtureDef.friction = 0.2f;
fixtureDef.restitution = 0.6f;
player.createFixture(fixtureDef);
debugRenderer = new Box2DDebugRenderer();
//Lighting
handler = new RayHandler(world);
handler.setCombinedMatrix(camera.combined);
PointLight l1 = new PointLight(handler,5000,Color.CYAN,width/PPM/2,width/PPM/2/2/2,height/PPM/2/2);
new PointLight(handler,5000,Color.PURPLE,width/PPM/2,width/PPM/2/1.5f,height/PPM/2/2);
shapeRenderer.setProjectionMatrix(camera.combined);
}
public void update() {
if(Gdx.input.isKeyJustPressed(Keys.UP)) {
player.applyForceToCenter(0, 0.75f, true);
}
if(Gdx.input.isKeyJustPressed(Keys.RIGHT)) {
player.applyForceToCenter(0.5f, 0f, true);
}
if(Gdx.input.isKeyJustPressed(Keys.LEFT)) {
player.applyForceToCenter(-0.5f, 0f, true);
}
}
#Override
public void dispose() {
}
#Override
public void render() {
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
debugRenderer.render(world, camera.combined);
world.step(1/60f, 6, 2);
handler.updateAndRender();
shapeRenderer.begin(ShapeType.Filled);
shapeRenderer.setColor(1, 1, 1, 1);
shapeRenderer.circle(player.getPosition().x, player.getPosition().y, 5f/PPM, 100);
shapeRenderer.end();
camera.position.set(player.getPosition().x, player.getPosition().y, 0);
camera.update();
update();
}
#Override
public void resize(int width, int height) {
}
#Override
public void pause() {
}
#Override
public void resume() {
}
}
You are only setting the shapeRenderers projectionmatrix once so it is not updating when you render.
You should put
shapeRenderer.setProjectionMatrix(camera.combined);
to your render method right before
shapeRenderer.begin(ShapeType.Filled);
i'm trying to make a program with Box2D and libgdx that makes the character jump on a static body (here, a circle). But my camera (that is following the dynamic body (the player)) keeps going down, even if my character stays on top of the circle as intended. So my questions are :
1) Why my camera keeps falling down, when it's supposed to follow the "playerBody" that is staying on top of the static body ?
2) Why my camera bounce when I press the Z key, but not my playerbody ?
Thanks in advance. You may try to run it in eclipse, to see better what I mean, here's what I put in my Activity class :
(I got no errors/warnings at all.)
//private SpriteBatch batch;
//private Texture texture;
//private Sprite sprite;
//public Body body;
World world;
Body playerBody;
Body planetBody;
CircleShape planetCircle;
PolygonShape playerBox;
OrthographicCamera camera;
Box2DDebugRenderer debugRenderer;
static final float BOX_STEP=1/60f;
static final int BOX_VELOCITY_ITERATIONS=6;
static final int BOX_POSITION_ITERATIONS=2;
static final float WORLD_TO_BOX=0.01f;
static final float BOX_WORLD_TO=100f;
boolean jump = false;
long lastGroundTime = 0;
#Override
public void create() {
world = new World(new Vector2(0, -50), true);
debugRenderer = new Box2DDebugRenderer();
camera = new OrthographicCamera();
camera.viewportHeight = 320;
camera.viewportWidth = 480;
camera.position.set(camera.viewportWidth * .5f, camera.viewportHeight * .5f, 0f);
camera.update();
//Ground body
/*BodyDef groundBodyDef =new BodyDef();
groundBodyDef.position.set(camera.viewportWidth / 2, camera.viewportHeight / 2 - 100 + 125);
Body groundBody = world.createBody(groundBodyDef);
PolygonShape groundBox = new PolygonShape();
groundBox.setAsBox((camera.viewportWidth) * 2, 10.0f);
groundBody.createFixture(groundBox, 0.0f);
*/
//Planet
BodyDef planetDef = new BodyDef();
planetDef.type = BodyType.StaticBody;
planetDef.position.set(camera.viewportWidth / 2, camera.viewportHeight / 2 - 100);
Body planetBody = world.createBody(planetDef);
CircleShape planetCircle = new CircleShape();
planetCircle.setRadius(125f);
FixtureDef planetFixtureDef = new FixtureDef();
planetFixtureDef.shape = planetCircle;
planetFixtureDef.density = 1.0f;
//planetFixtureDef.friction = 0.0f;
//planetFixtureDef.restitution = 0;
planetBody.createFixture(planetFixtureDef);
//Player
BodyDef playerBodyDef = new BodyDef();
playerBodyDef.type = BodyType.DynamicBody;
playerBodyDef.position.set(camera.viewportWidth / 2, camera.viewportHeight / 2 - 100 + 125 + 50);
playerBody = world.createBody(playerBodyDef);
PolygonShape playerBox = new PolygonShape();
playerBox.setAsBox(5.0f, 15.0f);
FixtureDef playerFixtureDef = new FixtureDef();
playerFixtureDef.shape = playerBox;
playerFixtureDef.density = 1.0f;
//playerFixtureDef.friction = 1.0f;
//playerFixtureDef.restitution = 1;
playerBody.createFixture(playerFixtureDef);
playerBody = world.createBody(playerBodyDef);
//Dynamic Body
/*BodyDef bodyDef = new BodyDef();
bodyDef.type = BodyType.DynamicBody;
bodyDef.position.set(camera.viewportWidth / 2, camera.viewportHeight / 2);
Body body = world.createBody(bodyDef);
CircleShape dynamicCircle = new CircleShape();
dynamicCircle.setRadius(5f);
FixtureDef fixtureDef = new FixtureDef();
fixtureDef.shape = dynamicCircle;
fixtureDef.density = 1.0f;
fixtureDef.friction = 0.0f;
fixtureDef.restitution = 1;
body.createFixture(fixtureDef); */
Gdx.input.setInputProcessor(this);
}
#Override
public void dispose() {
/*batch.dispose();
texture.dispose();*/
/*dynamicCircle.dispose();
groundBox.dispose();*/
playerBox.dispose();
planetCircle.dispose();
}
#Override
public void render() {
//Gdx.gl.glClearColor(1, 1, 1, 1);
update();
Gdx.gl.glClear(GL10.GL_COLOR_BUFFER_BIT);
/*batch.setProjectionMatrix(camera.combined);
batch.begin();
//sprite.draw(batch);
batch.end();*/
camera.position.set(playerBody.getPosition().x, playerBody.getPosition().y, 0);
camera.update();
//camera.apply(Gdx.gl10);
debugRenderer.render(world, camera.combined);
world.step(BOX_STEP, BOX_VELOCITY_ITERATIONS, BOX_POSITION_ITERATIONS);
//playerBody.setAwake(true);
}
#Override
public void resize(int width, int height) {
}
#Override
public void pause() {
}
public void update()
{
if(jump == true /*Gdx.input.isKeyPressed(Gdx.input.)*/ && grounded() == true)
{
playerBody.setLinearVelocity(0, 0);
playerBody.applyLinearImpulse(new Vector2(0,150), new Vector2(playerBody.getPosition().x, playerBody.getPosition().y));
jump = false;
}
//playerBody.setTransform(new Vector2(camera.viewportWidth / 2, playerBody.getPosition().y), playerBody.getAngle());
//planetBody.setTransform(new Vector2(camera.viewportWidth / 2, camera.viewportHeight / 2), 0);
}
#Override
public void resume() {
}
#Override
public boolean keyDown(int keycode) {
//if(keycode == Keys.S)
return false;
}
#Override
public boolean keyUp(int keycode) {
if(keycode == Keys.Z)
jump = true;
return false;
}
public boolean grounded()
{
if(playerBody.getPosition().y <= ((camera.viewportHeight / 2) - 100 + 125))
{
return true;
}
else
{
return false;
}
}
You are creating two playerBody in the world. The second one is assigned but has no fixture. This is the one you are manipulating in your code and your camera is following. Remove the second playerBody = world.createBody(playerBodyDef); and it should work (better).