我正在尝试绘制贝塞尔曲线(Core Graphics中的任意曲线),并根据另外两个端点按比例缩小(或扩展)它。我有一种可以进行这种工作的方法,但最终会“弄平”曲线,而不能完全保持形状。也许我弄乱了代码或逻辑,但我同时拥有两个原始点和控制点。给定另一组端点,我想计算适当的控制点以在新端点之间产生相同的形状。

这是将计算1个控制点的主要代码:

CGPoint (^ScaledCtrlPoint)(CGPoint, CGPoint, CGPoint, CGPoint, CGPoint) = ^CGPoint (CGPoint refPoint1, CGPoint refPoint2, CGPoint bevPoint1, CGPoint bevPoint2, CGPoint ctrlPoint){
        //Normalize points to refPoint1
        refPoint2.x -= refPoint1.x; refPoint2.y -= refPoint1.y;
        ctrlPoint.x -= refPoint1.x; ctrlPoint.y -= refPoint1.y;
        //Normalize bevPoints to bevPoint1
        bevPoint2.x -= bevPoint1.x; bevPoint2.y -= bevPoint1.y;
        //Calculate control point angle
        CGFloat theta = PointTheta(refPoint2);
        CGFloat refHyp = (refPoint2.y != 0.0f) ? refPoint2.y / sinf(theta) : refPoint2.x / cosf(theta);
        theta = PointTheta(bevPoint2);
        CGFloat bevHyp = (bevPoint2.y != 0.0f) ? bevPoint2.y / sinf(theta) : bevPoint2.x / cosf(theta);
        theta = PointTheta(ctrlPoint);
        CGFloat ctrlHyp = (ctrlPoint.y != 0.0f) ? ctrlPoint.y / sinf(theta) : ctrlPoint.x / cosf(theta);
        ctrlHyp *= (bevHyp / refHyp);
        return CGPointMake(bevPoint1.x + cosf(theta) * ctrlHyp, bevPoint1.y + sinf(theta) * ctrlHyp);
    };
bevPoints是我用来计算新控制点的新点。 refPointsctrlPoint是贝塞尔曲线的原始点。如您所见,我正在尝试按与原始端点到新端点相同的比例缩小ctrlPoint(也可以提高)。

我还使用另一个函数来计算入射角。很简单:
CGFloat         PointTheta(CGPoint point){
    //This assumes an origin of {0, 0} and returns a theta for the given point
    CGFloat theta = atanf(point.y / point.x);
    //Using arc tan requires some adjustment depending on the point quadrant
    if (point.x == 0.0f) theta = (point.y >= 0.0f) ? M_PI_2 : M_PI + M_PI_2;
    else if (point.x < 0.0f) theta += M_PI;
    else if (point.x > 0.0f && point.y < 0.0f) theta += (M_PI * 2);
    return theta;
}

最佳答案

我会用参数计算CGAffineTransform

(a, b, -b, a, tx, ty)

(即无偏斜的变换),将旧端点映射到新端点,然后将此变换应用于旧控制点以获取新控制点。

将2个旧端点映射到2个新端点的条件给出了a,b,tx,ty的4个方程,这些方程甚至可以在没有三角函数的情况下求解。

关于ios - 按比例缩放贝塞尔曲线-计算控制点,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/12264741/

10-09 09:39