Optimized _cairo_surface_composite for compositing local memory surface with an X11 server surface.

This commit is contained in:
Carl Worth 2003-08-29 17:57:08 +00:00
parent 0ed4d32d87
commit 44b3c4ca78
4 changed files with 66 additions and 15 deletions

View file

@ -1,3 +1,10 @@
2003-08-29 Carl Worth <cworth@isi.edu>
* src/cairo_surface.c (_cairo_surface_composite): Optimized case
where src is in memory, dst is on server, and mask is NULL. Will
now do a single XPutImage rather than the painful
GetImage/PutImage dance of the general code.
2003-08-28 Carl Worth <cworth at east.isi.edu>
* src/cairo_traps.c (_line_segs_intersect_ceil): One more

View file

@ -588,17 +588,39 @@ _cairo_surface_composite (cairo_operator_t operator,
{
if (dst->type == CAIRO_SURFACE_TYPE_DRAWABLE
&& CAIRO_SURFACE_RENDER_HAS_COMPOSITE (dst)
&& src->dpy == dst->dpy
&& (mask == NULL || mask->dpy == dst->dpy)) {
&& (mask == NULL || mask->dpy == dst->dpy)
&& (src->type == CAIRO_SURFACE_TYPE_ICIMAGE || src->dpy == dst->dpy)) {
cairo_surface_t *src_on_server = NULL;
if (src->type == CAIRO_SURFACE_TYPE_ICIMAGE) {
cairo_matrix_t matrix;
src_on_server = cairo_surface_create_similar (dst, CAIRO_FORMAT_ARGB32,
IcImageGetWidth (src->icimage),
IcImageGetWidth (src->icimage));
if (src_on_server == NULL)
return;
cairo_surface_get_matrix (src, &matrix);
cairo_surface_set_matrix (src_on_server, &matrix);
cairo_surface_put_image (src_on_server,
(char *) IcImageGetData (src->icimage),
IcImageGetWidth (src->icimage),
IcImageGetHeight (src->icimage),
IcImageGetStride (src->icimage));
}
XRenderComposite (dst->dpy, operator,
src->picture,
src_on_server ? src_on_server->picture : src->picture,
mask ? mask->picture : 0,
dst->picture,
src_x, src_y,
mask_x, mask_y,
dst_x, dst_y,
width, height);
} else {
_cairo_surface_pull_image (src);
_cairo_surface_pull_image (mask);

View file

@ -403,11 +403,11 @@ cairo_get_status_string (cairo_t *cr);
cairo_surface_create_for_pixmap with a cairo_format_t. Would that work?
*/
extern cairo_surface_t * __external_linkage
cairo_surface_create_for_drawable (Display *dpy,
Drawable drawable,
Visual *visual,
cairo_surface_create_for_drawable (Display *dpy,
Drawable drawable,
Visual *visual,
cairo_format_t format,
Colormap colormap);
Colormap colormap);
extern cairo_surface_t * __external_linkage
cairo_surface_create_for_image (char *data,
@ -418,7 +418,7 @@ cairo_surface_create_for_image (char *data,
extern cairo_surface_t * __external_linkage
cairo_surface_create_similar (cairo_surface_t *other,
cairo_format_t format,
cairo_format_t format,
int width,
int height);
@ -441,10 +441,10 @@ cairo_surface_destroy (cairo_surface_t *surface);
extern cairo_status_t __external_linkage
cairo_surface_put_image (cairo_surface_t *surface,
char *data,
int width,
int height,
int stride);
char *data,
int width,
int height,
int stride);
/* XXX: NYI
extern cairo_status_t __external_linkage

View file

@ -588,17 +588,39 @@ _cairo_surface_composite (cairo_operator_t operator,
{
if (dst->type == CAIRO_SURFACE_TYPE_DRAWABLE
&& CAIRO_SURFACE_RENDER_HAS_COMPOSITE (dst)
&& src->dpy == dst->dpy
&& (mask == NULL || mask->dpy == dst->dpy)) {
&& (mask == NULL || mask->dpy == dst->dpy)
&& (src->type == CAIRO_SURFACE_TYPE_ICIMAGE || src->dpy == dst->dpy)) {
cairo_surface_t *src_on_server = NULL;
if (src->type == CAIRO_SURFACE_TYPE_ICIMAGE) {
cairo_matrix_t matrix;
src_on_server = cairo_surface_create_similar (dst, CAIRO_FORMAT_ARGB32,
IcImageGetWidth (src->icimage),
IcImageGetWidth (src->icimage));
if (src_on_server == NULL)
return;
cairo_surface_get_matrix (src, &matrix);
cairo_surface_set_matrix (src_on_server, &matrix);
cairo_surface_put_image (src_on_server,
(char *) IcImageGetData (src->icimage),
IcImageGetWidth (src->icimage),
IcImageGetHeight (src->icimage),
IcImageGetStride (src->icimage));
}
XRenderComposite (dst->dpy, operator,
src->picture,
src_on_server ? src_on_server->picture : src->picture,
mask ? mask->picture : 0,
dst->picture,
src_x, src_y,
mask_x, mask_y,
dst_x, dst_y,
width, height);
} else {
_cairo_surface_pull_image (src);
_cairo_surface_pull_image (mask);