[goffice] Fixed text and path items positions. [see #704391]



commit 393c569d3f664a98dee9676b3c377db5bff0edcb
Author: Jean Brefort <jean brefort normalesup org>
Date:   Thu Jul 18 12:29:55 2013 +0200

    Fixed text and path items positions. [see #704391]

 ChangeLog                    |   13 +++++
 NEWS                         |    1 +
 goffice/canvas/goc-ellipse.c |    1 -
 goffice/canvas/goc-path.c    |   13 ++++-
 goffice/canvas/goc-text.c    |  118 ++++++++++++-----------------------------
 goffice/canvas/goc-text.h    |    1 -
 6 files changed, 60 insertions(+), 87 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index 680e136..5d1e39e 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,16 @@
+2013-07-18  Jean Brefort  <jean brefort normalesup org>
+
+       reviewed by: <delete if not using a buddy>
+
+       * goffice/canvas/goc-ellipse.c (goc_ellipse_distance): fixed.
+       * goffice/canvas/goc-path.c (goc_path_distance): fixed distance evaluation.
+       [#704391]
+       * goffice/canvas/goc-text.c (goc_text_set_property),
+       (goc_text_prepare_draw), (goc_text_update_bounds),
+       (goc_text_distance), (goc_text_draw), (goc_text_style_changed),
+       (goc_text_class_init): fixed text position. [#704391]
+       * goffice/canvas/goc-text.h: ditto.
+
 2013-07-17  Jean Brefort  <jean brefort normalesup org>
 
        * goffice/utils/go-emf.c (go_emf_new_from_data), (go_emf_parse): protect
diff --git a/NEWS b/NEWS
index 459997e..bf252d6 100644
--- a/NEWS
+++ b/NEWS
@@ -2,6 +2,7 @@ goffice 0.10.5:
 
 Jean:
        * Don't crash when loading an EMF image without valid data. [#704311]
+       * Fixed text and path items positions. [see #704391]
 
 Morten:
        * Add prescaling to go_linear_regression_leverage.  [#703381]
diff --git a/goffice/canvas/goc-ellipse.c b/goffice/canvas/goc-ellipse.c
index f962961..49a2037 100644
--- a/goffice/canvas/goc-ellipse.c
+++ b/goffice/canvas/goc-ellipse.c
@@ -194,7 +194,6 @@ goc_ellipse_distance (GocItem *item, double x, double y, GocItem **near_item)
                set_line = go_styled_object_set_cairo_line (GO_STYLED_OBJECT (item), cr);
                if (scale_line_width)
                        cairo_restore (cr);
-               if (set_line)
                if (style->fill.type != GO_STYLE_FILL_NONE ||
                        (style->fill.type == GO_STYLE_FILL_NONE && !set_line)) {
                        if (cairo_in_fill (cr, x, y))
diff --git a/goffice/canvas/goc-path.c b/goffice/canvas/goc-path.c
index 3a95f0f..320ed6a 100644
--- a/goffice/canvas/goc-path.c
+++ b/goffice/canvas/goc-path.c
@@ -170,6 +170,8 @@ goc_path_distance (GocItem *item, double x, double y, GocItem **near_item)
        double ppu = goc_canvas_get_pixels_per_unit (item->canvas);
        cairo_surface_t *surface;
        cairo_t *cr;
+       gboolean set_line,
+               scale_line_width = goc_styled_item_get_scale_line_width (GOC_STYLED_ITEM (item));
 
        *near_item = item;
        tmp_width = style->line.width;
@@ -180,15 +182,22 @@ goc_path_distance (GocItem *item, double x, double y, GocItem **near_item)
        surface = cairo_image_surface_create (CAIRO_FORMAT_ARGB32, 1, 1);
        cr = cairo_create (surface);
 
+       cairo_save (cr);
        if (goc_path_prepare_draw (item, cr, 0)) {
                /* Filled OR both fill and stroke are none */
+               if (!scale_line_width)
+                       cairo_restore (cr);
+               set_line = go_styled_object_set_cairo_line (GO_STYLED_OBJECT (item), cr);
+               if (scale_line_width)
+                       cairo_restore (cr);
                if ((path->closed && style->fill.type != GO_STYLE_FILL_NONE) ||
-                       (style->fill.type == GO_STYLE_FILL_NONE && !goc_styled_item_set_cairo_line 
(GOC_STYLED_ITEM (item), cr))) {
+                       (style->fill.type == GO_STYLE_FILL_NONE && !set_line)) {
                        if (cairo_in_fill (cr, x, y))
                                res = 0;
                }
-               if (goc_styled_item_set_cairo_line (GOC_STYLED_ITEM (item), cr) && cairo_in_stroke (cr, x, y))
+               if (set_line && cairo_in_stroke (cr, x, y)) {
                        res = 0;
+               }
        }
 
        cairo_destroy (cr);
diff --git a/goffice/canvas/goc-text.c b/goffice/canvas/goc-text.c
index 34a9ff7..8de9f00 100644
--- a/goffice/canvas/goc-text.c
+++ b/goffice/canvas/goc-text.c
@@ -106,8 +106,6 @@ goc_text_set_property (GObject *gobject, guint param_id,
        case TEXT_PROP_TEXT:
                g_free (text->text);
                text->text = g_value_dup_string (value);
-               if (text->layout)
-                       pango_layout_set_text (text->layout, text->text, -1);
                break;
 
        case TEXT_PROP_ATTRIBUTES: {
@@ -115,8 +113,6 @@ goc_text_set_property (GObject *gobject, guint param_id,
                if (text->attributes)
                        pango_attr_list_unref (text->attributes);
                text->attributes = (attrs)? pango_attr_list_copy (attrs): pango_attr_list_new ();
-               if (text->layout)
-                       pango_layout_set_attributes (text->layout, text->attributes);
                break;
        }
 
@@ -134,13 +130,6 @@ goc_text_set_property (GObject *gobject, guint param_id,
 
        case TEXT_PROP_WRAP_WIDTH:
                text->wrap_width = g_value_get_double (value);
-               if (text->layout) {
-                       if (text->wrap_width > 0) {
-                               pango_layout_set_width (text->layout, text->wrap_width * PANGO_SCALE);
-                               pango_layout_set_wrap (text->layout, PANGO_WRAP_WORD);
-                       } else
-                               pango_layout_set_width (text->layout, -1);
-               }
                break;
 
        default: G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, param_id, pspec);
@@ -204,44 +193,6 @@ goc_text_get_property (GObject *gobject, guint param_id,
 }
 
 static void
-goc_text_realize (GocItem *item)
-{
-#ifdef GOFFICE_WITH_GTK
-       GocText *text = GOC_TEXT (item);
-       GOStyle *style = go_styled_object_get_style (GO_STYLED_OBJECT (item));
-
-       if (parent_class->realize)
-               (*parent_class->realize) (item);
-
-       text->layout = pango_layout_new (gtk_widget_get_pango_context (GTK_WIDGET (item->canvas)));
-       pango_layout_set_font_description (text->layout, style->font.font->desc);
-       if (text->text)
-               pango_layout_set_text (text->layout, text->text, -1);
-       if (text->attributes)
-               pango_layout_set_attributes (text->layout, text->attributes);
-       if (text->wrap_width > 0) {
-               pango_layout_set_width (text->layout, text->wrap_width * PANGO_SCALE);
-               pango_layout_set_wrap (text->layout, PANGO_WRAP_WORD_CHAR);
-       } else
-               pango_layout_set_width (text->layout, -1);
-       goc_item_bounds_changed (item);
-#endif
-}
-
-static void
-goc_text_unrealize (GocItem *item)
-{
-       GocText *text = GOC_TEXT (item);
-
-       if (text->layout)
-               g_object_unref (text->layout);
-       text->layout = NULL;
-
-       if (parent_class->unrealize)
-               (*parent_class->unrealize) (item);
-}
-
-static void
 goc_text_finalize (GObject *gobject)
 {
        GocText *text = GOC_TEXT (gobject);
@@ -257,20 +208,38 @@ goc_text_prepare_draw (GocItem *item, cairo_t *cr, gboolean flag)
 {
        GocText *text = GOC_TEXT (item);
        PangoRectangle rect;
-       double sign = (goc_canvas_get_direction (item->canvas) == GOC_DIRECTION_RTL)? -1.: 1., dx, dy;
+       double sign = (goc_canvas_get_direction (item->canvas) == GOC_DIRECTION_RTL)? -1.: 1.;
+       double w, h, dx, dy;
+       PangoLayout *pl;
+       GOStyle *style = go_styled_object_get_style (GO_STYLED_OBJECT (item));
+       if (!text->text)
+               return;
+       w = (text->clip_width > 0.)? MIN (text->clip_width, text->w): text->w;
+       h = (text->clip_height > 0.)? MIN (text->clip_height, text->h): text->h;
+       pl = pango_cairo_create_layout (cr);
+       pango_layout_set_font_description (pl, style->font.font->desc);
+       pango_layout_set_text (pl, text->text, -1);
+       if (text->wrap_width > 0) {
+               pango_layout_set_width (pl, text->wrap_width * PANGO_SCALE);
+               pango_layout_set_wrap (pl, PANGO_WRAP_WORD_CHAR);
+       }
+       if (text->attributes)
+               pango_layout_set_attributes (pl, text->attributes);
 
-       pango_layout_get_extents (text->layout, NULL, &rect);
+       pango_layout_get_extents (pl, NULL, &rect);
        text->w = (double) rect.width / PANGO_SCALE;
        text->h = (double) rect.height / PANGO_SCALE;
        item->x0 = (goc_canvas_get_direction (item->canvas) == GOC_DIRECTION_RTL)? text->x + text->w: text->x;
        item->y0 = text->y;
        dx = dy = 0;
+       w = (text->clip_width > 0.)? MIN (text->clip_width, text->w): text->w;
+       h = (text->clip_height > 0.)? MIN (text->clip_height, text->h): text->h;
        /* adjust horizontally */
        switch (text->anchor) {
        case GO_ANCHOR_CENTER:
        case GO_ANCHOR_NORTH:
        case GO_ANCHOR_SOUTH:
-               dx = -text->w / 2.;
+               dx = -w / 2.;
                break;
        case GO_ANCHOR_NORTH_WEST:
        case GO_ANCHOR_SOUTH_WEST:
@@ -279,7 +248,7 @@ goc_text_prepare_draw (GocItem *item, cairo_t *cr, gboolean flag)
        case GO_ANCHOR_NORTH_EAST:
        case GO_ANCHOR_SOUTH_EAST:
        case GO_ANCHOR_EAST:
-               dx = -text->w;
+               dx = -w;
                break;
        default: /* should not occur */
                break;
@@ -293,12 +262,12 @@ goc_text_prepare_draw (GocItem *item, cairo_t *cr, gboolean flag)
        case GO_ANCHOR_CENTER:
        case GO_ANCHOR_WEST:
        case GO_ANCHOR_EAST:
-               dy = -text->h / 2.;
+               dy = -h / 2.;
                break;
        case GO_ANCHOR_SOUTH:
        case GO_ANCHOR_SOUTH_WEST:
        case GO_ANCHOR_SOUTH_EAST:
-               dy = -text->h;
+               dy = -h;
                break;
        default: /* should not occur */
                break;
@@ -307,24 +276,17 @@ goc_text_prepare_draw (GocItem *item, cairo_t *cr, gboolean flag)
        _goc_item_transform (item, cr, flag);
        cairo_translate (cr, item->x0, item->y0);
        cairo_rotate (cr, text->rotation * sign);
-       if (text->clip_height > 0. && text->clip_width > 0.) {
-               cairo_rectangle (cr, dx, dy, text->clip_width, text->clip_height);
-       } else {
-               cairo_rectangle (cr, dx, dy, text->w, text->h);
-       }
+       cairo_rectangle (cr, dx, dy, w, h);
        cairo_restore (cr);
+       g_object_unref (pl);
 }
 
 static void
 goc_text_update_bounds (GocItem *item)
 {
-       GocText *text = GOC_TEXT (item);
        cairo_surface_t *surface;
        cairo_t *cr;
 
-       if (!text->layout)
-               return;
-
        surface = cairo_image_surface_create (CAIRO_FORMAT_ARGB32, 1, 1);
        cr = cairo_create (surface);
        goc_text_prepare_draw (item, cr, FALSE);
@@ -336,16 +298,12 @@ goc_text_update_bounds (GocItem *item)
 static double
 goc_text_distance (GocItem *item, double x, double y, GocItem **near_item)
 {
-       GocText *text = GOC_TEXT (item);
        cairo_surface_t *surface;
        cairo_t *cr;
        double res = 20;
 
        *near_item = item;
 
-       if (!text->layout)
-               return res;
-
        surface = cairo_image_surface_create (CAIRO_FORMAT_ARGB32, 1, 1);
        cr = cairo_create (surface);
        goc_text_prepare_draw (item, cr, FALSE);
@@ -362,13 +320,15 @@ goc_text_draw (GocItem const *item, cairo_t *cr)
 {
        GocText *text = GOC_TEXT (item);
        double x = (goc_canvas_get_direction (item->canvas) == GOC_DIRECTION_RTL)? text->x + text->w: text->x,
-              y = text->y, dx = 0., dy = 0.;
+              y = text->y, dx = 0., dy = 0., h, w;
        double sign = (goc_canvas_get_direction (item->canvas) == GOC_DIRECTION_RTL)? -1.: 1.;
 
        PangoLayout *pl;
        GOStyle *style = go_styled_object_get_style (GO_STYLED_OBJECT (item));
        if (!text->text)
                return;
+       w = (text->clip_width > 0.)? MIN (text->clip_width, text->w): text->w;
+       h = (text->clip_height > 0.)? MIN (text->clip_height, text->h): text->h;
        pl = pango_cairo_create_layout (cr);
        pango_layout_set_font_description (pl, style->font.font->desc);
        pango_layout_set_text (pl, text->text, -1);
@@ -383,7 +343,7 @@ goc_text_draw (GocItem const *item, cairo_t *cr)
        case GO_ANCHOR_CENTER:
        case GO_ANCHOR_NORTH:
        case GO_ANCHOR_SOUTH:
-               dx = -text->w / 2.;
+               dx = -w / 2.;
                break;
        case GO_ANCHOR_NORTH_WEST:
        case GO_ANCHOR_SOUTH_WEST:
@@ -392,7 +352,7 @@ goc_text_draw (GocItem const *item, cairo_t *cr)
        case GO_ANCHOR_NORTH_EAST:
        case GO_ANCHOR_SOUTH_EAST:
        case GO_ANCHOR_EAST:
-               dx = -text->w;
+               dx = -w;
                break;
        default: /* should not occur */
                break;
@@ -406,12 +366,12 @@ goc_text_draw (GocItem const *item, cairo_t *cr)
        case GO_ANCHOR_CENTER:
        case GO_ANCHOR_WEST:
        case GO_ANCHOR_EAST:
-               dy = -text->h / 2.;
+               dy = -h / 2.;
                break;
        case GO_ANCHOR_SOUTH:
        case GO_ANCHOR_SOUTH_WEST:
        case GO_ANCHOR_SOUTH_EAST:
-               dy = -text->h;
+               dy = -h;
                break;
        default: /* should not occur */
                break;
@@ -422,10 +382,8 @@ goc_text_draw (GocItem const *item, cairo_t *cr)
        goc_group_cairo_transform (item->parent, cr, x, y);
        cairo_rotate (cr, text->rotation * sign);
        cairo_translate (cr, dx, dy);
-       if (text->clip_height > 0. && text->clip_width > 0.) {
-               cairo_rectangle (cr, 0., 0., text->clip_width, text->clip_height);
-               cairo_clip (cr);
-       }
+       cairo_rectangle (cr, 0., 0., w, h);
+       cairo_clip (cr);
        pango_cairo_show_layout (cr, pl);
        cairo_new_path (cr);
        cairo_restore (cr);
@@ -443,10 +401,6 @@ goc_text_init_style (G_GNUC_UNUSED GocStyledItem *item, GOStyle *style)
 static void
 goc_text_style_changed (GOStyledObject *obj)
 {
-       GOStyle *style = go_styled_object_get_style (obj);
-       GocText *text = GOC_TEXT (obj);
-       if (text->layout)
-               pango_layout_set_font_description (text->layout, style->font.font->desc);
        goc_item_bounds_changed (GOC_ITEM (obj));
 }
 
@@ -523,8 +477,6 @@ goc_text_class_init (GocItemClass *item_klass)
        item_klass->update_bounds = goc_text_update_bounds;
        item_klass->distance = goc_text_distance;
        item_klass->draw = goc_text_draw;
-       item_klass->realize = goc_text_realize;
-       item_klass->unrealize = goc_text_unrealize;
 }
 
 static void
diff --git a/goffice/canvas/goc-text.h b/goffice/canvas/goc-text.h
index 957df23..2aae5e3 100644
--- a/goffice/canvas/goc-text.h
+++ b/goffice/canvas/goc-text.h
@@ -37,7 +37,6 @@ struct _GocText {
        char *text;
        GOAnchorType anchor;
        PangoAttrList *attributes;
-       PangoLayout *layout;
        gpointer priv;
 };
 


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