Javascript 具有任意点数的逆运动学

Javascript 具有任意点数的逆运动学,javascript,html,canvas,inverse-kinematics,Javascript,Html,Canvas,Inverse Kinematics,我已经用HTML5画布修改了JavaScript中的反向运动学示例,并通过将其拆分为一个函数使其成为动态的,它可以工作,但示例仅使用3个点——开始点、中间点和结束点,我想随意更改点的数量。这是我目前的 如何使此函数与n个点一起工作?我在上找到了此函数。也许会有帮助。是的,我大约30分钟前找到的。有点混乱,但我可能能够实现它。 function _kinematics(joints, fx, mouse) { joints.forEach(function (joint) { join

我已经用HTML5画布修改了JavaScript中的反向运动学示例,并通过将其拆分为一个函数使其成为动态的,它可以工作,但示例仅使用3个点——开始点、中间点和结束点,我想随意更改点的数量。这是我目前的


如何使此函数与n个点一起工作?

我在上找到了此函数。也许会有帮助。是的,我大约30分钟前找到的。有点混乱,但我可能能够实现它。
function _kinematics(joints, fx, mouse) {
  joints.forEach(function (joint) {
    joint.target = joint.target || {
      x: fx.canvas.width / 2,
      y: fx.canvas.height / 2
    };
    joint.start = joint.start || {
      x: 0,
      y: 0
    };
    joint.middle = joint.middle || {
      x: 0,
      y: 0
    };
    joint.end = joint.end || {
      x: 0,
      y: 0
    };
    joint.length = joint.length || 50;
  });
  var theta,
    $theta,
    _theta,
    dx,
    dy,
    distance;
  joints.forEach(function (joint) {
    if (mouse) {
      joint.target.x = mouse.x;
      joint.target.y = mouse.y;
    }
    dx = joint.target.x - joint.start.x;
    dy = joint.target.y - joint.start.y;
    distance = Math.sqrt(Math.pow(dx, 2) + Math.pow(dy, 2));
    _theta = Math.atan2(dy, dx);
    if (distance < joint.length) {
      theta = Math.acos(distance / (joint.length + joint.length)) + _theta;
      dx = dx - joint.length * Math.cos(theta);
      dy = dy - joint.length * Math.sin(theta);
      $theta = Math.atan2(dy, dx);
    } else {
      theta = $theta = _theta;
    }
    joint.middle.x = joint.start.x + Math.cos(theta) * joint.length;
    joint.middle.y = joint.start.y + Math.sin(theta) * joint.length;
    joint.end.x = joint.middle.x + Math.cos($theta) * joint.length;
    joint.end.y = joint.middle.y + Math.sin($theta) * joint.length;
    fx.beginPath();
    fx.moveTo(joint.start.x, joint.start.y);
    /* for (var i = 0; i < joint.points.length / 2; i++) {
        fx.lineTo(joint.points[i].x, joint.points[i].y);
    } */
    fx.lineTo(joint.middle.x, joint.middle.y);
    /* for (var j = joint.points.length / 2; j < joint.points.length; j++) {
        fx.lineTo(joint.points[j].x, joint.points[j].y);
    } */
    fx.lineTo(joint.end.x, joint.end.y);
    fx.strokeStyle = "rgba(0,0,0,0.5)";
    fx.stroke();
    fx.beginPath();
    fx.arc(joint.start.x, joint.start.y, 10, 0, Math.PI * 2);
    fx.fillStyle = "rgba(255,0,0,0.5)";
    fx.fill();
    fx.beginPath();
    fx.arc(joint.middle.x, joint.middle.y, 10, 0, Math.PI * 2);
    fx.fillStyle = "rgba(0,255,0,0.5)";
    fx.fill();
    fx.beginPath();
    fx.arc(joint.end.x, joint.end.y, 10, 0, Math.PI * 2);
    fx.fillStyle = "rgba(0,0,255,0.5)";
    fx.fill();
  });
}
populate(_joints, $joints, function() {
  var coords = randCoords(map);
  var o = {
    start: {
      x: coords.x,
      y: coords.y
    },
    // points: [],
    target: {
      x: mouse.x,
      y: mouse.y
    }
  };
  /* for (var p = 0; p < 10; p++) {
    o.points.push({
      x: p === 0 ? o.start.x + (o.length || 50) : o.points[p - 1].x + (o.length || 50),
      y: p === 0 ? o.start.y + (o.length || 50) : o.points[p - 1].y + (o.length || 50)
    });
  }; */
  return o;
});