Find arc's mid-point given start, end, and center (of circle) points

强颜欢笑 提交于 2019-12-07 06:21:09

问题


I'm looking for some help on how to find an arc's mid-point. I have the start and end points, center of circle, and radius. I've searched everywhere online and cannot find an answer that I can convert into code anywhere. If anyone has any ideas, please let me know. The following picture is what I'm trying to find (assume that the center of the circle is already found).


回答1:


Atan2() of the mean of x1,x2 and the mean of y1,y2 gives you the angle to the mid point. The mid point at the arc is therefore found as:

double c=Math.Atan2(y1+y2, x1+x2);
double x_mid=R*Math.Cos(c);
double y_mid=R*Math.Sin(c);

Note that I removed the factor of 1/2 (for the mean) from both arguments to Atan2 since that does not change the angle.

Update: that this method will always find the mid point on the shortest arc between the two points on the perimeter. That may or may not be what you need.




回答2:


Although this function returns an approximate point, it's useful for practical purposes. I just figured this one out myself and it works great.

Prerequisites:
- An arc center of (0, 0) is assumed here, although this could be modified to work with a center point parameter
- You must know the angle at which the arc starts (270 for example)
- You must know the measurement of the angle of the arc (90 degrees for example)

The code below is written in Objective-C:

#define   DEGREES_TO_RADIANS(degrees)  ((M_PI * degrees)/ 180)
- (CGPoint)getApproximateMidPointForArcWithStartAngle:(CGFloat)startAngle andDegrees:(CGFloat)degrees {

CGFloat midPointDegrees = fmodf(startAngle + degrees / 2, 360);
CGFloat midStartAngle = midPointDegrees - .1f;
CGFloat midEndAngle = midPointDegrees + .1f;

UIBezierPath *midPointPath = [UIBezierPath bezierPathWithArcCenter:CGPointMake(0, 0) radius:self.radius startAngle:DEGREES_TO_RADIANS(midStartAngle) endAngle:DEGREES_TO_RADIANS(midEndAngle) clockwise:YES];

CGRect midPointPathFrame = CGPathGetPathBoundingBox(midPointPath.CGPath);
CGPoint approximateMidPointCenter = CGPointMake(CGRectGetMidX(midPointPathFrame), CGRectGetMidY(midPointPathFrame));
return approximateMidPointCenter;
}



回答3:


Take the end points.

(x1, y1), (x2, y2)

Normalize them about the center of the circle. Then convert to polar.

(r, theta1), (r, theta2)

The radii will be the same. The center of the arc is

(r, (theta2 + theta1) / 2)

Convert to Cartesian coordinates and add the coordinates of the center.

EDIT: something like this:

def Point CenterOfArc(Point start, end, center)
    let (x1, y1) = (start.x - center.x, start.y - center.y)
    let (x2, y2) = (end.x   - center.x, end.y   - center.y)

    let (r1, theta1) = (sqrt(x1^2 + y1^2), atan(y1/x1))
    let (r2, theta2) = (sqrt(x2^2 + y2^2), atan(y2/x2))
    if (theta1 > theta2) theta2 += 2 * pi

    let (r, theta) = ((r1 + r2) / 2, (theta1 + theta2) / 2) // averaging in case of rounding error

    let (x, y) = (r * cos(theta), r * sin(theta))

    return (x + center.x, y + center.y)
end

EDIT2: When you convert to polar, you need to ensure that theta2 > theta1, otherwise it'll be as though the arc was backward.

EDIT3: Also, tan<sup>-1</sup>(y/x) is the correct operation, but for many languages, you should call it as atan2(y, x) rather than atan(y/x). atan2 is designed for this use, and it avoids errors when x=0 and may give more accurate results.



来源:https://stackoverflow.com/questions/11674239/find-arcs-mid-point-given-start-end-and-center-of-circle-points

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!