2013-08-17 107 views
5

有没有人知道电缆样(或基本上任何线或绳)behviour很好的例子?

我目前正在编写一个半模块化合成器。我正在使用Raphael.js作为电缆。但他们似乎太僵硬。我想添加一些物理学,所以当我拖动一端并且第二个不连接时,另一端会挂起并以稍微弯曲的方式移动。我想我正在寻找的是重力。SVG - 示例|电缆与物理(重力)

眼下电缆这样的表现:

jsFiddle


有了这个代码:

window.onload = function() { 
    var r = Raphael("cables", 1420, 795), 
     discattr = { 
      fill: "#aaa", 
      stroke: "#ddd" 
     }; 



    function curve(x, y, ax, ay, bx, by, zx, zy, color) { 
     var movrattr = { 
      fill: color || Raphael.getColor(), 
      stroke: "none" 
     }; 
     var path = [ 
      ["M", x, y], 
      ["C", ax, ay, bx, by, zx, zy] 
     ], 
      path2 = [ 
       ["M", x, y], 
       ["L", ax, ay], 
       ["M", bx, by], 
       ["L", zx, zy] 
      ], 
      curve = r.path(path).attr({ 
       stroke: color || Raphael.getColor(), 
       "stroke-width": 4 
      }).shadow(), 
      controls = r.set(
       r.path(path2).attr({ 
        stroke: "none" 
       }), 
       r.circle(x, y, 7).attr(discattr).emboss(1).light(-100,-100,30,'#aaaaaa','diffuse'), 
       r.circle(ax, ay, 0).attr({ 
        stroke: "none" 
       }), 
       r.circle(bx, by, 0).attr({ 
        stroke: "none" 
       }), 
       r.circle(zx, zy, 7).attr(discattr).emboss(1).light(-100,-100,30,'#aaaaaa','diffuse') 
      ), 
      mover = r.set(

       r.circle(zx, zy + 9, 7).attr(movrattr) 
      ); 

     mover[0].move = function(x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 

      // path[1][5] = X; 
      // path[1][6] = Y; 
      // path2[3][2] = X; 
      // path2[3][3] = Y; 
      controls[1].update(x, y); 
      controls[4].update(x, y, true); 

     }; 
     mover[0].update = function(x, y, dragging) { 
      if (!dragging) return false; 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 



     }; 
     controls[1].update = function(x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[0][3] = X; 
      path[0][4] = Y; 
      path2[0][4] = X; 
      path2[0][5] = Y; 



      controls[2].update(x, y); 
     }; 
     controls[2].update = function(x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][5] = X; 
      path[1][6] = Y; 
      path2[1][6] = X; 
      path2[1][7] = Y; 
      curve.attr({ 
       path: path 
      }); 
      controls[0].attr({ 
       path: path2 
      }); 

     }; 
     controls[3].update = function(x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][3] = X; 
      path[1][4] = Y; 
      path2[2][7] = X; 
      path2[2][8] = Y; 

      curve.attr({ 
       path: path 
      }); 
      controls[0].attr({ 
       path: path2 
      }); 

     }; 

     controls[4].update = function(x, y, dragging) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 

      path[1][5] = X; 
      path[1][6] = Y; 
      path2[3][8] = X; 
      path2[3][9] = Y; 
      controls[3].update(x, y); 
      console.log(dragging) 
      if (dragging) return false; 

      mover[0].update(x, y, 'true'); 
     }; 
     controls.drag(move, up); 
     mover.drag(drag, up); 
    } 

    function move(dx, dy) { 
     this.update(dx - (this.dx || 0), dy - (this.dy || 0)); 
     this.dx = dx; 
     this.dy = dy; 

    } 

    function drag(dx, dy) { 
     this.move(dx - (this.dx || 0), dy - (this.dy || 0)); 
     this.dx = dx; 
     this.dy = dy; 

    } 



    function up() { 
     this.dx = this.dy = 0; 
    } 
var newCable = function(){ 
     curve(20, 20, 40, 270, 100, 270, 120, 20, "hsb(" + Math.random() + ", .75, .75)"); 

}; 





    $('#newCable').on('click', newCable); 


}; 

编辑


这里还有一个FID用颤抖的电缆DLE(只需将顶部的灰色圆圈)

jsFiddle


