void free_scanlines(TTF_Scan_Line *scanlines, int num_scanlines) { if (!scanlines) { return; } int i; for (i = 0; i < num_scanlines; i++) { free_scanline(&scanlines[i]); } free(scanlines); }
int init_scanline(TTF_Scan_Line *scanline, int base_size) { CHECKPTR(scanline); RETINIT(SUCCESS); scanline->x = malloc(base_size * sizeof(*scanline->x)); CHECKFAIL(scanline->x, warnerr("failed to alloc scanline")); scanline->size_x = base_size; scanline->num_intersections = 0; RETFAIL(free_scanline(scanline)); }
ASImage *GdkPixbuf2ASImage (GdkPixbuf * pixbuf) { ASImage *im = NULL; if (pixbuf) { guchar *pixels; int width = gdk_pixbuf_get_width (pixbuf); int height = gdk_pixbuf_get_height (pixbuf); int n_channels = gdk_pixbuf_get_n_channels (pixbuf); int rowstride = gdk_pixbuf_get_rowstride (pixbuf); int has_alpha = gdk_pixbuf_get_has_alpha (pixbuf) ? 1 : 0; if (gdk_pixbuf_get_colorspace (pixbuf) != GDK_COLORSPACE_RGB || gdk_pixbuf_get_bits_per_sample (pixbuf) != 8 || width <= 0 || height <= 0 || rowstride <= 0 || n_channels != 3 + has_alpha) return NULL; if ((pixels = gdk_pixbuf_get_pixels (pixbuf)) != NULL) { ASScanline buf; int y; LOCAL_DEBUG_OUT ("stored image size %dx%d", width, height); im = create_asimage (width, height, 100); prepare_scanline (im->width, 0, &buf, False); for (y = 0; y < height; ++y) { raw2scanline (pixels + y * rowstride, &buf, NULL, width, gdk_pixbuf_get_colorspace (pixbuf) != GDK_COLORSPACE_RGB, has_alpha); asimage_add_line (im, IC_RED, buf.red, y); asimage_add_line (im, IC_GREEN, buf.green, y); asimage_add_line (im, IC_BLUE, buf.blue, y); if (has_alpha) asimage_add_line (im, IC_ALPHA, buf.alpha, y); } free_scanline (&buf, True); } } return im; }
XImage* asimage2alpha_ximage (ASVisual *asv, ASImage *im, Bool bitmap ) { XImage *xim = NULL; int i; ASScanline xim_buf; ASImageOutput *imout ; ASFlagType flag = bitmap?0:ASIM_XIMAGE_8BIT_MASK; if (im == NULL) return xim; if( im->alt.mask_ximage ) if( (im->flags & ASIM_XIMAGE_8BIT_MASK )^flag) { #ifndef X_DISPLAY_MISSING XDestroyImage( im->alt.mask_ximage ); #endif im->alt.mask_ximage = NULL ; } clear_flags( im->flags, ASIM_XIMAGE_8BIT_MASK ); set_flags( im->flags, flag ); if( (imout = start_image_output( asv, im, ASA_MaskXImage, 0, ASIMAGE_QUALITY_POOR )) == NULL ) return xim; xim = im->alt.mask_ximage ; prepare_scanline( xim->width, 0, &xim_buf, asv->BGR_mode ); xim_buf.flags = SCL_DO_ALPHA ; for (i = 0; i < (int)im->height; i++) { int count = asimage_decode_line (im, IC_ALPHA, xim_buf.alpha, i, 0, xim_buf.width); if( count < (int)xim_buf.width ) xim_set_component( xim_buf.alpha, ARGB32_ALPHA8(im->back_color), count, xim_buf.width ); imout->output_image_scanline( imout, &xim_buf, 1 ); } free_scanline(&xim_buf, True); stop_image_output(&imout); return xim; }
ASImage * picture_ximage2asimage (ASVisual *asv, XImage *xim, XImage *alpha_xim, unsigned int compression) { ASImage *im = NULL; unsigned char *xim_line; int i, height, width, bpl; ASScanline xim_buf; #ifdef LOCAL_DEBUG CARD32 *tmp ; #endif #if 0 struct timeval stv; gettimeofday (&stv,NULL); #define PRINT_BACKGROUND_OP_TIME do{ struct timeval tv;gettimeofday (&tv,NULL); tv.tv_sec-= stv.tv_sec;\ fprintf (stderr,__FILE__ "%d: elapsed %ld usec\n",__LINE__,\ tv.tv_sec*1000000+tv.tv_usec-stv.tv_usec );}while(0) #else #define PRINT_BACKGROUND_OP_TIME do{}while(0) #endif if( xim && alpha_xim ) if( xim->width != alpha_xim->width || xim->height != alpha_xim->height ) return NULL ; if( xim == NULL && alpha_xim == NULL ) return NULL ; width = xim?xim->width:alpha_xim->width; height = xim?xim->height:alpha_xim->height; im = create_asimage( width, height, compression); prepare_scanline( width, 0, &xim_buf, asv->BGR_mode ); #ifdef LOCAL_DEBUG tmp = safemalloc( width * sizeof(CARD32)); #endif PRINT_BACKGROUND_OP_TIME; if( xim ) { bpl = xim->bytes_per_line; xim_line = (unsigned char *)xim->data; for (i = 0; i < height; i++) { #if 0 /* unfortunately this method does not seem to yield any better results performancewise: */ if (asv->true_depth == 32 || asv->true_depth == 24) { if( asv->msb_first ) { }else asimage_add_line_bgra (im, xim_line, i); }else #endif if( xim->depth == (int)asv->true_depth ) { GET_SCANLINE(asv,xim,&xim_buf,i,xim_line); asimage_add_line (im, IC_RED, xim_buf.red, i); asimage_add_line (im, IC_GREEN, xim_buf.green, i); asimage_add_line (im, IC_BLUE, xim_buf.blue, i); if( xim->depth == 32 && alpha_xim == NULL ) asimage_add_line (im, IC_ALPHA, xim_buf.alpha, i); #ifdef LOCAL_DEBUG if( !asimage_compare_line( im, IC_RED, xim_buf.red, tmp, i, True ) ) exit(0); if( !asimage_compare_line( im, IC_GREEN, xim_buf.green, tmp, i, True ) ) exit(0); if( !asimage_compare_line( im, IC_BLUE, xim_buf.blue, tmp, i, True ) ) exit(0); #endif }else if( xim->depth == 8 ) { register int x = width; while(--x >= 0 ) xim_buf.blue[x] = (CARD32)(xim_line[x]); asimage_add_line (im, IC_RED, xim_buf.red, i); asimage_add_line (im, IC_GREEN, xim_buf.red, i); asimage_add_line (im, IC_BLUE, xim_buf.red, i); }else if( xim->depth == 1 ) { register int x = width; while(--x >= 0 ) { #ifndef X_DISPLAY_MISSING xim_buf.red[x] = (XGetPixel(xim, x, i) == 0)?0x00:0xFF; #else xim_buf.red[x] = 0xFF ; #endif } asimage_add_line (im, IC_RED, xim_buf.red, i); asimage_add_line (im, IC_GREEN, xim_buf.red, i); asimage_add_line (im, IC_BLUE, xim_buf.red, i); } xim_line += bpl; } } PRINT_BACKGROUND_OP_TIME; if( alpha_xim ) { CARD32 *dst = xim_buf.alpha ; bpl = alpha_xim->bytes_per_line; xim_line = (unsigned char *)alpha_xim->data; for (i = 0; i < height; i++) { register int x = width; if( alpha_xim->depth == 8 ) { while(--x >= 0 ) dst[x] = (CARD32)(xim_line[x]); }else { while(--x >= 0 ) #ifndef X_DISPLAY_MISSING dst[x] = (XGetPixel(alpha_xim, x, i) == 0)?0x00:0xFF; #else dst[x] = 0xFF ; #endif } asimage_add_line (im, IC_ALPHA, xim_buf.alpha, i); #ifdef LOCAL_DEBUG if( !asimage_compare_line( im, IC_ALPHA, xim_buf.alpha, tmp, i, True ) ) exit(0); #endif xim_line += bpl; } } free_scanline(&xim_buf, True); PRINT_BACKGROUND_OP_TIME; return im; }
static XImage* asimage2ximage_ext (ASVisual *asv, ASImage *im, Bool scratch) { XImage *xim = NULL; int i; ASImageOutput *imout ; ASImageDecoder *imdec; /*#ifdef DO_CLOCKING clock_t started = clock (); #endif*/ if (im == NULL) { LOCAL_DEBUG_OUT( "Attempt to convert NULL ASImage into XImage.", "" ); return xim; } if( (imout = start_image_output( asv, im, scratch?ASA_ScratchXImage:ASA_XImage, 0, ASIMAGE_QUALITY_DEFAULT )) == NULL ) { LOCAL_DEBUG_OUT( "Failed to start ASImageOutput for ASImage %p and ASVisual %p", im, asv ); return xim; } xim = im->alt.ximage ; /* no data in ximage yet */ set_flags( im->flags, ASIM_XIMAGE_NOT_USEFUL); /*#ifdef DO_CLOCKING started = clock (); #endif*/ #if 1 if ((imdec = start_image_decoding( asv, im, (xim->depth >= 24)?SCL_DO_ALL:SCL_DO_COLOR, 0, 0, im->width, im->height, NULL)) != NULL ) { for (i = 0; i < (int)im->height; i++) { imdec->decode_image_scanline( imdec ); imout->output_image_scanline( imout, &(imdec->buffer), 1); } stop_image_decoding( &imdec ); } #else { ASScanline xim_buf; prepare_scanline( im->width, 0, &xim_buf, asv->BGR_mode ); set_flags( xim_buf.flags, SCL_DO_ALL ); for (i = 0; i < (int)im->height; i++) { int count ; if( (count = asimage_decode_line (im, IC_RED, xim_buf.red, i, 0, xim_buf.width)) < (int)xim_buf.width ) xim_set_component( xim_buf.red, ARGB32_RED8(im->back_color), count, xim_buf.width ); if( (count = asimage_decode_line (im, IC_GREEN, xim_buf.green, i, 0, xim_buf.width))< (int)xim_buf.width ) xim_set_component( xim_buf.green, ARGB32_GREEN8(im->back_color), count, xim_buf.width ); if( (count = asimage_decode_line (im, IC_BLUE, xim_buf.blue, i, 0, xim_buf.width)) < (int)xim_buf.width ) xim_set_component( xim_buf.blue, ARGB32_BLUE8(im->back_color), count, xim_buf.width ); if( xim->depth == 32 ) if( (count = asimage_decode_line (im, IC_ALPHA, xim_buf.alpha, i, 0, xim_buf.width)) < (int)xim_buf.width ) xim_set_component( xim_buf.alpha, ARGB32_ALPHA8(im->back_color), count, xim_buf.width ); imout->output_image_scanline( imout, &xim_buf, 1 ); } free_scanline(&xim_buf, True); } #endif /*#ifdef DO_CLOCKING fprintf (stderr, "asimage->ximage time (clocks): %lu\n", clock () - started); #endif*/ stop_image_output(&imout); clear_flags( im->flags, ASIM_XIMAGE_NOT_USEFUL); return xim; }
Bool subimage2ximage (ASVisual *asv, ASImage *im, int x, int y, XImage* xim) { int i, max_i; ASScanline xim_buf; ASImageOutput *imout ; /*#ifdef DO_CLOCKING clock_t started = clock (); #endif*/ int width, height ; ASImage *scratch_im ; if (im == NULL) { LOCAL_DEBUG_OUT( "Attempt to convert NULL ASImage into XImage.", "" ); return False; } if( x >= (int)im->width || y >= (int)im->height ) return False; width = xim->width ; if( width > (int)im->width - x) width = (int)im->width - x; width = ( x > (int)im->width - width )?im->width - width:im->width - x ; height = xim->height ; if( height > (int)im->height - y ) height = im->height - y ; scratch_im = create_asimage( width, height, 0); scratch_im->alt.ximage = xim ; LOCAL_DEBUG_OUT( "target width = %d, height = %d", width, height ); if( (imout = start_image_output( asv, scratch_im, ASA_ScratchXImage, 0, ASIMAGE_QUALITY_DEFAULT )) == NULL ) { LOCAL_DEBUG_OUT( "Failed to start ASImageOutput for ASImage %p and ASVisual %p", im, asv ); return False; } prepare_scanline( width, 0, &xim_buf, asv->BGR_mode ); /*#ifdef DO_CLOCKING started = clock (); #endif*/ set_flags( xim_buf.flags, SCL_DO_ALL ); max_i = y + height ; for (i = y; i < max_i; i++) { int count ; if( (count = asimage_decode_line (im, IC_RED, xim_buf.red, i, x, xim_buf.width)) < (int)xim_buf.width ) xim_set_component( xim_buf.red, ARGB32_RED8(im->back_color), count, xim_buf.width ); if( (count = asimage_decode_line (im, IC_GREEN, xim_buf.green, i, x, xim_buf.width))< (int)xim_buf.width ) xim_set_component( xim_buf.green, ARGB32_GREEN8(im->back_color), count, xim_buf.width ); if( (count = asimage_decode_line (im, IC_BLUE, xim_buf.blue, i, x, xim_buf.width)) < (int)xim_buf.width ) xim_set_component( xim_buf.blue, ARGB32_BLUE8(im->back_color), count, xim_buf.width ); if( xim->depth == 32 ) if( (count = asimage_decode_line (im, IC_ALPHA, xim_buf.alpha, i, x, xim_buf.width)) < (int)xim_buf.width ) xim_set_component( xim_buf.alpha, ARGB32_ALPHA8(im->back_color), count, xim_buf.width ); imout->output_image_scanline( imout, &xim_buf, 1 ); /* LOCAL_DEBUG_OUT( "line %d, count = %d", i, count ); */ } /*#ifdef DO_CLOCKING fprintf (stderr, "asimage->ximage time (clocks): %lu\n", clock () - started); #endif*/ free_scanline(&xim_buf, True); stop_image_output(&imout); scratch_im->alt.ximage = NULL ; destroy_asimage( &scratch_im ); return True; }