[cairo] RFC v3: Path Effects API

Bryce Harrington bryce at osg.samsung.com
Mon Oct 17 18:15:57 UTC 2016


In September 2013, Henry proposed[0] adding a feature for Gaussian blur
and shadow, based on work carried in his cairogles branch[1].  The
proposed API[2] was felt to have too many entry points to the context
for setting all the various parameters (shadow color and type, blur
direction, etc.), and Chris suggested[3] coming up with a more generic
API that would handle path effects in a way more analogous to patterns.

In 2014 I posted[4] a rough cut at such an API, following
cairo_pattern's API design, and a v2 shortly thereafter[5].  Following
is a v3 of that proposal, incorporating some of Chris Wilson's suggested
changes.

In particular, this divides the API into a base class (Effects), and
sub-class (Path Effects), allowing for future introduction of pen
effects, material effects, etc.  This common API is intended to
provide a consistent way of handling all effects in the rendering
pipeline.

v2:
  + Add get_data, set_data, reference_count for the cairo_object_t api
  + Rename enums
v3:
  + Path Effects are handled as a subclass of Effects

---

/*
 * Effect lifecycle management
 */
cairo_public cairo_status_t
cairo_effect_status (cairo_effect_t *effect);

cairo_public cairo_effect_t *
cairo_effect_reference (cairo_effect_t *effect);

cairo_public void
cairo_effect_destroy (cairo_effect_t *effect);

cairo_public unsigned int
cairo_effect_get_reference_count (cairo_effect_t *effect);

cairo_public void *
cairo_effect_get_user_data (cairo_effect_t *effect,
			    const cairo_user_data_key_t *key);
cairo_public cairo_status_t
cairo_effect_set_user_data (cairo_effect_t *effect,
			    const cairo_user_data_key_t *key,
			    void *user_data,
			    cairo_destroy_funct_t destroy);

/*
 * Effect properties
 */
typedef enum _cairo_effect_type {
    CAIRO_EFFECT_TYPE_NONE = 0,
    CAIRO_EFFECT_TYPE_PATH
} cairo_effect_type_t;

/* Future types might include:
 *  CAIRO_EFFECT_TYPE_PEN
 *  CAIRO_EFFECT_TYPE_MATERIAL
 *  CAIRO_EFFECT_TYPE_OPERATOR
 *  CAIRO_EFFECT_TYPE_CLIP
 *  ...
 */

cairo_public cairo_effect_type_t
cairo_effect_get_type (cairo_effect_t *effect);



/* ---------------------------------------------------------------------- */

/*
 * Path effect creation
 *
 * These create effects of type CAIRO_EFFECT_TYPE_PATH.
 */ 
cairo_public cairo_effect_t *
cairo_effect_create_drop_shadow_path (double x_offset, double y_offset,
                                      double x_blur,   double y_blur);

cairo_public cairo_effect_t *
cairo_effect_create_inset_shadow_path (double x_inset, double y_inset,
                                       double x_blur,  double y_blur);

/*
 * Applying path effects to the context
 */
cairo_public void
cairo_set_path_effect (cairo_t *cr, cairo_effect_t *source);

cairo_public cairo_effect_t *
cairo_get_path_effect (cairo_t *cr);

/*
 * Path effect properties
 */
typedef enum _cairo_path_effect_type {
    CAIRO_PATH_EFFECT_NONE = 0,
    CAIRO_PATH_EFFECT_DROP_SHADOW,
    CAIRO_PATH_EFFECT_INSET_SHADOW
} cairo_path_effect_type_t;

/* Future path effect types could include:
 *  CAIRO_PATH_EFFECT_PATTERN
 *  CAIRO_PATH_EFFECT_UNION
 *  CAIRO_PATH_EFFECT_DIFFERENCE
 *  CAIRO_PATH_EFFECT_INTERSECTION
 *  ...
 */

cairo_public cairo_path_effect_type_t
cairo_path_effect_get_subtype (cairo_effect_t *effect);

cairo_public void
cairo_path_effect_set_rgba (cairo_path_effect_t *path_effect,
            		    double red, double green, double blue,
                       	    double alpha);

Internally, both the effect type and subtype can be tracked in a single
property, e.g.:

    type = CAIRO_EFFECT_TYPE_PATH << 24 | CAIRO_PATH_EFFECT_DROP_SHADOW;


Henry's API proposal included provision for shadow caching by the
application.  That certainly made a huge difference in the demos, so
maybe it's still going to be needed.  An idea is to provide a
backend/user preference as to whether effects should be cached or
applied on the fly, e.g. cairo_effect_set_cached.

Bryce

0:  https://lists.cairographics.org/archives/cairo/2013-September/024596.html
1:  The cairogles branch is no longer available publically.  The private
    branch is at https://github.com/SRA-SiliconValley/cairogles
2:  https://lists.cairographics.org/archives/cairo/2013-September/024598.html
3:  https://lists.cairographics.org/archives/cairo/2013-September/024597.html
4:  https://lists.cairographics.org/archives/cairo/2014-October/025748.html
5:  https://lists.cairographics.org/archives/cairo/2014-October/025766.html


More information about the cairo mailing list