in src/common/surface.c [1890:1976]
static void __guac_common_surface_flush(guac_common_surface* surface) {
/* Flush final dirty rectangle to queue. */
__guac_common_surface_flush_to_queue(surface);
guac_common_surface_bitmap_rect* current = surface->bitmap_queue;
int i, j;
int original_queue_length;
int flushed = 0;
original_queue_length = surface->bitmap_queue_length;
/* Sort updates to make combination less costly */
qsort(surface->bitmap_queue, surface->bitmap_queue_length, sizeof(guac_common_surface_bitmap_rect),
__guac_common_surface_bitmap_rect_compare);
/* Flush all rects in queue */
for (i=0; i < surface->bitmap_queue_length; i++) {
/* Get next unflushed candidate */
guac_common_surface_bitmap_rect* candidate = current;
if (!candidate->flushed) {
int combined = 0;
/* Build up rect as much as possible */
for (j=i; j < surface->bitmap_queue_length; j++) {
if (!candidate->flushed) {
/* Clip candidate within current bounds */
__guac_common_bound_rect(surface, &candidate->rect, NULL, NULL);
if (candidate->rect.width <= 0 || candidate->rect.height <= 0)
candidate->flushed = 1;
/* Combine if reasonable */
else if (__guac_common_should_combine(surface, &candidate->rect, 0) || !surface->dirty) {
__guac_common_mark_dirty(surface, &candidate->rect);
candidate->flushed = 1;
combined++;
}
}
candidate++;
}
/* Re-add to queue if there's room and this update was modified or we expect others might be */
if ((combined > 1 || i < original_queue_length)
&& surface->bitmap_queue_length < GUAC_COMMON_SURFACE_QUEUE_SIZE)
__guac_common_surface_flush_to_queue(surface);
/* Flush as bitmap otherwise */
else if (surface->dirty) {
flushed++;
int opaque = __guac_common_surface_is_opaque(surface,
&surface->dirty_rect);
/* Prefer WebP when reasonable */
if (__guac_common_surface_should_use_webp(surface,
&surface->dirty_rect))
__guac_common_surface_flush_to_webp(surface, opaque);
/* If not WebP, JPEG is the next best (lossy) choice */
else if (opaque && __guac_common_surface_should_use_jpeg(
surface, &surface->dirty_rect))
__guac_common_surface_flush_to_jpeg(surface);
/* Use PNG if no lossy formats are appropriate */
else
__guac_common_surface_flush_to_png(surface, opaque);
}
}
current++;
}
/* Flush complete */
surface->bitmap_queue_length = 0;
}