Personal tools

Site Navigation

« June 2017 »
June
MoTuWeThFrSaSu
1234
567891011
12131415161718
19202122232425
2627282930
 
You are here: Home / public download / libgdx crash example

libgdx crash example

Single file example to reproduce android crash. See https://github.com/libgdx/libgdx/issues/2083

C1.java — Java source code, 6 kB (7127 bytes)

File contents

package com.dahetral.C1;

import com.badlogic.gdx.ApplicationListener;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.GL20;
import com.badlogic.gdx.graphics.PerspectiveCamera;
import com.badlogic.gdx.graphics.VertexAttributes.Usage;
import com.badlogic.gdx.graphics.g3d.*;
import com.badlogic.gdx.graphics.g3d.attributes.BlendingAttribute;
import com.badlogic.gdx.graphics.g3d.attributes.ColorAttribute;
import com.badlogic.gdx.graphics.g3d.environment.DirectionalLight;
import com.badlogic.gdx.graphics.g3d.utils.CameraInputController;
import com.badlogic.gdx.graphics.g3d.utils.MeshPartBuilder;
import com.badlogic.gdx.graphics.g3d.utils.ModelBuilder;
import com.badlogic.gdx.math.Vector3;
import com.badlogic.gdx.physics.bullet.Bullet;
import com.badlogic.gdx.physics.bullet.collision.*;
import com.badlogic.gdx.physics.bullet.dynamics.btRigidBody;
import com.badlogic.gdx.utils.Disposable;

/*
Simple bouncing ball inside a translucent sphere, elastic collsions and
no external forces (gravity)

based on http://blog.xoppa.com/using-the-libgdx-3d-physics-bullet-wrapper-part1

*/

public class C1 implements ApplicationListener {
	final static short GROUND_FLAG = 1<<8;
	final static short OBJECT_FLAG = 1<<9;
	final static short ALL_FLAG = -1;

	class MyContactListener extends ContactListener {

        @Override
        public boolean onContactAdded (btManifoldPoint p,
                                       btCollisionObject colObj0, int partId0, int index0,
                                       btCollisionObject colObj1, int partId1, int index1) {

            // *** crashes on android, see issue 2083 ***
            float vec[] = p.getNormalWorldOnB().getFloats();
            // float vec[] = new float[] {0, 1f, 0};  // works

            Vector3 bN = new Vector3(vec);


            mMove.trn(bN);

            return true;
        }
	}

	PerspectiveCamera cam;
	CameraInputController camController;
	ModelBatch modelBatch;
	Environment environment;

	btCollisionConfiguration collisionConfig;
	btDispatcher dispatcher;
	MyContactListener contactListener;
	btBroadphaseInterface broadphase;
	btCollisionWorld collisionWorld;

