JobFileSvg::JobFileSvg(const char* filename, double scale): JobFile(filename,scale), m_pCairo(NULL), m_cairoMutex(), m_pSurface(NULL), m_pRsvgHandle(NULL) { m_cairoMutex.lock(); float dpi=254.0; GError *error = NULL; RsvgDimensionData dimensions; g_type_init(); rsvg_set_default_dpi_x_y (dpi,dpi);//no reaction? m_pRsvgHandle = rsvg_handle_new_from_file (filename, &error); if( m_pRsvgHandle != NULL ){ rsvg_handle_get_dimensions (m_pRsvgHandle, &dimensions); //m_position.x = (1024-dimensions.width)/2; //m_position.y = (768-dimensions.height)/2; m_pSurface = (cairo_surface_t *)cairo_image_surface_create( CAIRO_FORMAT_ARGB32, m_scale*dimensions.width, m_scale*dimensions.height //1024, 768 ); m_pCairo = cairo_create(m_pSurface); cairo_scale( m_pCairo, m_scale, m_scale); m_size.width = m_scale*dimensions.width; m_size.height = m_scale*dimensions.height; m_position.x = (1024- m_size.width)/2; m_position.y = (768- m_size.height)/2; /* Check existens of layers "#layer0","#layer1",... * to get number of layers and the guarantee that * no inner layer is missed. * */ m_nmbrOfLayers = 0; while( true ){ std::ostringstream layerid; layerid << "#layer" << m_nmbrOfLayers; if( !rsvg_handle_has_sub( m_pRsvgHandle, layerid.str().c_str() )){ break; } m_nmbrOfLayers++; //std::cout << "Found layer " << layerid.str() << std::endl; } std::cout << "Found layers: " << m_nmbrOfLayers << std::endl; m_maxLayer = m_nmbrOfLayers-1; m_cairoMutex.unlock(); }else{ std::cout << "Error while loading file '" << filename << "'." << std::endl; m_cairoMutex.unlock(); throw JOB_LOAD_EXCEPTION; } }
JNIEXPORT void JNICALL Java_org_gnome_rsvg_RsvgMain_rsvg_1set_1default_1dpi_1x_1y ( JNIEnv* env, jclass cls, jdouble _dpiX, jdouble _dpiY ) { double dpiX; double dpiY; // convert parameter dpiX dpiX = (double) _dpiX; // convert parameter dpiY dpiY = (double) _dpiY; // call function rsvg_set_default_dpi_x_y(dpiX, dpiY); // cleanup parameter dpiX // cleanup parameter dpiY }
static VALUE rg_s_set_default_dpi_x_y(VALUE self, VALUE dpi_x, VALUE dpi_y) { #ifdef HAVE_RSVG_SET_DEFAULT_DPI_X_Y rsvg_set_default_dpi_x_y(NUM2DBL(dpi_x), NUM2DBL(dpi_y)); #else rb_warning("rsvg_set_default_dpi_x_y isn't supported in your librsvg"); #endif return self; }
int main(int argc, char *argv[]) { FILE *fp; RsvgHandle *rsvg; cairo_device_t *dev = NULL; cairo_surface_t *surface = NULL; cairo_t *cr = NULL; RsvgDimensionData dimensions; if (argc < 3) { usage(); return 0; } fp = fopen(argv[1], "r"); if (fp == NULL) { printf("could not open '%s' for read\n", argv[1]); return 1; } fclose(fp); fp = fopen(argv[2], "w"); if (fp == NULL) { printf("could not open '%s' for write\n", argv[2]); return 1; } dev = cairo_xml_create_for_stream((cairo_write_func_t)write_func, fp); rsvg_set_default_dpi_x_y(-1, -1); rsvg = rsvg_handle_new_from_file(argv[1], NULL); rsvg_handle_get_dimensions(rsvg, &dimensions); fprintf(fp, "<image width='%d' height='%d'>\n", dimensions.width, dimensions.height); surface = cairo_xml_surface_create(dev, CAIRO_CONTENT_COLOR_ALPHA, dimensions.width, dimensions.height); cr = cairo_create(surface); rsvg_handle_render_cairo(rsvg, cr); rsvg_handle_close(rsvg, NULL); cairo_destroy(cr); cairo_surface_destroy(surface); fprintf(fp, "</image>\n"); fclose(fp); return 0; }
QImage QImageProvider::requestImage(const QString &id, QSize *size, const QSize &requestedSize) { Q_UNUSED(size); QUrl dir(id); RsvgDimensionData dimensions; int width = 1; int height = 1; /* Set the locale so that UTF-8 filenames work */ setlocale(LC_ALL, ""); double zoom = 1.0; rsvg_set_default_dpi_x_y (-1, -1); RsvgHandle *rsvg = rsvg_handle_new_from_file(dir.toLocalFile().toStdString().c_str(),NULL); if(rsvg!=NULL) { rsvg_handle_get_dimensions(rsvg, &dimensions); QRect desktop = QRect(0,0,requestedSize.width(),requestedSize.height()); if(dimensions.width!=dimensions.height) { width = (dimensions.width<dimensions.height) ? (double)desktop.height() / (double)dimensions.height * dimensions.width : desktop.width() ; height = (dimensions.height<dimensions.width) ? (double)desktop.width() / (double)dimensions.width * dimensions.height : desktop.height() ; zoom = (width > height) ? (double)width / (double)dimensions.width : (double)height / (double)dimensions.height; } else if(desktop.width() > desktop.height()) { width = desktop.height(); height = desktop.height(); zoom = (double)height / (double)dimensions.height; } else { width = desktop.width(); height = desktop.width(); zoom = (double)width / (double)dimensions.width; } qDebug() << width << "x" << height << ";" << dimensions.width << "x" << dimensions.height << ";" << zoom; } cairo_surface_t *surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, width, height); cairo_t *cr = cairo_create(surface); cairo_scale(cr, zoom, zoom); rsvg_handle_render_cairo(rsvg, cr); QImage *source = new QImage( cairo_image_surface_get_data(surface), cairo_image_surface_get_width(surface), cairo_image_surface_get_height(surface), cairo_image_surface_get_stride(surface), QImage::Format_ARGB32_Premultiplied ); QImage image(cairo_image_surface_get_width(surface), cairo_image_surface_get_height(surface), QImage::Format_ARGB32_Premultiplied); image.fill(qRgba(0, 0, 0, 0)); QPainter painter(&image); painter.drawImage(QPoint(0, 0), *source); delete source; g_object_unref(rsvg); cairo_destroy(cr); cairo_surface_destroy(surface); return image; }
/** * fo_doc_cairo_place_image: * @fo_doc: * @fo_image: * @x: * @y: * @xscale: * @yscale: * * **/ static void fo_doc_cairo_place_image (FoDoc *fo_doc, FoImage *fo_image, gdouble x G_GNUC_UNUSED, gdouble y G_GNUC_UNUSED, gdouble xscale G_GNUC_UNUSED, gdouble yscale G_GNUC_UNUSED) { GdkPixbuf *pixbuf = g_object_ref (fo_pixbuf_get_pixbuf (fo_image)); gint width = gdk_pixbuf_get_width (pixbuf); gint height = gdk_pixbuf_get_height (pixbuf); guchar *gdk_pixels = gdk_pixbuf_get_pixels (pixbuf); int gdk_rowstride = gdk_pixbuf_get_rowstride (pixbuf); int n_channels = gdk_pixbuf_get_n_channels (pixbuf); guchar *cairo_pixels; cairo_format_t format; cairo_surface_t *surface; static const cairo_user_data_key_t key; int j; cairo_translate (FO_DOC_CAIRO (fo_doc)->cr, 0, FO_DOC_CAIRO(fo_doc)->page_height); cairo_save (FO_DOC_CAIRO(fo_doc)->cr); cairo_scale (FO_DOC_CAIRO (fo_doc)->cr, xscale * 72.0 / PIXELS_PER_INCH, yscale * 72.0 / PIXELS_PER_INCH); #if HAVE_LIBRSVG if (g_str_has_suffix( fo_image_get_uri(fo_image), ".svg")) { RsvgHandle *rsvg; GError *error = NULL; g_log (G_LOG_DOMAIN, G_LOG_LEVEL_DEBUG, "rendering %s as SVG\n", fo_image_get_uri(fo_image)); rsvg_init(); rsvg_set_default_dpi_x_y (PIXELS_PER_INCH, PIXELS_PER_INCH); rsvg = rsvg_handle_new_from_file (fo_image_get_uri(fo_image), &error); rsvg_handle_render_cairo (rsvg, FO_DOC_CAIRO(fo_doc)->cr); rsvg_term(); cairo_restore (FO_DOC_CAIRO(fo_doc)->cr); if (error) { g_log (G_LOG_DOMAIN, G_LOG_LEVEL_ERROR, error->message); g_error_free (error); } return; } #endif if (n_channels == 3) { format = CAIRO_FORMAT_RGB24; } else { format = CAIRO_FORMAT_ARGB32; } cairo_pixels = g_malloc (4 * width * height); surface = cairo_image_surface_create_for_data ((unsigned char *)cairo_pixels, format, width, height, 4 * width); cairo_surface_set_user_data (surface, &key, cairo_pixels, (cairo_destroy_func_t)g_free); for (j = height; j; j--) { guchar *p = gdk_pixels; guchar *q = cairo_pixels; if (n_channels == 3) { guchar *end = p + 3 * width; while (p < end) { #if G_BYTE_ORDER == G_LITTLE_ENDIAN q[0] = p[2]; q[1] = p[1]; q[2] = p[0]; #else q[1] = p[0]; q[2] = p[1]; q[3] = p[2]; #endif p += 3; q += 4; } } else { guchar *end = p + 4 * width; guint t1,t2,t3; #define MULT(d,c,a,t) G_STMT_START { t = c * a + 0x7f; d = ((t >> 8) + t) >> 8; } G_STMT_END while (p < end) { #if G_BYTE_ORDER == G_LITTLE_ENDIAN MULT(q[0], p[2], p[3], t1); MULT(q[1], p[1], p[3], t2); MULT(q[2], p[0], p[3], t3); q[3] = p[3]; #else q[0] = p[3]; MULT(q[1], p[0], p[3], t1); MULT(q[2], p[1], p[3], t2); MULT(q[3], p[2], p[3], t3); #endif p += 4; q += 4; } #undef MULT } gdk_pixels += gdk_rowstride; cairo_pixels += 4 * width; } cairo_surface_set_fallback_resolution (surface, PIXELS_PER_INCH, PIXELS_PER_INCH); cairo_set_source_surface (FO_DOC_CAIRO (fo_doc)->cr, surface, 0, 0); cairo_pattern_t *pattern = cairo_get_source (FO_DOC_CAIRO (fo_doc)->cr); cairo_pattern_set_extend (pattern, CAIRO_EXTEND_NONE); cairo_paint (FO_DOC_CAIRO (fo_doc)->cr); cairo_surface_destroy (surface); g_object_unref (pixbuf); cairo_restore (FO_DOC_CAIRO(fo_doc)->cr); }
int main (int argc, char **argv) { GError *err = NULL; GOptionContext *g_option_context; double x_zoom = 1.0; double y_zoom = 1.0; double dpi_x = -1.0; double dpi_y = -1.0; int width = -1; int height = -1; int bVersion = 0; char *bg_color = NULL; char *base_uri = NULL; int bKeepAspect = 0; char *id = NULL; int xid = -1; int from_stdin = 0; ViewerCbInfo info; struct RsvgSizeCallbackData size_data; char **args = NULL; gint n_args = 0; GOptionEntry options_table[] = { #ifdef ENABLE_XEMBED {"xid", 'i', 0, G_OPTION_ARG_INT, &xid, N_("XWindow ID [for X11 embedding]"), N_("<int>")}, #endif {"stdin", 's', 0, G_OPTION_ARG_NONE, &from_stdin, N_("Read from stdin instead of a file"), NULL}, {"dpi-x", 'd', 0, G_OPTION_ARG_DOUBLE, &dpi_x, N_("Set the # of Pixels Per Inch"), N_("<float>")}, {"dpi-y", 'p', 0, G_OPTION_ARG_DOUBLE, &dpi_y, N_("Set the # of Pixels Per Inch"), N_("<float>")}, {"x-zoom", 'x', 0, G_OPTION_ARG_DOUBLE, &x_zoom, N_("Set the x zoom factor"), N_("<float>")}, {"y-zoom", 'y', 0, G_OPTION_ARG_DOUBLE, &y_zoom, N_("Set the y zoom factor"), N_("<float>")}, {"width", 'w', 0, G_OPTION_ARG_INT, &width, N_("Set the image's width"), N_("<int>")}, {"height", 'h', 0, G_OPTION_ARG_INT, &height, N_("Set the image's height"), N_("<int>")}, {"bg-color", 'b', 0, G_OPTION_ARG_STRING, &bg_color, N_("Set the image background color (default: transparent)"), N_("<string>")}, {"base-uri", 'u', 0, G_OPTION_ARG_STRING, &base_uri, N_("Set the base URI (default: none)"), N_("<string>")}, {"id", 0, 0, G_OPTION_ARG_STRING, &id, N_("Only show one node (default: all)"), N_("<string>")}, {"keep-aspect", 'k', 0, G_OPTION_ARG_NONE, &bKeepAspect, N_("Preserve the image's aspect ratio"), NULL}, {"version", 'v', 0, G_OPTION_ARG_NONE, &bVersion, N_("Show version information"), NULL}, {G_OPTION_REMAINING, 0, 0, G_OPTION_ARG_FILENAME_ARRAY, &args, NULL, N_("[FILE...]")}, {NULL} }; g_thread_init (NULL); info.pixbuf = NULL; info.svg_bytes = NULL; info.window = NULL; info.popup_menu = NULL; g_option_context = g_option_context_new ("- SVG Viewer"); g_option_context_add_main_entries (g_option_context, options_table, NULL); g_option_context_add_group (g_option_context, gtk_get_option_group (TRUE)); g_option_context_set_help_enabled (g_option_context, TRUE); if (!g_option_context_parse (g_option_context, &argc, &argv, NULL)) { exit (1); } g_option_context_free (g_option_context); if (bVersion != 0) { g_message (_("rsvg-view version %s\n"), VERSION); return 0; } if (args) { while (args[n_args] != NULL) n_args++; } if ((!from_stdin) && (n_args != 1)) { g_print (_("No files specified, and not using --stdin\n")); return 1; } /* initialize gtk+ and rsvg */ rsvg_init (); rsvg_set_default_dpi_x_y (dpi_x, dpi_y); /* if both are unspecified, assume user wants to zoom the pixbuf in at least 1 dimension */ if (width == -1 && height == -1) { size_data.type = RSVG_SIZE_ZOOM; size_data.x_zoom = x_zoom; size_data.y_zoom = y_zoom; } /* if both are unspecified, assume user wants to resize pixbuf in at least 1 dimension */ else if (x_zoom == 1.0 && y_zoom == 1.0) { size_data.type = RSVG_SIZE_WH; size_data.width = width; size_data.height = height; } /* assume the user wants to zoom the pixbuf, but cap the maximum size */ else { size_data.type = RSVG_SIZE_ZOOM_MAX; size_data.x_zoom = x_zoom; size_data.y_zoom = y_zoom; size_data.width = width; size_data.height = height; } size_data.keep_aspect_ratio = bKeepAspect; if (!from_stdin) { if (base_uri == NULL) base_uri = (char *) args[0]; info.svg_bytes = _rsvg_acquire_xlink_href_resource (args[0], base_uri, NULL); } else { info.svg_bytes = g_byte_array_new (); for (;;) { unsigned char buf[1024 * 8]; size_t nread = fread (buf, 1, sizeof (buf), stdin); if (nread > 0) g_byte_array_append (info.svg_bytes, buf, nread); if (nread < sizeof (buf)) { if (ferror (stdin)) { g_print (_("Error reading\n")); g_byte_array_free (info.svg_bytes, TRUE); fclose (stdin); return 1; } else if (feof (stdin)) break; } } fclose (stdin); } if (!info.svg_bytes || !info.svg_bytes->len) { g_print (_("Couldn't open %s\n"), args[0]); return 1; } info.base_uri = base_uri; info.id = id; info.pixbuf = pixbuf_from_data_with_size_data (info.svg_bytes->data, info.svg_bytes->len, &size_data, base_uri, id, &err); if (!info.pixbuf) { g_print (_("Error displaying image")); if (err) { g_print (": %s", err->message); g_error_free (err); } g_print ("\n"); return 1; } info.accel_group = gtk_accel_group_new (); view_pixbuf (&info, xid, bg_color); /* run the gtk+ main loop */ gtk_main (); g_object_unref (G_OBJECT (info.pixbuf)); g_byte_array_free (info.svg_bytes, TRUE); rsvg_term (); return 0; }