import java.awt.Color; import java.util.ArrayList; import java.util.Iterator; import processing.core.PApplet; import processing.core.PConstants; /* * Implement and draw the timeline * * timeline spans time=0 to the last transaction * * mouseover will cause a partial rect to be drawn from t=0 to the mouse point * */ public class Timeline { float x,y; float width,height; float current_x; //where the mouse was last float highlight_vpad = 5; //padding on top/bottom of highlight rect if desired float extra_range_x = 32; //space to left and right of timeline that counts as 'mouse over' float extra_range_y = 16; //space to top and bottom of timeline that counts as 'mouse over' float snap_range = 10;//pixels boolean tick_snapping = true; String[] labels; ArrayList ticks; Integrator highlight_integrator; boolean draw_midpoints = true; float[] midpoints_y; //an array with one midpoint (absolute) y for each integer x in the timeline Timeline(float _x, float _y, float _width, float _height, String[] _labels, float[] _midpts, ArrayList _ticks){ x=_x; y=_y; width=_width; height=_height; current_x = x; ticks = _ticks; highlight_vpad = height/10; System.out.println(""+height+""+ width); highlight_integrator = new Integrator(x); //animates the current_x val of the highlight rectangle highlight_integrator.attraction = 1f; highlight_integrator.damping = 0f; labels = _labels; midpoints_y = _midpts; } //Set where the mouse is / where to draw the highlight rectangle void setCurrentX(float _x){ float val=_x; if(tick_snapping){ val = getSnapX(_x); if(val < 0) val = _x; //reset to _x } highlight_integrator.set(val); } //put it at a % of the total width void setCurrentPercent(double pct){ if(pct < 0) pct = 0; if(pct > 1) pct = 1; float px = (float) pct*width+x; setCurrentX(px); } //Tell if the mouse at this coord is inside the timeline box boolean mouseOverGenerally(float mx, float my){ return ( (mx > (x-extra_range_x)) && (mx < (x+width+extra_range_x))&&(my > (y-extra_range_y))&&(my < (y+height+extra_range_y)) ); } boolean mouseOverExactly(float mx, float my){ return ( (mx > x) && (mx < (x+width))&&(my > y)&&(my < (y+height)) ); } //only see if its over the Y-space of the timeline boolean mouseOverY(float my){ return ( (my > y)&&(my < (y+height)) ); } boolean nearTick(float mx){ Iterator itr = ticks.iterator(); float tx; int count=0; while(itr.hasNext()){ count++; tx = ((Float)itr.next()).floatValue(); if(count==1) continue; //skip first tick if(Math.abs(mx-tx)<=snap_range) return true; } return false; } float getSnapX(float mx){ Iterator itr = ticks.iterator(); float tx; int count=0; while(itr.hasNext()){ count++; tx = ((Float)itr.next()).floatValue(); if(count == 1) continue; //skip first tick if(Math.abs(mx-tx)<=snap_range) return tx; } return -1; //return -1 to signify failure to find a snapping x } double getPercent(float cx){ //the x represents which percent of the timeline? if(cx < x) cx=x; else if(cx > (x+width)) cx = (x+width); return ((cx-x) / width); } }