cairo_new_sub_path: Making cairo_arc easier to use and more.

This adds a new function which has as its only effect the elimination
of
the current point. This makes it much easier to use the various
cairo_arc calls when the initial line_to is not actually desired.

This function also unifies and generalizes the long-existing behavior
of cairo_line_to being treated as cairo_move_to when there is no
current point. With the addition of cairo_new_sub_path this becomes a
documented feature with similar behavior in cairo_curve_to as well.
This commit is contained in:
Carl Worth 2006-02-23 22:01:07 -08:00
parent 0354956a09
commit 1dc1b57b4e
14 changed files with 209 additions and 124 deletions

1
.gitignore vendored
View file

@ -22,3 +22,4 @@ stamp-h
stamp-h1
stamp-h.in
*~
*.orig

View file

@ -47,7 +47,6 @@ typedef struct cairo_stroker {
cairo_pen_t pen;
cairo_bool_t has_current_point;
cairo_point_t current_point;
cairo_point_t first_point;
@ -159,7 +158,6 @@ _cairo_stroker_init (cairo_stroker_t *stroker,
stroke_style->line_width / 2.0,
tolerance, ctm);
stroker->has_current_point = FALSE;
stroker->has_current_face = FALSE;
stroker->has_first_face = FALSE;
@ -607,7 +605,6 @@ _cairo_stroker_move_to (void *closure, cairo_point_t *point)
stroker->first_point = *point;
stroker->current_point = *point;
stroker->has_current_point = 1;
stroker->has_first_face = 0;
stroker->has_current_face = 0;
@ -624,9 +621,6 @@ _cairo_stroker_line_to (void *closure, cairo_point_t *point)
cairo_point_t *p1 = &stroker->current_point;
cairo_point_t *p2 = point;
if (!stroker->has_current_point)
return _cairo_stroker_move_to (stroker, point);
if (p1->x == p2->x && p1->y == p2->y) {
/* XXX: Need to rethink how this case should be handled, (both
here and in cairo_stroker_add_sub_edge and in _compute_face). The
@ -674,9 +668,6 @@ _cairo_stroker_line_to_dashed (void *closure, cairo_point_t *point)
cairo_point_t *p1 = &stroker->current_point;
cairo_point_t *p2 = point;
if (!stroker->has_current_point)
return _cairo_stroker_move_to (stroker, point);
dx = _cairo_fixed_to_double (p2->x - p1->x);
dy = _cairo_fixed_to_double (p2->y - p1->y);
@ -914,14 +905,12 @@ _cairo_stroker_close_path (void *closure)
cairo_status_t status;
cairo_stroker_t *stroker = closure;
if (stroker->has_current_point) {
if (stroker->dashed)
status = _cairo_stroker_line_to_dashed (stroker, &stroker->first_point);
else
status = _cairo_stroker_line_to (stroker, &stroker->first_point);
if (status)
return status;
}
if (stroker->dashed)
status = _cairo_stroker_line_to_dashed (stroker, &stroker->first_point);
else
status = _cairo_stroker_line_to (stroker, &stroker->first_point);
if (status)
return status;
if (stroker->has_first_face && stroker->has_current_face) {
status = _cairo_stroker_join (stroker, &stroker->current_face, &stroker->first_face);
@ -931,7 +920,6 @@ _cairo_stroker_close_path (void *closure)
stroker->has_first_face = 0;
stroker->has_current_face = 0;
stroker->has_current_point = 0;
return CAIRO_STATUS_SUCCESS;
}

View file

@ -87,7 +87,7 @@ _cairo_path_fixed_init (cairo_path_fixed_t *path)
path->current_point.x = 0;
path->current_point.y = 0;
path->has_current_point = 0;
path->has_current_point = FALSE;
path->last_move_point = path->current_point;
}
@ -163,7 +163,7 @@ _cairo_path_fixed_fini (cairo_path_fixed_t *path)
}
path->arg_buf_tail = NULL;
path->has_current_point = 0;
path->has_current_point = FALSE;
}
void
@ -189,12 +189,18 @@ _cairo_path_fixed_move_to (cairo_path_fixed_t *path,
return status;
path->current_point = point;
path->has_current_point = 1;
path->has_current_point = TRUE;
path->last_move_point = path->current_point;
return CAIRO_STATUS_SUCCESS;
}
void
_cairo_path_fixed_new_sub_path (cairo_path_fixed_t *path)
{
path->has_current_point = FALSE;
}
cairo_status_t
_cairo_path_fixed_rel_move_to (cairo_path_fixed_t *path,
cairo_fixed_t dx,
@ -202,7 +208,7 @@ _cairo_path_fixed_rel_move_to (cairo_path_fixed_t *path,
{
cairo_fixed_t x, y;
if (!path->has_current_point)
if (! path->has_current_point)
return CAIRO_STATUS_NO_CURRENT_POINT;
x = path->current_point.x + dx;
@ -222,12 +228,16 @@ _cairo_path_fixed_line_to (cairo_path_fixed_t *path,
point.x = x;
point.y = y;
status = _cairo_path_fixed_add (path, CAIRO_PATH_OP_LINE_TO, &point, 1);
if (! path->has_current_point)
status = _cairo_path_fixed_add (path, CAIRO_PATH_OP_MOVE_TO, &point, 1);
else
status = _cairo_path_fixed_add (path, CAIRO_PATH_OP_LINE_TO, &point, 1);
if (status)
return status;
path->current_point = point;
path->has_current_point = 1;
path->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}
@ -239,7 +249,7 @@ _cairo_path_fixed_rel_line_to (cairo_path_fixed_t *path,
{
cairo_fixed_t x, y;
if (!path->has_current_point)
if (! path->has_current_point)
return CAIRO_STATUS_NO_CURRENT_POINT;
x = path->current_point.x + dx;
@ -261,12 +271,19 @@ _cairo_path_fixed_curve_to (cairo_path_fixed_t *path,
point[1].x = x1; point[1].y = y1;
point[2].x = x2; point[2].y = y2;
if (! path->has_current_point) {
status = _cairo_path_fixed_add (path, CAIRO_PATH_OP_MOVE_TO,
&point[0], 1);
if (status)
return status;
}
status = _cairo_path_fixed_add (path, CAIRO_PATH_OP_CURVE_TO, point, 3);
if (status)
return status;
path->current_point = point[2];
path->has_current_point = 1;
path->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}
@ -281,7 +298,7 @@ _cairo_path_fixed_rel_curve_to (cairo_path_fixed_t *path,
cairo_fixed_t x1, y1;
cairo_fixed_t x2, y2;
if (!path->has_current_point)
if (! path->has_current_point)
return CAIRO_STATUS_NO_CURRENT_POINT;
x0 = path->current_point.x + dx0;
@ -304,13 +321,16 @@ _cairo_path_fixed_close_path (cairo_path_fixed_t *path)
{
cairo_status_t status;
if (! path->has_current_point)
return CAIRO_STATUS_SUCCESS;
status = _cairo_path_fixed_add (path, CAIRO_PATH_OP_CLOSE_PATH, NULL, 0);
if (status)
return status;
path->current_point.x = path->last_move_point.x;
path->current_point.y = path->last_move_point.y;
path->has_current_point = 1;
path->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}

View file

@ -1263,22 +1263,15 @@ intersect (cairo_line_t *line, cairo_fixed_t y)
_cairo_fixed_to_double (line->p2.y - line->p1.y);
}
typedef struct
{
cairo_output_stream_t *output_stream;
cairo_bool_t has_current_point;
} pdf_path_info_t;
static cairo_status_t
_cairo_pdf_path_move_to (void *closure, cairo_point_t *point)
{
pdf_path_info_t *info = closure;
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
_cairo_output_stream_printf (output_stream,
"%f %f m ",
_cairo_fixed_to_double (point->x),
_cairo_fixed_to_double (point->y));
info->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}
@ -1286,20 +1279,12 @@ _cairo_pdf_path_move_to (void *closure, cairo_point_t *point)
static cairo_status_t
_cairo_pdf_path_line_to (void *closure, cairo_point_t *point)
{
pdf_path_info_t *info = closure;
const char *pdf_operator;
if (info->has_current_point)
pdf_operator = "l";
else
pdf_operator = "m";
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
"%f %f %s ",
_cairo_output_stream_printf (output_stream,
"%f %f l ",
_cairo_fixed_to_double (point->x),
_cairo_fixed_to_double (point->y),
pdf_operator);
info->has_current_point = TRUE;
_cairo_fixed_to_double (point->y));
return CAIRO_STATUS_SUCCESS;
}
@ -1310,9 +1295,9 @@ _cairo_pdf_path_curve_to (void *closure,
cairo_point_t *c,
cairo_point_t *d)
{
pdf_path_info_t *info = closure;
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
_cairo_output_stream_printf (output_stream,
"%f %f %f %f %f %f c ",
_cairo_fixed_to_double (b->x),
_cairo_fixed_to_double (b->y),
@ -1327,11 +1312,10 @@ _cairo_pdf_path_curve_to (void *closure,
static cairo_status_t
_cairo_pdf_path_close_path (void *closure)
{
pdf_path_info_t *info = closure;
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
_cairo_output_stream_printf (output_stream,
"h\r\n");
info->has_current_point = FALSE;
return CAIRO_STATUS_SUCCESS;
}
@ -1349,7 +1333,6 @@ _cairo_pdf_surface_fill (void *abstract_surface,
cairo_pdf_document_t *document = surface->document;
const char *pdf_operator;
cairo_status_t status;
pdf_path_info_t info;
status = emit_pattern (surface, pattern);
if (status)
@ -1360,16 +1343,13 @@ _cairo_pdf_surface_fill (void *abstract_surface,
assert (document->current_stream != NULL &&
document->current_stream == surface->current_stream);
info.output_stream = document->output_stream;
info.has_current_point = FALSE;
status = _cairo_path_fixed_interpret (path,
CAIRO_DIRECTION_FORWARD,
_cairo_pdf_path_move_to,
_cairo_pdf_path_line_to,
_cairo_pdf_path_curve_to,
_cairo_pdf_path_close_path,
&info);
document->output_stream);
switch (fill_rule) {
case CAIRO_FILL_RULE_WINDING:
@ -1600,7 +1580,6 @@ _cairo_pdf_surface_intersect_clip_path (void *dst,
cairo_pdf_document_t *document = surface->document;
cairo_output_stream_t *output = document->output_stream;
cairo_status_t status;
pdf_path_info_t info;
const char *pdf_operator;
_cairo_pdf_surface_ensure_stream (surface);
@ -1617,16 +1596,13 @@ _cairo_pdf_surface_intersect_clip_path (void *dst,
surface->has_clip = TRUE;
}
info.output_stream = document->output_stream;
info.has_current_point = FALSE;
status = _cairo_path_fixed_interpret (path,
CAIRO_DIRECTION_FORWARD,
_cairo_pdf_path_move_to,
_cairo_pdf_path_line_to,
_cairo_pdf_path_curve_to,
_cairo_pdf_path_close_path,
&info);
document->output_stream);
switch (fill_rule) {
case CAIRO_FILL_RULE_WINDING:

View file

@ -1049,22 +1049,16 @@ _cairo_ps_surface_composite_trapezoids (cairo_operator_t op,
return CAIRO_STATUS_SUCCESS;
}
typedef struct
{
cairo_output_stream_t *output_stream;
cairo_bool_t has_current_point;
} cairo_ps_surface_path_info_t;
static cairo_status_t
_cairo_ps_surface_path_move_to (void *closure, cairo_point_t *point)
{
cairo_ps_surface_path_info_t *info = closure;
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
_cairo_output_stream_printf (output_stream,
"%f %f moveto ",
_cairo_fixed_to_double (point->x),
_cairo_fixed_to_double (point->y));
info->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}
@ -1072,33 +1066,25 @@ _cairo_ps_surface_path_move_to (void *closure, cairo_point_t *point)
static cairo_status_t
_cairo_ps_surface_path_line_to (void *closure, cairo_point_t *point)
{
cairo_ps_surface_path_info_t *info = closure;
const char *ps_operator;
cairo_output_stream_t *output_stream = closure;
if (info->has_current_point)
ps_operator = "lineto";
else
ps_operator = "moveto";
_cairo_output_stream_printf (info->output_stream,
"%f %f %s ",
_cairo_output_stream_printf (output_stream,
"%f %f lineto ",
_cairo_fixed_to_double (point->x),
_cairo_fixed_to_double (point->y),
ps_operator);
info->has_current_point = TRUE;
_cairo_fixed_to_double (point->y));
return CAIRO_STATUS_SUCCESS;
}
static cairo_status_t
_cairo_ps_surface_path_curve_to (void *closure,
cairo_point_t *b,
cairo_point_t *c,
cairo_point_t *d)
cairo_point_t *b,
cairo_point_t *c,
cairo_point_t *d)
{
cairo_ps_surface_path_info_t *info = closure;
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
_cairo_output_stream_printf (output_stream,
"%f %f %f %f %f %f curveto ",
_cairo_fixed_to_double (b->x),
_cairo_fixed_to_double (b->y),
@ -1113,11 +1099,10 @@ _cairo_ps_surface_path_curve_to (void *closure,
static cairo_status_t
_cairo_ps_surface_path_close_path (void *closure)
{
cairo_ps_surface_path_info_t *info = closure;
cairo_output_stream_t *output_stream = closure;
_cairo_output_stream_printf (info->output_stream,
_cairo_output_stream_printf (output_stream,
"closepath\n");
info->has_current_point = FALSE;
return CAIRO_STATUS_SUCCESS;
}
@ -1132,7 +1117,6 @@ _cairo_ps_surface_intersect_clip_path (void *abstract_surface,
cairo_ps_surface_t *surface = abstract_surface;
cairo_output_stream_t *stream = surface->stream;
cairo_status_t status;
cairo_ps_surface_path_info_t info;
const char *ps_operator;
_cairo_output_stream_printf (stream,
@ -1143,16 +1127,13 @@ _cairo_ps_surface_intersect_clip_path (void *abstract_surface,
return CAIRO_STATUS_SUCCESS;
}
info.output_stream = stream;
info.has_current_point = FALSE;
status = _cairo_path_fixed_interpret (path,
CAIRO_DIRECTION_FORWARD,
_cairo_ps_surface_path_move_to,
_cairo_ps_surface_path_line_to,
_cairo_ps_surface_path_curve_to,
_cairo_ps_surface_path_close_path,
&info);
stream);
switch (fill_rule) {
case CAIRO_FILL_RULE_WINDING:
@ -1276,7 +1257,6 @@ _cairo_ps_surface_fill (void *abstract_surface,
cairo_ps_surface_t *surface = abstract_surface;
cairo_output_stream_t *stream = surface->stream;
cairo_int_status_t status;
cairo_ps_surface_path_info_t info;
const char *ps_operator;
if (pattern_operation_needs_fallback (op, source))
@ -1293,16 +1273,13 @@ _cairo_ps_surface_fill (void *abstract_surface,
emit_pattern (surface, source);
info.output_stream = stream;
info.has_current_point = FALSE;
status = _cairo_path_fixed_interpret (path,
CAIRO_DIRECTION_FORWARD,
_cairo_ps_surface_path_move_to,
_cairo_ps_surface_path_line_to,
_cairo_ps_surface_path_curve_to,
_cairo_ps_surface_path_close_path,
&info);
stream);
switch (fill_rule) {
case CAIRO_FILL_RULE_WINDING:

View file

@ -783,7 +783,6 @@ emit_pattern (cairo_svg_surface_t *surface, cairo_pattern_t *pattern,
typedef struct
{
cairo_svg_document_t *document;
cairo_bool_t has_current_point;
xmlBufferPtr path;
} svg_path_info_t;
@ -801,7 +800,6 @@ _cairo_svg_path_move_to (void *closure, cairo_point_t *point)
_cairo_dtostr (buffer, sizeof buffer, _cairo_fixed_to_double (point->y));
xmlBufferCat (path, CC2XML (buffer));
xmlBufferCat (path, CC2XML (" "));
info->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}
@ -813,10 +811,7 @@ _cairo_svg_path_line_to (void *closure, cairo_point_t *point)
xmlBufferPtr path = info->path;
char buffer[CAIRO_SVG_DTOSTR_BUFFER_LEN];
if (info->has_current_point)
xmlBufferCat (path, CC2XML ("L "));
else
xmlBufferCat (path, CC2XML ("M "));
xmlBufferCat (path, CC2XML ("L "));
_cairo_dtostr (buffer, sizeof buffer, _cairo_fixed_to_double (point->x));
xmlBufferCat (path, CC2XML (buffer));
@ -825,8 +820,6 @@ _cairo_svg_path_line_to (void *closure, cairo_point_t *point)
xmlBufferCat (path, CC2XML (buffer));
xmlBufferCat (path, CC2XML (" "));
info->has_current_point = TRUE;
return CAIRO_STATUS_SUCCESS;
}
@ -868,10 +861,7 @@ _cairo_svg_path_close_path (void *closure)
{
svg_path_info_t *info = closure;
if (info->has_current_point)
xmlBufferCat (info->path, CC2XML ("Z "));
info->has_current_point = FALSE;
xmlBufferCat (info->path, CC2XML ("Z "));
return CAIRO_STATUS_SUCCESS;
}
@ -893,7 +883,6 @@ _cairo_svg_surface_fill (void *abstract_surface,
xmlBufferPtr style;
info.document = document;
info.has_current_point = FALSE;
info.path = xmlBufferCreate ();
style = xmlBufferCreate ();
@ -1035,7 +1024,6 @@ _cairo_svg_surface_stroke (void *abstract_dst,
char buffer[CAIRO_SVG_DTOSTR_BUFFER_LEN];
info.document = document;
info.has_current_point = FALSE;
info.path = xmlBufferCreate ();
rx = ry = stroke_style->line_width;
@ -1176,7 +1164,6 @@ _cairo_svg_surface_intersect_clip_path (void *dst,
if (path != NULL) {
info.document = document;
info.has_current_point = FALSE;
info.path = xmlBufferCreate ();
group = xmlNewChild (surface->xml_node, NULL, CC2XML ("g"), NULL);

View file

@ -957,8 +957,8 @@ cairo_device_to_user_distance (cairo_t *cr, double *dx, double *dy)
* cairo_new_path:
* @cr: a cairo context
*
* Clears the current path. After this call there will be no current
* point.
* Clears the current path. After this call there will be no path and
* no current point.
**/
void
cairo_new_path (cairo_t *cr)
@ -976,8 +976,8 @@ slim_hidden_def(cairo_new_path);
* @x: the X coordinate of the new position
* @y: the Y coordinate of the new position
*
* If the current subpath is not empty, begin a new subpath. After
* this call the current point will be (@x, @y).
* Begin a new subpath. After this call the current point will be (@x,
* @y).
**/
void
cairo_move_to (cairo_t *cr, double x, double y)
@ -997,6 +997,31 @@ cairo_move_to (cairo_t *cr, double x, double y)
}
slim_hidden_def(cairo_move_to);
/**
* cairo_new_sub_path:
* @cr: a cairo context
*
* Begin a new subpath. Note that the existing path is not
* affected. After this call there will be no current point.
*
* In many cases, this call is not needed since new subpaths are
* frequently started with cairo_move_to().
*
* A call to cairo_new_sub_path() is particularly useful when
* beginning a new subpath with one of the cairo_arc() calls. This
* makes things easier as it is no longer necessary to manually
* compute the arc's initial coordinates for a call to
* cairo_move_to().
**/
void
cairo_new_sub_path (cairo_t *cr)
{
if (cr->status)
return;
_cairo_path_fixed_new_sub_path (&cr->path);
}
/**
* cairo_line_to:
* @cr: a cairo context
@ -1006,6 +1031,9 @@ slim_hidden_def(cairo_move_to);
* Adds a line to the path from the current point to position (@x, @y)
* in user-space coordinates. After this call the current point
* will be (@x, @y).
*
* If there is no current point before the call to cairo_line_to()
* this function will behave as cairo_move_to (@cr, @x, @y).
**/
void
cairo_line_to (cairo_t *cr, double x, double y)
@ -1038,6 +1066,10 @@ cairo_line_to (cairo_t *cr, double x, double y)
* position (@x3, @y3) in user-space coordinates, using (@x1, @y1) and
* (@x2, @y2) as the control points. After this call the current point
* will be (@x3, @y3).
*
* If there is no current point before the call to cairo_curve_to()
* this function will behave as if preceded by a call to
* cairo_move_to (@cr, @x1, @y1).
**/
void
cairo_curve_to (cairo_t *cr,
@ -1208,11 +1240,15 @@ cairo_arc_to (cairo_t *cr,
* @dx: the X offset
* @dy: the Y offset
*
* If the current subpath is not empty, begin a new subpath. After
* this call the current point will offset by (@x, @y).
* Begin a new subpath. After this call the current point will offset
* by (@x, @y).
*
* Given a current point of (x, y), cairo_rel_move_to(@cr, @dx, @dy)
* is logically equivalent to cairo_move_to (@cr, x + @dx, y + @dy).
*
* It is an error to call this function with no current point. Doing
* so will cause @cr to shutdown with a status of
* CAIRO_STATUS_NO_CURRENT_POINT.
**/
void
cairo_rel_move_to (cairo_t *cr, double dx, double dy)
@ -1244,6 +1280,10 @@ cairo_rel_move_to (cairo_t *cr, double dx, double dy)
*
* Given a current point of (x, y), cairo_rel_line_to(@cr, @dx, @dy)
* is logically equivalent to cairo_line_to (@cr, x + @dx, y + @dy).
*
* It is an error to call this function with no current point. Doing
* so will cause @cr to shutdown with a status of
* CAIRO_STATUS_NO_CURRENT_POINT.
**/
void
cairo_rel_line_to (cairo_t *cr, double dx, double dy)
@ -1284,6 +1324,10 @@ slim_hidden_def(cairo_rel_line_to);
* @dy1, @dx2, @dy2, @dx3, @dy3) is logically equivalent to
* cairo_curve_to (@cr, x + @dx1, y + @dy1, x + @dx2, y + @dy2, x +
* @dx3, y + @dy3).
*
* It is an error to call this function with no current point. Doing
* so will cause @cr to shutdown with a status of
* CAIRO_STATUS_NO_CURRENT_POINT.
**/
void
cairo_rel_curve_to (cairo_t *cr,
@ -1378,8 +1422,10 @@ cairo_stroke_to_path (cairo_t *cr)
* The behavior of cairo_close_path() is distinct from simply calling
* cairo_line_to() with the equivalent coordinate in the case of
* stroking. When a closed subpath is stroked, there are no caps on
* the ends of the subpath. Instead, their is a line join connecting
* the ends of the subpath. Instead, there is a line join connecting
* the final and initial segments of the subpath.
*
* If there is no current point, this function will have no effect.
**/
void
cairo_close_path (cairo_t *cr)

View file

@ -435,6 +435,9 @@ cairo_new_path (cairo_t *cr);
cairo_public void
cairo_move_to (cairo_t *cr, double x, double y);
cairo_public void
cairo_new_sub_path (cairo_t *cr);
cairo_public void
cairo_line_to (cairo_t *cr, double x, double y);

View file

@ -1394,6 +1394,9 @@ _cairo_path_fixed_move_to (cairo_path_fixed_t *path,
cairo_fixed_t x,
cairo_fixed_t y);
cairo_private void
_cairo_path_fixed_new_sub_path (cairo_path_fixed_t *path);
cairo_private cairo_status_t
_cairo_path_fixed_rel_move_to (cairo_path_fixed_t *path,
cairo_fixed_t dx,

1
test/.gitignore vendored
View file

@ -37,6 +37,7 @@ move-to-show-surface
multi-page
multi-page.pdf
multi-page.ps
new-sub-path
nil-surface
operator-clear
operator-source

View file

@ -29,6 +29,7 @@ mask \
mask-ctm \
mask-surface-ctm \
move-to-show-surface \
new-sub-path \
nil-surface \
operator-clear \
operator-source \
@ -143,6 +144,8 @@ mask-surface-ctm-ref.png \
mask-surface-ctm-rgb24-ref.png \
move-to-show-surface-ref.png \
move-to-show-surface-rgb24-ref.png \
new-sub-path-ref.png \
new-sub-path-rgb24-ref.png \
nil-surface-ref.png \
nil-surface-rgb24-ref.png \
operator-clear-ref.png \
@ -311,6 +314,7 @@ mask_ctm_LDADD = $(LDADDS)
mask_surface_ctm_LDADD = $(LDADDS)
multi_page_LDADD = $(LDADDS)
move_to_show_surface_LDADD = $(LDADDS)
new_sub_path_LDADD = $(LDADDS)
nil_surface_LDADD = $(LDADDS)
operator_clear_LDADD = $(LDADDS)
operator_source_LDADD = $(LDADDS)

BIN
test/new-sub-path-ref.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 386 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 355 B

79
test/new-sub-path.c Normal file
View file

@ -0,0 +1,79 @@
/*
* Copyright © 2005 Red Hat, Inc.
*
* Permission to use, copy, modify, distribute, and sell this software
* and its documentation for any purpose is hereby granted without
* fee, provided that the above copyright notice appear in all copies
* and that both that copyright notice and this permission notice
* appear in supporting documentation, and that the name of
* Red Hat, Inc. not be used in advertising or publicity pertaining to
* distribution of the software without specific, written prior
* permission. Red Hat, Inc. makes no representations about the
* suitability of this software for any purpose. It is provided "as
* is" without express or implied warranty.
*
* RED HAT, INC. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
* SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
* FITNESS, IN NO EVENT SHALL RED HAT, INC. BE LIABLE FOR ANY SPECIAL,
* INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
* RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
* IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
* Author: Carl D. Worth <cworth@cworth.org>
*/
#include "cairo-test.h"
#define SIZE 10
cairo_test_t test = {
"new-sub-path",
"Test the cairo_new_sub_path call",
8 * SIZE,
3 * SIZE
};
static cairo_test_status_t
draw (cairo_t *cr, int width, int height)
{
cairo_set_source_rgb (cr, 0.0, 0.0, 1.0); /* blue */
/* Test cairo_new_sub_path followed by several different
* path-modification functions in turn...
*/
/* ... cairo_move_to */
cairo_new_sub_path (cr);
cairo_move_to (cr, SIZE, SIZE);
cairo_line_to (cr, SIZE, 2 * SIZE);
/* ... cairo_line_to */
cairo_new_sub_path (cr);
cairo_line_to (cr, 2 * SIZE, 1.5 * SIZE);
cairo_line_to (cr, 3 * SIZE, 1.5 * SIZE);
/* ... cairo_curve_to */
cairo_new_sub_path (cr);
cairo_curve_to (cr,
4.0 * SIZE, 1.5 * SIZE,
4.5 * SIZE, 1.0 * SIZE,
5.0 * SIZE, 1.5 * SIZE);
/* ... cairo_arc */
cairo_new_sub_path (cr);
cairo_arc (cr,
6.5 * SIZE, 1.5 * SIZE,
0.5 * SIZE,
0.0, 2.0 * M_PI);
cairo_stroke (cr);
return CAIRO_TEST_SUCCESS;
}
int
main (void)
{
return cairo_test (&test, draw);
}