Capsule collision psychics between characters

 Geometry reBoxg = new Geometry("brick", brick);
        reBoxg.setMaterial(mat);
        reBoxg.setLocalTranslation(ori);
        //for geometry with sphere mesh the physics system automatically uses a sphere collision shape
        reBoxg.addControl(new RigidBodyControl(1.5f));
        reBoxg.setShadowMode(ShadowMode.CastAndReceive);
        reBoxg.getControl(RigidBodyControl.class).setFriction(0.6f);
        this.rootNode.attachChild(reBoxg);
        this.getPhysicsSpace().add(reBoxg);

bricks example

try add this to my models

1 Like

Update
i add this code:

    characterModel.addControl(new RigidBodyControl(1.5f)); 

1 Like

Player inside player… but capsule add and control add…

1 Like

Player init:
//
// We set up collision detection for the player by creating
// a capsule collision shape and a CharacterControl.
// The CharacterControl offers extra settings for
// size, stepheight, jumping, falling, and gravity.
// We also put the player in its starting position.
capsuleShape = new CapsuleCollisionShape(1.1f, 3.1f, 1);

        //capsuleShape.
        characterControl = new PlayerControl(capsuleShape, 0.05f);
        
        characterControl.setJumpSpeed(20);
        
        characterControl.setFallSpeed(100);
        characterControl.setGravity(60);

        // characterControl.setPhysicsLocation(new Vector3f( 0.9f,  0.02f, 0.22f));

        characterModel = (Node) assetManager.loadModel(modelPath);

        characterModel.addControl(new RigidBodyControl(1.5f)); 
        
        
        moveSpatial = characterModel.getChild("base.obj");
        
        
        
        characterModel.move(0.050779365f, -1.74886445f, 12.0f);

        characterModel.rotate(1.0f, 0.0f, 0.0f);

        
        moveSpatial.setLocalTranslation(new Vector3f(0, -0.2f, 0));
        
        AnimListener rotateListener = new AnimListener();
        AnimListener runListener = new AnimListener();

        rotateControl = characterModel.getChild("base.obj").getControl(AnimControl.class);

        rotateControl.addListener(rotateListener);

        rotateChannel = rotateControl.createChannel();
        
        

        runControl    = characterModel.getChild("base.obj").getControl(AnimControl.class);

        runControl.addListener(runListener);

        runChannel    = runControl.createChannel();

        characterControl.setPhysicsLocation(startLocation);
        
        
        //rotateChannel.setAnim("direct-left");
        runChannel.setAnim("run");
        runChannel.setSpeed(0);
        runChannel.setLoopMode(LoopMode.Loop);

        
        rotateChannel.setAnim("direct");
        rotateChannel.setSpeed(0);
        rotateChannel.setLoopMode(LoopMode.DontLoop);
1 Like
1 Like
          //   CollisionShape characterShape = CollisionShapeFactory.createMeshShape(moveSpatial);

    //RigidBodyControl
   // rigidControl = new RigidBodyControl(characterShape,1.5f);
    
  //  characterModel.addControl(rigidControl); 
    


            game.bulletAppState.getPhysicsSpace().add(player.characterControl);
            game.bulletAppState.getPhysicsSpace().add(player.rigidControl);

Not work

1 Like

See tests
*

  • Copyright © 2009-2012 jMonkeyEngine All rights reserved.

  • Redistribution and use in source and binary forms, with or without
  • modification, are permitted provided that the following conditions are met:
    • Redistributions of source code must retain the above copyright notice,
  • this list of conditions and the following disclaimer.

    * Redistributions

  • in binary form must reproduce the above copyright notice, this list of
  • conditions and the following disclaimer in the documentation and/or other
  • materials provided with the distribution.

    * Neither the name of

  • ‘jMonkeyEngine’ nor the names of its contributors may be used to endorse or
  • promote products derived from this software without specific prior written
  • permission.

    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND

  • CONTRIBUTORS “AS IS” AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT
  • NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
  • PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  • CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  • EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  • PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
  • OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
  • WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
  • OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
  • ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    */
    package jme3test.bullet;

import com.jme3.app.SimpleApplication;
import com.jme3.bullet.BulletAppState;
import com.jme3.bullet.PhysicsSpace;
import com.jme3.bullet.collision.shapes.CapsuleCollisionShape;
import com.jme3.bullet.control.CharacterControl;
import com.jme3.input.KeyInput;
import com.jme3.input.MouseInput;
import com.jme3.input.controls.ActionListener;
import com.jme3.input.controls.KeyTrigger;
import com.jme3.input.controls.MouseButtonTrigger;
import com.jme3.math.Vector3f;
import com.jme3.renderer.RenderManager;
import com.jme3.scene.CameraNode;
import com.jme3.scene.Node;
import com.jme3.scene.Spatial;
import com.jme3.scene.control.CameraControl.ControlDirection;

