Author Topic: Rotation pivot  (Read 6496 times)

Offline ErDetEnAnd?

  • int
  • **
  • Posts: 87
    • View Profile
Rotation pivot
« on: December 29, 2008, 04:19:39 pm »
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?

Offline EgonOlsen

  • Administrator
  • quad
  • *****
  • Posts: 12295
    • View Profile
    • http://www.jpct.net
Re: Rotation pivot
« Reply #1 on: December 29, 2008, 08:01:35 pm »
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... ;)

Offline ErDetEnAnd?

  • int
  • **
  • Posts: 87
    • View Profile
Re: Rotation pivot
« Reply #2 on: December 29, 2008, 08:32:19 pm »
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.


Offline EgonOlsen

  • Administrator
  • quad
  • *****
  • Posts: 12295
    • View Profile
    • http://www.jpct.net
Re: Rotation pivot
« Reply #3 on: December 29, 2008, 08:41:36 pm »
I see...i'll think about it as soon as i find the time. A simple translation doesn't cut it, i assume?

Offline ErDetEnAnd?

  • int
  • **
  • Posts: 87
    • View Profile
Re: Rotation pivot
« Reply #4 on: December 29, 2008, 08:48:59 pm »
After any translation the billboard is still attached to its parent at the billboard's upper left corner.

Offline paulscode

  • double
  • *****
  • Posts: 863
    • View Profile
    • PaulsCode.Com
Re: Rotation pivot
« Reply #5 on: December 30, 2008, 01:11:34 am »
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.

Offline ErDetEnAnd?

  • int
  • **
  • Posts: 87
    • View Profile
Re: Rotation pivot
« Reply #6 on: December 30, 2008, 10:10:41 am »
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)?
« Last Edit: December 30, 2008, 10:35:18 am by ErDetEnAnd? »

Offline paulscode

  • double
  • *****
  • Posts: 863
    • View Profile
    • PaulsCode.Com
Re: Rotation pivot
« Reply #7 on: December 30, 2008, 01:19:16 pm »
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:

Code: [Select]
        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();

Offline EgonOlsen

  • Administrator
  • quad
  • *****
  • Posts: 12295
    • View Profile
    • http://www.jpct.net
Re: Rotation pivot
« Reply #8 on: December 30, 2008, 02:15:46 pm »
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:

Code: [Select]
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...

Offline ErDetEnAnd?

  • int
  • **
  • Posts: 87
    • View Profile
Re: Rotation pivot
« Reply #9 on: December 30, 2008, 02:26:50 pm »
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!

Offline paulscode

  • double
  • *****
  • Posts: 863
    • View Profile
    • PaulsCode.Com
Re: Rotation pivot
« Reply #10 on: December 30, 2008, 10:18:10 pm »
Thanks, Egon, that offset method is just what I was looking for.