Given a point outside of an arc, how can one find the point on the arc which extends to that point?

104 Views Asked by At

Given a point outside of an arc, how can one find the point on the arc which extends to that point?

For example, the radius of the circle (R) is 10cm, it's center point is [0,0].
The origin (o) of the line (8) is at [-3, 10]
How can we find the point (p) (p8) were the tangent at that point continues to the origin of the line?

A brute force solution would not be acceptable.

Extensions of arc

3

There are 3 best solutions below

2
On BEST ANSWER

If i understood your question correctly, you want to find the point at which the tangent of the circle that passes through [-3, 10] touches the circle. Using the fact that a radius to that point will be perpendicular to the tangent, we can find that point quite easily. Lets build the triangle with vertices in [-3, 10], [0, 0] and the point we are trying to find. It will be a right triangle, so we can use the Pythagoras theorem. We know the length of one of the catheti is 10 (radius), and the hypotenuse is $\sqrt{3^2 + 10^2} = \sqrt{109}$. The length of the second cathetus will therefore be $\sqrt{109 - 10^2} = 3$. Lets build a circle with this radius and the center in [-3, 10]. The point of intersection of two circles will be the desired point. enter image description here

1
On

Construct a half-circle on diameter $PO$ (see figure below) to intersect the circle at tangency point $T$. That works because $\angle OTP=90°$.

enter image description here

0
On

Here's the code I came up with. I'm sure it can be improved but my math is not holding there!

Based on @Aretino answer.

  1. Make a circle with a radius half the distance between o and p, originate it at the midpoint of the line op.
  2. Calculate the intersection point of the original circle and the newly made circle.

Can see a working snippet https://stackoverflow.com/questions/60156373/given-a-point-outside-of-an-arc-how-can-one-find-the-point-on-the-arc-which-ext/60171900#60171900

Intersection point

// Function to find tangent intersection points to a point outside of the circle
// Credits
// https://math.stackexchange.com/questions/3541795/given-a-point-outside-of-an-arc-how-can-one-find-the-point-on-the-arc-which-ext/3541928#3541928
// https://stackoverflow.com/questions/60156373/given-a-point-outside-of-an-arc-how-can-one-find-the-point-on-the-arc-which-ext
/**
 *
 *
 * @param {number} centerX1 Center of circle 1 X
 * @param {number} centerY1 Center of circle 1 Y
 * @param {number} radius1 Radius of circle 1
 * @param {number} centerX2 Center of circle 2 X
 * @param {number} centerY2 Center of circle 2 Y
 * @param {number} radius2 Radius of circle 2
 * @returns {object | boolean} The to intersect points { point1: [x1, y1], point2: [x2, y2] } or false
 * @credit Math based on https://www.analyzemath.com/CircleEq/circle_intersection_calcu.html
 */
var circleIntersections = function(
  centerX1,
  centerY1,
  radius1,
  centerX2,
  centerY2,
  radius2
) {
  var a, b, c, A, B, C, delta, x1, x2, y1, y2;

  a = -(centerY1 - centerY2) / (centerX1 - centerX2);
  b = 2 * (centerX1 - centerX2);
  c =
    (-radius1 * radius1 +
      radius2 * radius2 +
      centerX1 * centerX1 -
      centerX2 * centerX2 +
      centerY1 * centerY1 -
      centerY2 * centerY2) /
    b;
  A = a * a + 1;
  B = 2 * a * c - 2 * centerX1 * a - 2 * centerY1;
  C =
    c * c +
    centerX1 * centerX1 -
    2 * centerX1 * c +
    centerY1 * centerY1 -
    radius1 * radius1;
  delta = B * B - 4 * A * C;
  if (delta < 0) {
    return false;
  }
  y1 = (-B + Math.sqrt(delta)) / (2 * A);
  x1 = a * y1 + c;
  y2 = (-B - Math.sqrt(delta)) / (2 * A);
  x2 = a * y2 + c;

  return {
    point1: [x1, y1],
    point2: [x2, y2]
  };
};

/**
 *
 *
 * @param {number} centerX Center of circle X
 * @param {number} centerY Center of circle Y
 * @param {number} radius Radius of circle
 * @param {number} pointX Point to tangent to X
 * @param {number} pointY Point to tangent to Y
 * @returns {object | boolean} The to intersect points { point1: [x1, y1], point2: [x2, y2] } or false
 */
var tangentLines = function(centerX, centerY, radius, pointX, pointY) {
  var centerX2, centerY2, radius2, dX, dY;
  centerX2 = centerX - (centerX - pointX) / 2;
  centerY2 = centerY - (centerY - pointY) / 2;
  dX = centerX2 - centerX;
  dY = centerY2 - centerY;
  radius2 = Math.sqrt(dX * dX + dY * dY);

  return circleIntersections(
    centerX,
    centerY,
    radius,
    centerX2,
    centerY2,
    radius2
  );
};

new Vue({
  el: '#app',
  template: `
        <div>
          <div>
            centerX: <input v-model="centerX" @input="intersectionPoints">
            centerY:  <input v-model="centerY" @input="intersectionPoints">
            <div>radius: <input v-model="radius" @input="intersectionPoints"></div>
          </div>
          <div>
            pointX: <input v-model="pointX" @input="intersectionPoints">
            pointY: <input v-model="pointY" @input="intersectionPoints">
          </div>
          <div v-if=result>
          <div>point1: {{result.point1}}</div>
          <div>point2: {{result.point2}}</div>
          </div>
          <div v-if=!result>No intersections :-(</div>
        </div>
            `,
  data: function() {
    return {
      centerX: 200,
      centerY: 200,
      radius: 100,
      pointX: 160,
      pointY: 100,
      result: null
    };
  },
  methods: {
    intersectionPoints() {
      this.result = tangentLines(
        this.centerX,
        this.centerY,
        this.radius,
        this.pointX,
        this.pointY
      );
    }
  },
  mounted: function() {
    this.intersectionPoints();
  }
});

// Without Vue just use something like
// tangentLines(200, 200, 100, 160, 100);
div {
margin:5px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id=app></div>