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.
IndexProgramming Questions & HelpPrograms › Rectangular selection of curves using mouse
Page Index Toggle Pages: 1
Rectangular selection of curves using mouse (Read 2882 times)
Rectangular selection of curves using mouse
Jun 14th, 2010, 2:51pm
 
Hello everybody,

I am a newbie of processing. I am supposed draw curves (or connected points) from a file and select rectangular area on the screen and identify the curves partially fall within the rectangle.



is it possible?

thank you very much in advance.
Re: Rectangular selection of curves using mouse
Reply #1 - Jun 15th, 2010, 12:25am
 
Re: Rectangular selection of curves using mouse
Reply #2 - Jun 15th, 2010, 7:59am
 
It is quite simple with lines as shown. It should be quite harder with curves... It depends on the kind of curves, too.
Re: Rectangular selection of curves using mouse
Reply #3 - Jun 15th, 2010, 9:05am
 
I was going to just write you a small example program but thing kinda got out of hand... good exercise though!

Anyways here's one way you can do it:

Code:
class Point{
 public float x;
 public float y;
 public Point(float nx,float ny){
   x = nx;
   y = ny;
 }
}

class Line{
 //every line is a list of connected points
 public ArrayList listOfPoints;
 public color c;
 public boolean selected;
 public Line(){
   listOfPoints = new ArrayList();
   selected = false;
   //Every line is given a random color with low alpha so that
   //1) you can tell them apart and 2) the selected onces will be more visible when selected
   c = color(random(255),random(255),random(255),100);
 }

 public void drawLine(){
   // A line needs two points to be a line....
   if(listOfPoints.size() >=2){
     if(selected){
       stroke(255,0,0,255);//full red
     }
     else{
       stroke(c);
     }  
     beginShape();
     for(int i = 0; i<listOfPoints.size();i++){
       Point currentPoint =  (Point)listOfPoints.get(i);
       vertex(currentPoint.x,currentPoint.y);
     }
     endShape();
   }
 }

 public void addPointToLine(float x,float y){
   //Note: there is no sorting going on, so every point will be connected to the previously added point
   listOfPoints.add(new Point(x,y));
 }
}

ArrayList lines;
float selectionStartX;
float selectionStartY;
void setup(){
 size(800,800);
 background(255);
 lines = new ArrayList();
 noFill();
 smooth();
 //Create 10 lines with 10 random points
 //this should give you an idea of how lines are created
 for(int l = 0;l<10;l++){
   Line temp = new Line();
   for(int p = 0;p<10;p++){
     temp.addPointToLine(random(width),random(height));
   }
   lines.add(temp);
 }

}

void draw(){
 background(255);
 //if the mouse is pressed then we want to draw a selection rectangle
 if(mousePressed){
   stroke(0);
   rect(selectionStartX,selectionStartY,mouseX-selectionStartX,mouseY-selectionStartY);
 }

 for(int i = 0;i<lines.size();i++){
   Line currentLine = (Line)lines.get(i);
   currentLine.drawLine();
 }
}

void mousePressed(){
 selectionStartX = mouseX;
 selectionStartY = mouseY;
}

void mouseReleased(){
 //Run the line select code
 //The cordinates that are passed to the function must be top-left x&y and bottom right x&y
 //So we need to take care of the senario where there mouse is draged in a direction that isn't right-down
 if(mouseX <selectionStartX && mouseY < selectionStartY){
   selectLines(mouseX,mouseY,selectionStartX,selectionStartY);
 }else if(mouseX <selectionStartX){
    selectLines(mouseX,selectionStartY,selectionStartX,mouseY);
 }else if(mouseY < selectionStartY){
   selectLines(selectionStartX,mouseY,mouseX,selectionStartY);
 }else{
   selectLines(selectionStartX,selectionStartY,mouseX,mouseY);
 }
}

void selectLines(float x1,float y1,float x2,float y2){
 for(int l = 0; l < lines.size();l++){
   Line currentLine = (Line)lines.get(l);
   currentLine.selected = false; //reset every line
   for(int p = 0; p< currentLine.listOfPoints.size()-1;p++){
     //a line need two points to be a line! also becouse we are doing .get(p+1) we are stopping the iteration at .size()-1;
     Point currentPoint = (Point)currentLine.listOfPoints.get(p);
     Point nextPoint = (Point)currentLine.listOfPoints.get(p+1);
     if(lineRectangleIntersect(currentPoint.x,currentPoint.y,nextPoint.x,nextPoint.y,x1,y1,x2,y2)){
       currentLine.selected = true;
       //the line is selected - no need to keep looking at it's remaining points so we BREAK!
       break;
     }
   }
 }
}

// As it turns out i didn't know how to do line-text collision detection (only knew how to do point-rect) so here's REAS code on how to do it,
//slighly modified though :D
// Code from REAS:
// http://www.openprocessing.org/portal/?userID=54

boolean lineRectangleIntersect(float x1, float y1, float  x2, float y2,
float rx1, float ry1, float rx2, float ry2) {

 float topIntersection;
 float bottomIntersection;
 float topPoint;
 float bottomPoint;
 // Calculate m and c for the equation for the line (y = mx+c)
 float m = (y2-y1) / (x2-x1);
 float c = y1 -(m*x1);
 // If the line is going up from right to left then the top intersect point is on the left
 if(m > 0) {
   topIntersection = (m*rx1  + c);
   bottomIntersection = (m*(rx2)  + c);
 }
 // Otherwise it's on the right
 else {
   topIntersection = (m*(rx2)  + c);
   bottomIntersection = (m*rx1  + c);
 }
 // Work out the top and bottom extents for the triangle
 if(y1 < y2) {
   topPoint = y1;
   bottomPoint = y2;
 }
 else {
   topPoint = y2;
   bottomPoint = y1;
 }
 float topOverlap;
 float botOverlap;
 // Calculate the overlap between those two bounds
 topOverlap = topIntersection > topPoint ? topIntersection : topPoint;
 botOverlap = bottomIntersection < bottomPoint ? bottomIntersection : bottomPoint;

 return (topOverlap<botOverlap) && (!((botOverlap<ry1) || (topOverlap>ry2)));

}
Re: Rectangular selection of curves using mouse
Reply #4 - Jun 16th, 2010, 12:31pm
 
guss, you are wonderful !!

thank you very much, now I should modify your code, in order to get data from text file.

any idea of reading from external text file?

Re: Rectangular selection of curves using mouse
Reply #5 - Jun 16th, 2010, 2:39pm
 
syntor2001 wrote on Jun 16th, 2010, 12:31pm:
guss, you are wonderful !!

thank you very much, now I should modify your code, in order to get data from text file.

any idea of reading from external text file


np, as what goes for reading from an external file:
http://processing.org/reference/BufferedReader.html
Smiley
Re: Rectangular selection of curves using mouse
Reply #6 - Jun 17th, 2010, 4:48am
 
For small amount of text, loadStrings() does the job nicely. (BufferedReader is harder to use but perfect for large data files.)
Page Index Toggle Pages: 1