From 0d0c6a199c5b631299c72dce80d66ac0f4936a64 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Sun, 26 Oct 2008 12:53:29 +0000 Subject: [PATCH] [matrix] Optimise invert for simple scaling|translation matrices. The matrix is quite often just a simple scale and translate (or even identity!). For this class of matrix, we can skip the full adjoint rearrangement and determinant calculation and just compute the inverse directly. --- src/cairo-matrix.c | 26 +++++++++++++++++++++++++- 1 file changed, 25 insertions(+), 1 deletion(-) diff --git a/src/cairo-matrix.c b/src/cairo-matrix.c index 643c9867e..b644dec82 100644 --- a/src/cairo-matrix.c +++ b/src/cairo-matrix.c @@ -525,9 +525,33 @@ _cairo_matrix_compute_adjoint (cairo_matrix_t *matrix) cairo_status_t cairo_matrix_invert (cairo_matrix_t *matrix) { - /* inv (A) = 1/det (A) * adj (A) */ double det; + /* Simple scaling|translation matrices are quite common... */ + if (matrix->xy == 0. && matrix->yx == 0.) { + matrix->x0 = -matrix->x0; + matrix->y0 = -matrix->y0; + + if (matrix->xx != 1.) { + if (matrix->xx == 0.) + return _cairo_error (CAIRO_STATUS_INVALID_MATRIX); + + matrix->xx = 1. / matrix->xx; + matrix->x0 *= matrix->xx; + } + + if (matrix->yy != 1.) { + if (matrix->yy == 0.) + return _cairo_error (CAIRO_STATUS_INVALID_MATRIX); + + matrix->yy = 1. / matrix->yy; + matrix->y0 *= matrix->yy; + } + + return CAIRO_STATUS_SUCCESS; + } + + /* inv (A) = 1/det (A) * adj (A) */ det = _cairo_matrix_compute_determinant (matrix); if (! ISFINITE (det))