Skip to main content

How to get Canvas Pixel of Object

No replies
Omnipotent_Penny
Offline
Joined: 2012-04-08
Points: 0

Hi,
I find it really strange that no where in Java3d is there a function to get an objects screen pixel. What I also found even stranger is that, after scowering the net to find a routine to do such a thing, no one has ever bothered to explain how to do it. So, hopefully, with my post I plan to save students days and days of pulling their hair out!!!!!!!! This has taken me the best part of a week to finally get results and be assured I am going to celebrate tomorrow, in style!!!

Please enjoy my little routine and savour your time in the student bar, have a drink for me :)

Notes:
#1 made static simply so it can be used as a uninstantiated tool.
#2 the node should be a child of a TransformGroup that has the
capability of ALLOW_LOCAL_TO_VWORLD_READ
#3 viewInfo has already been instantiated using canvasInstance
and ViewInfo.CANVAS_AUTO_UPDATE+ViewInfo.PLATFORM_AUTO_UPDATE
#4 canvasInstance pointer has been set to the Rendering canvas3D
#5 the point is transformed into clip space where -1,-1 and 1,1 signify clip bounds before being scaled to canvas space
#6 the returned point is set to -1,-1 if the node object is off screen :)
#7 the canvas computation returns Y IS DOWN to suit graphics coordinates.

I really hope this helps someone out.
Bye for now :)

//################################################################################
// get canvas pixel of node
//################################################################################
private static Transform3D gncp_t1=new Transform3D();
private static Transform3D gncp_t2=new Transform3D();
private static Point3d gncp_p3=new Point3d();
private static Vector4d gncp_v4=new Vector4d();
public static void getCanvasPixelOfNode(Node _node,Point _point)
  {
  _node.getLocalToVworld(gncp_t1); // get local to vworld transform
  gncp_p3.set(0,0,0);
  gncp_t1.transform(gncp_p3); // transform origin
  viewInfo.getInverseVworldProjection(canvasInstance,gncp_t1,gncp_t2);
  gncp_t1.invert(); // transform now vworld to clip projection
  gncp_v4.set(gncp_p3.x,gncp_p3.y,gncp_p3.z,1); // requires W
  gncp_t1.transform(gncp_v4);
  gncp_p3.set(gncp_v4.x/gncp_v4.w,gncp_v4.y/gncp_v4.w,0); // widthatise < thats special terminology.
  if(gncp_p3.x<-1||gncp_p3.x>1||gncp_p3.y<-1||gncp_p3.y>1) // test if on screen
   {
   _point.setLocation(-1,-1); // set both to -1 to signify off screen :)
   return;
   }
  _point.setLocation(((gncp_p3.x+1)/2)*canvasInstance.getWidth(),((1-gncp_p3.y)/2)*canvasInstance.getHeight()); // compute clip space point to canvas point
  }