[cairo] Problems with cairo_get_line_width and "new" semantics

Carl Worth cworth at cworth.org
Tue May 16 12:53:41 PDT 2006


On Tue, 16 May 2006 09:49:50 -0700, Carl Worth wrote:
> Perhaps what we should do is to add two new functions for working with
> the pen directly as the ellipse it is?

> 	cairo_set_pen (cairo_t			*cr,
> 	cairo_get_pen (cairo_t			*cr,

I've started working on a patch for this. It's available as the
line-width-scale branch in my personal tree[1].

I've included the new documentation from the patch so far below[2] for
review on the API itself.

The results so far are close, but not quite right. The PostScript
backend is passing perfectly, but the PDF and SVG backends will need a
bit more work to properly transform the pen. For SVG I think the path
coordinates will have to be transformed by the inverse of then pen
matrix since I don't think the path and pen can be transformed
independently. I don't know if PDF will require all that or if it will
be as simple as PS, (where we just emit the pen matrix before
stroking).

But that should all be fairly straightforward.

More surprising was the image backend, which I thought would just work
but is currently failing as can be seen here:

http://cairographics.org/~cworth/images/line-width-scale-ref.png
http://cairographics.org/~cworth/images/line-width-scale-image-argb32-out.png
http://cairographics.org/~cworth/images/line-width-scale-image-argb32-diff.png

It looks like I'm not computing the polygonal pen with enough accuracy
somehow. Oh, or maybe I'm using the wrong matrix when I'm adding the
extra face points to the pen. Yeah, I bet that's it...

-Carl

[1] You can grab the branch with:

    git fetch git://git.cairographics.org/~cworth/cairo line-width-scale

    then browse it with:

    gitk line-width-scale

    or since it's only one big patch, look at it with:

    git show line-width-scale

    It's also available via gitweb of course:

http://gitweb.cairographics.org/?p=users-cworth-cairo;a=commitdiff;h=646032a471cfc23fdf1abe6b9bbc745718812108

[2] Here's the piece of the patch that adds documentation and new
public API:

commit 646032a471cfc23fdf1abe6b9bbc745718812108
Author: Carl Worth <cworth at cworth.org>
Date:   Tue May 16 12:38:51 2006 -0700

    First attempt at fixing line-width-scale
    
    PS works with this. PDF and SVG still need to be fixed. And the image backend
    is oddly broken. So this definitely isn't ready for prime-time yet.

diff --git a/src/cairo.c b/src/cairo.c
index 8ec603a..75176b5 100644
--- a/src/cairo.c
+++ b/src/cairo.c
@@ -800,30 +800,73 @@ cairo_set_fill_rule (cairo_t *cr, cairo_
 }
 
 /**
+ * cairo_set_pen:
+ * @cr: a #cairo_t
+ * @line_width: a line width, specifying the diameter of a pen in "pen space"
+ * @matrix: a matrix mapping from pen space to device space
+ * 
+ * Sets the pen within the cairo context (which will be used by
+ * subsequent calls to cairo_stroke()). The pen is elliptical in
+ * device spacel and is specified by a circle of diameter @line_width
+ * as well as the @matrix to transform that circle to an ellipse in
+ * device space.
+ *
+ * Note: The pen will be "locked" at the time of cairo_set_pen() and
+ * will not be modified by subsequent changes to the CTM.
+ *
+ * As with the other stroke parameters, the pen is examined by
+ * cairo_stroke(), cairo_stroke_extents(), and cairo_stroke_to_path(),
+ * but does not have any effect during path construction.
+ *
+ * See also cairo_set_line_width() for a more convenient way to
+ * specify the pen, (by using the CTM rather than an explicit matrix
+ * object).
+ **/
+void
+cairo_set_pen (cairo_t			*cr,
+	       double			 line_width,
+	       const cairo_matrix_t	*matrix)
...
+/**
  * cairo_set_line_width:
  * @cr: a #cairo_t
  * @width: a line width, as a user-space value
  * 
- * Sets the current line width within the cairo context. The line
- * width specifies the diameter of a pen that is circular in
- * user space.
+ * Sets the pen within the cairo context to have a user-space width of
+ * @width. The line width specifies the diameter of a pen that is
+ * circular in user space, (though the device-space pen may be an
+ * ellipse in general due to scaling/shear/rotation of the CTM).
  *
- * As with the other stroke parameters, the current line width is
- * examined by cairo_stroke(), cairo_stroke_extents(), and
- * cairo_stroke_to_path(), but does not have any effect during path
- * construction.
+ * Note: The pen will be "locked" at the time of
+ * cairo_set_line_width() and will not be modified by subsequent
+ * changes to the CTM.
+ *
+ * As with the other stroke parameters, the pen is examined by
+ * cairo_stroke(), cairo_stroke_extents(), and cairo_stroke_to_path(),
+ * but does not have any effect during path construction.
+ *
+ * See also cairo_set_pen() for another way to specify the pen, (by
+ * using an explicit matrix rather than the CTM).
  **/
 void
 cairo_set_line_width (cairo_t *cr, double width)
...
@@ -2588,17 +2631,52 @@ cairo_get_fill_rule (cairo_t *cr)
 }
 
 /**
+ * cairo_get_pen:
+ * @cr: a cairo context
+ * @line_width: the line width of the current pen
+ * @matrix: the matrix of the current pen
+ * 
+ * Stores the line width and the matrix of the current pen, (as set by
+ * cairo_set_pen() or cairo_set_line_width()), into @line_width and
+ * @matrix. If the current pen was set by cairo_set_line_width() then
+ * the matrix returned here is the CTM that was in effect at the time
+ * of the call to cairo_set_line_width().
+ **/
+void
+cairo_get_pen (cairo_t		*cr,
+	       double		*line_width,
+	       cairo_matrix_t	*matrix)
...
+/**
  * cairo_get_line_width:
  * @cr: a cairo context
  * 
- * Gets the current line width, as set by cairo_set_line_width().
+ * Gets the line width of the current pen, as set by either
+ * cairo_set_line_width() or cairo_set_pen().
+ *
+ * Note: The line width is returned as the same value originally
+ * passed to either cairo_set_line_width() or cairo_set_pen(). In
+ * other words, the return line width is in units the user space that
+ * was active at the time of cairo_set_line_width() and not in current
+ * user-space units (if the CTM has changed in the meantime). In order
+ * to reason about the size of the pen with respect to the current
+ * user-space it may be necessary to also examine the pen's matrix
+ * (see cairo_get_pen()).
  * 
- * Return value: the current line width, in user-space units.
+ * Return value: the line width of the current pen
  **/
 double
 cairo_get_line_width (cairo_t *cr)
...
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 189 bytes
Desc: not available
Url : http://lists.freedesktop.org/archives/cairo/attachments/20060516/a6104437/attachment.pgp


More information about the cairo mailing list