void QNanoPainter::quadTo(const QPointF &controlPoint, const QPointF &endPoint)
{
    quadTo(controlPoint.x(), controlPoint.y(), endPoint.x(), endPoint.y());
}
Exemple #2
0
void WPainterPath::quadTo(const WPointF& c, const WPointF& endPoint)
{
  quadTo(c.x(), c.y(), endPoint.x(), endPoint.y());
}
Exemple #3
0
/* genEllipticPath:
 * Approximate an elliptical arc via Beziers of given degree
 * threshold indicates quality of approximation
 * if isSlice is true, the path begins and ends with line segments
 * to the center of the ellipse.
 * Returned path must be freed by the caller.
 */
static Ppolyline_t *genEllipticPath(ellipse_t * ep, int degree,
				    double threshold, boolean isSlice)
{
    double dEta;
    double etaB;
    double cosEtaB;
    double sinEtaB;
    double aCosEtaB;
    double bSinEtaB;
    double aSinEtaB;
    double bCosEtaB;
    double xB;
    double yB;
    double xBDot;
    double yBDot;
    double t;
    double alpha;
    Ppolyline_t *path = NEW(Ppolyline_t);

    // find the number of Bezier curves needed
    boolean found = FALSE;
    int i, n = 1;
    while ((!found) && (n < 1024)) {
	double dEta = (ep->eta2 - ep->eta1) / n;
	if (dEta <= 0.5 * M_PI) {
	    double etaB = ep->eta1;
	    found = TRUE;
	    for (i = 0; found && (i < n); ++i) {
		double etaA = etaB;
		etaB += dEta;
		found =
		    (estimateError(ep, degree, etaA, etaB) <= threshold);
	    }
	}
	n = n << 1;
    }

    dEta = (ep->eta2 - ep->eta1) / n;
    etaB = ep->eta1;

    cosEtaB = cos(etaB);
    sinEtaB = sin(etaB);
    aCosEtaB = ep->a * cosEtaB;
    bSinEtaB = ep->b * sinEtaB;
    aSinEtaB = ep->a * sinEtaB;
    bCosEtaB = ep->b * cosEtaB;
    xB = ep->cx + aCosEtaB * ep->cosTheta - bSinEtaB * ep->sinTheta;
    yB = ep->cy + aCosEtaB * ep->sinTheta + bSinEtaB * ep->cosTheta;
    xBDot = -aSinEtaB * ep->cosTheta - bCosEtaB * ep->sinTheta;
    yBDot = -aSinEtaB * ep->sinTheta + bCosEtaB * ep->cosTheta;

    if (isSlice) {
	moveTo(path, ep->cx, ep->cy);
	lineTo(path, xB, yB);
    } else {
	moveTo(path, xB, yB);
    }

    t = tan(0.5 * dEta);
    alpha = sin(dEta) * (sqrt(4 + 3 * t * t) - 1) / 3;

    for (i = 0; i < n; ++i) {

	double xA = xB;
	double yA = yB;
	double xADot = xBDot;
	double yADot = yBDot;

	etaB += dEta;
	cosEtaB = cos(etaB);
	sinEtaB = sin(etaB);
	aCosEtaB = ep->a * cosEtaB;
	bSinEtaB = ep->b * sinEtaB;
	aSinEtaB = ep->a * sinEtaB;
	bCosEtaB = ep->b * cosEtaB;
	xB = ep->cx + aCosEtaB * ep->cosTheta - bSinEtaB * ep->sinTheta;
	yB = ep->cy + aCosEtaB * ep->sinTheta + bSinEtaB * ep->cosTheta;
	xBDot = -aSinEtaB * ep->cosTheta - bCosEtaB * ep->sinTheta;
	yBDot = -aSinEtaB * ep->sinTheta + bCosEtaB * ep->cosTheta;

	if (degree == 1) {
	    lineTo(path, xB, yB);
#if DO_QUAD
	} else if (degree == 2) {
	    double k = (yBDot * (xB - xA) - xBDot * (yB - yA))
		/ (xADot * yBDot - yADot * xBDot);
	    quadTo(path, (xA + k * xADot), (yA + k * yADot), xB, yB);
#endif
	} else {
	    curveTo(path, (xA + alpha * xADot), (yA + alpha * yADot),
		    (xB - alpha * xBDot), (yB - alpha * yBDot), xB, yB);
	}

    }

    endPath(path, isSlice);

    return path;
}