/// <summary> /// 以半径为基准作为获取过渡圆弧 /// </summary> /// <param name="lineStart">线起点</param> /// <param name="intersection">线与原始圆弧交点</param> /// <param name="oriArcCenter">原始圆弧圆心</param> /// <param name="transitionR">过渡圆弧半径</param> /// <param name="oriArcClockwise">原始圆弧方向</param> /// <returns>过渡圆弧的起点、圆心、终点</returns> public static List <PointD> GetLineToArcTransitionArcByR(PointD lineStart, PointD intersection, PointD oriArcCenter, double transitionR, double oriArcClockwise) { List <PointD> points = new List <PointD>(); PointD transitionArcCenter, newLineEnd, newArcStart; double angle = GetAngleOfTwoLine(lineStart, intersection, oriArcCenter); VectorD vArcS = intersection - oriArcCenter; double oriR = vArcS.Length; VectorD vArcSRotate1; if (oriArcClockwise == 1) { vArcSRotate1 = vArcS.Rotate(-90); } else { vArcSRotate1 = vArcS.Rotate(90); } if (angle != Math.PI) { //求原始圆弧半径 double len1; if (GetAngleOfTwoLine(lineStart, intersection, (intersection + vArcSRotate1)) > (Math.PI / 2)) { len1 = oriR * Math.Sin(Math.PI - angle) + transitionR; } else { len1 = oriR * Math.Sin(Math.PI - angle) - transitionR; } double len2 = Math.Sqrt((oriR + transitionR) * (oriR + transitionR) - len1 * len1); PointD footPoint = MathUtils.GetFootPoint(oriArcCenter, lineStart, intersection); VectorD vLenTemp = (footPoint - oriArcCenter); VectorD vLen1 = vLenTemp.ScaleBy(len1 / vLenTemp.Length); VectorD vLine = lineStart - intersection; VectorD vLen2 = vLine.ScaleBy(len2 / vLine.Length); transitionArcCenter = oriArcCenter + vLen1 + vLen2; newLineEnd = MathUtils.GetFootPoint(transitionArcCenter, lineStart, intersection); newArcStart = transitionArcCenter + (oriArcCenter - transitionArcCenter).ScaleBy(transitionR / (oriR + transitionR)); } else { double len1 = transitionR; double len2 = Math.Sqrt((oriR + transitionR) * (oriR + transitionR) - len1 * len1); VectorD vLen2 = vArcS.ScaleBy(len2 / oriR); newLineEnd = oriArcCenter + vLen2; VectorD vLen1 = vArcSRotate1.ScaleBy(transitionR / vArcSRotate1.Length); transitionArcCenter = newLineEnd + vLen1; newArcStart = transitionArcCenter + (oriArcCenter - transitionArcCenter).ScaleBy(transitionR / (transitionR + oriR)); } points.Add(newLineEnd); points.Add(transitionArcCenter); points.Add(newArcStart); return(points); }
/// <summary> /// 获取直线到圆弧的过渡圆弧 /// </summary> /// <param name="lineStart">线起点</param> /// <param name="intersection">线与圆弧交点</param> /// <param name="oriArcCenter">圆弧圆心</param> /// <param name="transitionAngle">过渡舍去的圆弧角度,单位度</param> /// <returns>过渡圆弧的起点、圆心、终点</returns> public static List <PointD> GetLineToArcTransitionArc(PointD lineStart, PointD intersection, PointD oriArcCenter, double transitionAngle, double oriArcClockwise) { List <PointD> points = new List <PointD>(); // 获取圆弧上过渡的切点(即过渡圆弧的终点) VectorD vOriArcStart = intersection - oriArcCenter; if (oriArcClockwise == 0) { transitionAngle = -transitionAngle; } VectorD temp = vOriArcStart.Rotate(transitionAngle); PointD newArcStart = oriArcCenter + temp; // 做圆弧切点切线,与原直线相交得到新的拐角交点 VectorD tempV1 = temp.Rotate(90); PointD inflexionLinePoint1 = newArcStart + tempV1 * 10; PointD inflexionLinePoint2 = newArcStart - tempV1 * 10; PointD newIntersection = GetIntersection(lineStart, intersection, inflexionLinePoint1, inflexionLinePoint2); // 得到新的拐角角度 double newAngle = GetAngleOfTwoLine(lineStart, newIntersection, newArcStart); // 求得新的拐角圆弧半径 VectorD tempV2 = newArcStart - newIntersection; double r = Math.Tan(newAngle / 2) * tempV2.Length; points = GetLineTransitionArc(lineStart, newIntersection, newArcStart, r); return(points); }