[cairo-commit] goocanvas/src goocanvastextview.c,1.18,1.19
Damon Chaplin
commit at pdx.freedesktop.org
Thu Oct 12 15:16:58 PDT 2006
Committed by: damon
Update of /cvs/cairo/goocanvas/src
In directory kemper:/tmp/cvs-serv23400/src
Modified Files:
goocanvastextview.c
Log Message:
2006-10-12 Damon Chaplin <damon at gnome.org>
* src/goocanvastextview.c (goo_canvas_text_view_create_layout)
(goo_canvas_text_view_get_item_view_at)
(goo_canvas_text_view_paint): patch from Martin Soto to fix a text
positioning bug. The position was wrong when the text width was set
and the alignment wasn't PANGO_ALIGN_LEFT. (Pango uses the set width
to calculate the text origin, but we were using the logical width.)
Index: goocanvastextview.c
===================================================================
RCS file: /cvs/cairo/goocanvas/src/goocanvastextview.c,v
retrieving revision 1.18
retrieving revision 1.19
diff -u -d -r1.18 -r1.19
--- goocanvastextview.c 24 Aug 2006 08:06:23 -0000 1.18
+++ goocanvastextview.c 12 Oct 2006 22:16:55 -0000 1.19
@@ -99,12 +99,14 @@
goo_canvas_text_view_create_layout (GooCanvasTextView *text_view,
GooCanvasText *text,
cairo_t *cr,
- GooCanvasBounds *bounds)
+ GooCanvasBounds *bounds,
+ gdouble *origin_x_return,
+ gdouble *origin_y_return)
{
PangoLayout *layout;
PangoContext *context;
PangoRectangle logical_rect;
- double width, height;
+ double logical_width, logical_height, align_width, origin_x, origin_y;
gchar *string;
string = text->text ? text->text : "";
@@ -137,44 +139,84 @@
/* Get size of the text, so we can position it according to anchor. */
pango_layout_get_extents (layout, NULL, &logical_rect);
- width = (double) logical_rect.width / PANGO_SCALE;
- height = (double) logical_rect.height / PANGO_SCALE;
+ logical_width = (double) logical_rect.width / PANGO_SCALE;
+ logical_height = (double) logical_rect.height / PANGO_SCALE;
- bounds->x1 = text->x;
- bounds->y1 = text->y;
+ /* If the text width has been set, that width is used to do the alignment
+ positioning. Otherwise the actual width is used. */
+ if (text->width > 0)
+ align_width = text->width;
+ else
+ align_width = logical_width;
- switch (text->anchor) {
- case GTK_ANCHOR_N:
- case GTK_ANCHOR_CENTER:
- case GTK_ANCHOR_S:
- bounds->x1 -= width / 2.0;
- break;
- case GTK_ANCHOR_NE:
- case GTK_ANCHOR_E:
- case GTK_ANCHOR_SE:
- bounds->x1 -= width;
- break;
- default:
- break;
- }
+ /* Now calculate the origin of the text, i.e. where we will tell Pango
+ to draw it. */
+ origin_x = text->x;
+ origin_y = text->y;
- switch (text->anchor) {
- case GTK_ANCHOR_W:
- case GTK_ANCHOR_CENTER:
- case GTK_ANCHOR_E:
- bounds->y1 -= height / 2.0;
- break;
- case GTK_ANCHOR_SW:
- case GTK_ANCHOR_S:
- case GTK_ANCHOR_SE:
- bounds->y1 -= height;
- break;
- default:
+ switch (text->anchor)
+ {
+ case GTK_ANCHOR_N:
+ case GTK_ANCHOR_CENTER:
+ case GTK_ANCHOR_S:
+ origin_x -= align_width / 2.0;
break;
- }
+ case GTK_ANCHOR_NE:
+ case GTK_ANCHOR_E:
+ case GTK_ANCHOR_SE:
+ origin_x -= align_width;
+ break;
+ default:
+ break;
+ }
- bounds->x2 = bounds->x1 + width;
- bounds->y2 = bounds->y1 + height;
+ switch (text->anchor)
+ {
+ case GTK_ANCHOR_W:
+ case GTK_ANCHOR_CENTER:
+ case GTK_ANCHOR_E:
+ origin_y -= logical_height / 2.0;
+ break;
+ case GTK_ANCHOR_SW:
+ case GTK_ANCHOR_S:
+ case GTK_ANCHOR_SE:
+ origin_y -= logical_height;
+ break;
+ default:
+ break;
+ }
+
+ /* Return the origin of the text if required. */
+ if (origin_x_return)
+ *origin_x_return = origin_x;
+ if (origin_y_return)
+ *origin_y_return = origin_y;
+
+ /* Now calculate the bounds. */
+ bounds->x1 = origin_x;
+ bounds->y1 = origin_y;
+
+ if (text->width > 0)
+ {
+ /* If the text width has been set, and the alignment isn't
+ PANGO_ALIGN_LEFT, we need to adjust for the difference between
+ the actual width of the text and the width that was used for
+ alignment. */
+ switch (text->alignment)
+ {
+ case PANGO_ALIGN_CENTER:
+ bounds->x1 += (align_width - logical_width) / 2.0;
+ break;
+ case PANGO_ALIGN_RIGHT:
+ bounds->x1 += align_width - logical_width;
+ break;
+ default:
+ break;
+ }
+ }
+
+ bounds->x2 = origin_x + logical_width;
+ bounds->y2 = origin_y + logical_height;
}
return layout;
@@ -209,7 +251,8 @@
/* Compute the new bounds. */
layout = goo_canvas_text_view_create_layout (text_view, text, cr,
- &simple_view->bounds);
+ &simple_view->bounds,
+ NULL, NULL);
g_object_unref (layout);
goo_canvas_item_simple_user_bounds_to_device (simple, cr,
@@ -245,6 +288,7 @@
PangoRectangle log_rect;
int px, py;
double user_x = x, user_y = y;
+ gdouble origin_x, origin_y;
/* If there is no text just return. */
if (!text->text || !text->text[0])
@@ -281,11 +325,12 @@
cairo_device_to_user (cr, &user_x, &user_y);
- layout = goo_canvas_text_view_create_layout (text_view, text, cr, &bounds);
+ layout = goo_canvas_text_view_create_layout (text_view, text, cr, &bounds,
+ &origin_x, &origin_y);
- /* Convert the coordinates into Pango units. */
- px = (user_x - bounds.x1) * PANGO_SCALE;
- py = (user_y - bounds.y1) * PANGO_SCALE;
+ /* Convert the coordinates into Pango units relative to the text. */
+ px = (user_x - origin_x) * PANGO_SCALE;
+ py = (user_y - origin_y) * PANGO_SCALE;
/* We use line extents here. Note that SVG uses character cells to determine
hits so we have slightly different behavior. */
@@ -325,6 +370,7 @@
GooCanvasText *text = (GooCanvasText*) simple;
PangoLayout *layout;
GooCanvasBounds layout_bounds;
+ gdouble origin_x, origin_y;
/* If there is no text just return. */
if (!text->text || !text->text[0])
@@ -351,8 +397,9 @@
cairo_new_path (cr);
layout = goo_canvas_text_view_create_layout (text_view, text, cr,
- &layout_bounds);
- cairo_move_to (cr, layout_bounds.x1, layout_bounds.y1);
+ &layout_bounds,
+ &origin_x, &origin_y);
+ cairo_move_to (cr, origin_x, origin_y);
pango_cairo_show_layout (cr, layout);
g_object_unref (layout);
More information about the cairo-commit
mailing list