mdjvu_image_t mdjvu_split(mdjvu_bitmap_t bitmap, int32 dpi, mdjvu_split_options_t opt) { int32 width = mdjvu_bitmap_get_width(bitmap); int32 height = mdjvu_bitmap_get_height(bitmap); mdjvu_image_t result = mdjvu_image_create(width, height); mdjvu_image_enable_suspiciously_big_flags(result); mdjvu_image_set_resolution(result, dpi); add_to_image(result, bitmap, dpi, opt, 0, 0, /* big: */ 0); return result; }
int read_jpeg(FILE *infile) { struct jpeg_decompress_struct cinfo; struct my_error_mgr jerr; int i,y; JSAMPARRAY buffer; /* Output row buffer */ int row_stride; /* physical row width in output buffer */ cinfo.err = jpeg_std_error(&jerr.pub); jerr.pub.error_exit = my_error_exit; if (setjmp(jerr.setjmp_buffer)) { jpeg_destroy_decompress(&cinfo); fclose(infile); return 0; } jpeg_create_decompress(&cinfo); jpeg_stdio_src(&cinfo, infile); jpeg_read_header(&cinfo, TRUE); jpeg_start_decompress(&cinfo); row_stride = cinfo.output_width * cinfo.output_components; buffer = (*cinfo.mem->alloc_sarray) ((j_common_ptr) &cinfo, JPOOL_IMAGE, row_stride, 1); image_maxx = cinfo.output_width; image_maxy = 0; while (cinfo.output_scanline < cinfo.output_height) { jpeg_read_scanlines(&cinfo, buffer, 1); add_to_image(image_maxy++,buffer[0], image_maxx); } jpeg_finish_decompress(&cinfo); jpeg_destroy_decompress(&cinfo); return 1; }
/* Margins (1 pixel) from each side are required. */ static void process_row(unsigned char **pixels, unsigned char **map, int32 y, int32 w, int32 h, mdjvu_image_t image, int32 shift_x, int32 shift_y, int32 max_shape_width, int32 blit_shift_x, int32 blit_shift_y, int32 dpi, mdjvu_split_options_t opt, int big) { unsigned char *row = pixels[y]; int32 i; for (i = 0; i < w; i++) { if (row[i]) { int32 min_x, max_x, min_y, max_y, shape_width; /* extract the contour */ mdjvu_bitmap_t bitmap; walk_around_a_black_contour(pixels, map, i, y, &min_x, &max_x, &min_y, &max_y); bitmap = interpret_runs(min_x, max_x, min_y, max_y, map, pixels); shape_width = mdjvu_bitmap_get_width(bitmap); assert(shape_width == max_x - min_x + 1); assert(mdjvu_bitmap_get_height(bitmap) == max_y - min_y + 1); if (shape_width <= max_shape_width) { mdjvu_image_add_bitmap(image, bitmap); mdjvu_image_add_blit(image, shift_x + min_x + blit_shift_x, y + shift_y + blit_shift_y, bitmap); mdjvu_image_set_suspiciously_big_flag(image, bitmap, big); } else { /* further split the bitmap */ int32 number_of_chunks = (shape_width + max_shape_width - 1) / max_shape_width; int32 j; int32 shape_height = mdjvu_bitmap_get_height(bitmap); for (j = 0; j < number_of_chunks; j++) { int32 chunk_x = shape_width * j / number_of_chunks; mdjvu_bitmap_t chunk = mdjvu_bitmap_crop(bitmap, chunk_x, 0, shape_width * (j+1) / number_of_chunks - chunk_x, shape_height ); /* After splitting, some white margins may be left, * or the bitmap may lose connectivity. * Apply the algorithm recursively to the chunk. */ add_to_image(image, chunk, dpi, opt, shift_x + chunk_x + min_x + blit_shift_x, y + shift_y + blit_shift_y, /* big: */ 1); mdjvu_bitmap_destroy(chunk); } mdjvu_bitmap_destroy(bitmap); } /* if (shape_width <= max_shape_width) */ } } }