var r = Raphael("holder", window.innerWidth, window.innerHeight) 

    function findReflected(coord, about) { 
     var diff = about - coord; 
     return about + diff; 
    } 

    function curve(x1, y1, cx1, cy1, cx2, cy2, x2, y2, cx3, cy3, x3, y3, color) { //zx --x1 
     var cx2b = findReflected(cx2, x2), 
      cy2b = findReflected(cy2, y2), 
      path = [ 
       ["M", x1, y1], 
       ["C", cx1, cy1, cx2, cy2, x2, y2, "S", cx3, cy3, x3, y3] 
      ], 
      path2 = [ 
       ["M", x1, y1], 
       ["L", cx1, cy1], 
       ["M", cx2, cy2], 
       ["L", cx2b, cy2b], 
       ["M", x3, y3], 
       ['L', cx3, cy3] 
      ], 
      curve = r.path(path).attr({ 
       stroke: color || Raphael.getColor(), 
        "stroke-width": 4, 
        "stroke-linecap": "round" 
      }), 
      controls = r.set(
      r.path(path2).attr({ 
       stroke: "none" 
      }), 
      r.circle(x1, y1, 7).attr({ 
       fill: "#ccc", 
       stroke: "none" 
      }), 
      r.circle(cx1, cy1, 5).attr({ 
       fill: "transparent", 
       stroke: "none" 
      }), 
      r.circle(cx2, cy2, 5).attr({ 
       fill: "transparent", 
       stroke: "none" 
      }), 
      r.circle(x2, y2, 5).attr({ 
       fill: "transparent", 
       stroke: "none" 
      }), 
      r.circle(cx2b, cy2b, 5).attr({ 
       fill: "transparent", 
       stroke: "none" 
      }), 
      r.circle(cx3, cy3, 5).attr({ 
       fill: "transparent", 
       stroke: "none" 
      }), 
      r.circle(x3, y3, 7).attr({ 
       fill: "#ccc", 
       stroke: "none" 
      }) 

      ); 
     controls[1].update = function (x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[0][1] = X; 
      path[0][2] = Y; 
      path2[0][1] = X; 
      path2[0][2] = Y; 
      controls[2].update(x, y); 
     }; 
     controls[2].update = function (x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][1] = X; 
      path[1][2] = Y; 
      path2[1][1] = X; 
      path2[1][2] = Y; 
      curve.attr({ 
       path: path 
      }); 
      controls[0].attr({ 
       path: path2 
      }); 
     }; 
     controls[3].update = function (x, y, doReflect) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][3] = X; 
      path[1][4] = Y; 
      path2[2][1] = X; 
      path2[2][2] = Y; 
      curve.attr({ 
       path: path 
      }); 
      controls[0].attr({ 
       path: path2 
      }); 
      if (typeof doReflect === undefined || doReflect == null) controls[5].update(-x, -y, false); 
     }; 
     controls[4].update = function (x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][5] = X; 
      path[1][6] = Y; 
      controls[3].update(x, y, false); 
      controls[5].update(x, y, false); 
     }; 
     controls[5].update = function (x, y, doReflect) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path2[3][1] = X; 
      path2[3][2] = Y; 
      controls[0].attr({ 
       path: path2 
      }); 
      if (typeof doReflect === undefined || doReflect == null) controls[3].update(-x, -y, false); 
     }; 
     controls[6].update = function (x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][8] = X; 
      path[1][9] = Y; 
      path2[5][1] = X; 
      path2[5][2] = Y; 
      curve.attr({ 
       path: path 
      }); 
      controls[0].attr({ 
       path: path2 
      }); 
     }; 
     controls[7].update = function (x, y) { 
      var X = this.attr("cx") + x, 
       Y = this.attr("cy") + y; 
      this.attr({ 
       cx: X, 
       cy: Y 
      }); 
      path[1][10] = X; 
      path[1][11] = Y; 
      path2[4][1] = X; 
      path2[4][2] = Y; 
      controls[1].update(x, y); 
      controls[4].update(x, y); 
      controls[6].update(x, y); 
     }; 

     controls.drag(move, up); 
     var count = 0; 
     var shake; 


     $('circle:eq(6)').on('mousedown', function() { 
      shake = setInterval(function() { 
       count++; 
       if (count <= 4) { 
        controls[4].update(-1, 0); 
        controls[1].update(2, 0); 
       } else if (count <= 12) { 
        controls[4].update(1, 0); 
        controls[1].update(-2, 0); 

       } else if (count <= 16) { 
        controls[4].update(-1, 0); 
        controls[1].update(2, 0); 

       } else { 
        count = 0; 

       } 

      }, 30); 
     }).on('mouseup', function() { 
      clearInterval(shake); 
     }); 

    } 

    function move(dx, dy) { 
     this.update(dx - (this.dx || 0), dy - (this.dy || 0)); 
     this.dx = dx; 
     this.dy = dy; 
    } 

    function up() { 
     this.dx = this.dy = 0; 
    } 
curve(100, 350, 100, 300, 100, 300, 100, 200, 100, 100, 100, 50, "hsb(0.2, 0.7, 0.8)"); 

这里是什么,我目前工作的一个屏幕截图。

Roland System 100 in javascript html5 and css3

回答

0

确定这里是我的新手答案。这看起来可能很有趣,但如果将线材多边形化到很高的程度,并且将每个顶点附加一个模拟重力的行为会怎样?就像在页面底部的加速度数学一样,直到他们到达他们看起来像是在垂下的某个点?

如果失败了,我知道有一个相当广泛的JS物理引擎,名为Ammo.js。不知道它如何在SVG上使用,因为我只看到它与3D Three.js对象一起工作