summaryrefslogtreecommitdiff
path: root/src/drv/cdmf.c
diff options
context:
space:
mode:
authorscuri <scuri>2008-10-17 06:10:33 +0000
committerscuri <scuri>2008-10-17 06:10:33 +0000
commit7b52cc13af4e85f1ca2deb6b6c77de9c95ea0dcf (patch)
treed0857278bde2eff784227c57dcaf930346ceb7ac /src/drv/cdmf.c
First commit - moving from LuaForge to SourceForge
Diffstat (limited to 'src/drv/cdmf.c')
-rw-r--r--src/drv/cdmf.c1188
1 files changed, 1188 insertions, 0 deletions
diff --git a/src/drv/cdmf.c b/src/drv/cdmf.c
new file mode 100644
index 0000000..6c2e711
--- /dev/null
+++ b/src/drv/cdmf.c
@@ -0,0 +1,1188 @@
+/** \file
+ * \brief CD Metafile driver
+ *
+ * See Copyright Notice in cd.h
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <limits.h>
+
+#include "cd.h"
+#include "wd.h"
+#include "cd_private.h"
+#include "cdmf.h"
+#include "cdmf_private.h"
+
+
+/* codes for the primitives and attributes in the metafile
+ Can NOT be changed, only added for backward compatibility.
+*/
+enum
+{
+ CDMF_FLUSH, /* 0 */
+ CDMF_CLEAR, /* 1 */
+ CDMF_CLIP, /* 2 */
+ CDMF_CLIPAREA, /* 3 */
+ CDMF_LINE, /* 4 */
+ CDMF_BOX, /* 5 */
+ CDMF_ARC, /* 6 */
+ CDMF_SECTOR, /* 7 */
+ CDMF_TEXT, /* 8 */
+ CDMF_BEGIN, /* 9 */
+ CDMF_VERTEX, /* 10 */
+ CDMF_END, /* 11 */
+ CDMF_MARK, /* 12 */
+ CDMF_BACKOPACITY, /* 13 */
+ CDMF_WRITEMODE, /* 14 */
+ CDMF_LINESTYLE, /* 15 */
+ CDMF_LINEWIDTH, /* 16 */
+ CDMF_INTERIORSTYLE, /* 17 */
+ CDMF_HATCH, /* 18 */
+ CDMF_STIPPLE, /* 19 */
+ CDMF_PATTERN, /* 20 */
+ CDMF_OLDFONT, /* 21 */
+ CDMF_NATIVEFONT, /* 22 */
+ CDMF_TEXTALIGNMENT, /* 23 */
+ CDMF_MARKTYPE, /* 24 */
+ CDMF_MARKSIZE, /* 25 */
+ CDMF_PALETTE, /* 26 */
+ CDMF_BACKGROUND, /* 27 */
+ CDMF_FOREGROUND, /* 28 */
+ CDMF_PUTIMAGERGB, /* 29 */
+ CDMF_PUTIMAGEMAP, /* 30 */
+ CDMF_PIXEL, /* 31 */
+ CDMF_SCROLLAREA, /* 32 */
+ CDMF_TEXTORIENTATION, /* 33 */
+ CDMF_RECT, /* 34 */
+ CDMF_PUTIMAGERGBA, /* 35 */
+ CDMF_WLINE, /* 36 */
+ CDMF_WRECT, /* 37 */
+ CDMF_WBOX, /* 38 */
+ CDMF_WARC, /* 39 */
+ CDMF_WSECTOR, /* 40 */
+ CDMF_WTEXT, /* 41 */
+ CDMF_WVERTEX, /* 42 */
+ CDMF_WMARK, /* 43 */
+ CDMF_VECTORTEXT, /* 44 */
+ CDMF_MULTILINEVECTORTEXT, /* 45 */
+ CDMF_WVECTORTEXT, /* 46 */
+ CDMF_WMULTILINEVECTORTEXT, /* 47 */
+ CDMF_WINDOW, /* 48 */
+ CDMF_WCLIPAREA, /* 49 */
+ CDMF_VECTORFONT, /* 50 */
+ CDMF_VECTORTEXTDIRECTION, /* 51 */
+ CDMF_VECTORTEXTTRANSFORM, /* 52 */
+ CDMF_VECTORTEXTSIZE, /* 53 */
+ CDMF_VECTORCHARSIZE, /* 54 */
+ CDMF_WVECTORTEXTDIRECTION, /* 55 */
+ CDMF_WVECTORTEXTSIZE, /* 56 */
+ CDMF_WVECTORCHARSIZE, /* 57 */
+ CDMF_FILLMODE, /* 58 */
+ CDMF_LINESTYLEDASHES, /* 59 */
+ CDMF_LINECAP, /* 60 */
+ CDMF_LINEJOIN, /* 61 */
+ CDMF_CHORD, /* 62 */
+ CDMF_WCHORD, /* 63 */
+ CDMF_FLINE, /* 64 */
+ CDMF_FRECT, /* 65 */
+ CDMF_FBOX, /* 66 */
+ CDMF_FARC, /* 67 */
+ CDMF_FSECTOR, /* 68 */
+ CDMF_FTEXT, /* 69 */
+ CDMF_FVERTEX, /* 70 */
+ CDMF_MATRIX, /* 71 */
+ CDMF_FCHORD, /* 72 */
+ CDMF_FCLIPAREA, /* 73 */
+ CDMF_FONT, /* 74 */
+ CDMF_RESETMATRIX /* 75 */
+};
+
+struct _cdCtxCanvas
+{
+ /* public */
+ cdCanvas* canvas;
+ char* filename;
+ void* data; /* used by other drivers */
+
+ /* private */
+ int last_line_style;
+ int last_fill_mode;
+ FILE* file;
+};
+
+void cdkillcanvasMF(cdCanvasMF *mfcanvas)
+{
+ cdCtxCanvas *ctxcanvas = (cdCtxCanvas*)mfcanvas;
+ free(ctxcanvas->filename);
+ fclose(ctxcanvas->file);
+ memset(ctxcanvas, 0, sizeof(cdCtxCanvas));
+ free(ctxcanvas);
+}
+
+static void cdflush(cdCtxCanvas *ctxcanvas)
+{
+ fflush(ctxcanvas->file);
+ fprintf(ctxcanvas->file, "%d\n", CDMF_FLUSH);
+}
+
+static void cdclear(cdCtxCanvas *ctxcanvas)
+{
+ fprintf(ctxcanvas->file, "%d\n", CDMF_CLEAR);
+}
+
+static int cdclip(cdCtxCanvas *ctxcanvas, int mode)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_CLIP, mode);
+ return mode;
+}
+
+static void cdcliparea(cdCtxCanvas *ctxcanvas, int xmin, int xmax, int ymin, int ymax)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d\n", CDMF_CLIPAREA, xmin, xmax, ymin, ymax);
+}
+
+static void cdfcliparea(cdCtxCanvas *ctxcanvas, double xmin, double xmax, double ymin, double ymax)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g\n", CDMF_FCLIPAREA, xmin, xmax, ymin, ymax);
+}
+
+static void cdtransform(cdCtxCanvas *ctxcanvas, const double* matrix)
+{
+ if (matrix)
+ fprintf(ctxcanvas->file, "%d %g %g %g %g %g %g\n", CDMF_MATRIX, matrix[0], matrix[1], matrix[2], matrix[3], matrix[4], matrix[5]);
+ else
+ fprintf(ctxcanvas->file, "%d\n", CDMF_RESETMATRIX);
+}
+
+static void cdline(cdCtxCanvas *ctxcanvas, int x1, int y1, int x2, int y2)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d\n", CDMF_LINE, x1, y1, x2, y2);
+}
+
+static void cdfline(cdCtxCanvas *ctxcanvas, double x1, double y1, double x2, double y2)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g\n", CDMF_FLINE, x1, y1, x2, y2);
+}
+
+static void cdrect(cdCtxCanvas *ctxcanvas, int xmin, int xmax, int ymin, int ymax)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d\n", CDMF_RECT, xmin, xmax, ymin, ymax);
+}
+
+static void cdfrect(cdCtxCanvas *ctxcanvas, double xmin, double xmax, double ymin, double ymax)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g\n", CDMF_FRECT, xmin, xmax, ymin, ymax);
+}
+
+static void cdbox(cdCtxCanvas *ctxcanvas, int xmin, int xmax, int ymin, int ymax)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d\n", CDMF_BOX, xmin, xmax, ymin, ymax);
+}
+
+static void cdfbox(cdCtxCanvas *ctxcanvas, double xmin, double xmax, double ymin, double ymax)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g\n", CDMF_FBOX, xmin, xmax, ymin, ymax);
+}
+
+static void cdarc(cdCtxCanvas *ctxcanvas, int xc, int yc, int w, int h, double a1, double a2)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %g %g\n", CDMF_ARC, xc, yc, w, h, a1, a2);
+}
+
+static void cdfarc(cdCtxCanvas *ctxcanvas, double xc, double yc, double w, double h, double a1, double a2)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g %g %g\n", CDMF_FARC, xc, yc, w, h, a1, a2);
+}
+
+static void cdsector(cdCtxCanvas *ctxcanvas, int xc, int yc, int w, int h, double a1, double a2)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %g %g\n", CDMF_SECTOR, xc, yc, w, h, a1, a2);
+}
+
+static void cdfsector(cdCtxCanvas *ctxcanvas, double xc, double yc, double w, double h, double a1, double a2)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g %g %g\n", CDMF_FSECTOR, xc, yc, w, h, a1, a2);
+}
+
+static void cdchord(cdCtxCanvas *ctxcanvas, int xc, int yc, int w, int h, double a1, double a2)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %g %g\n", CDMF_CHORD, xc, yc, w, h, a1, a2);
+}
+
+static void cdfchord(cdCtxCanvas *ctxcanvas, double xc, double yc, double w, double h, double a1, double a2)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %g %g %g %g\n", CDMF_FCHORD, xc, yc, w, h, a1, a2);
+}
+
+static void cdtext(cdCtxCanvas *ctxcanvas, int x, int y, const char *text)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %s\n", CDMF_TEXT, x, y, text);
+}
+
+static void cdftext(cdCtxCanvas *ctxcanvas, double x, double y, const char *text)
+{
+ fprintf(ctxcanvas->file, "%d %g %g %s\n", CDMF_FTEXT, x, y, text);
+}
+
+static void cdpoly(cdCtxCanvas *ctxcanvas, int mode, cdPoint* poly, int n)
+{
+ int i;
+
+ if (mode == CD_FILL && ctxcanvas->canvas->fill_mode != ctxcanvas->last_fill_mode)
+ {
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_FILLMODE, ctxcanvas->canvas->fill_mode);
+ ctxcanvas->last_fill_mode = ctxcanvas->canvas->fill_mode;
+ }
+
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_BEGIN, mode);
+
+ for(i = 0; i<n; i++)
+ fprintf(ctxcanvas->file, "%d %d %d\n", CDMF_VERTEX, poly[i].x, poly[i].y);
+
+ fprintf(ctxcanvas->file, "%d\n", CDMF_END);
+}
+
+static void cdfpoly(cdCtxCanvas *ctxcanvas, int mode, cdfPoint* poly, int n)
+{
+ int i;
+
+ if (mode == CD_FILL && ctxcanvas->canvas->fill_mode != ctxcanvas->last_fill_mode)
+ {
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_FILLMODE, ctxcanvas->canvas->fill_mode);
+ ctxcanvas->last_fill_mode = ctxcanvas->canvas->fill_mode;
+ }
+
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_BEGIN, mode);
+
+ for(i = 0; i<n; i++)
+ fprintf(ctxcanvas->file, "%d %g %g\n", CDMF_FVERTEX, poly[i].x, poly[i].y);
+
+ fprintf(ctxcanvas->file, "%d\n", CDMF_END);
+}
+
+static int cdbackopacity(cdCtxCanvas *ctxcanvas, int opacity)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_BACKOPACITY, opacity);
+ return opacity;
+}
+
+static int cdwritemode(cdCtxCanvas *ctxcanvas, int mode)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_WRITEMODE, mode);
+ return mode;
+}
+
+static int cdlinestyle(cdCtxCanvas *ctxcanvas, int style)
+{
+ if (style == CD_CUSTOM && ctxcanvas->canvas->line_style != ctxcanvas->last_line_style)
+ {
+ int i;
+ fprintf(ctxcanvas->file, "%d %d", CDMF_LINESTYLEDASHES, ctxcanvas->canvas->line_dashes_count);
+ for (i = 0; i < ctxcanvas->canvas->line_dashes_count; i++)
+ fprintf(ctxcanvas->file, " %d", ctxcanvas->canvas->line_dashes[i]);
+ fprintf(ctxcanvas->file, "\n");
+ ctxcanvas->last_line_style = ctxcanvas->canvas->line_style;
+ }
+
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_LINESTYLE, style);
+ return style;
+}
+
+static int cdlinewidth(cdCtxCanvas *ctxcanvas, int width)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_LINEWIDTH, width);
+ return width;
+}
+
+static int cdlinecap(cdCtxCanvas *ctxcanvas, int cap)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_LINECAP, cap);
+ return cap;
+}
+
+static int cdlinejoin(cdCtxCanvas *ctxcanvas, int join)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_LINEJOIN, join);
+ return join;
+}
+
+static int cdinteriorstyle(cdCtxCanvas *ctxcanvas, int style)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_INTERIORSTYLE, style);
+ return style;
+}
+
+static int cdhatch(cdCtxCanvas *ctxcanvas, int style)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_HATCH, style);
+ return style;
+}
+
+static void cdstipple(cdCtxCanvas *ctxcanvas, int w, int h, const unsigned char *stipple)
+{
+ int c, t;
+
+ fprintf(ctxcanvas->file, "%d %d %d\n", CDMF_STIPPLE, w, h);
+
+ t = w * h;
+
+ for (c = 0; c < t; c++)
+ {
+ fprintf(ctxcanvas->file, "%d ", (int)*stipple++);
+ if ((c + 1) % w == 0)
+ fprintf(ctxcanvas->file, "\n");
+ }
+}
+
+static void cdpattern(cdCtxCanvas *ctxcanvas, int w, int h, const long int *pattern)
+{
+ int c, t;
+ unsigned char r, g, b;
+
+ fprintf(ctxcanvas->file, "%d %d %d\n", CDMF_PATTERN, w, h);
+
+ t = w * h;
+
+ /* stores the pattern with separeted RGB values */
+ for (c = 0; c < t; c++)
+ {
+ cdDecodeColor(*pattern++, &r, &g, &b);
+ fprintf(ctxcanvas->file, "%d %d %d ", (int)r, (int)g, (int)b);
+ if (c % w == 0)
+ fprintf(ctxcanvas->file, "\n");
+ }
+}
+
+static int cdfont(cdCtxCanvas *ctxcanvas, const char* type_face, int style, int size)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %s\n", CDMF_FONT, style, size, type_face);
+ return 1;
+}
+
+static int cdnativefont(cdCtxCanvas *ctxcanvas, const char* font)
+{
+ fprintf(ctxcanvas->file, "%d %s\n", CDMF_NATIVEFONT, font);
+ return 1;
+}
+
+static int cdtextalignment(cdCtxCanvas *ctxcanvas, int alignment)
+{
+ fprintf(ctxcanvas->file, "%d %d\n", CDMF_TEXTALIGNMENT, alignment);
+ return alignment;
+}
+
+static double cdtextorientation(cdCtxCanvas *ctxcanvas, double angle)
+{
+ fprintf(ctxcanvas->file, "%d %g\n", CDMF_TEXTORIENTATION, angle);
+ return angle;
+}
+
+static void cdpalette(cdCtxCanvas *ctxcanvas, int n, const long int *palette, int mode)
+{
+ int c;
+ unsigned char r, g, b;
+
+ fprintf(ctxcanvas->file, "%d %d %d\n", CDMF_PALETTE, n, mode);
+
+ for (c = 0; c < n; c++)
+ {
+ cdDecodeColor(*palette++, &r, &g, &b);
+ fprintf(ctxcanvas->file, "%d %d %d\n", (int)r, (int)g, (int)b);
+ }
+}
+
+static long cdbackground(cdCtxCanvas *ctxcanvas, long int color)
+{
+ unsigned char r, g, b;
+ cdDecodeColor(color, &r, &g, &b);
+ fprintf(ctxcanvas->file, "%d %d %d %d\n", CDMF_BACKGROUND, (int)r, (int)g, (int)b);
+ return color;
+}
+
+static long cdforeground(cdCtxCanvas *ctxcanvas, long int color)
+{
+ unsigned char r, g, b;
+ cdDecodeColor(color, &r, &g, &b);
+ fprintf(ctxcanvas->file, "%d %d %d %d\n", CDMF_FOREGROUND, (int)r, (int)g, (int)b);
+ return color;
+}
+
+static void cdputimagerectrgb(cdCtxCanvas *ctxcanvas, int iw, int ih, const unsigned char *r, const unsigned char *g, const unsigned char *b, int x, int y, int w, int h, int xmin, int xmax, int ymin, int ymax)
+{
+ int c, l, offset;
+
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %d %d\n", CDMF_PUTIMAGERGB, iw, ih, x, y, w, h);
+
+ offset = ymin*iw + xmin;
+ r += offset;
+ g += offset;
+ b += offset;
+
+ offset = iw - (xmax-xmin+1);
+
+ for (l = ymin; l <= ymax; l++)
+ {
+ for (c = xmin; c <= xmax; c++)
+ {
+ fprintf(ctxcanvas->file, "%d %d %d ", (int)*r++, (int)*g++, (int)*b++);
+ }
+
+ r += offset;
+ g += offset;
+ b += offset;
+
+ fprintf(ctxcanvas->file, "\n");
+ }
+}
+
+static void cdputimagerectrgba(cdCtxCanvas *ctxcanvas, int iw, int ih, const unsigned char *r, const unsigned char *g, const unsigned char *b, const unsigned char *a, int x, int y, int w, int h, int xmin, int xmax, int ymin, int ymax)
+{
+ int c, l, offset;
+
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %d %d\n", CDMF_PUTIMAGERGBA, iw, ih, x, y, w, h);
+
+ offset = ymin*iw + xmin;
+ r += offset;
+ g += offset;
+ b += offset;
+ a += offset;
+
+ offset = iw - (xmax-xmin+1);
+
+ for (l = ymin; l <= ymax; l++)
+ {
+ for (c = xmin; c <= xmax; c++)
+ {
+ fprintf(ctxcanvas->file, "%d %d %d %d ", (int)*r++, (int)*g++, (int)*b++, (int)*a++);
+ }
+
+ r += offset;
+ g += offset;
+ b += offset;
+ a += offset;
+
+ fprintf(ctxcanvas->file, "\n");
+ }
+}
+
+static void cdputimagerectmap(cdCtxCanvas *ctxcanvas, int iw, int ih, const unsigned char *index, const long int *colors, int x, int y, int w, int h, int xmin, int xmax, int ymin, int ymax)
+{
+ int c, l, n = 0, offset;
+ unsigned char r, g, b;
+
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %d %d\n", CDMF_PUTIMAGEMAP, iw, ih, x, y, w, h);
+
+ index += ymin*iw + xmin;
+ offset = iw - (xmax-xmin+1);
+
+ for (l = ymin; l <= ymax; l++)
+ {
+ for (c = xmin; c <= xmax; c++)
+ {
+ if (*index > n)
+ n = *index;
+
+ fprintf(ctxcanvas->file, "%d ", (int)*index++);
+ }
+
+ index += offset;
+
+ fprintf(ctxcanvas->file, "\n");
+ }
+
+ n++;
+
+ for (c = 0; c < n; c++)
+ {
+ cdDecodeColor(*colors++, &r, &g, &b);
+ fprintf(ctxcanvas->file, "%d %d %d\n", (int)r, (int)g, (int)b);
+ }
+}
+
+static void cdpixel(cdCtxCanvas *ctxcanvas, int x, int y, long int color)
+{
+ unsigned char r, g, b;
+ cdDecodeColor(color, &r, &g, &b);
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %d\n", CDMF_PIXEL, x, y, (int)r, (int)g, (int)b);
+}
+
+static void cdscrollarea(cdCtxCanvas *ctxcanvas, int xmin,int xmax, int ymin,int ymax, int dx,int dy)
+{
+ fprintf(ctxcanvas->file, "%d %d %d %d %d %d %d\n", CDMF_SCROLLAREA, xmin, xmax, ymin, ymax, dx, dy);
+}
+
+
+/**********/
+/* cdPlay */
+/**********/
+
+
+static double factorX = 1;
+static double factorY = 1;
+static int offsetX = 0;
+static int offsetY = 0;
+static double factorS = 1;
+
+static int sScaleX(int x)
+{
+ return cdRound(x * factorX + offsetX);
+}
+
+static int sScaleY(int y)
+{
+ return cdRound(y * factorY + offsetY);
+}
+
+static double sfScaleX(double x)
+{
+ return x * factorX + offsetX;
+}
+
+static double sfScaleY(double y)
+{
+ return y * factorY + offsetY;
+}
+
+static int sScaleW(int w)
+{
+ w = (int)(w * factorX + 0.5); /* always positive */
+ return w == 0? 1: w;
+}
+
+static double sfScaleH(double h)
+{
+ h = h * factorY;
+ return h == 0? 1: h;
+}
+
+static double sfScaleW(double w)
+{
+ w = w * factorX; /* always positive */
+ return w == 0? 1: w;
+}
+
+static int sScaleH(int h)
+{
+ h = (int)(h * factorY + 0.5);
+ return h == 0? 1: h;
+}
+
+static int sScaleS(int s)
+{
+ s = (int)(s * factorS + 0.5);
+ return s == 0? 1: s;
+}
+
+typedef int(*_cdsizecb)(cdCanvas* canvas, int w, int h, double w_mm, double h_mm);
+static _cdsizecb cdsizecb = NULL;
+
+static int cdregistercallback(int cb, cdCallback func)
+{
+ switch (cb)
+ {
+ case CD_SIZECB:
+ cdsizecb = (_cdsizecb)func;
+ return CD_OK;
+ }
+
+ return CD_ERROR;
+}
+
+static int cdplay(cdCanvas* canvas, int xmin, int xmax, int ymin, int ymax, void *data)
+{
+ char* filename = (char*)data;
+ FILE* file;
+ char TextBuffer[512];
+ int iparam1, iparam2, iparam3, iparam4, iparam5, iparam6, iparam7, iparam8, iparam9, iparam10;
+ int c, t, n, w, h, func;
+ double dparam1, dparam2, dparam3, dparam4, dparam5, dparam6;
+ unsigned char* stipple, * _stipple, *red, *green, *blue, *_red, *_green, *_blue, *index, *_index, *_alpha, *alpha;
+ long int *pattern, *palette, *_pattern, *_palette, *colors, *_colors;
+ int* dashes;
+ double matrix[6];
+ const char * font_family[] =
+ {
+ "System", /* CD_SYSTEM */
+ "Courier", /* CD_COURIER */
+ "Times", /* CD_TIMES_ROMAN */
+ "Helvetica" /* CD_HELVETICA */
+ };
+
+ file = fopen(filename, "r");
+ if (!file)
+ return CD_ERROR;
+
+ func = -1;
+ w = 0;
+ h = 0;
+
+ factorX = 1;
+ factorY = 1;
+ offsetX = 0;
+ offsetY = 0;
+ factorS = 1;
+
+ fscanf(file, "%s %d %d", TextBuffer, &w, &h);
+
+ if (strcmp(TextBuffer, "CDMF") != 0)
+ {
+ fclose(file);
+ return CD_ERROR;
+ }
+
+ if (w>1 && h>1 && xmax!=0 && ymax!=0)
+ {
+ offsetX = xmin;
+ offsetY = ymin;
+ factorX = ((double)(xmax-xmin)) / (w-1);
+ factorY = ((double)(ymax-ymin)) / (h-1);
+
+ if (factorX < factorY)
+ factorS = factorX;
+ else
+ factorS = factorY;
+ }
+
+ if (cdsizecb)
+ {
+ int err;
+ err = cdsizecb(canvas, w, h, w, h);
+ if (err)
+ return CD_ERROR;
+ }
+
+ while (!feof(file))
+ {
+ fscanf(file, "%d", &func);
+ if (feof(file))
+ break;
+
+ switch (func)
+ {
+ case CDMF_FLUSH:
+ cdCanvasFlush(canvas);
+ break;
+ case CDMF_CLEAR:
+ cdCanvasClear(canvas);
+ break;
+ case CDMF_CLIP:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasClip(canvas, iparam1);
+ break;
+ case CDMF_CLIPAREA:
+ fscanf(file, "%d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4);
+ cdCanvasClipArea(canvas, sScaleX(iparam1), sScaleX(iparam2), sScaleY(iparam3), sScaleY(iparam4));
+ break;
+ case CDMF_FCLIPAREA:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ cdfCanvasClipArea(canvas, sfScaleX(dparam1), sfScaleX(dparam2), sfScaleY(dparam3), sfScaleY(dparam4));
+ break;
+ case CDMF_MATRIX:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &matrix[0], &matrix[1], &matrix[2], &matrix[3], &matrix[4], &matrix[5]);
+ cdCanvasTransform(canvas, matrix);
+ break;
+ case CDMF_RESETMATRIX:
+ cdCanvasTransform(canvas, NULL);
+ break;
+ case CDMF_WCLIPAREA:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ wdCanvasClipArea(canvas, dparam1, dparam2, dparam3, dparam4);
+ break;
+ case CDMF_LINE:
+ fscanf(file, "%d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4);
+ cdCanvasLine(canvas, sScaleX(iparam1), sScaleY(iparam2), sScaleX(iparam3), sScaleY(iparam4));
+ break;
+ case CDMF_FLINE:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ cdfCanvasLine(canvas, sfScaleX(dparam1), sfScaleY(dparam2), sfScaleX(dparam3), sfScaleY(dparam4));
+ break;
+ case CDMF_WLINE:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ wdCanvasLine(canvas, dparam1, dparam2, dparam3, dparam4);
+ break;
+ case CDMF_RECT:
+ fscanf(file, "%d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4);
+ cdCanvasRect(canvas, sScaleX(iparam1), sScaleX(iparam2), sScaleY(iparam3), sScaleY(iparam4));
+ break;
+ case CDMF_FRECT:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ cdfCanvasRect(canvas, sfScaleX(dparam1), sfScaleX(dparam2), sfScaleY(dparam3), sfScaleY(dparam4));
+ break;
+ case CDMF_WRECT:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ wdCanvasRect(canvas, dparam1, dparam2, dparam3, dparam4);
+ break;
+ case CDMF_BOX:
+ fscanf(file, "%d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4);
+ cdCanvasBox(canvas, sScaleX(iparam1), sScaleX(iparam2), sScaleY(iparam3), sScaleY(iparam4));
+ break;
+ case CDMF_WBOX:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ wdCanvasBox(canvas, dparam1, dparam2, dparam3, dparam4);
+ break;
+ case CDMF_FBOX:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ cdfCanvasBox(canvas, sfScaleX(dparam1), sfScaleX(dparam2), sfScaleY(dparam3), sfScaleY(dparam4));
+ break;
+ case CDMF_ARC:
+ fscanf(file, "%d %d %d %d %lg %lg", &iparam1, &iparam2, &iparam3, &iparam4, &dparam1, &dparam2);
+ cdCanvasArc(canvas, sScaleX(iparam1), sScaleY(iparam2), sScaleW(iparam3), sScaleH(iparam4), dparam1, dparam2);
+ break;
+ case CDMF_FARC:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4, &dparam5, &dparam6);
+ cdfCanvasArc(canvas, sfScaleX(dparam1), sfScaleY(dparam2), sfScaleW(dparam3), sfScaleH(dparam4), dparam5, dparam6);
+ break;
+ case CDMF_WARC:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4, &dparam5, &dparam6);
+ wdCanvasArc(canvas, dparam1, dparam2, dparam3, dparam4, dparam5, dparam6);
+ break;
+ case CDMF_SECTOR:
+ fscanf(file, "%d %d %d %d %lg %lg", &iparam1, &iparam2, &iparam3, &iparam4, &dparam1, &dparam2);
+ cdCanvasSector(canvas, sScaleX(iparam1), sScaleY(iparam2), sScaleW(iparam3), sScaleH(iparam4), dparam1, dparam2);
+ break;
+ case CDMF_FSECTOR:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4, &dparam5, &dparam6);
+ cdfCanvasSector(canvas, sfScaleX(dparam1), sfScaleY(dparam2), sfScaleW(dparam3), sfScaleH(dparam4), dparam5, dparam6);
+ break;
+ case CDMF_WSECTOR:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4, &dparam5, &dparam6);
+ wdCanvasSector(canvas, dparam1, dparam2, dparam3, dparam4, dparam5, dparam6);
+ break;
+ case CDMF_CHORD:
+ fscanf(file, "%d %d %d %d %lg %lg", &iparam1, &iparam2, &iparam3, &iparam4, &dparam1, &dparam2);
+ cdCanvasChord(canvas, sScaleX(iparam1), sScaleY(iparam2), sScaleW(iparam3), sScaleH(iparam4), dparam1, dparam2);
+ break;
+ case CDMF_FCHORD:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4, &dparam5, &dparam6);
+ cdfCanvasChord(canvas, sfScaleX(dparam1), sfScaleY(dparam2), sfScaleW(dparam3), sfScaleH(dparam4), dparam5, dparam6);
+ break;
+ case CDMF_WCHORD:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4, &dparam5, &dparam6);
+ wdCanvasChord(canvas, dparam1, dparam2, dparam3, dparam4, dparam5, dparam6);
+ break;
+ case CDMF_TEXT:
+ fscanf(file, "%d %d %[^\n]", &iparam1, &iparam2, TextBuffer);
+ cdCanvasText(canvas, sScaleX(iparam1), sScaleY(iparam2), TextBuffer);
+ break;
+ case CDMF_FTEXT:
+ fscanf(file, "%lg %lg %[^\n]", &dparam1, &dparam2, TextBuffer);
+ cdfCanvasText(canvas, sfScaleX(dparam1), sfScaleY(dparam2), TextBuffer);
+ break;
+ case CDMF_WTEXT:
+ fscanf(file, "%lg %lg %[^\n]", &dparam1, &dparam2, TextBuffer);
+ wdCanvasText(canvas, dparam1, dparam2, TextBuffer);
+ break;
+ case CDMF_BEGIN:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasBegin(canvas, iparam1);
+ break;
+ case CDMF_VERTEX:
+ fscanf(file, "%d %d", &iparam1, &iparam2);
+ cdCanvasVertex(canvas, sScaleX(iparam1), sScaleY(iparam2));
+ break;
+ case CDMF_FVERTEX:
+ fscanf(file, "%lg %lg", &dparam1, &dparam2);
+ cdfCanvasVertex(canvas, sfScaleX(dparam1), sfScaleY(dparam2));
+ break;
+ case CDMF_WVERTEX:
+ fscanf(file, "%lg %lg", &dparam1, &dparam2);
+ wdCanvasVertex(canvas, dparam1, dparam2);
+ break;
+ case CDMF_END:
+ cdCanvasEnd(canvas);
+ break;
+ case CDMF_MARK:
+ fscanf(file, "%d %d", &iparam1, &iparam2);
+ cdCanvasMark(canvas, sScaleX(iparam1), sScaleY(iparam2));
+ break;
+ case CDMF_WMARK:
+ fscanf(file, "%lg %lg", &dparam1, &dparam2);
+ wdCanvasMark(canvas, dparam1, dparam2);
+ break;
+ case CDMF_BACKOPACITY:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasBackOpacity(canvas, iparam1);
+ break;
+ case CDMF_WRITEMODE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasWriteMode(canvas, iparam1);
+ break;
+ case CDMF_LINESTYLE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasLineStyle(canvas, iparam1);
+ break;
+ case CDMF_LINEWIDTH:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasLineWidth(canvas, sScaleS(iparam1));
+ break;
+ case CDMF_LINECAP:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasLineCap(canvas, iparam1);
+ break;
+ case CDMF_LINEJOIN:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasLineJoin(canvas, iparam1);
+ break;
+ case CDMF_LINESTYLEDASHES:
+ fscanf(file, "%d", &iparam1);
+ dashes = (int*)malloc(iparam1*sizeof(int));
+ for (c = 0; c < iparam1; c++)
+ fscanf(file, "%d", &dashes[c]);
+ cdCanvasLineStyleDashes(canvas, dashes, iparam1);
+ free(dashes);
+ break;
+ case CDMF_FILLMODE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasFillMode(canvas, iparam1);
+ break;
+ case CDMF_INTERIORSTYLE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasInteriorStyle(canvas, iparam1);
+ break;
+ case CDMF_HATCH:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasHatch(canvas, iparam1);
+ break;
+ case CDMF_STIPPLE:
+ fscanf(file, "%d %d", &iparam1, &iparam2);
+ t = iparam1 * iparam2;
+ stipple = (unsigned char*)malloc(t);
+ _stipple = stipple;
+ for (c = 0; c < t; c++)
+ {
+ fscanf(file, "%d", &iparam3);
+ *_stipple++ = (unsigned char)iparam3;
+ }
+ cdCanvasStipple(canvas, iparam1, iparam2, stipple);
+ free(stipple);
+ break;
+ case CDMF_PATTERN:
+ fscanf(file, "%d %d", &iparam1, &iparam2);
+ t = iparam1 * iparam2;
+ pattern = (long int*)malloc(t * sizeof(long));
+ _pattern = pattern;
+ for (c = 0; c < t; c++)
+ {
+ fscanf(file, "%d %d %d", &iparam3, &iparam4, &iparam5);
+ *_pattern++ = cdEncodeColor((unsigned char)iparam3, (unsigned char)iparam4, (unsigned char)iparam5);
+ }
+ cdCanvasPattern(canvas, iparam1, iparam2, pattern);
+ free(pattern);
+ break;
+ case CDMF_OLDFONT:
+ fscanf(file, "%d %d %d", &iparam1, &iparam2, &iparam3);
+ if (iparam1 < 0 || iparam1 > 3) break;
+ if (iparam3 < 0)
+ {
+ iparam3 = -sScaleH(abs(iparam3));
+ if (iparam3 > -5) iparam3 = -5;
+ }
+ else
+ {
+ iparam3 = sScaleH(abs(iparam3));
+ if (iparam3 < 5) iparam3 = 5;
+ }
+ cdCanvasFont(canvas, font_family[iparam1], iparam2, iparam3);
+ break;
+ case CDMF_FONT:
+ fscanf(file, "%d %d %[^\n]", &iparam2, &iparam3, TextBuffer);
+ if (iparam3 < 0)
+ {
+ iparam3 = -sScaleH(abs(iparam3));
+ if (iparam3 > -5) iparam3 = -5;
+ }
+ else
+ {
+ iparam3 = sScaleH(abs(iparam3));
+ if (iparam3 < 5) iparam3 = 5;
+ }
+ cdCanvasFont(canvas, TextBuffer, iparam2, iparam3);
+ break;
+ case CDMF_NATIVEFONT:
+ fscanf(file, "%[^\n]", TextBuffer);
+ cdCanvasNativeFont(canvas, TextBuffer);
+ break;
+ case CDMF_TEXTALIGNMENT:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasTextAlignment(canvas, iparam1);
+ break;
+ case CDMF_TEXTORIENTATION:
+ fscanf(file, "%lg", &dparam1);
+ cdCanvasTextOrientation(canvas, dparam1);
+ break;
+ case CDMF_MARKTYPE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasMarkType(canvas, iparam1);
+ break;
+ case CDMF_MARKSIZE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasMarkSize(canvas, sScaleS(iparam1));
+ break;
+ case CDMF_PALETTE:
+ fscanf(file, "%d %d", &iparam1, &iparam2);
+ _palette = palette = (long int*)malloc(iparam1);
+ for (c = 0; c < iparam1; c++)
+ {
+ fscanf(file, "%d %d %d", &iparam3, &iparam4, &iparam5);
+ *_palette++ = cdEncodeColor((unsigned char)iparam3, (unsigned char)iparam4, (unsigned char)iparam5);
+ }
+ cdCanvasPalette(canvas, iparam1, palette, iparam2);
+ free(palette);
+ break;
+ case CDMF_BACKGROUND:
+ fscanf(file, "%d %d %d", &iparam1, &iparam2, &iparam3);
+ cdCanvasSetBackground(canvas, cdEncodeColor((unsigned char)iparam1, (unsigned char)iparam2, (unsigned char)iparam3));
+ break;
+ case CDMF_FOREGROUND:
+ fscanf(file, "%d %d %d", &iparam1, &iparam2, &iparam3);
+ cdCanvasSetForeground(canvas, cdEncodeColor((unsigned char)iparam1, (unsigned char)iparam2, (unsigned char)iparam3));
+ break;
+ case CDMF_PUTIMAGERGB:
+ fscanf(file, "%d %d %d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4, &iparam5, &iparam6);
+ t = iparam1 * iparam2;
+ _red = red = (unsigned char*) malloc(t);
+ _green = green = (unsigned char*) malloc(t);
+ _blue = blue = (unsigned char*) malloc(t);
+ for (c = 0; c < t; c++)
+ {
+ fscanf(file, "%d %d %d", &iparam7, &iparam8, &iparam9);
+ *_red++ = (unsigned char)iparam7;
+ *_green++ = (unsigned char)iparam8;
+ *_blue++ = (unsigned char)iparam9;
+ }
+ cdCanvasPutImageRectRGB(canvas, iparam1, iparam2, red, green, blue, sScaleX(iparam3), sScaleY(iparam4), sScaleW(iparam5), sScaleH(iparam6), 0, 0, 0, 0);
+ free(red);
+ free(green);
+ free(blue);
+ break;
+ case CDMF_PUTIMAGERGBA:
+ fscanf(file, "%d %d %d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4, &iparam5, &iparam6);
+ t = iparam1 * iparam2;
+ _red = red = (unsigned char*) malloc(t);
+ _green = green = (unsigned char*) malloc(t);
+ _blue = blue = (unsigned char*) malloc(t);
+ _alpha = alpha = (unsigned char*) malloc(t);
+ for (c = 0; c < t; c++)
+ {
+ fscanf(file, "%d %d %d %d", &iparam7, &iparam8, &iparam9, &iparam10);
+ *_red++ = (unsigned char)iparam7;
+ *_green++ = (unsigned char)iparam8;
+ *_blue++ = (unsigned char)iparam9;
+ *_alpha++ = (unsigned char)iparam10;
+ }
+ cdCanvasPutImageRectRGBA(canvas, iparam1, iparam2, red, green, blue, alpha, sScaleX(iparam3), sScaleY(iparam4), sScaleW(iparam5), sScaleH(iparam6), 0, 0, 0, 0);
+ free(red);
+ free(green);
+ free(blue);
+ free(alpha);
+ break;
+ case CDMF_PUTIMAGEMAP:
+ fscanf(file, "%d %d %d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4, &iparam5, &iparam6);
+ t = iparam1 * iparam2;
+ n = 0;
+ _index = index = (unsigned char*) malloc(t);
+ for (c = 0; c < t; c++)
+ {
+ fscanf(file, "%d", &iparam7);
+ *_index++ = (unsigned char)iparam7;
+ if (iparam7 > n)
+ n = iparam7;
+ }
+ _colors = colors = (long int*)malloc(n);
+ for (c = 0; c < n; c++)
+ {
+ fscanf(file, "%d %d %d", &iparam7, &iparam8, &iparam9);
+ *_colors++ = cdEncodeColor((unsigned char)iparam7, (unsigned char)iparam8, (unsigned char)iparam9);
+ }
+ cdCanvasPutImageRectMap(canvas, iparam1, iparam2, index, colors, sScaleX(iparam3), sScaleY(iparam4), sScaleW(iparam5), sScaleH(iparam6), 0, 0, 0, 0);
+ free(index);
+ free(colors);
+ break;
+ case CDMF_PIXEL:
+ fscanf(file, "%d %d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4, &iparam5);
+ cdCanvasPixel(canvas, sScaleX(iparam1), sScaleY(iparam2), cdEncodeColor((unsigned char)iparam3, (unsigned char)iparam4, (unsigned char)iparam5));
+ break;
+ case CDMF_SCROLLAREA:
+ fscanf(file, "%d %d %d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4, &iparam5, &iparam6);
+ cdCanvasScrollArea(canvas, sScaleX(iparam1), sScaleX(iparam2), sScaleY(iparam3), sScaleY(iparam4), sScaleX(iparam5), sScaleY(iparam6));
+ break;
+ case CDMF_WVECTORTEXT:
+ fscanf(file, "%lg %lg %[^\n]", &dparam1, &dparam2, TextBuffer);
+ wdCanvasVectorText(canvas, dparam1, dparam2, TextBuffer);
+ break;
+ case CDMF_WMULTILINEVECTORTEXT:
+ fscanf(file, "%lg %lg %[^\n]", &dparam1, &dparam2, TextBuffer);
+ wdCanvasVectorText(canvas, dparam1, dparam2, TextBuffer);
+ break;
+ case CDMF_VECTORTEXT:
+ fscanf(file, "%d %d %[^\n]", &iparam1, &iparam2, TextBuffer);
+ cdCanvasVectorText(canvas, iparam1, iparam2, TextBuffer);
+ break;
+ case CDMF_MULTILINEVECTORTEXT:
+ fscanf(file, "%d %d %[^\n]", &iparam1, &iparam2, TextBuffer);
+ cdCanvasVectorText(canvas, iparam1, iparam2, TextBuffer);
+ break;
+ case CDMF_WVECTORCHARSIZE:
+ fscanf(file, "%lg", &dparam1);
+ wdCanvasVectorCharSize(canvas, dparam1);
+ break;
+ case CDMF_WVECTORTEXTSIZE:
+ fscanf(file, "%lg %lg %[^\n]", &dparam1, &dparam2, TextBuffer);
+ wdCanvasVectorTextSize(canvas, dparam1, dparam2, TextBuffer);
+ break;
+ case CDMF_WVECTORTEXTDIRECTION:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ wdCanvasVectorTextDirection(canvas, dparam1, dparam2, dparam3, dparam4);
+ break;
+ case CDMF_VECTORCHARSIZE:
+ fscanf(file, "%d", &iparam1);
+ cdCanvasVectorCharSize(canvas, iparam1);
+ break;
+ case CDMF_VECTORTEXTSIZE:
+ fscanf(file, "%d %d %[^\n]", &iparam1, &iparam2, TextBuffer);
+ cdCanvasVectorTextSize(canvas, iparam1, iparam2, TextBuffer);
+ break;
+ case CDMF_VECTORTEXTDIRECTION:
+ fscanf(file, "%d %d %d %d", &iparam1, &iparam2, &iparam3, &iparam4);
+ cdCanvasVectorTextDirection(canvas, iparam1, iparam2, iparam3, iparam4);
+ break;
+ case CDMF_VECTORFONT:
+ fscanf(file, "%[^\n]", TextBuffer);
+ cdCanvasVectorFont(canvas, TextBuffer);
+ break;
+ case CDMF_VECTORTEXTTRANSFORM:
+ fscanf(file, "%lg %lg %lg %lg %lg %lg", &matrix[0], &matrix[1], &matrix[2], &matrix[3], &matrix[4], &matrix[5]);
+ cdCanvasVectorTextTransform(canvas, matrix);
+ break;
+ case CDMF_WINDOW:
+ fscanf(file, "%lg %lg %lg %lg", &dparam1, &dparam2, &dparam3, &dparam4);
+ wdCanvasWindow(canvas, dparam1, dparam2, dparam3, dparam4);
+ break;
+ default:
+ fclose(file);
+ return CD_ERROR;
+ }
+ }
+
+ fclose(file);
+
+ return CD_OK;
+}
+
+/*******************/
+/* Canvas Creation */
+/*******************/
+
+void cdcreatecanvasMF(cdCanvas *canvas, void *data)
+{
+ char filename[10240] = "";
+ char* strdata = (char*)data;
+ double w_mm = INT_MAX*3.78, h_mm = INT_MAX*3.78, res = 3.78;
+ cdCtxCanvas* ctxcanvas;
+ int size;
+
+ strdata += cdGetFileName(strdata, filename);
+ if (filename[0] == 0)
+ return;
+
+ sscanf(strdata, "%lgx%lg %lg", &w_mm, &h_mm, &res);
+
+ ctxcanvas = (cdCtxCanvas *)malloc(sizeof(cdCtxCanvas));
+ memset(ctxcanvas, 0, sizeof(cdCtxCanvas));
+
+ ctxcanvas->file = fopen(filename, "w");
+ if (!ctxcanvas->file)
+ {
+ free(ctxcanvas);
+ return;
+ }
+
+ size = strlen(filename);
+ ctxcanvas->filename = malloc(size+1);
+ memcpy(ctxcanvas->filename, filename, size+1);
+
+ ctxcanvas->canvas = canvas;
+
+ /* update canvas context */
+ canvas->w = (int)(w_mm * res);
+ canvas->h = (int)(h_mm * res);
+ canvas->w_mm = w_mm;
+ canvas->h_mm = h_mm;
+ canvas->bpp = 24;
+ canvas->xres = res;
+ canvas->yres = res;
+ canvas->ctxcanvas = ctxcanvas;
+
+ ctxcanvas->last_line_style = -1;
+ ctxcanvas->last_fill_mode = -1;
+
+ fprintf(ctxcanvas->file, "CDMF %d %d\n", canvas->w, canvas->h);
+}
+
+void cdinittableMF(cdCanvas* canvas)
+{
+ canvas->cxFlush = cdflush;
+ canvas->cxClear = cdclear;
+ canvas->cxPixel = cdpixel;
+ canvas->cxLine = cdline;
+ canvas->cxPoly = cdpoly;
+ canvas->cxRect = cdrect;
+ canvas->cxBox = cdbox;
+ canvas->cxArc = cdarc;
+ canvas->cxSector = cdsector;
+ canvas->cxChord = cdchord;
+ canvas->cxText = cdtext;
+ canvas->cxPutImageRectRGB = cdputimagerectrgb;
+ canvas->cxPutImageRectRGBA = cdputimagerectrgba;
+ canvas->cxPutImageRectMap = cdputimagerectmap;
+ canvas->cxScrollArea = cdscrollarea;
+ canvas->cxFLine = cdfline;
+ canvas->cxFPoly = cdfpoly;
+ canvas->cxFRect = cdfrect;
+ canvas->cxFBox = cdfbox;
+ canvas->cxFArc = cdfarc;
+ canvas->cxFSector = cdfsector;
+ canvas->cxFChord = cdfchord;
+ canvas->cxFText = cdftext;
+ canvas->cxClip = cdclip;
+ canvas->cxClipArea = cdcliparea;
+ canvas->cxBackOpacity = cdbackopacity;
+ canvas->cxWriteMode = cdwritemode;
+ canvas->cxLineStyle = cdlinestyle;
+ canvas->cxLineWidth = cdlinewidth;
+ canvas->cxLineCap = cdlinecap;
+ canvas->cxLineJoin = cdlinejoin;
+ canvas->cxInteriorStyle = cdinteriorstyle;
+ canvas->cxHatch = cdhatch;
+ canvas->cxStipple = cdstipple;
+ canvas->cxPattern = cdpattern;
+ canvas->cxFont = cdfont;
+ canvas->cxNativeFont = cdnativefont;
+ canvas->cxTextAlignment = cdtextalignment;
+ canvas->cxTextOrientation = cdtextorientation;
+ canvas->cxPalette = cdpalette;
+ canvas->cxBackground = cdbackground;
+ canvas->cxForeground = cdforeground;
+ canvas->cxFClipArea = cdfcliparea;
+ canvas->cxTransform = cdtransform;
+
+ canvas->cxKillCanvas = (void (*)(cdCtxCanvas*))cdkillcanvasMF;
+}
+
+static cdContext cdMetafileContext =
+{
+ CD_CAP_ALL & ~(CD_CAP_GETIMAGERGB | CD_CAP_IMAGESRV |
+ CD_CAP_REGION | CD_CAP_FONTDIM | CD_CAP_TEXTSIZE),
+ 0,
+ cdcreatecanvasMF,
+ cdinittableMF,
+ cdplay,
+ cdregistercallback,
+};
+
+cdContext* cdContextMetafile(void)
+{
+ return &cdMetafileContext;
+}