/* Matt Martell
   IAT 800 - Dr. Christopher Shaw
   Due Nov. 12, 2008
   Assignment 4 - Scatter Plot Graph with Widgets

   1. Add at least two sliders that control the properties of the marks 
      that the are being plotted (size of mark, orientation, color...)
   2. Add a button to clear the screen
   3. Add a pull-down menu that enables the user to select what data value
      gets plotted along X, and what gets plotted along Y. 

Make this into classes zones of agreement, data plots

Slider created thanks to tutorial from Johnny Rodgers.

*/   

//import controlP5 library
import controlP5.*;

//initialize controls
    ControlP5 controller;
    Slider Slider1, Slider2;  
    controlP5.Button resetButton, clearButton; // need to specify that this is the ControlP5 library's button, not the built-in Button class of Processing
    ControlP5 controlP5;
    MultiList Rater;

//initialize variables (make control variables public or they won't work online) 
    public int pointSize; 
    int pointSizeDefault = 7;   
    public float anotherSliderVal;    
    float zAIntensityDefault = 0;   

//Define Classes
    zoneAgreement zA = new zoneAgreement() ;
    callRaterXY cRXY = new callRaterXY();
    gridlines gl = new gridlines();


void setup (){
    smooth();
    size (575,625);

//instantiate control object
 	controller = new ControlP5(this);

//set parameters for all control objects
	controller.setColorLabel(0);

//add controls to canvas with labels (default label will be name of variable)                                                       
	Slider1 = controller.addSlider("pointSize", 1, 12, pointSizeDefault, 20, 550, 100, 20);
	Slider1.setLabel("Point Size");
	Slider2 = controller.addSlider("zAIntensity", -1.0, 1.0, zAIntensityDefault, 20, 580, 100, 20);
	Slider2.setLabel("Color Intensity");                                   
	resetButton = controller.addButton("reset", 0, 540, 515, 31, 20);   
        clearButton = controller.addButton("clear", 0, 540, 540, 31, 20);

//Choose Rater for x axis
  Rater = controller.addMultiList("myListX",220,550,75,12);
  MultiListButton x;
  x = Rater.add("X Axis Rater",1);
  x.add("Rater 1x",1).setLabel("Rater 1");
  x.add("Rater 2x",2).setLabel("Rater 2");

//Choose Rater for y axis
  Rater = controller.addMultiList("myListY",380,550,75,12);
  MultiListButton y;
  y = Rater.add("Y Axis Rater",1);
  y.add("Rater 1y",3).setLabel("Rater 1");
  y.add("Rater 2y",4).setLabel("Rater 2");
}



//Variables

// Define Averages to set bottom 25%, middle 50%, top 25%
// Numbers comes from original excel file using rank cut off's
    float btmAvgX = .45;
    float btmAvgY = .40;
    float topAvgX = .65;
    float topAvgY = .65;

// Definintion of variables to turn bottom, middle, top into boundary points
    float btmX;
    float btmY;
    float topX;
    float topY;

// Color definitions
    color btm = color (255,0,0);         // red
    color mid = color(255,204,0);        // yellow
    color top = color (0,255,0);         // green  

// Define Variables for use in calling data from text file
    int n = 132; // n = number of lines in text file 
    float  xArr[] = new float[n] ;
    float  yArr[] = new float[n] ;
    float  colorArr[] = new float[n] ; // 1 = top, 2 = mid, 3 = btm
    int rX;      //Used to define rater from pull down menu for x Axis
    int rY;      //Used to define rater from pull down menu for Y Axis
    String labelX;
    String labelY;
    
// Define size of program area   
    int m = 75; // size of margin for text and reference points
    int wAlt = 500; //width of graph
    int hAlt = 500; //height of graph
    int a = hAlt+m;
    int b = wAlt+m;

// prints out current value of exampleSliderVal variable
void exampleSliderVal() {
	println("sliderVal set to " + Slider1.value());
}

//reset sets sliders to their original values
void reset() {                     
	println("reset called");
	Slider1.setValue(pointSizeDefault);
	Slider2.setValue(zAIntensityDefault);        
        rX = 0;
        rY = 0;
        n = 132;
}

//reset sets sliders to their original values
void clear() {                     
	println("clear called");
        n = 0;
}

