rsvg_alpha_blt (GdkPixbuf * src, gint srcx, gint srcy, gint srcwidth,
                gint srcheight, GdkPixbuf * dst, gint dstx, gint dsty)
{
    gint rightx;
    gint bottomy;
    gint dstwidth;
    gint dstheight;

    gint srcoffsetx;
    gint srcoffsety;
    gint dstoffsetx;
    gint dstoffsety;

    gint x, y, srcrowstride, dstrowstride, sx, sy, dx, dy;
    guchar *src_pixels, *dst_pixels;

    dstheight = srcheight;
    dstwidth = srcwidth;

    rightx = srcx + srcwidth;
    bottomy = srcy + srcheight;

    if (rightx > gdk_pixbuf_get_width (src))
        rightx = gdk_pixbuf_get_width (src);
    if (bottomy > gdk_pixbuf_get_height (src))
        bottomy = gdk_pixbuf_get_height (src);
    srcwidth = rightx - srcx;
    srcheight = bottomy - srcy;

    rightx = dstx + dstwidth;
    bottomy = dsty + dstheight;
    if (rightx > gdk_pixbuf_get_width (dst))
        rightx = gdk_pixbuf_get_width (dst);
    if (bottomy > gdk_pixbuf_get_height (dst))
        bottomy = gdk_pixbuf_get_height (dst);
    dstwidth = rightx - dstx;
    dstheight = bottomy - dsty;

    if (dstwidth < srcwidth)
        srcwidth = dstwidth;
    if (dstheight < srcheight)
        srcheight = dstheight;

    if (srcx < 0)
        srcoffsetx = 0 - srcx;
    else
        srcoffsetx = 0;

    if (srcy < 0)
        srcoffsety = 0 - srcy;
    else
        srcoffsety = 0;

    if (dstx < 0)
        dstoffsetx = 0 - dstx;
    else
        dstoffsetx = 0;

    if (dsty < 0)
        dstoffsety = 0 - dsty;
    else
        dstoffsety = 0;

    if (dstoffsetx > srcoffsetx)
        srcoffsetx = dstoffsetx;
    if (dstoffsety > srcoffsety)
        srcoffsety = dstoffsety;

    srcrowstride = gdk_pixbuf_get_rowstride (src);
    dstrowstride = gdk_pixbuf_get_rowstride (dst);

    src_pixels = gdk_pixbuf_get_pixels (src);
    dst_pixels = gdk_pixbuf_get_pixels (dst);

    for (y = srcoffsety; y < srcheight; y++)
        for (x = srcoffsetx; x < srcwidth; x++) {
            guint a, c, ad, cd, ar, cr, i;

            sx = x + srcx;
            sy = y + srcy;
            dx = x + dstx;
            dy = y + dsty;
            a = src_pixels[4 * sx + sy * srcrowstride + 3];

            if (a) {
                ad = dst_pixels[4 * dx + dy * dstrowstride + 3];
                ar = a + ad * (255 - a) / 255;
                dst_pixels[4 * dx + dy * dstrowstride + 3] = ar;
                for (i = 0; i < 3; i++) {
                    c = src_pixels[4 * sx + sy * srcrowstride + i];
                    cd = dst_pixels[4 * dx + dy * dstrowstride + i];
                    cr = c + cd * (255 - a) / 255;
                    dst_pixels[4 * dx + dy * dstrowstride + i] = cr;
                }
            }
        }
}
rsvg_alpha_blt (GdkPixbuf * src, gint srcx, gint srcy, gint srcwidth,
                gint srcheight, GdkPixbuf * dst, gint dstx, gint dsty)
{
    gint rightx;
    gint bottomy;
    gint dstwidth;
    gint dstheight;

    gint srcoffsetx;
    gint srcoffsety;
    gint dstoffsetx;
    gint dstoffsety;

    gint x, y, srcrowstride, dstrowstride, sx, sy, dx, dy;
    guchar *src_pixels, *dst_pixels;

    dstheight = srcheight;
    dstwidth = srcwidth;

    rightx = srcx + srcwidth;
    bottomy = srcy + srcheight;

    if (rightx > gdk_pixbuf_get_width (src))
        rightx = gdk_pixbuf_get_width (src);
    if (bottomy > gdk_pixbuf_get_height (src))
        bottomy = gdk_pixbuf_get_height (src);
    srcwidth = rightx - srcx;
    srcheight = bottomy - srcy;

    rightx = dstx + dstwidth;
    bottomy = dsty + dstheight;
    if (rightx > gdk_pixbuf_get_width (dst))
        rightx = gdk_pixbuf_get_width (dst);
    if (bottomy > gdk_pixbuf_get_height (dst))
        bottomy = gdk_pixbuf_get_height (dst);
    dstwidth = rightx - dstx;
    dstheight = bottomy - dsty;

    if (dstwidth < srcwidth)
        srcwidth = dstwidth;
    if (dstheight < srcheight)
        srcheight = dstheight;

    if (srcx < 0)
        srcoffsetx = 0 - srcx;
    else
        srcoffsetx = 0;

    if (srcy < 0)
        srcoffsety = 0 - srcy;
    else
        srcoffsety = 0;

    if (dstx < 0)
        dstoffsetx = 0 - dstx;
    else
        dstoffsetx = 0;

    if (dsty < 0)
        dstoffsety = 0 - dsty;
    else
        dstoffsety = 0;

    if (dstoffsetx > srcoffsetx)
        srcoffsetx = dstoffsetx;
    if (dstoffsety > srcoffsety)
        srcoffsety = dstoffsety;

    srcrowstride = gdk_pixbuf_get_rowstride (src);
    dstrowstride = gdk_pixbuf_get_rowstride (dst);

    src_pixels = gdk_pixbuf_get_pixels (src);
    dst_pixels = gdk_pixbuf_get_pixels (dst);

    for (y = srcoffsety; y < srcheight; y++)
        for (x = srcoffsetx; x < srcwidth; x++) {
            guint a, c, ad, cd, ar, cr, i;

            sx = x + srcx;
            sy = y + srcy;
            dx = x + dstx;
            dy = y + dsty;
            a = src_pixels[4 * sx + sy * srcrowstride + 3];

            if (a) {
                ad = dst_pixels[4 * dx + dy * dstrowstride + 3];
                ar = a + ad * (255 - a) / 255;
                dst_pixels[4 * dx + dy * dstrowstride + 3] = ar;
                for (i = 0; i < 3; i++) {
                    c = src_pixels[4 * sx + sy * srcrowstride + i];
                    cd = dst_pixels[4 * dx + dy * dstrowstride + i];
                    cr = c + cd * (255 - a) / 255;
                    dst_pixels[4 * dx + dy * dstrowstride + i] = cr;
                }
            }
        }
}