/**

  • A walking physical character followed by a 3rd person camera. (No animation.)
  • @author normenhansen, zathras
    */
    public class TestPhysicsCharacter extends SimpleApplication implements ActionListener {

private BulletAppState bulletAppState;
private CharacterControl physicsCharacter;
private Node characterNode;
private CameraNode camNode;
boolean rotate = false;
private Vector3f walkDirection = new Vector3f(0,0,0);
private Vector3f viewDirection = new Vector3f(0,0,0);
boolean leftStrafe = false, rightStrafe = false, forward = false, backward = false,
leftRotate = false, rightRotate = false;

public static void main(String[] args) {
TestPhysicsCharacter app = new TestPhysicsCharacter();
app.start();
}

private void setupKeys() {
    inputManager.addMapping("Strafe Left", 
            new KeyTrigger(KeyInput.KEY_Q), 
            new KeyTrigger(KeyInput.KEY_Z));
    inputManager.addMapping("Strafe Right", 
            new KeyTrigger(KeyInput.KEY_E),
            new KeyTrigger(KeyInput.KEY_X));
    inputManager.addMapping("Rotate Left", 
            new KeyTrigger(KeyInput.KEY_A), 
            new KeyTrigger(KeyInput.KEY_LEFT));
    inputManager.addMapping("Rotate Right", 
            new KeyTrigger(KeyInput.KEY_D), 
            new KeyTrigger(KeyInput.KEY_RIGHT));
    inputManager.addMapping("Walk Forward", 
            new KeyTrigger(KeyInput.KEY_W), 
            new KeyTrigger(KeyInput.KEY_UP));
    inputManager.addMapping("Walk Backward", 
            new KeyTrigger(KeyInput.KEY_S),
            new KeyTrigger(KeyInput.KEY_DOWN));
    inputManager.addMapping("Jump", 
            new KeyTrigger(KeyInput.KEY_SPACE), 
            new KeyTrigger(KeyInput.KEY_RETURN));
    inputManager.addMapping("Shoot", 
            new MouseButtonTrigger(MouseInput.BUTTON_LEFT));
    inputManager.addListener(this, "Strafe Left", "Strafe Right");
    inputManager.addListener(this, "Rotate Left", "Rotate Right");
    inputManager.addListener(this, "Walk Forward", "Walk Backward");
    inputManager.addListener(this, "Jump", "Shoot");
}

@Override
public void simpleInitApp() {
// activate physics
bulletAppState = new BulletAppState();
stateManager.attach(bulletAppState);

// init a physical test scene
PhysicsTestHelper.createPhysicsTestWorldSoccer(rootNode, assetManager, bulletAppState.getPhysicsSpace());
setupKeys();

// Add a physics character to the world
physicsCharacter = new CharacterControl(new CapsuleCollisionShape(0.5f, 1.8f), .1f);
physicsCharacter.setPhysicsLocation(new Vector3f(0, 1, 0));
characterNode = new Node("character node");
Spatial model = assetManager.loadModel("Models/Sinbad/Sinbad.mesh.xml");
model.scale(0.25f);
characterNode.addControl(physicsCharacter);
getPhysicsSpace().add(physicsCharacter);
rootNode.attachChild(characterNode);
characterNode.attachChild(model);

// set forward camera node that follows the character
camNode = new CameraNode("CamNode", cam);
camNode.setControlDir(ControlDirection.SpatialToCamera);
camNode.setLocalTranslation(new Vector3f(0, 1, -5));
camNode.lookAt(model.getLocalTranslation(), Vector3f.UNIT_Y);
characterNode.attachChild(camNode);

//disable the default 1st-person flyCam (don't forget this!!)
flyCam.setEnabled(false);

}

@Override
public void simpleUpdate(float tpf) {
Vector3f camDir = cam.getDirection().mult(0.2f);
Vector3f camLeft = cam.getLeft().mult(0.2f);
camDir.y = 0;
camLeft.y = 0;
viewDirection.set(camDir);
walkDirection.set(0, 0, 0);
if (leftStrafe) {
walkDirection.addLocal(camLeft);
} else
if (rightStrafe) {
walkDirection.addLocal(camLeft.negate());
}
if (leftRotate) {
viewDirection.addLocal(camLeft.mult(0.02f));
} else
if (rightRotate) {
viewDirection.addLocal(camLeft.mult(0.02f).negate());
}
if (forward) {
walkDirection.addLocal(camDir);
} else
if (backward) {
walkDirection.addLocal(camDir.negate());
}
physicsCharacter.setWalkDirection(walkDirection);
physicsCharacter.setViewDirection(viewDirection);
}

public void onAction(String binding, boolean value, float tpf) {
    if (binding.equals("Strafe Left")) {
        if (value) {
            leftStrafe = true;
        } else {
            leftStrafe = false;
        }
    } else if (binding.equals("Strafe Right")) {
        if (value) {
            rightStrafe = true;
        } else {
            rightStrafe = false;
        }
    } else if (binding.equals("Rotate Left")) {
        if (value) {
            leftRotate = true;
        } else {
            leftRotate = false;
        }
    } else if (binding.equals("Rotate Right")) {
        if (value) {
            rightRotate = true;
        } else {
            rightRotate = false;
        }
    } else if (binding.equals("Walk Forward")) {
        if (value) {
            forward = true;
        } else {
            forward = false;
        }
    } else if (binding.equals("Walk Backward")) {
        if (value) {
            backward = true;
        } else {
            backward = false;
        }
    } else if (binding.equals("Jump")) {
        physicsCharacter.jump();
    }
}

private PhysicsSpace getPhysicsSpace() {
return bulletAppState.getPhysicsSpace();
}

@Override
public void simpleRender(RenderManager rm) {
//TODO: add render code
}
}

