Updates reflection test page.
authordsc <david.schoonover@gmail.com>
Fri, 5 Nov 2010 01:06:47 +0000 (18:06 -0700)
committerdsc <david.schoonover@gmail.com>
Fri, 5 Nov 2010 01:06:47 +0000 (18:06 -0700)
src/portal/math/line.js
src/portal/math/vec.js
test/math/math.test.js

index 7229216..2d84eb2 100644 (file)
@@ -5,8 +5,8 @@ math.Line = new Y.Class('Line', math.Vec, {
     
     init : function init(x1,y1, x2,y2, t){
         this.t  = 1/(t || 1);
-        this.x1 = x1; this.y1 = y1;
-        this.x2 = x2; this.y2 = y2;
+        this.x1 = x1; this.y1 = y1; this.p1 = new math.Vec(x1,y1);
+        this.x2 = x2; this.y2 = y2; this.p2 = new math.Vec(x2,y2);
         
         var xdelta = x2-x1, ydelta = y2-y1
         ,    m = this.slope  =  ydelta/xdelta
@@ -32,6 +32,10 @@ math.Line = new Y.Class('Line', math.Vec, {
         return y/this.slope + this.xint;
     },
     
+    base : function base(){
+        return new math.Line(0,0, this.x,this.y);
+    },
+    
     toString : function toString(){
         return 'Line('+this.x1+','+this.y1+', '+this.x2+','+this.y2+', slope='+this.slope+')';
     }
index 84b90a3..7b042a8 100644 (file)
@@ -18,7 +18,7 @@ math.Vec = new Y.Class('Vec', {
     },
     
     clone : function clone(){
-        return new Vec(this.x, this.y);
+        return new math.Vec(this.x, this.y);
     },
     
     scale : function scale(s){
@@ -69,11 +69,11 @@ math.Vec = new Y.Class('Vec', {
 
 Y.extend(math.Vec, {
     sum : function sum(a, b) {
-        return new Vec(a.x+b.x, a.y+b.y);
+        return new math.Vec(a.x+b.x, a.y+b.y);
     },
     
     difference : function difference(a, b) {
-        return new Vec(a.x-b.x, a.y-b.y);
+        return new math.Vec(a.x-b.x, a.y-b.y);
     },
     
     dot : function dot(a, b) {
@@ -81,14 +81,17 @@ Y.extend(math.Vec, {
     },
     
     lerp : function lerp(x, a, b) {
-        return new Vec( math.lerp(a.x, b.x, x),
+        return new math.Vec( math.lerp(a.x, b.x, x),
                         math.lerp(a.y, b.y, x)  );
     },
     
     reflect : function reflect(v, line){
+        var dot   = math.Vec.dot
+        ,   basev = math.Vec.difference(v, line.p1);
         return line.clone()
-            .scale(2 * v.dot(line) / line.dot(line))
-            .subtract(v);
+            .scale(2 * dot(basev,line) / dot(line,line))
+            .subtract(basev)
+            .add(line.p1);
     }
     
 });
index ee96a8b..2dc338d 100644 (file)
@@ -15,6 +15,13 @@ grid.lineWidth = 1.0;
 grid.strokeStyle = '#E0E0E0'; //'#EEEEEE'; //
 grid.draw();
 
+// Draw axes
+ctx = grid.ctx;
+drawLine(-w,-h2, w,-h2, '#CCCCCC', 2.0);
+drawLine(w2,-h,  w2,h, '#CCCCCC', 2.0);
+
+
+
 P = new Layer()
     .width(w).height(h)
     .appendTo(grid);
@@ -23,39 +30,110 @@ ctx = P.ctx;
 ctx.translate(w2, h2);
 ctx.scale(PPU, PPU);
 
-// Draw axes
-drawLine(-W2,0, W2,0, '#CCCCCC');
-drawLine(0,-H2, 0,H2, '#CCCCCC');
+points = Y([]);
+line = mkLine(-3,2, 4,7);
+addPoint(-5,2);
 
-testLine(1,2, 4,7,    'rgba(231,48,117, 0.5)',  'rgba(69,150,255, 1)');
-// testLine(-4,-2, 7,13, 'rgba(131,187,50, 0.75)', 'rgba(69,150,255, 1)');
+dragging = false;
+P.layer.bind('click', function(evt){
+    if (!dragging) {
+        var v = convertLoc(evt);
+        addPoint(v.x,v.y);
+    }
+    return false;
+});
 
 });
 
-function testLine(x1,y1, x2,y2, color, pcolor){
-    var t,p, line = new math.Line(x1,y1, x2,y2, 10);
+function convertLoc(evt){
+    var off = P.layer.offset()
+    ,   x   = (evt.pageX - off.left - w2)/(PPU)
+    ,   y   = (evt.pageY - off.top  - h2)/PPU * -1;
+    return new math.Vec(x,y);
+}
+
+function clear(){
+    ctx.clearRect(-2*w,-2*h, 4*w,4*h);
+    points.forEach(removePoint);
+    p1.remove(); p2.remove();
+}
+
+function mvLine(pn, x,y){
+    var x1 = (pn === 1 ? x : line.x1)
+    ,   y1 = (pn === 1 ? y : line.y1)
+    ,   x2 = (pn === 2 ? x : line.x2)
+    ,   y2 = (pn === 2 ? y : line.y2)
+    ;
+    mkLine(x1,y1, x2,y2);
+    redraw();
+}
+
+function redraw(color){
+    color = color || 'rgba(231,48,117, 0.5)';
+    var pts = points.clone();
+    clear();
     drawLine(-W/2, line.calcY(-W2), line.calcX(H2), H2, color);
-    drawPoint(line.x1, line.y1);
-    drawPoint(line.x2, line.y2);
-    
-    drawPoint(0, 0, pcolor);
+    P.append(p1, p2);
+    pts.forEach(addPoint);
+}
+
+function removePoint(c){
+    if (c.reflected) c.reflected.remove();
+    points.remove(c);
+    c.remove();
+}
+
+function addPoint(x,y){
+    if (x instanceof Shape) {
+        var c = x;
+        removePoint(c);
+        P.append(x);
+    } else {
+        var v = new math.Vec(x,y)
+        ,   c = drawPoint(v, null, '#552F74');
+    }
     
-    t = 0;
-    p = line.pcalc(t);
-    drawPoint(p.x, p.y, pcolor);
+    var rv = math.Vec.reflect(c.vec,line)
+    ,   rc = c.reflected = drawPoint(rv, null, '#F25522');
+    points.push(c);
+}
+
+function mkLine(x1,y1, x2,y2, color, pcolor){
+    if (window.p1) p1.remove();
+    if (window.p2) p2.remove();
     
-    t = 1;
-    p = line.pcalc(t);
-    drawPoint(p.x, p.y, pcolor);
+    color = color || 'rgba(231,48,117, 0.5)';
+    pcolor = pcolor || 'rgba(69,150,255, 1)';
+    var line = new math.Line(x1,y1, x2,y2, 10);
+    drawLine(-W/2, line.calcY(-W2), line.calcX(H2), H2, color);
     
-    t = -1;
-    p = line.pcalc(t);
-    drawPoint(p.x, p.y, pcolor);
+    p1 = drawPoint(line.x1, line.y1, pcolor);
+    p1.layer.bind('mousedown', function(){
+        dragging = true;
+        function onMove(evt){
+            var r = 3.75, v = convertLoc(evt);
+            mvLine(1, v.x,v.y);
+            
+            // _p1.appendTo(P);
+            // p1.position(w2-r + v.x*PPU, h2-r - v.y*PPU)
+            
+            return false;
+        }
+        P.layer.bind('mousemove', onMove);
+        P.layer.bind('mouseup', function(evt){
+            dragging = false;
+            P.layer.unbind('mousemove', onMove);
+            P.layer.unbind('mouseup', arguments.callee);
+            // _p1.remove();
+            return false;
+        });
+        return false;
+    });
     
-    return line;
+    p2 = drawPoint(line.x2, line.y2, pcolor);
+    return (window.line = line);
 }
 
-
 function drawLine(x1,y1, x2,y2, color, width){
     ctx.beginPath();
     ctx.lineWidth = width || PX;
@@ -68,11 +146,19 @@ function drawLine(x1,y1, x2,y2, color, width){
 
 function drawPoint(x,y, color, r){
     r = r || 3.75;
+    if (x instanceof math.Vec) {
+        var v = x;
+        x = v.x;
+        y = v.y;
+    } else
+        var v = new math.Vec(x,y);
+    
     var c = new Circle(r)
         .position(w2-r + x*PPU, h2-r - y*PPU)
         .attr({ 'fillStyle': color || 'rgba(0,0,0,0.5)' })
         .appendTo(P)
         .draw();
+    c.vec = v;
     c.layer.attr('title', '('+x+','+y+')');
     return c;
 }