]> granicus.if.org Git - graphviz/commitdiff
Merge formatter and device plugin apis.
authorellson <devnull@localhost>
Wed, 29 Aug 2007 19:39:49 +0000 (19:39 +0000)
committerellson <devnull@localhost>
Wed, 29 Aug 2007 19:39:49 +0000 (19:39 +0000)
Selecting device by format, e.g. -Tsvgz, or -Tpng:cairo:gd
Automatically load correct renderer, e.g. cairo, gd, core_dot
Improve plugin listings.
Accurately reflecte available formats.

13 files changed:
lib/gvc/gvplugin.c
lib/gvc/gvplugin.h
lib/gvc/gvplugin_device.h
lib/gvc/gvrender.c
plugin/core/gvplugin_core.c
plugin/core/gvrender_core_dot.c
plugin/core/gvrender_core_fig.c
plugin/core/gvrender_core_map.c
plugin/core/gvrender_core_ps.c
plugin/core/gvrender_core_svg.c
plugin/core/gvrender_core_vml.c
plugin/devil/Makefile.am
plugin/devil/gvdevice_devil.c [new file with mode: 0644]

index 0ba4f413267022fa3e057184362ea9cebb266143..76817e27b26eed6368ac06352d0c57372358a6d4 100644 (file)
@@ -218,46 +218,69 @@ gvplugin_library_t *gvplugin_library_load(GVC_t *gvc, char *path)
 
 
 /* load a plugin of type=str
-       where str can optionally contain a ":packagename" modifier */
+       the str can optionally contain one or more ":dependencies" 
+
+       examples:
+               png
+               png:cairo
+        fully qualified:
+               png:cairo:cairo
+               png:cairo:gd
+               png:gd:gd
+      
+*/
 gvplugin_available_t *gvplugin_load(GVC_t * gvc, api_t api, char *str)
 {
     gvplugin_available_t **pnext, *rv;
     gvplugin_library_t *library;
     gvplugin_api_t *apis;
     gvplugin_installed_t *types;
-    char *s, *p;
+#define TYPBUFSIZ 64
+    char reqtyp[TYPBUFSIZ], typ[TYPBUFSIZ];
+    char *reqdep, *dep = NULL, *reqpkg;
     int i;
-
+    api_t apidep;
 
     /* check for valid apis[] index */
     if (api < 0)
        return NULL;
 
-    /* does str have a :packagename modifier? */
-    s = strdup(str);
-    p = strchr(s, ':');
-    if (p)
-       *p++ = '\0';
+    if (api == API_device) /* api dependencies - FIXME - find better way to code these *s */
 
-    /* point to the beginning of the linked list of plugins for this api */
-    pnext = &(gvc->apis[api]);
+        apidep = API_render;   
+    else
+       apidep = api;
 
-    while (*pnext) {
-       if (strcmp(s, (*pnext)->typestr) == 0) {
-           if (p) {
-               if (strcmp(p, (*pnext)->packagename) == 0)
-                   break;
-           }
-           else
-               break;
-       }
-       pnext = &((*pnext)->next);
+    strncpy(reqtyp, str, TYPBUFSIZ-1);
+    reqdep = strchr(reqtyp, ':');
+    if (reqdep) {
+       *reqdep++ = '\0';
+        reqpkg = strchr(reqdep, ':');
+        if (reqpkg)
+            *reqpkg++ = '\0';
+    }
+    else
+       reqpkg = NULL;
+
+    /* iterate the linked list of plugins for this api */
+    for (pnext = &(gvc->apis[api]); *pnext; pnext = &((*pnext)->next)) {
+        strncpy(typ, (*pnext)->typestr, TYPBUFSIZ-1);
+       dep = strchr(typ, ':');
+       if (dep) 
+           *dep++ = '\0';
+       if (! typ || ! reqtyp || strcmp(typ, reqtyp)) 
+           continue;  /* types empty or mismatched */
+       if (dep && reqdep && strcmp(dep, reqdep))
+           continue;  /* dependencies not empty, but mismatched */
+       if (! reqpkg)
+           break; /* found with no packagename constraints */
+       if (strcmp(reqpkg, (*pnext)->packagename) == 0)
+           break;  /* found with required matching packagname */
     }
 
     rv = *pnext;
-    if ((*pnext) && (*pnext)->typeptr == NULL) {
-        rv = NULL;
-       library = gvplugin_library_load(gvc, (*pnext)->path);
+    if (rv && rv->typeptr == NULL) {
+       library = gvplugin_library_load(gvc, rv->path);
        if (library) {
 
             /* Now activate the library with real type ptrs */
@@ -269,40 +292,32 @@ gvplugin_available_t *gvplugin_load(GVC_t * gvc, api_t api, char *str)
                                apis->api,
                                types[i].type,
                                library->packagename,
-                               (*pnext)->path,
+                               rv->path,
                                &types[i]);
                }
             }
-           
-           /* Now search again for the specific plugin type */
-           pnext = &(gvc->apis[api]);
-           while (*pnext) {
-               if (strcmp(s, (*pnext)->typestr) == 0) {
-                   if (p) {
-                       if (strcmp(p, (*pnext)->packagename) == 0)
-                           break;
-                   }
-                   else
-                       break;
-               }
-               pnext = &((*pnext)->next);
-           }
-           rv = *pnext;
+           if (gvc->common.verbose >= 1)
+               fprintf(stderr, "Activated plugin library: %s\n",
+                       rv->path ? rv->path : "<builtin>");
         }
     }