1 Like
//bulletAppState.getPhysicsSpace().enableDebug(assetManager);

not work…

Try collision listener

1 Like

When i create level i add player controls to level (landscape bodycontrol)

if i create body control at player and another player?

1 Like

I’m not sure if it is of any help, but I found a chapter “Physics Integration” here https://jmonkeyengine.github.io/wiki/jme3.html there are also a lot of links to test cases, including HelloCollision (I guess that one you already studied). Maybe that helps.

I’m also not an expert for physics, but if you can make that bricks fall because of the ball you can shoot (the sample in the beginners section), then you just have to find the difference between your player setup and the ball setup. I would do it that way I guess.

1 Like

Don’t have code for this example, i think:

/**
 * Add to player another player for collision
 */
public void addPlayerPhysics(CharacterControl anotherControl){
        
    characterControl.getPhysicsSpace().add(anotherControl);
    
}
1 Like

No clue what you want to tell me :frowning:

2 Likes

in this sample:
https://jmonkeyengine.github.io/wiki/jme3/beginner/hello_physics.html

Author use RigidBodyControl(2f);

brick_phy = new RigidBodyControl(2f);
brick_geo.addControl(brick_phy);
bulletAppState.getPhysicsSpace().add(brick_phy);

next he add ball

ball_phy = new RigidBodyControl(1f);
/** Add physical ball to physics space. */
ball_geo.addControl(ball_phy);
bulletAppState.getPhysicsSpace().add(ball_phy);
/** Accelerate the physcial ball to shoot it. */
ball_phy.setLinearVelocity(cam.getDirection().mult(25));

But this is work for RigidBodyControl.

In my sample use: PlayerControl.

When capsule collision between game level and player.
And not between the players.

1 Like

If i add to player RigidBodyControl how in the sample - it’s not work.

Next i try add RigidBodyControl and add player to player.

1 Like

Maybe use the BetterCharacterControl, maybe that control object has mode where you can say “colide” or something like that. Just guessing, it’s a while since I used that.

NOTE: in case you already tried that, just ignore me, often I missinterpret a question or just don’t read it carefully enough :wink:

1 Like

Where in bettercharactercontrol method “getPhysicsPosition” ?

1 Like

See player capsule:

Add player to player - not work.

Okay we have methods:

getCollideWithGruops()
setCollideWithGruops()
removeCollideWithGruops()

1 Like

I don’t know really. I only know that ther is a better character control and I would have to check it as well, I don’t want to put away the fun for you :slight_smile:

2 Likes

physics listener for bad happening :grinning:

Changes the collision shape after creation.

setCollideWithGroups()
setCollisionGroup()
addCollideWithGroup(COLLISION_GROUP_01)
removeCollideWithGroup(COLLISION_GROUP_01)

Collision Groups are integer bit masks – enums are available in the CollisionObject. All physics objects are by default in COLLISION_GROUP_01. Two objects collide when the collideWithGroups set of one contains the Collision Group of the other. Use this to improve performance by grouping objects that will never collide in different groups (the the engine saves times because it does not need to check on them).

I try this)))))

1 Like

Level collide with group = 1

   //capsuleShape.
    characterControl = new PlayerControl(capsuleShape, 0.05f);
    
    characterControl.addCollideWithGroup(collide_group_1);

collide_group_1 = 1

not work.

Try add rigid body control and add group = 1 to all

1 Like