jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: cairo_path_t: Cairo: A Vector Graphics Library jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68: jpayne@68:
jpayne@68:

jpayne@68: cairo_path_t

jpayne@68:

jpayne@68: The cairo_path_t type is one jpayne@68: area in which most language bindings will differ significantly jpayne@68: from the C API. The C API for cairo_path_t is jpayne@68: designed for efficiency and to avoid auxiliary objects that jpayne@68: would be have to be manually memory managed by the jpayne@68: application. However, jpayne@68: a language binding should not present cairo_path_t as an jpayne@68: array, but rather as an opaque that can be iterated jpayne@68: over. Different languages have quite different conventions for jpayne@68: how iterators work, so it is impossible to give an exact jpayne@68: specification for how this API should work, but the type names jpayne@68: and methods should be similar to the language's mapping of the following: jpayne@68:

jpayne@68:
jpayne@68: typedef struct cairo_path_iterator cairo_path_iterator_t;
jpayne@68: typedef struct cairo_path_element cairo_path_element_t;
jpayne@68: 
jpayne@68: cairo_path_iterator_t *
jpayne@68: cairo_path_get_iterator (cairo_path_t *path);
jpayne@68: 
jpayne@68: cairo_bool_t
jpayne@68: cairo_path_iterator_has_next (cairo_path_iterator_t *iterator);
jpayne@68:       
jpayne@68: cairo_path_element_t *
jpayne@68: cairo_path_iterator_next (cairo_path_iterator_t *iterator);
jpayne@68: 
jpayne@68: cairo_path_element_type_t
jpayne@68: cairo_path_element_get_type (cairo_path_element_t *element);
jpayne@68:       
jpayne@68: void
jpayne@68: cairo_path_element_get_point (cairo_path_element_t *element,
jpayne@68:                               int                   index,
jpayne@68:                               double                *x,
jpayne@68:                               double                *y);
jpayne@68:     
jpayne@68:

jpayne@68: The above is written using the Java conventions for jpayne@68: iterators. To illustrate how the API for PathIterator might jpayne@68: depend on the native iteration conventions of the API, examine jpayne@68: three versions of the loop, first written in a hypothetical Java jpayne@68: binding: jpayne@68:

jpayne@68:
jpayne@68: PathIterator iter = cr.copyPath().iterator();
jpayne@68: while (cr.hasNext()) {
jpayne@68:     PathElement element = iter.next();
jpayne@68:     if (element.getType() == PathElementType.MOVE_TO) {
jpayne@68:         Point p = element.getPoint(0);
jpayne@68:         doMoveTo (p.x, p.y);
jpayne@68:     }
jpayne@68: }
jpayne@68:

jpayne@68: And then in a hypothetical C++ binding: jpayne@68:

jpayne@68:
jpayne@68: Path path = cr.copyPath();
jpayne@68: for (PathIterator iter = path.begin(); iter != path.end(); iter++) {
jpayne@68:     PathElement element = *iter;
jpayne@68:     if (element.getType() == PathElementType.MOVE_TO) {
jpayne@68:         Point p = element.getPoint(0);
jpayne@68:         doMoveTo (p.x, p.y);
jpayne@68:     }
jpayne@68: }
jpayne@68:

jpayne@68: And then finally in a Python binding: jpayne@68:

jpayne@68:
jpayne@68: for element in cr.copy_path():
jpayne@68:     if element.getType == cairo.PATH_ELEMENT_MOVE_TO:
jpayne@68:         (x, y) = element.getPoint(0)
jpayne@68:         doMoveTo (x, y);
jpayne@68:

jpayne@68: While many of the API elements stay the same in the three jpayne@68: examples, the exact iteration mechanism is quite different, to jpayne@68: match how users of the language would expect to iterate over jpayne@68: a container. jpayne@68:

jpayne@68:

jpayne@68: You should not present an API for mutating or for creating new jpayne@68: cairo_path_t objects. In the future, these jpayne@68: guidelines may be extended to present an API for creating a jpayne@68: cairo_path_t from scratch for use with jpayne@68: cairo_append_path() jpayne@68: but the current expectation is that cairo_append_path() will jpayne@68: mostly be used with paths from jpayne@68: cairo_copy_path(). jpayne@68:

jpayne@68:
jpayne@68: jpayne@68: jpayne@68: