Loading...
Logo
Processing Forum
Hello!  I'm attempting to make a GUI for controlling a robot, and I need FPS style mouse controls.  I thought I figured out how it's done in games, but it turns out I have no idea.  This is what I have....
Copy code
  1. import processing.core.*;
    import java.awt.Robot;

    public class FPSMouse extends PApplet {
        public static void main(String args[]) {
            PApplet.main(new String[] { "--present", "FPSMouse" }); 
        }
       
        int margin = 100;
        Robot robot;
        PFont f;
        float rmx, rmy;

        public void setup() {
          size(displayWidth,displayHeight);
          noCursor();
          frameRate(1000);
          f = createFont ("Arial",16,true);
          println("height: "+displayHeight+" width: "+displayWidth);
          try{ robot = new Robot(); }
          catch(Throwable e){}
        }

        public void draw() {
          background(204);
           
          robot.mouseMove(frame.getX()+this.getX()+round(width/2),
            frame.getY()+this.getY()+round(height/2));
          rmx += mouseX-width/2;
          rmy += mouseY-height/2;
          rmx = rmx>=width/2+margin?width/2+margin:rmx;
          rmx = rmx<=width/2-margin?width/2-margin:rmx;
          rmy = rmy>=height/2+margin?height/2+margin:rmy;
          rmy = rmy<=height/2-margin?height/2-margin:rmy;
       
          if (rmx > width/2) { rmx-=1; }
          else if (rmx < width/2) { rmx+=1; }
          if (rmy > height/2) { rmy-=1; }
          else if (rmy < height/2) { rmy+=1; }
         
          noFill();
          ellipse(rmx,rmy, 7,7);
         
          textFont(f,16);
          fill(0);
          text("X: "+(rmx-(width/2))+", Y: "+(-(rmy-(height/2))),10,100);
          text(((rmx-(width/2))/margin),10,150);
          text((-(rmy-(height/2))/margin),10,165);
          noFill();
          rect(width/2+margin, height/2+margin,-(margin*2),-(margin*2),7);
        }

        public boolean sketchFullScreen() {
          return true;
        }
    }
It's unresponsive and slow and just disappointing.  Is there a better way of doing this?  Thanks!
p.s.   I'm using Eclipse, not the Processing IDE, in case you were wondering...

Replies(7)



the trick is to use a lib called robot

see

http://www.openprocessing.org/sketch/25255
That's funny  :P  I'm actually using the Robot library (I think) because of advice I got from you in a thread a few weeks ago (am I actually using Robot??).  I apparently am not doing it right though.  I can make the mouse move from one side of the screen to the other when hitting it, but I can't figure out how to translate that into position...  The robot (actual physical robot) I am controlling takes one value for rotation which is scaled from -1 to +1 in the x axis (like the text displayed in the previous program), in the same way as the right(?) gimbal on a game-pad.  I don't know if this helps...
Copy code
  1. //Basic test of Robot library (for moving the mouse)

    import processing.core.*;    //add this line ALWAYS to compile Processing
    import java.awt.Robot;

    public class MouseInput extends PApplet {                            //always need this line
        public static void main(String args[]) {                         //and this line
            PApplet.main(new String[] { "--present", "MouseInput" });    //and this line (has to match the class name)
        }                                                                //...this one too
       
        //basically just regular processing code from here on
        Robot robot;
        float rmx, rmy;

        public void setup() {                  //all "voids" muse be changed to "public voids"
            size(displayWidth,displayHeight);  //NEED to have this line for game-like GUI
            noCursor();
            try{ robot = new Robot(); }
            catch(Throwable e){}
        }

        public void draw() {
            background(204);
       
            robot.mouseMove(frame.getX()+this.getX()+round(width/2), frame.getY()+this.getY()+round(height/2));
            rmx += mouseX-width/2;
            rmy += mouseY-height/2;
            rmx = rmx>width?rmx-width:rmx;
            rmx = rmx<0?width+rmx:rmx;
            rmy = rmy>height?rmy-height:rmy;
            rmy = rmy<0?height+rmy:rmy;
            rect(rmx,rmy, 7,7);
        }
    }

