[cairo] OpenGL backend news and a few words about shading

Thomas Hunger info at teh-web.de
Sun Feb 29 11:04:00 PST 2004

> Shading in Cairo
> What I've done with the OpenGL patch is that I've added a new type of
> surface called a cairo_gradient_surface (should probably be programmatic

Thats what I did first, but had the following problem: The surface size needs 
to be known before the gradient_surface can be created. So the user has to 
take care of that. I'd like to have that hidden in the internals.

I'd also like to be able to plug in a custom shader callback on the public api 
side of cairo, although I am not sure how important that is for others.

It seems that solid color and pattern fill are just a subset of a general 
shader interface. currently _cairo_source_ensure does make sure that there is 
a source to composite against. In the case of a user-set pattern, it just 
keeps source as it is, in the case of a solid color it used create_similar to 
create a 1x1 (repeat ==1) source to composite against. 

If the _cairo_ensure_source function would be replaced by the custom shader 
callback, there would be a solid_shader_func, pattern_shader_func and we 
could also add linear_shader_func and others. 

In addition to that we would have to add a few callbacks to the 
cairo_surface_backend_t for standard shaders like linear, radial, gouraud, 
whatever, to allow surface backends to plug in their own accelerated shaders. 
Since the shaded surface would be created with the create_similar function,
e.g. a surface->shade_linear(size_x, size_y, extradata) would be enough within 
the custom callback function. Right now the glc backend is the only one which 
supports hardware accelerated shading, so all the other would need to use 

Also, it could make sense to alter the set_repeat argument from an int to 
CAIRO_REPEAT_TRIANGULAR, to allow different behaviours for the standard 
shaders. These repeats do not make sense for a pattern, so I am not quite 
sure if they are really a good idea.

Carl said he'd rather not have a cairo_shader_t in the public api, so we would 
need a way to express shaders through functions. Since they usually take a 
ridiculous amount of arguments I think it would make sense to split shader 
creation into seperate functions. I really like color_stop you introduced in 
the glc-backend introduced for shading. Here are a few functions I can think 
of to modify surface looks (old ones included):

cairo_set_pattern (...
cairo_set_rgb_color (...
cairo_set_alpha (...
cairo_set_shader_linear (double x1, double  y1, double x2, double y2)
cairo_set_shader_radial (double xc, double yc, double t, double focalx, double 
cairo_set_shader_custom (cairo_shader_callback_t *shader_callback);
cairo_set_shader_color_stop (double position, double r, g, b, a);

These functions would internally just alter the callback function or change 
the internal data.

I know this is very intrusive and would take some work, since every 
backend-source would have to modified. Other ideas are welcome :)

> in their own way or just request an image version of the gradient from
> the gradient surface backend. You should have a look at the GL backend

I had a look at it, I think this could integrate well with the framework 
described above. 


P.s. Do you know how I can make my radeon9000 support programmatic surfaces 
(and antialiasing)? All the other demos from you work fine and fast - cool!

More information about the cairo mailing list