Bug 354341 - quit depending on cairo extent calculation bug. r+sr=roc

git-svn-id: svn://10.0.0.236/trunk@212420 18797224-902f-48f8-a5cc-f745e15eee43
This commit is contained in:
tor%cs.brown.edu
2006-09-26 22:27:56 +00:00
parent 4ec4c61286
commit a86d1febf4
4 changed files with 38 additions and 17 deletions

View File

@@ -429,13 +429,12 @@ nsSVGGlyphFrame::UpdateCoveredRegion()
if (hasStroke) {
SetupCairoStrokeGeometry(ctx);
cairo_stroke_extents(ctx, &xmin, &ymin, &xmax, &ymax);
nsSVGUtils::UserToDeviceBBox(ctx, &xmin, &ymin, &xmax, &ymax);
} else {
cairo_identity_matrix(ctx);
cairo_fill_extents(ctx, &xmin, &ymin, &xmax, &ymax);
}
cairo_user_to_device(ctx, &xmin, &ymin);
cairo_user_to_device(ctx, &xmax, &ymax);
mRect = nsSVGUtils::ToBoundingPixelRect(xmin, ymin, xmax, ymax);
return NS_OK;
@@ -495,13 +494,12 @@ nsSVGGlyphFrame::GetBBox(nsIDOMSVGRect **_retval)
LoopCharacters(ctx, text, cp, cairo_text_path);
cairo_identity_matrix(ctx);
double xmin, ymin, xmax, ymax;
cairo_fill_extents(ctx, &xmin, &ymin, &xmax, &ymax);
cairo_user_to_device(ctx, &xmin, &ymin);
cairo_user_to_device(ctx, &xmax, &ymax);
return NS_NewSVGRect(_retval, xmin, ymin, xmax - xmin, ymax - ymin);
}
@@ -873,12 +871,11 @@ nsSVGGlyphFrame::GetExtentOfChar(PRUint32 charnum, nsIDOMSVGRect **_retval)
cairo_rel_line_to(ctx, 0, extent.height);
cairo_rel_line_to(ctx, -extent.width, 0);
cairo_close_path(ctx);
cairo_identity_matrix(ctx);
double xmin, ymin, xmax, ymax;
cairo_fill_extents(ctx, &xmin, &ymin, &xmax, &ymax);
cairo_user_to_device(ctx, &xmin, &ymin);
cairo_user_to_device(ctx, &xmax, &ymax);
cairo_set_matrix(ctx, &matrix);

View File

@@ -405,7 +405,6 @@ nsSVGPathGeometryFrame::UpdateCoveredRegion()
mRect.Empty();
cairo_t *ctx = cairo_create(nsSVGUtils::GetCairoComputationalSurface());
GeneratePath(ctx, nsnull);
double xmin, ymin, xmax, ymax;
@@ -413,11 +412,11 @@ nsSVGPathGeometryFrame::UpdateCoveredRegion()
if (HasStroke()) {
SetupCairoStrokeGeometry(ctx);
cairo_stroke_extents(ctx, &xmin, &ymin, &xmax, &ymax);
nsSVGUtils::UserToDeviceBBox(ctx, &xmin, &ymin, &xmax, &ymax);
} else {
cairo_identity_matrix(ctx);
cairo_fill_extents(ctx, &xmin, &ymin, &xmax, &ymax);
}
cairo_user_to_device(ctx, &xmin, &ymin);
cairo_user_to_device(ctx, &xmax, &ymax);
if (!IsDegeneratePath(xmin, ymin, xmax, ymax))
mRect = nsSVGUtils::ToBoundingPixelRect(xmin, ymin, xmax, ymax);
@@ -482,19 +481,14 @@ nsSVGPathGeometryFrame::GetBBox(nsIDOMSVGRect **_retval)
cairo_t *ctx = cairo_create(nsSVGUtils::GetCairoComputationalSurface());
GeneratePath(ctx, nsnull);
cairo_identity_matrix(ctx);
cairo_fill_extents(ctx, &xmin, &ymin, &xmax, &ymax);
cairo_user_to_device(ctx, &xmin, &ymin);
cairo_user_to_device(ctx, &xmax, &ymax);
if (IsDegeneratePath(xmin, ymin, xmax, ymax)) {
/* cairo_stroke_extents doesn't work with stroke width zero, fudge */
cairo_set_line_width(ctx, 0.0001);
cairo_stroke_extents(ctx, &xmin, &ymin, &xmax, &ymax);
cairo_user_to_device(ctx, &xmin, &ymin);
cairo_user_to_device(ctx, &xmax, &ymax);
}
cairo_destroy(ctx);

View File

@@ -991,3 +991,25 @@ nsSVGUtils::HitTestRect(nsIDOMSVGMatrix *aMatrix,
return result;
}
void
nsSVGUtils::UserToDeviceBBox(cairo_t *ctx,
double *xmin, double *ymin,
double *xmax, double *ymax)
{
double x[3], y[3];
x[0] = *xmin; y[0] = *ymax;
x[1] = *xmax; y[1] = *ymax;
x[2] = *xmax; y[2] = *ymin;
cairo_user_to_device(ctx, xmin, ymin);
*xmax = *xmin;
*ymax = *ymin;
for (int i = 0; i < 3; i++) {
cairo_user_to_device(ctx, &x[i], &y[i]);
*xmin = PR_MIN(*xmin, x[i]);
*xmax = PR_MAX(*xmax, x[i]);
*ymin = PR_MIN(*ymin, y[i]);
*ymax = PR_MAX(*ymax, y[i]);
}
}

View File

@@ -268,6 +268,14 @@ public:
float aRX, float aRY, float aRWidth, float aRHeight,
float aX, float aY);
/*
* Convert a rectangle from cairo user space to device space.
*/
static void
UserToDeviceBBox(cairo_t *ctx,
double *xmin, double *ymin,
double *xmax, double *ymax);
private:
/* Cairo computational (nil) surface */
static cairo_surface_t *mCairoComputationalSurface;