Projected box around item

I'm trying to achieve an effect similar to what Deus Ex or System Shock did. When aiming at an item in the world, it displayed the name and a box around the item on the HUD. I'm not getting it, I'm afraid. The idea I had is:

  1. Get vertices of bounding box
  2. project on camera
  3. construct box around projected points (getting min and max of points - not really hard)
  4. draw rectangle with those points (or something like that)


  5. and 2) can be changed for other bounding volumes, obviously. Using the bounding volume does probably not give the tightest possible fit, but I don't really care at this moment. I'm having a problem with 4).



    I suppose it is some magic with ortho mode and Line, but I can't seem to figure it out. My current code goes like


   private void setFocus(WorldObject obj) {
      if(obj == null)
         return;
      OrientedBoundingBox b = (OrientedBoundingBox) obj.getNode().getWorldBound();
      Vector3f e = b.getExtent();
      Box box = new Box(null,b.getCenter(),e.getX(),e.getY(),e.getZ());
      Vector3f[] vert = box.computeVertices();
      Vector3f min = new Vector3f();
      Vector3f max = new Vector3f();
      for(Vector3f vect : vert){
         Vector3f v = getRenderer().getCamera().getScreenCoordinates(vect);
         if(v.getX() < min.getX())
            min.setX(v.getX());
         else if(v.getX() > max.getX())
            max.setX(v.getX());
         if(v.getY() < min.getY())
            min.setY(v.getY());
         else if(v.getY() > max.getY())
            max.setY(v.getY());
      }
      
      Vector3f[] lines = {min,
            new Vector3f(min.getX(),max.getY(),max.getZ()),
            max,
            new Vector3f(max.getX(),min.getY(),min.getZ())};
      ColorRGBA color[] = new ColorRGBA[] { new ColorRGBA(1f, 1f, 1f, 0f), new ColorRGBA(1f, 1f, 1f, 0f) };
        Vector2f tex[] = new Vector2f[] { new Vector2f(0f, 0f), new Vector2f(1f, 1f) };
      Line l = new Line(null,lines,null,color,tex);
      l.setMode(Line.LOOP);
      l.setRenderQueueMode(Renderer.QUEUE_ORTHO);
      l.setCullMode(Spatial.CULL_NEVER);
      l.setLightCombineMode(LightState.OFF);
      getRootNode().attachChild(l);
   }


But this doesn't seem to display anything.

I was thinking a optimized way of achieving the same result. Not that it would matter really, but I'm a kind of fps maniac.



I think it is cheaper (in computing cost) to do this:

1 - float distance =  target.getWorldTranslation().subtract(camera.getLocation()).lenght();

2 - float boundRadius = computRadius(target.getWorldBound()); // using some fast method I didn't think of yet - but really simple for boxes and spheres

3 - create the rectangle with size based on k*boundRadius/distance, being k some ajusting constant.



Does it make sense?

Yeah, makes sense to me, but sounds like it'll look strange for long and tall objects that aren't very sphere-like… Besides, projecting 8 points (of a bounding box - it'd be even easier for a sphere I think) doesn't really take that much of time compared to what else needs to be done every frame.

Hmm… adding this line to simpleInit in TestRenderQueue, you can see that lines work fine in ortho:


        orthos.attachChild(new Line("line", new Vector3f[] {new Vector3f(0, 0, 0), new Vector3f(100, 100, 0) }, null, null, null));



Looking at your min/max code, it appears to have the bug of never getting the right min value... Changing the init of min to this makes it work for me:

Vector3f min = new Vector3f(Float.MAX_VALUE, Float.MAX_VALUE, 0);

Grid and DialogBox from cigame may be useful (for 4, not for the other stuff :wink: )



http://www.captiveimagination.com/svn/public/cigame/trunk/src/com/captiveimagination/game/spatial/



They let you draw nice looking “frames” using a texture (without stretching the texture so it looks crappy).



I can’t remember whether I asked before, but would Grid and DialogBox be useful in jME? (maybe called something different - DialogBox should really be called something like Frame) It’s just simple geometry but it does work well for HUD stuff. There may already be something that does the same thing, but I couldn’t find anything :slight_smile:

Yeah, Renanse and Mojo you oughta take a look into cigame…it's like a grab-bag of wonderful enhancements to jME several of us have added. :slight_smile:



Many of them can't really be migrated to jME directly though because of their dependencies.

renanse said:
Looking at your min/max code, it appears to have the bug of never getting the right min value... Changing the init of min to this makes it work for me:

Vector3f min = new Vector3f(Float.MAX_VALUE, Float.MAX_VALUE, 0);


Good catch, thanks.

Grid and Dialogbox are interesting. Smart way to prevent stretches. Might be useful if I want to expand on the effect, but doesn't really solve this problem.

Oh well. if no-one sees it right off I'll be doing some more searching myself. Thanks anyway.

EDIT: someone shoot me. updateRenderState().

Though I have another problem now, it seems like the borders aren't correct. I'll be fixing it I suppose.