It's commented so a friend of mine could learn how to do this in Eclipse... not trying to insult your intelligence  :P  I think the speed value would be calculated by using the current mouse position and the previous mouse position, but I don't know how this would work when hitting the boundaries and moving to the other side of the screen...  That's why I have the poorly done example in my first post.


you should be able to see how this works from the code of the example in openprocessing.org

There are also other examples there if you search first person etc.


In the following I move the mouse to the center of the window, then each frame calculate how far it has moved from that point adding the difference to an accumulating variable and then move it back to the center. It is quite a basic example with comments.
http://www.openprocessing.org/sketch/20675
Yeah that's the program I based mine off of (I just modified it).  Thanks for that, btw!  Maybe I'll just have to settle with the original program.  By the way Chrisir, I keep getting an error with your program involving opengl...  that's why I haven't learned much from it...

Oh, an error!

I suppose I wrote it under 1.51 or earlier where old OPENGL stuff was still in place. It won't work with 2.0 I guess.

It never worked in the browser, it is very annoying.

in my code (which is based on rbauers of course)

these are the lines:

Copy code
  1. void draw () {

  2.  

  3.   fill(101);

  4.   background(0);

  5.  

  6.   plane();  // Floor

  7.   walls () ;

  8.   buildings() ;

  9.  

  10.   // very important that this is last in draw()

  11.   CheckVirtualMouse ();

  12.   CheckCameraMouse ();

  13. }

  14.  

  15. // ===========================================================================================

  16.  

  17. void CheckCameraMouse () {

  18.   // Mouse

  19.   // note: Makes use of the values of Robot-Mouse.

  20.   float Radius = 450.0;  // Anfangsradius des Kreises

  21.  

  22.   // command map: See Help.

  23.   angle = map(rmx,width,0,0,359); // left right

  24.  

  25.   // look at

  26.   xlookat = Radius*sin(radians(angle)) + xpos;

  27.   ylookat = map(rmy,-300,floorLevel-120,-270,height); // look up / down

  28.   zlookat = Radius*cos(radians(angle)) + zpos;

  29.  

  30.   camera (xpos,ypos,zpos,

  31.   xlookat, ylookat, zlookat,

  32.   0.0, 1.0, 0.0

  33.     );

  34. }

  35.  

  36. // -------------------------------------------------------------------------------------------

  37.  

  38. void CheckVirtualMouse () {

  39.  

  40.   // Code by rbrauer.

  41.   // it won't work in the applet, ie online.

  42.   // Copy the source code and try it from the PDE.

  43.  

  44.   //line moves mouse pos to center of canvas

  45.   //frame.getX() is the horizontal pos of the window top left (or so)

  46.   //this.getX (or just getX()) gets offset from window frame to canvas

  47.   //required because robot's coords are global not relative to canvas

  48.   robot.mouseMove(

  49.   frame.getX()+this.getX()+round(width/2),

  50.   frame.getY()+this.getY()+round(height/2));

  51.  

  52.   //mouse pos is locked in center of canvas

  53.   //above lines subtract the centering, get whatever offset from

  54.   //center user creates by moving mouse before robot resets it, then

  55.   //continously adds that to our new mouse pos variables

  56.   rmx += mouseX-width/2;

  57.   rmy += mouseY-height/2;

  58.  

  59.   //these lines are just shortened conditionals to handle

  60.   //wrapping of our mouse pos variables when they go outside canvas

  61.   //first one:

  62.   //if rmx>width? set rmx to rmx-width else : set rmx to rmx

  63.   rmx = rmx>width?rmx-width:rmx;

  64.   rmx = rmx<0?width+rmx:rmx;

  65.   // check ceiling

  66.   if (rmy<-300) {

  67.     rmy= -300;

  68.   }

  69.   // check floor

  70.   if (rmy>floorLevel-20) {

  71.     rmy= floorLevel-20;

  72.   }

  73. } // CheckVirtualMouse

  74.  
  75. // -----------------------------------------------------------

what is interesting maybe is that
I use sin and cos in CheckCameraMouse
to get the camera lookAt position.

Maybe that is the leap you need to make?