void draw (){
background (255,255,255);

//Function to turn percentage into boundary points "m" adjusts for margin
    btmX = btmAvgX*wAlt+m;
    btmY = btmAvgY*hAlt-m;
    topX = topAvgX*wAlt+m;
    topY = topAvgY*hAlt-m;
    
    zA.drawMe();     //Draw Zones of agreement
    cRXY.drawMe();   //Draw Rater XY points
    gl.drawMe();     //Draw gridlines

}



class gridlines {
void drawMe(){
// Draw gridlines at half way marks and to frame
    
    strokeWeight (1);
    stroke ( 0, 0, 0,50);
    line (wAlt*1/2+m,0,wAlt*1/2+m,hAlt);
    
    strokeWeight (1);
    stroke ( 0, 0, 0,50);
    line (m,hAlt*1/2,wAlt+m,hAlt*1/2);
    
    strokeWeight (2);
    stroke (0,0,0);
    line(m,0,m,hAlt);
    line(m,hAlt,wAlt+m,hAlt);

//Print the axis descriptors
    PFont font;
    font = loadFont("Graph.vlw");
    textFont(font);
    fill(0, 102, 153, 51);
    text("50", 45, hAlt*1/2+6);
    text("50", wAlt*1/2+m-7, hAlt+25);
    text("0", m-12, hAlt+20);
      
//Print the rater on the rater being used for each axis
      if (rX ==0){
        labelX = "Rater 1";
          }
      if (rX == 1){
        labelX = "Rater 2";
          }    
      fill(0, 102, 153, 85);
      text(labelX, wAlt*1/2+m-20, hAlt+45);
  pushMatrix();
      if (rY == 0){
        labelY = "Rater 1";
          }
      if (rY == 1){
        labelY = "Rater 2";
          }  
    rotate (-PI*1/2);
    text(labelY, -275, hAlt*1/12);    
    popMatrix();  

  }    
  
}

class zoneAgreement {   
void drawMe(){  
// Draw the boxes for zones of agreement
    stroke ( 40, 50, 200,5 );   
    
    float intB = (53+53*Slider2.value());
    color btmZone = color(255,0,0,intB);   // lower percentage (red)
    fill (btmZone);
    rect (m,hAlt-btmY-m, btmX-m,btmY+m);
  
    float intM =(33+33*Slider2.value());    
    color midZone = color(255,204,0,intM); // middle percentage (yellow)
    fill (midZone);
    rect (btmX,hAlt-topY-m,topX-btmX,topY-btmY);

    float intT =(30+30*Slider2.value());
    color topZone = color(0,255,0,intT);   // upper percentage (green)
    fill (topZone);
    rect(topX,0,wAlt-topY-m,hAlt-topY-m);

    }
} 

//Key activation of List Menu
void keyPressed() {
  if(controlP5.controller("level23")!=null) {
    println("removing multilist button level23.");
    controlP5.controller("level23").remove();
  }
}
 void controlEvent(ControlEvent theEvent) {
  println(theEvent.controller().name()+" = "+theEvent.value()); 
    if (theEvent.value() == 1)
      {
        rX=0;
      }
    if (theEvent.value() == 2){
        rX=1;
    }
    if (theEvent.value() == 3)
      {
        rY=0;
      }
    if (theEvent.value() == 4){
        rY=1;
    }
  }




class callRaterXY{


  void drawMe(){
// Call information from text file (only pulling first 3 variables) average and
// Code adapted from IAT 355 class example using some help from Allen




    float  xArr[] = new float[n] ;
     String lines[] = loadStrings( "data.txt" );
         for (int i=0; i < n  && i < lines.length ; i++ )
          {
             float[] numbers = float( split( lines[i], "," ) );
             for( int j = 0 ; j < numbers.length ; j++ )
               {
                if( j == 0 )
                   {
                      xArr[i] = numbers[rX] ;
                   }  
                if( j == 1 )
                   {
                      yArr[i] = numbers[rY] ;
                   }
                if( j == 2 )
                   {
                      colorArr[i] = numbers[j] ;
                   }

              }
          }
  
// Posting elipses to the spreadsheet  
  stroke( 40, 50, 200,75 );
  strokeWeight (1);
  for (int i=0; i<n; i++)
    {
      if (colorArr[i] == 1)
        {
          fill (top);
        }
      if (colorArr[i] == 2)
        {
          fill (mid);
        }
      if (colorArr[i] == 3)
        {
          fill (btm);
        }
  
// Draw data points (height - ... used because y-axis is inverse in processing    
  ellipse(xArr[i]*wAlt/10+m,hAlt - yArr[i]*hAlt/10, Slider1.value(), Slider1.value() );

    }   
  }
}