[librsvg: 5/6] rect: add an utility to get the closest outer rect



commit a75d3abefe955982d62a61a9b1e1fd8e5adc68ad
Author: Paolo Borelli <pborelli gnome org>
Date:   Tue May 15 10:11:26 2018 +0200

    rect: add an utility to get the closest outer rect
    
    Use it for the drawing-ctx code path

 librsvg/rsvg-drawing-ctx.c        | 14 +++++++-------
 rsvg_internals/src/drawing_ctx.rs | 19 ++++++++++---------
 rsvg_internals/src/rect.rs        | 27 +++++++++++++++++++++++++++
 3 files changed, 44 insertions(+), 16 deletions(-)
---
diff --git a/librsvg/rsvg-drawing-ctx.c b/librsvg/rsvg-drawing-ctx.c
index 02132cfb..fa2995b1 100644
--- a/librsvg/rsvg-drawing-ctx.c
+++ b/librsvg/rsvg-drawing-ctx.c
@@ -56,7 +56,7 @@ void rsvg_cairo_add_clipping_rect (RsvgDrawingCtx *ctx,
 G_GNUC_INTERNAL
 void rsvg_drawing_ctx_transformed_image_bounding_box (cairo_matrix_t *affine,
                                                       double width, double height,
-                                                      double *x0, double *y0, double *x1, double *y1);
+                                                      double *bbx, double *bby, double *bbw, double *bbh);
 
 static void
 rsvg_cairo_generate_mask (cairo_t * cr, RsvgNode *mask, RsvgDrawingCtx *ctx)
@@ -269,7 +269,7 @@ rsvg_drawing_ctx_new (cairo_t *cr, RsvgHandle *handle)
     RsvgState *state;
     cairo_matrix_t affine;
     cairo_matrix_t state_affine;
-    double bbx0, bby0, bbx1, bby1;
+    double bbx, bby, bbw, bbh;
 
     rsvg_handle_get_dimensions (handle, &data);
     if (data.width == 0 || data.height == 0)
@@ -284,17 +284,17 @@ rsvg_drawing_ctx_new (cairo_t *cr, RsvgHandle *handle)
      * surfaces allocated during drawing. */
     rsvg_drawing_ctx_transformed_image_bounding_box (&affine,
                                                      data.width, data.height,
-                                                     &bbx0, &bby0, &bbx1, &bby1);
+                                                     &bbx, &bby, &bbw, &bbh);
 
     draw->initial_cr = cr;
     draw->cr = cr;
     draw->cr_stack = NULL;
     draw->surfaces_stack = NULL;
 
-    draw->offset_x = bbx0;
-    draw->offset_y = bby0;
-    draw->width = bbx1 - bbx0;
-    draw->height = bby1 - bby0;
+    draw->offset_x = bbx;
+    draw->offset_y = bby;
+    draw->width = bbw;
+    draw->height = bbh;
 
     draw->state = NULL;
 
diff --git a/rsvg_internals/src/drawing_ctx.rs b/rsvg_internals/src/drawing_ctx.rs
index 7edd9e69..ae2ef8af 100644
--- a/rsvg_internals/src/drawing_ctx.rs
+++ b/rsvg_internals/src/drawing_ctx.rs
@@ -396,10 +396,10 @@ pub extern "C" fn rsvg_drawing_ctx_transformed_image_bounding_box(
     affine: *const cairo::Matrix,
     w: f64,
     h: f64,
-    x0: *mut libc::c_double,
-    y0: *mut libc::c_double,
-    x1: *mut libc::c_double,
-    y1: *mut libc::c_double,
+    bbx: *mut libc::c_double,
+    bby: *mut libc::c_double,
+    bbw: *mut libc::c_double,
+    bbh: *mut libc::c_double,
 ) {
     let affine = unsafe { &*affine };
     let r = cairo::Rectangle {
@@ -409,13 +409,14 @@ pub extern "C" fn rsvg_drawing_ctx_transformed_image_bounding_box(
         height: h,
     };
 
-    let r_out = rect::transform(affine, &r);
+    let r_tr = rect::transform(affine, &r);
+    let r_out = rect::outer(&r_tr);
 
     unsafe {
-        *x0 = r_out.x.floor();
-        *y0 = r_out.y.floor();
-        *x1 = (r_out.x + r_out.width).ceil();
-        *y1 = (r_out.y + r_out.height).ceil();
+        *bbx = r_out.x;
+        *bby = r_out.y;
+        *bbw = r_out.width;
+        *bbh = r_out.height;
     }
 }
 
diff --git a/rsvg_internals/src/rect.rs b/rsvg_internals/src/rect.rs
index 1a6a6fa9..76e5a041 100644
--- a/rsvg_internals/src/rect.rs
+++ b/rsvg_internals/src/rect.rs
@@ -89,6 +89,17 @@ pub fn transform(affine: &cairo::Matrix, rect: &cairo::Rectangle) -> cairo::Rect
     }
 }
 
+pub fn outer(r: &cairo::Rectangle) -> cairo::Rectangle {
+    let (x, y) = (r.x.floor(), r.y.floor());
+
+    cairo::Rectangle {
+        x: x,
+        y: y,
+        width: (r.x + r.width).ceil() - x,
+        height: (r.y + r.height).ceil() - y,
+    }
+}
+
 #[cfg(test)]
 mod tests {
     use super::*;
@@ -186,4 +197,20 @@ mod tests {
         assert_approx_eq_cairo!(6.28_f64, tr.width);
         assert_approx_eq_cairo!(6.28_f64, tr.height);
     }
+
+    #[test]
+    fn outer_rect() {
+        let r = cairo::Rectangle {
+            x: 1.42,
+            y: 1.42,
+            width: 3.14,
+            height: 3.14,
+        };
+
+        let or = outer(&r);
+        assert_eq!(1.0, or.x);
+        assert_eq!(1.0, or.y);
+        assert_eq!(4.0, or.width);
+        assert_eq!(4.0, or.height);
+    }
 }


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]