Rotation pivot

Started by ErDetEnAnd?, December 29, 2008, 04:19:39 PM

Previous topic - Next topic

ErDetEnAnd?

A billboard object3d should rotate around its center rather than its corner when transformed in the world. I'd guess setRotationPivot is the answer. Nomatter what I give this method the object is still rotation around its corner. Build is called before setting the pivot. What is wrong?

EgonOlsen

Hmm...a bill boarded object should not rotate at all, or otherwise it won't be bill boarded any longer. It may rotate around the parents' pivots, but setting a pivot on a bill board itself doesn't make sense to me. As usual, a drawing or some test case always helps... ;)

ErDetEnAnd?

Of course, you're right..

I want a billboard at the bulls eye, but it should appear in the middle when rotating. Its like the attachment point is wrong.


EgonOlsen

I see...i'll think about it as soon as i find the time. A simple translation doesn't cut it, i assume?

ErDetEnAnd?

After any translation the billboard is still attached to its parent at the billboard's upper left corner.

paulscode

I don't know if this is related to your problem, but I noticed that you asked why setRotationPivot doesn't seem to work.  The reason is that a billboarded child will not rotate around the pivot point you specify, it will only rotate around what jPCT decides is the rotation pivot for the object (see this thread for reference).  Egon mentioned that the reason for this was that he always found it questionable to use another pivot for bill boarded objects.

I had a similar issue to this when I made a billboarded quad for the firefly demo applet.  In that case, the workaround that I ended up using was to add aditional polys to the Object3D to "trick" jPCT into using the correct pivot.  For a more complex geometry, this might be difficult to do.

ErDetEnAnd?

#6
I see. How are these extra polygons positioned?

Why is this "workaround" necessary Egon?

Edit: My billboard's rotation pivot is not at origin but at 0;0 (unchanged), which I understand is not correct (http://www.jpct.net/forum2/index.php/topic,1253.msg8488.html#msg8488)?

paulscode

My problem was somewhat different, in that the pivot was in the center of the object, but I wanted it to have a z-depth, so the billboarded object was always some distance from where it was attached to the parent object.  I did this by placing two polys at a further z-depth than the original two:



I'm not sure how you are creating your original billboarded object, but in your case maybe just defining the original two polys with a lower x-value might fix the problem, rather than creating additional polys:

        obj = new Object3D( 2 );
        float offset = 200;  // width / height of the billboard (assumes it is square)
        obj.addTriangle( new SimpleVector( -offset, -offset, 0 ),
                           0, 0,
                           new SimpleVector( -offset, offset, 0 ), 0, 1,
                           new SimpleVector( offset, offset, 0 ), 1, 1,
                           TextureManager.getInstance().getTextureID(
                                                             "Some texture" ) );
        obj.addTriangle( new SimpleVector( offset, offset, 0 ),
                           1, 1,
                           new SimpleVector( offset, -offset, 0 ), 1, 0,
                           new SimpleVector( -offset, -offset, 0 ), 0, 0,
                           TextureManager.getInstance().getTextureID(
                                                             "Some Texture" ) );
        obj.build();

EgonOlsen

Any other rotation pivot then (0,0,0) for a bill boarded object makes not much sense IMHO, because albeit supported, the outcome is unpredictable (maybe not for people which are better in thinking in 3d than i am, but for me, it is...). Translation doesn't really work either, because (like mentioned in the other thread), the translation is rotated too, which is correct but doesn't create the result one wants in this special case. I suggest to shift the object in object space to get the desired result. You don't need to create additional polygons...just translate the existing ones and make that translation permanent to the mesh. That's pretty easy. If you would be using the getPlane()-method from Primitives, the returned planes already are build in a way that the parent of the bill boarded object in at the desired position. If it's not, apply an offset to the mesh like so:


import java.awt.Color;

import com.threed.jpct.*;

public class TestBB2 {

public static void main(String[] args) {
World w = new World();
FrameBuffer fb = new FrameBuffer(800, 600, FrameBuffer.SAMPLINGMODE_NORMAL);
fb.disableRenderer(IRenderer.RENDERER_SOFTWARE);
fb.enableRenderer(IRenderer.RENDERER_OPENGL);
Object3D toy= Primitives.getCube(5);
Object3D toy2=Primitives.getPlane(2, 10f);

toy2.setBillboarding(Object3D.BILLBOARDING_ENABLED);

toy.setScale(0.5f);
toy2.setScale(2f);

toy.setAdditionalColor(Color.BLUE);
toy2.setAdditionalColor(Color.YELLOW);

w.getCamera().moveCamera(Camera.CAMERA_MOVEOUT, 100);
w.getCamera().moveCamera(Camera.CAMERA_MOVEUP, 50);
w.setAmbientLight(130, 130, 130);
toy.build();
toy2.build();

toy.setRotationPivot(new SimpleVector(-50,0,0));
toy2.addParent(toy);

w.addObject(toy);
w.addObject(toy2);

w.getCamera().lookAt(toy.getTransformedCenter());

offset(toy2, new SimpleVector(10,10,0));

while(!org.lwjgl.opengl.Display.isCloseRequested()) {

fb.clear(Color.RED);
w.renderScene(fb);
w.draw(fb);
fb.update();
fb.displayGLOnly();

toy.rotateZ(-0.02f);
toy.translate(0.01f,0,0);

try {
Thread.sleep(10);
} catch(Exception e) {}

}
fb.dispose();
System.exit(0);
}

static private void offset(Object3D which, SimpleVector amount) {
Matrix mb=which.getTranslationMatrix();
which.setTranslationMatrix(new Matrix());
which.translate(amount);
which.translateMesh();
which.setTranslationMatrix(mb);
}

}



In this test case, i'm offsetting the plane in a way that creates the result that you already have. If you leave out the offset-call, you'll get what you want. Transfered to your case, just use that little offset-method on your bill boards with the proper value and i hope it works out well enough...

ErDetEnAnd?

You guys are the best!

I'm creating the object from scratch, so moved the object in object space and got a pivot in the object's center.

Excellent!

paulscode

Thanks, Egon, that offset method is just what I was looking for.