Free Rotation Joint SixDofJoint help

Well, I guess its just force of habit :

Vector3f direction = posJoint.add(posJoint).add(rotVec).subtract(posObj).normalize();

should be the same of :

Vector3f direction = new Vector3f( posJoint.x+rotVec.x-posObj.x , posJoint.y+rotVec.y-posObj.y , posJoint.z+rotVec.z-posObj.z ).normalize();

It seens the object is just going into the direction of the vector rotVec ignoring any other forces…
Maybe a few ifs could fix it, but I dont know…

Also if I change : Vector3f rotVec = new Vector3f(0,-radios,0);
The object stands still in the same position since its in this position…

Are you sure it should work ?

Of course it does that, you set the velocity so it won’t be anything else, I thought that was the point, having it rotate from collisions but stay on its orbit:

Its offset to a Z position, so if you don’t change the rotating quaternion to rotate around another axis rotating that vector by it will do nothing…

I am not sure I understood, change it to UNIT_XYZ do the same results :

Quaternion rotQuat = distObjRigid.getPhysicsRotation().fromAngleAxis(0.1f*tpf, Vector3f.UNIT_XYZ );

I dont think this is the problem…

Your new vector points in the Z direction. So you’d rotate it around Y to make a circle.

That way ?

direction.mult(Vector3f.UNIT_Y);

Are you trolling now?

Course not ! I am just not following you as I would like to do.
I started to understand the code you sent, but then I get lost… :slight_smile:
My understanding of rotating a vector is to mult it, so.

Here, my last offer, take it or leave it, I’m out.

package mygame;

import com.jme3.app.SimpleApplication;
import com.jme3.bullet.BulletAppState;
import com.jme3.bullet.PhysicsSpace;
import com.jme3.bullet.PhysicsTickListener;
import com.jme3.bullet.control.RigidBodyControl;
import com.jme3.material.Material;
import com.jme3.math.ColorRGBA;
import com.jme3.math.FastMath;
import com.jme3.math.Quaternion;
import com.jme3.math.Vector3f;
import com.jme3.renderer.RenderManager;
import com.jme3.scene.Geometry;
import com.jme3.scene.shape.Box;
import java.util.Random;

/**
 * test
 *
 * @author normenhansen
 */
public class Main extends SimpleApplication implements PhysicsTickListener {

    RigidBodyControl rigid;
    float dist = 5f;
    Vector3f rotVec = new Vector3f(0, dist, 0);
    Vector3f planetPos = new Vector3f(0,-2,0);
    Random rnd = new Random(System.currentTimeMillis());
    float speed = 1;

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

    @Override
    public void simpleInitApp() {
        Box b = new Box(1, 1, 1);
        Geometry geom = new Geometry("Box", b);

        Material mat = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
        mat.setColor("Color", ColorRGBA.Blue);
        geom.setMaterial(mat);

        BulletAppState bullet = new BulletAppState();
        stateManager.attach(bullet);
        bullet.getPhysicsSpace().addTickListener(this);

        rigid = new RigidBodyControl(1);
        
        geom.addControl(rigid);

        bullet.getPhysicsSpace().add(rigid);

        // find actual start position
        Vector3f startPos = planetPos.add(rotVec);
        // put physics object to start position
        rigid.setPhysicsLocation(startPos);

        rootNode.attachChild(geom);
    }

    @Override
    public void simpleUpdate(float tpf) {
        //TODO: add update code
    }

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

    public void prePhysicsTick(PhysicsSpace space, float tpf) {
        Quaternion rotQuat = new Quaternion().fromAngleAxis(speed * tpf, Vector3f.UNIT_Z);
        // rotate vector a bit for new position
        rotQuat.multLocal(rotVec);
        // find direction to new position
        Vector3f direction = planetPos.add(rotVec).subtract(rigid.getPhysicsLocation());
        direction.normalizeLocal();
        // needed speed depends on circle size (2*Pi*radius) and the speed you rotate the vector 
        direction.multLocal(speed * tpf * (2f * FastMath.PI * dist));
        rigid.setLinearVelocity(direction);
    }

    public void physicsTick(PhysicsSpace space, float tpf) {
        //simulate things bouncing into the object, causing it to rotate (but not go out of orbit)
        if(rnd.nextFloat()>0.7f)
            rigid.applyTorque(new Vector3f(rnd.nextFloat(),rnd.nextFloat(),rnd.nextFloat()));
    }
}

Edit: updated code to include a distance (from planet) parameter

Thank you for your code Normen.
I tested and it is working.
But it is still not what I need…
I am looking more for a joint simulation like the Distance Joint point out by @RatKod.
I need the object to complete free move around the planet.
Its a pitty that Jm3 and bullet dont have this functionality, it improves a lot the realist of scenes where you use it.
I am going to try to do some solution myself using the angle aprouch : http://postimg.org/image/s4v0xpm67/
If I come along with a solution for this I will point out here.
Also if someone can help or has a solution I will be glad to hear !

So if you just want it to always keep the same distance to the planet (but not the same orbit) just add forces that push it back to that distance when its not (which is basically what a joint would do too). I won’t go step by step through that with you again though. Especially as we can still just guess what exactly you want to do.

I dont think its so easy. Every time I apply force to the object with out considering angles it just fix the object spinning at some point. It moves if you apply forces but dosent fell natural.
The maths to build such thing seems to be quite complex :

http://www.dyn4j.org/2010/09/distance-constraint/

An object that doesn’t leave its orbit on collisions isn’t natural

Maybe you are right. I am using this code and its working, but just dont feel natural for me yet.
Can you validade ?

    Vector3f centerPosition = centerDistNode.getWorldTranslation();
    Vector3f objposition    = distObjRigid.getPhysicsLocation();
    float radius = 2f;

    Vector3f gravity = centerPosition.subtract(objposition);
    float currentDistance = gravity.length();

    if(currentDistance>radius) {
        distObjRigid.setLinearVelocity( distObjRigid.getLinearVelocity().add( gravity ) );
    } else {
        distObjRigid.setLinearVelocity( distObjRigid.getLinearVelocity().add( gravity.negate() ) );
    }

You’re not applying forces there, you set the velocity directly which basically resets all movement the moment you do that.

distObjRigid.applyForce(gravity.mult(distObjRigid.getMass()), centerPosition);

Right ?
If I do that it works only if I put higher mass into the rigidbody like 10.
But seens to be simulating well, will do some more tests.

Hey @normen , I way a video of you : (jMonkeyEngine BetterCharacter variable gravity)

I think it may be exactly what I need to fix this problem, can you share this code or explain how you did it ?

Not its not what you need but the code is in TestBetterCharacterControl and BetterCharacterControl.

You are right, its not what I need, I dont have a ground to break the impulse, but it was good to look at your code thought.
I have read the bullet source code, its using this complex Jacobians equations for all joints and constraints.
With the forces I am using the objects never stop to bounce in / out of the orbit, I was thinking to reduce the force using the distance as parameter, but I am not sure it will work.
Do you have any idea or should I go straight to the Jacobians ?