We closed this forum 18 June 2010. It has served us well since 2005 as the ALPHA forum did before it from 2002 to 2005. New discussions are ongoing at the new URL http://forum.processing.org. You'll need to sign up and get a new user account. We're sorry about that inconvenience, but we think it's better in the long run. The content on this forum will remain online.
Page Index Toggle Pages: 1
Simple picking in 3D (Read 982 times)
Simple picking in 3D
Jun 1st, 2009, 3:58pm
 
Hi all

Thought I'd post this little hack. I picked up the Terzidis book Algorithms for Visual Design (using Processing) and found a version of my own little 3D picking hack and thought that my hack might be ok. I never saw this as anything but a quick hack, but it has helped me alot, still does. I thought that it hopefully could help some people having difficulties solving the picking problem the "real" (and hard) way. It would have helped me.

Heres the code:

/**
* Selecting_objects_3D - easy way
* by Johan Wastring
*
* Quick and dirty way f picking in 3D if you have less
* than 200 objects in a list. It's not fancy,
* but it works on small numbers of objects.
* Run sketch and pick with mouse to change the color.
*
*/

import processing.opengl.*;

int numOfShapes = 5;
Shape[] myShapes = new Shape[numOfShapes];

void setup() {
 noStroke ();
 size (400, 400, OPENGL);

 // create your shapes in a list
 for (int i = 0; i < numOfShapes; i ++) {
   myShapes[i] = new Shape(i*20, 0, 0);
 }
}

void draw() {
 background(255);

 // Call theSelector before you draw your shapes
 theSelector();

 // draw your shapes
 for (int i = 0; i < numOfShapes; i ++) {
   myShapes[i].display();
 }

 // a Camera well placed after all above
 camera(
 40, 0, -120,
 40, 0, 0,
 0, 1, 0 );

}

// the nice Selector
void theSelector() {
 // SELECTION BY MOUSE
 int tolerance = 10; // to make it easy to pick the shape
 for ( int i = 0; i < numOfShapes; i ++) {
   // get objects screenX coords
   float checkX = myShapes[i].getScreenX();
   // if it matches the mouseX decently proceed to get Y
   if (checkX >= (mouseX-tolerance) && checkX <= (mouseX+tolerance)) {
     boolean yes = true;
     if (yes == true) {
       // get the Y one
       float checkY = myShapes[i].getScreenY();
       // if that one matches decently with the mouseY do something with that shape
       if (checkY >= (mouseY-tolerance) && checkY <= (mouseY+tolerance)) {
         // make new cursor indicating selection is possible
         cursor(MOVE);
         if (mousePressed == true && mouseButton == LEFT) {  
           // here the action happens if it gets this far            
           myShapes[i].setSelected(i);

         }
       }
     }
   }
 }

}

class Shape {
 float x, y, z;
 boolean isSelected = false;

 Shape(float inX, float inY, float inZ) {
   x = inX;
   y = inY;
   z = inZ;
 }

 void display(){
   pushMatrix();
   translate(x, y, z);
   rotateX(HALF_PI/2);
   stroke(255);
   if (isSelected == true) {
     fill(255, 0, 0);
   }
   else {
     fill(0, 0, 255);
   }
   box(10);
   popMatrix();
 }
 void setSelected(int i) {
   this.isSelected = true;
   println("Got it " + i);
 }

 float getScreenX() {
   float f = screenX(x, y, z);
   return f;
 }
 float getScreenY() {
   float f = screenY(x, y, z);
   return f;
 }
}

//JohanW
blog: http://visualinformation.org
Page Index Toggle Pages: 1