	@Override
	public void create () {
		Bullet.init();

		modelBatch = new ModelBatch();
		environment = new Environment();
		environment.set(
                new ColorAttribute(ColorAttribute.AmbientLight, 0.4f, 0.4f, 0.4f, 1f));
		environment.add(
                new DirectionalLight().set(0.8f, 0.8f, 0.8f, -1f, -0.8f, -0.2f));

		cam = new PerspectiveCamera(67, Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
		cam.position.set(3f, 7f, 10f);
		cam.lookAt(0, 0f, 0);
		cam.near = 1f;
		cam.far = 300f;
		cam.update();

		camController = new CameraInputController(cam);
		Gdx.input.setInputProcessor(camController);

		collisionConfig = new btDefaultCollisionConfiguration();
		dispatcher = new btCollisionDispatcher(collisionConfig);
		broadphase = new btDbvtBroadphase();
		collisionWorld = new btCollisionWorld(dispatcher, broadphase, collisionConfig);
		contactListener = new MyContactListener();

        createMove();
        createDome();
	}

    ModelBuilder mb = new ModelBuilder();
    RigidObjectX mMove;
    private void createMove() {
        mb.begin();

        mb.node().id = "move1";
        mb.part("sphere", GL20.GL_TRIANGLES, Usage.Position | Usage.Normal,
                new Material(ColorAttribute.createDiffuse(Color.RED)))
                .sphere(1f, 1f, 1f, 16, 16);
        Model m = mb.end();

        btCollisionShape b = new btSphereShape(0.5f);

        mMove = new RigidObjectX(m, "move1", b, 1f);
        mMove.translate(0f, 0f, 0f);  // place object
        mMove.setVelocity(0f, -.1f, 0f, .1f); // set velocity vector
        mMove.body.setCollisionFlags(mMove.body.getCollisionFlags() |
                btCollisionObject.CollisionFlags.CF_CUSTOM_MATERIAL_CALLBACK);
        collisionWorld.addCollisionObject(mMove.body, OBJECT_FLAG, GROUND_FLAG);
    }

    RigidObjectX mDome;
    private void createDome() {

        mb.begin();
        mb.node().id = "Dome";
        Material mat = new Material();
        mat.set(new ColorAttribute(ColorAttribute.Diffuse, Color.WHITE));
        mat.set(new BlendingAttribute(GL20.GL_SRC_ALPHA, GL20.GL_ONE_MINUS_SRC_ALPHA, .3f));
        MeshPartBuilder mpb = mb.part("dome", GL20.GL_TRIANGLES,
                Usage.Position | Usage.Normal,
                mat);

        mpb.sphere(10f, 10f, 10f, 32, 32);

        Model m = mb.end();

        btCollisionShape b = Bullet.obtainStaticNodeShape(m.nodes);

        mDome = new RigidObjectX(m, "Dome", b, 0f);

        collisionWorld.addCollisionObject(mDome.body, GROUND_FLAG, ALL_FLAG);
    }

    @Override
	public void render () {

        mMove.trn();

        collisionWorld.performDiscreteCollisionDetection();

		camController.update();

		Gdx.gl.glClearColor(0.2f, 0.2f, 0.2f, 1.f);
		Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT | GL20.GL_DEPTH_BUFFER_BIT);

		modelBatch.begin(cam);
        modelBatch.render(mMove, environment);
        modelBatch.render(mDome, environment);
		modelBatch.end();
	}

	@Override
	public void dispose () {

        mMove.dispose();
        mDome.dispose();

		collisionWorld.dispose();
		broadphase.dispose();
		dispatcher.dispose();
		collisionConfig.dispose();

		contactListener.dispose();

		modelBatch.dispose();
	}

	@Override
	public void pause () {
	}

	@Override
	public void resume () {
	}

	@Override
	public void resize (int width, int height) {
	}

    class RigidObjectX extends ModelInstance implements Disposable {

        public final btRigidBody body;
        public Vector3 localI = new Vector3();
        public float velocityscale = .1f;
        public Vector3 velocity = new Vector3();

        public RigidObjectX(Model model, String node, btCollisionShape shape, float mass) {
            super(model, node);

            if (mass > 0f)
                shape.calculateLocalInertia(mass, localI);
            else
                localI.set(0, 0, 0);

            body = new btRigidBody(
                    new btRigidBody.btRigidBodyConstructionInfo(mass, null, shape, localI)
            );
        }

        public void setVelocity(float x, float y, float z, float scale) {

            velocity.set(x, y, z);
            velocityscale = scale;
        }

        // translate object based on velocity and update collision location
        public void trn() {
            this.transform.trn(velocity);
            this.body.setWorldTransform(this.transform);
        }

        // reposition object and update collision location
        public void translate(float x, float y, float z) {
            this.transform.translate(x, y, z);
            this.body.setWorldTransform(this.transform);
        }

        // update velocity and translate
        public void trn(Vector3 collisionNormal) {

            collisionNormal.scl(this.velocityscale);
            this.velocity.set(collisionNormal);
            this.trn();
        }

        @Override
        public void dispose() {
            body.dispose();
        }
    }

}

Document Actions