Apat and added acos to spherycolor, not included in color yet but working
[SugarCubes.git] / TimBavaro.pde
index a10e89ee01560db6104280148ac11a661bdc3250..3fcd5b160353986498ff01793cd8cf64c5d05bf9 100644 (file)
@@ -3,8 +3,9 @@
  */
 class TimSpheres extends SCPattern {
   private BasicParameter hueParameter = new BasicParameter("RAD", 1.0);
+  private BasicParameter periodParameter = new BasicParameter("PERIOD", 4000.0, 200.0, 10000.0);
   private final SawLFO lfo = new SawLFO(0, 1, 10000);
-  private final SinLFO sinLfo = new SinLFO(0, 1, 4000);
+  private final SinLFO sinLfo = new SinLFO(0, 1, periodParameter);
   private final float centerX, centerY, centerZ;
   
   class Sphere {
@@ -18,6 +19,7 @@ class TimSpheres extends SCPattern {
   public TimSpheres(GLucose glucose) {
     super(glucose);
     addParameter(hueParameter);
+    addParameter(periodParameter);
     addModulator(lfo).trigger();
     addModulator(sinLfo).trigger();
     centerX = (model.xMax + model.xMin) / 2;
@@ -53,7 +55,7 @@ class TimSpheres extends SCPattern {
     spheres[0].radius = 100 * hueParameter.getValuef();
     spheres[1].radius = 100 * hueParameter.getValuef();
     
-    for (Point p : model.points) {
+    for (LXPoint p : model.points) {
       float value = 0;
 
       color c = lx.hsb(0, 0, 0);      
@@ -124,7 +126,7 @@ class Vector3 {
     return distanceTo(v.x, v.y, v.z);
   }
   
-  float distanceTo(Point p) {
+  float distanceTo(LXPoint p) {
     return distanceTo(p.x, p.y, p.z);
   }
   
@@ -246,7 +248,7 @@ class TimRaindrops extends SCPattern {
       raindrops.add(new Raindrop());
     }
     
-    for (Point p : model.points) {
+    for (LXPoint p : model.points) {
       color c = 
         blendColor(
           lx.hsb(210, 20, (float)Math.max(0, 1 - Math.pow((model.yMax - p.y) / 10, 2)) * 50),
@@ -337,14 +339,14 @@ class TimCubes extends SCPattern {
       flashes.add(new CubeFlash());
     }
     
-    for (Point p : model.points) {
+    for (LXPoint p : model.points) {
       colors[p.index] = 0;
     }
     
     for (CubeFlash flash : flashes) {
       float hue = (hueParameter.getValuef() + (hueVarianceParameter.getValuef() * flash.hue)) % 1.0;
       color c = lx.hsb(hue * 360, saturationParameter.getValuef() * 100, (flash.value) * 100);
-      for (Point p : flash.c.points) {
+      for (LXPoint p : flash.c.points) {
         colors[p.index] = c;
       }
     }
@@ -456,7 +458,7 @@ class TimPlanes extends SCPattern {
     
     Vector3 normalizedPoint = new Vector3();
 
-    for (Point p : model.points) {
+    for (LXPoint p : model.points) {
       if (random(1.0) < derez) {
         continue;
       }
@@ -631,7 +633,7 @@ class TimPinwheels extends SCPattern {
     float zSlope = (zSlopeParameter.getValuef() - 0.5) * 2;
     
     int i = -1;
-    for (Point p : model.points) {
+    for (LXPoint p : model.points) {
       ++i;
       
       int value = 0;
@@ -663,25 +665,25 @@ class TimPinwheels extends SCPattern {
  * it but there may be useful code here.
  */
 class TimTrace extends SCPattern {
-  private Map<Point, List<Point>> pointToNeighbors;
-  private Map<Point, Strip> pointToStrip;
+  private Map<LXPoint, List<LXPoint>> pointToNeighbors;
+  private Map<LXPoint, Strip> pointToStrip;
   //  private final Map<Strip, List<Strip>> stripToNearbyStrips;
   
   int extraMs;
   
   class MovingPoint {
-    Point currentPoint;
+    LXPoint currentPoint;
     float hue;
     private Strip currentStrip;
     private int currentStripIndex;
     private int direction; // +1 or -1
     
-    MovingPoint(Point p) {
+    MovingPoint(LXPoint p) {
       this.setPointOnNewStrip(p);
       hue = random(360);
     }
     
-    private void setPointOnNewStrip(Point p) {
+    private void setPointOnNewStrip(LXPoint p) {
       this.currentPoint = p;
       this.currentStrip = pointToStrip.get(p);
       for (int i = 0; i < this.currentStrip.points.size(); ++i) {
@@ -703,9 +705,9 @@ class TimTrace extends SCPattern {
     }
     
     void step() {
-      List<Point> neighborsOnOtherStrips = pointToNeighbors.get(this.currentPoint);
+      List<LXPoint> neighborsOnOtherStrips = pointToNeighbors.get(this.currentPoint);
 
-      Point nextPointOnCurrentStrip = null;      
+      LXPoint nextPointOnCurrentStrip = null;      
       this.currentStripIndex += this.direction;
       if (this.currentStripIndex >= 0 && this.currentStripIndex < this.currentStrip.points.size()) {
         nextPointOnCurrentStrip = this.currentStrip.points.get(this.currentStripIndex);
@@ -745,7 +747,7 @@ class TimTrace extends SCPattern {
     Map<Strip, Vector3> stripToCenter = new HashMap();
     for (Strip s : model.strips) {
       Vector3 v = new Vector3();
-      for (Point p : s.points) {
+      for (LXPoint p : s.points) {
         v.add(p.x, p.y, p.z);
       }
       v.divide(s.points.size());
@@ -770,23 +772,23 @@ class TimTrace extends SCPattern {
     return stripToNeighbors;
   }
   
-  private Map<Point, List<Point>> buildPointToNeighborsMap() {
-    Map<Point, List<Point>> m = new HashMap();
+  private Map<LXPoint, List<LXPoint>> buildPointToNeighborsMap() {
+    Map<LXPoint, List<LXPoint>> m = new HashMap();
     Map<Strip, List<Strip>> stripToNearbyStrips = this.buildStripToNearbyStripsMap();
     
     for (Strip s : model.strips) {
       List<Strip> nearbyStrips = stripToNearbyStrips.get(s);
       
-      for (Point p : s.points) {
+      for (LXPoint p : s.points) {
         Vector3 v = new Vector3(p.x, p.y, p.z);
         
-        List<Point> neighbors = new ArrayList();
+        List<LXPoint> neighbors = new ArrayList();
         
         for (Strip nearbyStrip : nearbyStrips) {
-          Point closestPoint = null;
+          LXPoint closestPoint = null;
           float closestPointDistance = 100000;
           
-          for (Point nsp : nearbyStrip.points) {
+          for (LXPoint nsp : nearbyStrip.points) {
             float distance = v.distanceTo(nsp.x, nsp.y, nsp.z);
             if (closestPoint == null || distance < closestPointDistance) {
               closestPoint = nsp;
@@ -806,10 +808,10 @@ class TimTrace extends SCPattern {
     return m;
   }
   
-  private Map<Point, Strip> buildPointToStripMap() {
-    Map<Point, Strip> m = new HashMap();
+  private Map<LXPoint, Strip> buildPointToStripMap() {
+    Map<LXPoint, Strip> m = new HashMap();
     for (Strip s : model.strips) {
-      for (Point p : s.points) {
+      for (LXPoint p : s.points) {
         m.put(p, s);
       }
     }
@@ -817,7 +819,7 @@ class TimTrace extends SCPattern {
   }
   
   public void run(double deltaMs) {
-    for (Point p : model.points) {
+    for (LXPoint p : model.points) {
       color c = colors[p.index];
       colors[p.index] = lx.hsb(lx.h(c), lx.s(c), lx.b(c) - 3);
     }
@@ -828,3 +830,72 @@ class TimTrace extends SCPattern {
     }
   }
 }
+
+class TimMetronome extends SCPattern {
+  private BasicParameter clickyParameter = new BasicParameter("CLICK", 0, 0, 10.0);
+  private BasicParameter derezParameter = new BasicParameter("DREZ", 0.5, 0, 1.0);
+  private BasicParameter driftParameter = new BasicParameter("DRIFT", 0, 0, 1.0);
+  private BasicParameter fadeParameter = new BasicParameter("FADE", 0.05, 0, 0.2);
+  private float modelWidth;
+  private int beatNum;
+  private float prevTempoRamp;
+  private LXProjection projection;
+  private float[] values;
+  private float[] hues;
+  
+  TimMetronome(GLucose glucose) {
+    super(glucose);
+    addParameter(clickyParameter);
+    addParameter(derezParameter);
+    addParameter(driftParameter);
+    addParameter(fadeParameter);
+    modelWidth = model.xMax - model.xMin;
+    projection = new LXProjection(model);
+    beatNum = 0;
+    prevTempoRamp = 0;
+    values = new float[model.points.size()];
+    hues = new float[model.points.size()];
+  }
+  
+  public void run(double deltaMs) {
+    float tempoRamp = lx.tempo.rampf();
+    if (tempoRamp < prevTempoRamp) {
+      beatNum = (beatNum + 1) % 1000;
+    }
+    prevTempoRamp = tempoRamp;
+    
+    float phase = beatNum + pow(tempoRamp, 1.0 + clickyParameter.getValuef());
+    
+    projection.reset();
+    projection.translateCenter(model.xMin, model.yMin, model.cz);
+    projection.rotate(phase * 0.5 * PI, 0, 0, 1);
+    
+    projection.translate(driftParameter.getValuef() * tempoRamp * modelWidth * 0.5, 0, 0);
+    
+    float derezCutoff = derezParameter.getValuef();
+    
+    float fadeMultiplier = (1.0 - fadeParameter.getValuef());
+    
+    float armRadius = modelWidth * 0.1;
+    for (LXVector p : projection) {
+      boolean onArm = false;
+      if (abs(p.x) < armRadius) {
+        onArm = (p.y > 0) || (sqrt(pow(p.x, 2) + pow(p.y, 2)) < armRadius);
+      }
+      if (onArm) {
+        values[p.index] = 1.0;
+        hues[p.index] = (floor(phase / 4) * 90) % 360;
+      } else {
+        values[p.index] *= fadeMultiplier;
+      }
+      
+      float saturation = pow(1 - values[p.index], 0.5) * 0.7 + 0.3;
+      float brightness = values[p.index];
+      
+      if (random(1.0) > derezCutoff) {
+        colors[p.index] = lx.hsb(hues[p.index], saturation * 100, brightness * 100);
+      }
+    }
+  }
+}
+