-    free(s);
 
-    /* one last check for succesfull load */
-    if ((*pnext) && (*pnext)->typeptr == NULL)
+    if (dep && (apidep != api)) /* load dependency if needed */
+       if (! (gvplugin_load(gvc, apidep, dep)))
+           rv = NULL;
+
+    /* one last check for successfull load */
+    if (rv && rv->typeptr == NULL)
        rv = NULL;
-    gvc->api[api] = rv;
 
     if (rv && gvc->common.verbose >= 1)
-       fprintf(stderr, "Using plugin: %s %s %s\n",
+       fprintf(stderr, "Using %s: %s:%s\n",
                api_names[api],
                rv->typestr,
-               rv->path ? rv->path : "<builtin>" );
+               rv->packagename
+               );
 
+    gvc->api[api] = rv;
     return rv;
 }
 
@@ -332,9 +347,9 @@ static const char *append_buf(char sep, char *str, boolean new)
 /* assemble a string list of available plugins */
 const char *gvplugin_list(GVC_t * gvc, api_t api, char *str)
 {
-    gvplugin_available_t **pnext, **plugin, **pprev;
+    gvplugin_available_t **pnext, **plugin;
     const char *buf = NULL;
-    char *s, *p, *typestr_last;
+    char *s, *p, *q, *typestr_last;
     boolean new = TRUE;
 
     /* check for valid apis[] index */
@@ -352,40 +367,41 @@ const char *gvplugin_list(GVC_t * gvc, api_t api, char *str)
 
     if (p) {   /* if str contains a ':', and if we find a match for the type,
                   then just list the alternative paths for the plugin */
-       pnext = plugin;
-       pprev = NULL;
-       while (*pnext) {
-           /* list only the matching type, and only once*/
-           if (strcasecmp(s, (*pnext)->typestr) == 0
-               && !(pprev
-                   && strcasecmp(s, (*pprev)->typestr) == 0
-                   && strcasecmp((*pprev)->packagename, (*pnext)->packagename) == 0)) {
+       for (pnext = plugin; *pnext; pnext = &((*pnext)->next)) {
+            q = strdup((*pnext)->typestr);
+           if ((p = strchr(q, ':')))
+                *p++ = '\0';
+           /* list only the matching type */
+           if (strcasecmp(s, q) == 0) {
                /* list each member of the matching type as "type:path" */
                append_buf(' ', (*pnext)->typestr, new);
                buf = append_buf(':', (*pnext)->packagename, FALSE);
                new = FALSE;
            }
-           pprev = pnext;
-           pnext = &((*pnext)->next);
+           free(q);
        }
     }
+    free(s);
     if (new) {                 /* if the type was not found, or if str without ':',
                                   then just list available types */
-       pnext = plugin;
        typestr_last = NULL;
-       while (*pnext) {
+       for (pnext = plugin; *pnext; pnext = &((*pnext)->next)) {
            /* list only one instance of type */
-           if (!typestr_last
-               || strcasecmp(typestr_last, (*pnext)->typestr) != 0) {
+           q = strdup((*pnext)->typestr);
+           if ((p = strchr(q, ':')))
+               *p++ = '\0';
+           if (!typestr_last || strcasecmp(typestr_last, q) != 0) {
                /* list it as "type"  i.e. w/o ":path" */
-               buf = append_buf(' ', (*pnext)->typestr, new);
+               buf = append_buf(' ', q, new);
                new = FALSE;
            }
-           typestr_last = (*pnext)->typestr;
-           pnext = &((*pnext)->next);
+           if(!typestr_last)
+               free(typestr_last);
+           typestr_last = q;
        }
+       if(!typestr_last)
+           free(typestr_last);
     }
-    free(s);
     if (!buf)
        buf = "";
     return buf;
index 9976277e273878731e856040fa90596a10b20fe6..00097bcc3d4faa5a3f888c7f169a2d7b7976de74 100644 (file)
@@ -38,7 +38,7 @@ extern "C" {
  * The enumerated type is defined here.  The apis array is
  * inititialized in gvplugin.c by redefining ELEM and reinvoking APIS.
  */
-#define APIS ELEM(render) ELEM(layout) ELEM(textlayout) ELEM(device) ELEM(loadimage) ELEM(formatter)
+#define APIS ELEM(render) ELEM(layout) ELEM(textlayout) ELEM(device) ELEM(loadimage)
 
 /*
  * Define api_t using names based on the plugin names with API_ prefixed.
index cd03318dc253a582d8eb9f70b53e015dc74ef8b9..d626e5e340bc3b9df34e06af07a778a2be006016 100644 (file)
@@ -27,6 +27,7 @@ extern "C" {
 
     struct gvdevice_engine_s {
        void (*initialize) (GVJ_t * firstjob);
+       void (*format) (GVJ_t * firstjob, unsigned int width, unsigned int height, unsigned char *data);
        void (*finalize) (GVJ_t * firstjob);
     };
 
index b74f531d74e9e9651451763b45d01b4ef126a33a..421ebb4e77beb7c03f174d701e559c4102a7f909 100644 (file)
@@ -53,71 +53,49 @@ int gvrender_select(GVJ_t * job, char *str)
     GVC_t *gvc = job->gvc;
     gvplugin_available_t *plugin;
     gvplugin_installed_t *typeptr;
-    char *device, *formatter, *p, buf[40]; 
 #ifdef WITH_CODEGENS
     codegen_info_t *cg_info;
 #endif
 
-    plugin = gvplugin_load(gvc, API_render, str);
+    gvplugin_load(gvc, API_device, str);
+
+    plugin = gvc->api[API_device];
     if (plugin) {
 #ifdef WITH_CODEGENS
        if (strcmp(plugin->packagename, "cg") == 0) {
            cg_info = (codegen_info_t *) (plugin->typeptr);
            job->codegen = cg_info->cg;
            job->render.engine = NULL;
-           job->device.engine = NULL;
            return cg_info->id;
-       } else {
+       }
 #endif
-           typeptr = plugin->typeptr;
-           job->render.engine = (gvrender_engine_t *) (typeptr->engine);
-           job->render.features = (gvrender_features_t *) (typeptr->features);
-           job->render.id = typeptr->id;
-
-           formatter = job->render.features->formatter;
-           if (formatter) {
-               strcpy(buf, formatter);
-               strcat(buf, "2");
-               strcat(buf, str);
-               if ((p=strchr(buf, ':')))
-                       *p = '\0';
-               formatter = buf;
-               plugin = gvplugin_load(gvc, API_formatter, formatter);
-               if (! plugin) {
-                   job->formatter.engine = NULL;
-                   return NO_SUPPORT;  /* FIXME - should differentiate no device from no renderer */
-               }
-               typeptr = plugin->typeptr;
-               job->formatter.engine = (gvformatter_engine_t *) (typeptr->engine);
-               job->formatter.features = (gvformatter_features_t *) (typeptr->features);
-               job->formatter.id = typeptr->id;
-           }
-           else {
-               job->formatter.engine = NULL;
-           }
-
-           device = job->render.features->device;
-           if (device) {
-               plugin = gvplugin_load(gvc, API_device, device);
-               if (! plugin) {
-                   job->device.engine = NULL;
-                   return NO_SUPPORT;  /* FIXME - should differentiate no device from no renderer */
-               }
-               typeptr = plugin->typeptr;
-               job->device.engine = (gvdevice_engine_t *) (typeptr->engine);
-               job->device.features = (gvdevice_features_t *) (typeptr->features);
-               job->device.id = typeptr->id;
-           }
-           else {
-               job->device.engine = NULL;
-           }
+        typeptr = plugin->typeptr;
+        job->device.engine = (gvdevice_engine_t *) (typeptr->engine);
+        job->device.features = (gvdevice_features_t *) (typeptr->features);
+        job->device.id = typeptr->id;
+    }
+    else
+       return NO_SUPPORT;  /* FIXME - should differentiate problem */
+    
+    plugin = gvc->api[API_render];
+    if (plugin) {
+        typeptr = plugin->typeptr;
+        job->render.engine = (gvrender_engine_t *) (typeptr->engine);
 
-           return GVRENDER_PLUGIN;
-#ifdef WITH_CODEGENS
+        if (job->device.engine) {
+            job->render.features = (gvrender_features_t *) (typeptr->features);
+            job->render.id = typeptr->id;
        }
-#endif
+       else {
+           /* a null device engine indicates that the renderer provides
+               the id and features */
+            job->render.features = (gvrender_features_t *) (job->device.features);
+            job->render.id = job->device.id;
+       }
+        return GVRENDER_PLUGIN;
     }
-    return NO_SUPPORT;
+    job->render.engine = NULL;
+    return NO_SUPPORT;  /* FIXME - should differentiate problem */
 }
 
 int gvrender_features(GVJ_t * job)
index 8c45a03050d65f93f9b29d4d94272489a8197cfa..80a086b7b6b19d1e4a19e2df94a0d91805c9cbcd 100644 (file)
 
 #include "gvplugin.h"
 
+extern gvplugin_installed_t gvdevice_core_dot_types;
+extern gvplugin_installed_t gvdevice_core_ps_types;
+extern gvplugin_installed_t gvdevice_core_fig_types;
+extern gvplugin_installed_t gvdevice_core_svg_types;
+extern gvplugin_installed_t gvdevice_core_vml_types;
+extern gvplugin_installed_t gvdevice_core_map_types;
 extern gvplugin_installed_t gvrender_core_dot_types;
 extern gvplugin_installed_t gvrender_core_ps_types;
 extern gvplugin_installed_t gvrender_core_fig_types;
@@ -25,6 +31,12 @@ extern gvplugin_installed_t gvrender_core_map_types;
 extern gvplugin_installed_t gvloadimage_core_types;
 
 static gvplugin_api_t apis[] = {
+    {API_device, &gvdevice_core_dot_types},
+    {API_device, &gvdevice_core_ps_types},
+    {API_device, &gvdevice_core_fig_types},
+    {API_device, &gvdevice_core_svg_types},
+    {API_device, &gvdevice_core_vml_types},
+    {API_device, &gvdevice_core_map_types},
     {API_render, &gvrender_core_dot_types},
     {API_render, &gvrender_core_ps_types},
     {API_render, &gvrender_core_fig_types},
index f4a040042b3ad4e1227a8223fdc701c897d7652a..c8943b2bba04311ad743ad608e2a870db5a419e5 100644 (file)
@@ -43,7 +43,14 @@ extern void output_point(agxbuf *xbuf, pointf p);
 
 #define GNEW(t)          (t*)malloc(sizeof(t))
 
-typedef enum { FORMAT_DOT, FORMAT_CANON, FORMAT_PLAIN, FORMAT_PLAIN_EXT, FORMAT_XDOT } format_type;
+typedef enum {
+       FORMAT_DOT,
+       FORMAT_CANON,
+       FORMAT_PLAIN,
+       FORMAT_PLAIN_EXT,
+       FORMAT_XDOT
+} format_type;
+
 
 #define XDOTVERSION "1.2"
 
@@ -475,9 +482,7 @@ gvrender_features_t canon_features = {
     NULL,                      /* knowncolors */
     0,                         /* sizeof knowncolors */
     COLOR_STRING,              /* color_type */
-    NULL,                       /* device */
     NULL,                       /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvrender_features_t dot_features = {
@@ -489,9 +494,7 @@ gvrender_features_t dot_features = {
     NULL,                      /* knowncolors */
     0,                         /* sizeof knowncolors */
     COLOR_STRING,              /* color_type */
-    NULL,                       /* device */
     NULL,                       /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvrender_features_t xdot_features = {
@@ -503,16 +506,20 @@ gvrender_features_t xdot_features = {
     NULL,                      /* knowncolors */
     0,                         /* sizeof knowncolors */
     COLOR_STRING,              /* color_type */
-    NULL,                       /* device */
     "xdot",                     /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvplugin_installed_t gvrender_core_dot_types[] = {
-    {FORMAT_DOT, "dot", 1, &dot_engine, &dot_features},
-    {FORMAT_CANON, "canon", 1, &dot_engine, &canon_features},
-    {FORMAT_PLAIN, "plain", 1, &dot_engine, &dot_features},
-    {FORMAT_PLAIN_EXT, "plain-ext", 1, &dot_engine, &dot_features},
-    {FORMAT_XDOT, "xdot", 1, &xdot_engine, &xdot_features},
+    {FORMAT_DOT, "core_dot", 1, &dot_engine, NULL},
+    {FORMAT_XDOT, "core_xdot", 1, &xdot_engine, NULL},
+    {0, NULL, 0, NULL, NULL}
+};
+
+gvplugin_installed_t gvdevice_core_dot_types[] = {
+    {FORMAT_DOT, "dot:core_dot", 1, NULL, &dot_features},
+    {FORMAT_CANON, "canon:core_dot", 1, NULL, &canon_features},
+    {FORMAT_PLAIN, "plain:core_dot", 1, NULL, &dot_features},
+    {FORMAT_PLAIN_EXT, "plain-ext:core_dot", 1, NULL, &dot_features},
+    {FORMAT_XDOT, "xdot:core_xdot", 1, NULL, &xdot_features},
     {0, NULL, 0, NULL, NULL}
 };
index ca4a3391c527bb7e4fce7568924cba6fe313d816..6f6c90c51aae885b51a18ae4c5cf6426fcef88de 100644 (file)
@@ -532,12 +532,15 @@ gvrender_features_t fig_features = {
     fig_knowncolors,           /* knowncolors */
     sizeof(fig_knowncolors) / sizeof(char *), /* sizeof knowncolors */
     RGBA_BYTE,                 /* color_type */
-    NULL,                       /* device */
     "fig",                      /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvplugin_installed_t gvrender_core_fig_types[] = {
-    {FORMAT_FIG, "fig", 1, &fig_engine, &fig_features},
+    {FORMAT_FIG, "core_fig", 1, &fig_engine, NULL},
+    {0, NULL, 0, NULL, NULL}
+};
+
+gvplugin_installed_t gvdevice_core_fig_types[] = {
+    {FORMAT_FIG, "fig:core_fig", 1, NULL, &fig_features},
     {0, NULL, 0, NULL, NULL}
 };
index b323f9ad8369a83b662f91feb34e297b30458057..5a50f315c98ce2a4c3d5c287dd267b6243612f2e 100644 (file)
@@ -302,9 +302,7 @@ static gvrender_features_t map_features = {
     NULL,                      /* knowncolors */
     0,                         /* sizeof knowncolors */
     0,                         /* color_type */
-    NULL,                       /* device */
     NULL,                       /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 static gvrender_features_t map_features_nopoly = {
@@ -321,17 +319,20 @@ static gvrender_features_t map_features_nopoly = {
     NULL,                      /* knowncolors */
     0,                         /* sizeof knowncolors */
     0,                         /* color_type */
-    NULL,                       /* device */
     NULL,                       /* imageloader target for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvplugin_installed_t gvrender_core_map_types[] = {
-    {FORMAT_ISMAP, "ismap", 1, &map_engine, &map_features_nopoly},
-    {FORMAT_CMAP, "cmap", 1, &map_engine, &map_features},
-    {FORMAT_IMAP, "imap", 1, &map_engine, &map_features},
-    {FORMAT_CMAPX, "cmapx", 1, &map_engine, &map_features},
-    {FORMAT_IMAP, "imap_np", 1, &map_engine, &map_features_nopoly},
-    {FORMAT_CMAPX, "cmapx_np", 1, &map_engine, &map_features_nopoly},
+    {FORMAT_ISMAP, "core_map", 1, &map_engine, NULL},
+    {0, NULL, 0, NULL, NULL}
+};
+
+gvplugin_installed_t gvdevice_core_map_types[] = {
+    {FORMAT_ISMAP, "ismap:core_map", 1, NULL, &map_features_nopoly},
+    {FORMAT_CMAP, "cmap:core_map", 1, NULL, &map_features},
+    {FORMAT_IMAP, "imap:core_map", 1, NULL, &map_features},
+    {FORMAT_CMAPX, "cmapx:core_map", 1, NULL, &map_features},
+    {FORMAT_IMAP, "imap_np:core_map", 1, NULL, &map_features_nopoly},
+    {FORMAT_CMAPX, "cmapx_np:core_map", 1, NULL, &map_features_nopoly},
     {0, NULL, 0, NULL, NULL}
 };
index 40f8c03ca6d250e15f5e124d98d1ba57a6c91718..77b8d2cbcdbe951ea4ec1d9371072c87909233c2 100644 (file)
@@ -469,13 +469,16 @@ static gvrender_features_t psgen_features = {
     NULL,                      /* knowncolors */
     0,                         /* sizeof knowncolors */
     HSVA_DOUBLE,               /* color_type */
-    NULL,                       /* device */
     "ps",                       /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvplugin_installed_t gvrender_core_ps_types[] = {
-    {FORMAT_PS, "ps", 1, &psgen_engine, &psgen_features},
-    {FORMAT_PS2, "ps2", 1, &psgen_engine, &psgen_features},
+    {FORMAT_PS, "core_ps", 1, &psgen_engine, NULL},
+    {0, NULL, 0, NULL, NULL}
+};
+
+gvplugin_installed_t gvdevice_core_ps_types[] = {
+    {FORMAT_PS, "ps:core_ps", 1, NULL, &psgen_features},
+    {FORMAT_PS2, "ps2:core_ps", 1, NULL, &psgen_features},
     {0, NULL, 0, NULL, NULL}
 };
index 97bdece5498edfbefff2f416a22b669b1430683c..50675363e197018fe15319e43b64c92348eaa2c6 100644 (file)
@@ -483,15 +483,18 @@ gvrender_features_t svg_features = {
     svg_knowncolors,           /* knowncolors */
     sizeof(svg_knowncolors) / sizeof(char *),  /* sizeof knowncolors */
     RGBA_BYTE,                 /* color_type */
-    NULL,                       /* device */
     "svg",                      /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvplugin_installed_t gvrender_core_svg_types[] = {
-    {FORMAT_SVG, "svg", 1, &svg_engine, &svg_features},
+    {FORMAT_SVG, "core_svg", 1, &svg_engine, NULL},
+    {0, NULL, 0, NULL, NULL}
+};
+
+gvplugin_installed_t gvdevice_core_svg_types[] = {
+    {FORMAT_SVG, "svg:core_svg", 1, NULL, &svg_features},
 #if HAVE_LIBZ
-    {FORMAT_SVGZ, "svgz", 1, &svg_engine, &svg_features},
+    {FORMAT_SVGZ, "svgz:core_svg", 1, NULL, &svg_features},
 #endif
     {0, NULL, 0, NULL, NULL}
 };
index 953ae481366601b764a561830289f928e6e1fcaf..eeabca0b924d134864d639a92cff13cfb1a5ea56 100644 (file)
@@ -431,15 +431,18 @@ gvrender_features_t vml_features = {
     vml_knowncolors,           /* knowncolors */
     sizeof(vml_knowncolors) / sizeof(char *),  /* sizeof knowncolors */
     RGBA_BYTE,                 /* color_type */
-    NULL,                       /* device */
     "vml",                      /* imageloader for usershapes */
-    NULL,                       /* formatter */
 };
 
 gvplugin_installed_t gvrender_core_vml_types[] = {
-    {FORMAT_VML, "vml", 1, &vml_engine, &vml_features},
+    {FORMAT_VML, "core_vml", 1, &vml_engine, NULL},
+    {0, NULL, 0, NULL, NULL}
+};
+
+gvplugin_installed_t gvdevice_core_vml_types[] = {
+    {FORMAT_VML, "vml:core_vml", 1, NULL, &vml_features},
 #if HAVE_LIBZ
-    {FORMAT_VMLZ, "vmlz", 1, &vml_engine, &vml_features},
+    {FORMAT_VMLZ, "vmlz:core_vml", 1, NULL, &vml_features},
 #endif
     {0, NULL, 0, NULL, NULL}
 };
index eb4ad327a3c2e428452ad9e32bc3bf775ab011ba..23a4bfe491d29ed241c542204b9b4ae0d9816f1c 100644 (file)
@@ -17,7 +17,7 @@ endif
 
 libgvplugin_devil_C_la_SOURCES = \
        gvplugin_devil.c \
-       gvformatter_devil.c
+       gvdevice_devil.c
 
 libgvplugin_devil_la_LDFLAGS = -version-info @VERSION_INFO@ -no-undefined
 libgvplugin_devil_la_SOURCES = $(libgvplugin_devil_C_la_SOURCES)
diff --git a/plugin/devil/gvdevice_devil.c b/plugin/devil/gvdevice_devil.c
new file mode 100644 (file)
index 0000000..21110b8
--- /dev/null
@@ -0,0 +1,130 @@
+/* $Id$ $Revision$ */
+/* vim:set shiftwidth=4 ts=8: */
+
+/**********************************************************
+*      This software is part of the graphviz package      *
+*                http://www.graphviz.org/                 *
+*                                                         *
+*            Copyright (c) 1994-2004 AT&T Corp.           *
+*                and is licensed under the                *
+*            Common Public License, Version 1.0           *
+*                      by AT&T Corp.                      *
+*                                                         *
+*        Information and Software Systems Research        *
+*              AT&T Research, Florham Park NJ             *
+**********************************************************/
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#ifdef WIN32
+#include <io.h>
+#include <fcntl.h>
+#endif
+#include "gvplugin_device.h"
+#include <IL/il.h>
+#include <IL/ilu.h>
+
+static void
+Y_inv ( unsigned int width, unsigned int height, unsigned char *data)
+{
+        unsigned int x, y, rowsize, i;
+        unsigned char tmp, *data2;
+
+#define STRIDE 4
+
+        rowsize = width * STRIDE;
+        data2 = data + (height-1) * rowsize;
+        for (y = 0; y < height/2; y++) {
+                for (x = 0; x < width; x++) {
+                        for (i = 0; i < STRIDE; i++) {
+                                tmp = *data;
+                                *data++ = *data2;
+                                *data2++ = tmp;
+                        }
+                }
+                data2 -= 2*rowsize;
+        }
+}
+
+static void devil_format(GVJ_t * job, unsigned int width, unsigned int height, unsigned char *data)
+{
+    ILuint     ImgId;
+    ILenum     Error;
+    ILboolean rc;
+
+#ifdef HAVE_SETMODE
+#ifdef O_BINARY
+    /*
+     * Windows will do \n -> \r\n  translations on stdout
+     * unless told otherwise.
+     */
+    setmode(fileno(job->output_file), O_BINARY);
+#endif
+#endif
+
+    // Check if the shared lib's version matches the executable's version.
+    if (ilGetInteger(IL_VERSION_NUM) < IL_VERSION ||
+       iluGetInteger(ILU_VERSION_NUM) < ILU_VERSION) {
+       fprintf(stderr, "DevIL version is different...exiting!\n");
+    }
+
+    // Initialize DevIL.
+    ilInit();
+
+    // Generate the main image name to use.
+    ilGenImages(1, &ImgId);
+
+    // Bind this image name.
+    ilBindImage(ImgId);
+
+    Y_inv ( width, height, data );
+    
+    rc = ilTexImage( width, height,
+               1,              // Depth
+               4,              // Bpp
+               IL_BGRA,        // Format
+               IL_UNSIGNED_BYTE,// Type
+               data);
+    
+#if 1
+    ilSaveF(job->device.id, job->output_file);
+#endif
+
+#if 0
+    ilEnable(IL_FILE_OVERWRITE);
+    ilSaveImage("test-devil.bmp");
+#endif
+    
+    // We're done with the image, so let's delete it.
+    ilDeleteImages(1, &ImgId);
+    
+    // Simple Error detection loop that displays the Error to the user in a human-readable form.
+    while ((Error = ilGetError())) {
+       fprintf(stderr, "Error: %s\n", iluErrorString(Error));
+    }
+}
+
+static gvdevice_engine_t devil_engine = {
+    NULL,
+    devil_format,
+    NULL,
+};
+
+static gvdevice_features_t devil_features = {
+    0,  /* flags */
+};
+
+gvplugin_installed_t gvdevice_devil_types[] = {
+    {IL_BMP, "bmp:cairo", -1, &devil_engine, &devil_features},
+//    {IL_GIF, "gif:cairo", -1, &devil_engine, &devil_features},
+    {IL_JPG, "jpg:cairo", -1, &devil_engine, &devil_features},
+    {IL_JPG, "jpe:cairo", -1, &devil_engine, &devil_features},
+    {IL_JPG, "jpeg:cairo", -1, &devil_engine, &devil_features},
+    {IL_PNG, "png:cairo", -1, &devil_engine, &devil_features},
+    {IL_TIF, "tif:cairo", -1, &devil_engine, &devil_features},
+    {IL_TIF, "tiff:cairo", -1, &devil_engine, &devil_features},
+    {IL_TGA, "tga:cairo", -1, &devil_engine, &devil_features},
+    {0, NULL, 0, NULL, NULL}
+};