1 /***************************************************************************
2 * export.cpp is part of Math Graphic Library
3 * Copyright (C) 2007-2016 Alexey Balakin <mathgl.abalakin@gmail.ru> *
4 * *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU Lesser General Public License as *
7 * published by the Free Software Foundation; either version 3 of the *
8 * License, or (at your option) any later version. *
9 * *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
14 * *
15 * You should have received a copy of the GNU Lesser General Public *
16 * License along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
20 #include <time.h>
21 #include <stdarg.h>
22
23 #if defined(WIN32) || defined(_MSC_VER) || defined(__BORLANDC__)
24 #include <windows.h>
25 #else
26 #include <unistd.h>
27 #endif
28
29 #include "mgl2/canvas.h"
30 #include "mgl2/canvas_cf.h"
31
32 #if MGL_HAVE_PNG
33 #include <png.h>
34 #endif
35
36 #if MGL_HAVE_JPEG
37 extern "C" {
38 #include <jpeglib.h>
39 }
40 #endif
41
42 #if MGL_HAVE_GIF
43 #include <gif_lib.h>
44 #endif
45 //-----------------------------------------------------------------------------
mgl_pnga_save(const char * fname,int w,int h,unsigned char ** p)46 int MGL_NO_EXPORT mgl_pnga_save(const char *fname, int w, int h, unsigned char **p)
47 {
48 #if MGL_HAVE_PNG
49 bool fl = strcmp(fname,"-");
50 FILE *fp = fl ? fopen(fname, "wb") : stdout;
51 if (!fp) return 1;
52
53 png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING,0,0,0);
54 if (png_ptr)
55 {
56 png_infop info_ptr = png_create_info_struct(png_ptr);
57 if (info_ptr)
58 {
59 png_init_io(png_ptr, fp);
60 png_set_filter(png_ptr, 0, PNG_ALL_FILTERS);
61 png_set_compression_level(png_ptr, Z_BEST_COMPRESSION);
62 png_set_IHDR(png_ptr, info_ptr, w, h, 8,
63 PNG_COLOR_TYPE_RGB_ALPHA,
64 PNG_INTERLACE_NONE, PNG_COMPRESSION_TYPE_DEFAULT,
65 PNG_FILTER_TYPE_DEFAULT);
66 png_set_rows(png_ptr, info_ptr, p);
67 png_write_png(png_ptr, info_ptr, PNG_TRANSFORM_IDENTITY, 0);
68 // png_write_end(png_ptr, info_ptr);
69 }
70 png_destroy_write_struct(&png_ptr, &info_ptr);
71 }
72 if(fl) fclose(fp);
73 return 0;
74 #else
75 mgl_set_global_warn(_("PNG support was disabled. Please, enable it and rebuild MathGL."));
76 return 1;
77 #endif
78 }
79 //-----------------------------------------------------------------------------
mgl_png_save(const char * fname,int w,int h,unsigned char ** p)80 int MGL_NO_EXPORT mgl_png_save(const char *fname, int w, int h, unsigned char **p)
81 {
82 #if MGL_HAVE_PNG
83 bool fl = strcmp(fname,"-");
84 FILE *fp = fl ? fopen(fname, "wb") : stdout;
85 if (!fp) return 1;
86
87 png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING,0,0,0);
88 if (png_ptr)
89 {
90 png_infop info_ptr = png_create_info_struct(png_ptr);
91 if (info_ptr)
92 {
93 png_init_io(png_ptr, fp);
94 png_set_filter(png_ptr, 0, PNG_ALL_FILTERS);
95 png_set_compression_level(png_ptr, Z_BEST_COMPRESSION);
96 png_set_IHDR(png_ptr, info_ptr, w, h, 8,
97 PNG_COLOR_TYPE_RGB,
98 PNG_INTERLACE_NONE, PNG_COMPRESSION_TYPE_DEFAULT,
99 PNG_FILTER_TYPE_DEFAULT);
100 png_set_rows(png_ptr, info_ptr, p);
101 png_write_png(png_ptr, info_ptr, PNG_TRANSFORM_IDENTITY, 0);
102 // png_write_end(png_ptr, info_ptr);
103 }
104 png_destroy_write_struct(&png_ptr, &info_ptr);
105 }
106 if(fl) fclose(fp);
107 return 0;
108 #else
109 mgl_set_global_warn(_("PNG support was disabled. Please, enable it and rebuild MathGL."));
110 return 1;
111 #endif
112 }
113 //-----------------------------------------------------------------------------
mgl_bmp_save(const char * fname,int w,int h,unsigned char ** p)114 int MGL_NO_EXPORT mgl_bmp_save(const char *fname, int w, int h, unsigned char **p)
115 {
116 bool fl = strcmp(fname,"-");
117 FILE *fp = fl ? fopen(fname, "wb") : stdout;
118 if (!fp) return 1;
119
120 char z[4] = {0,0,0,0};
121 unsigned u = w*h*3 + 54;
122 // BITMAPFILEHEADER
123 fwrite("BM",2,1,fp); fwrite(&u,4,1,fp);
124 fwrite(z,4,1,fp); u=54; fwrite(&u,4,1,fp);
125 // BITMAPINFOHEADER
126 u=40; fwrite(&u,4,1,fp); fwrite(&w,4,1,fp); fwrite(&h,4,1,fp);
127 unsigned short pp=1;
128 fwrite(&pp,2,1,fp); pp=24; fwrite(&pp,2,1,fp); u = w*h*3;
129 fwrite(z,4,1,fp); fwrite(&u,4,1,fp);
130 fwrite(z,4,1,fp); fwrite(z,4,1,fp);
131 fwrite(z,4,1,fp); fwrite(z,4,1,fp);
132 // image
133 for(long i=h-1;i>=0;i--) for(long j=0;j<w;j++)
134 {
135 const unsigned char *q = p[i]+3*j;
136 fwrite(q+2,1,1,fp);
137 fwrite(q+1,1,1,fp);
138 fwrite(q+0,1,1,fp);
139 }
140 if(fl) fclose(fp);
141 return 0;
142 }
143 //-----------------------------------------------------------------------------
mgl_tga_save(const char * fname,int w,int h,unsigned char ** p)144 int MGL_NO_EXPORT mgl_tga_save(const char *fname, int w, int h, unsigned char **p)
145 {
146 bool fl = strcmp(fname,"-");
147 FILE *fp = fl ? fopen(fname, "wb") : stdout;
148 if (!fp) return 1;
149 // header
150 char head[14]={0,0,2, 0,0,0,0,0, 0,0,0,0, 32,0};
151 fwrite(head,12,1,fp);
152 fwrite(&w,2,1,fp); fwrite(&h,2,1,fp);
153 fwrite(head+12,2,1,fp);
154 // image
155 for(long i=h-1;i>=0;i--) for(long j=0;j<w;j++)
156 {
157 const unsigned char *q = p[i]+4*j;
158 fwrite(q+2,1,1,fp);
159 fwrite(q+1,1,1,fp);
160 fwrite(q+0,1,1,fp);
161 fwrite(q+3,1,1,fp);
162 }
163 if(fl) fclose(fp);
164 return 0;
165 }
166 //-----------------------------------------------------------------------------
mgl_jpeg_save(const char * fname,int w,int h,unsigned char ** p)167 int MGL_NO_EXPORT mgl_jpeg_save(const char *fname, int w, int h, unsigned char **p)
168 {
169 #if MGL_HAVE_JPEG
170 struct jpeg_compress_struct cinfo;
171 struct jpeg_error_mgr jerr;
172
173 bool fl = strcmp(fname,"-");
174 FILE *fp = fl ? fopen(fname, "wb") : stdout;
175 if (!fp) return 1;
176
177 cinfo.err = jpeg_std_error(&jerr);
178 jpeg_create_compress(&cinfo);
179 jpeg_stdio_dest(&cinfo, fp);
180 cinfo.image_width = w;
181 cinfo.image_height = h;
182 cinfo.input_components = 3;
183 cinfo.in_color_space = JCS_RGB;
184 jpeg_set_defaults(&cinfo);
185 jpeg_start_compress(&cinfo, TRUE);
186 jpeg_write_scanlines(&cinfo, p, h);
187 jpeg_finish_compress(&cinfo);
188 jpeg_destroy_compress(&cinfo);
189 if(fl) fclose(fp);
190 return 0;
191 #else
192 mgl_set_global_warn(_("JPEG support was disabled. Please, enable it and rebuild MathGL."));
193 return 1;
194 #endif
195 }
196 //-----------------------------------------------------------------------------
mgl_printf(void * fp,bool gz,const char * str,...)197 void MGL_NO_EXPORT mgl_printf(void *fp, bool gz, const char *str, ...) // NOTE This function is not thread-safe
198 {
199 static char buf[1024];
200 va_list lst;
201 va_start(lst,str);
202 vsnprintf(buf,1023,str,lst); buf[1023]=0;
203 va_end(lst);
204 if(gz) gzprintf((gzFile)fp, "%s", buf);
205 else fprintf((FILE *)fp, "%s", buf);
206 }
207 //---------------------------------------------------------------------------
mgl_sprintf(const char * str,...)208 std::string MGL_NO_EXPORT mgl_sprintf(const char *str, ...)
209 {
210 char *buf=new char[1024];
211 va_list lst;
212 va_start(lst,str);
213 vsnprintf(buf,1023,str,lst); buf[1023]=0;
214 va_end(lst);
215 std::string res = buf; delete []buf;
216 return res;
217 }
218 //---------------------------------------------------------------------------
mgl_bps_save(const char * fname,int w,int h,unsigned char ** p)219 int MGL_NO_EXPORT mgl_bps_save(const char *fname, int w, int h, unsigned char **p)
220 {
221 time_t now; time(&now);
222 bool gz = fname[strlen(fname)-1]=='z';
223
224 void *fp;
225 if(!strcmp(fname,"-")) fp = stdout; // allow to write in stdout
226 else
227 {
228 fp = gz ? (void*)gzopen(fname,"wt") : (void*)fopen(fname,"wt");
229 if(gz)
230 {
231 unsigned len = strlen(fname), pos=0;
232 char *buf = new char[len+4];
233 memcpy(buf,fname,len);
234 if(buf[len-3]=='.') pos = len-2;
235 else if(buf[len-2]=='.') pos = len-1;
236 else { buf[len-1]='.'; pos = len; }
237 if(pos) { buf[pos]=buf[pos+1]='b'; buf[pos+2]=0; }
238 FILE *fb = fopen(buf,"w");
239 fprintf(fb, "%%%%BoundingBox: 0 0 %d %d\n", w, h);
240 fclose(fb); delete []buf;
241 }
242 }
243 mgl_printf(fp, gz, "%%!PS-Adobe-3.0 EPSF-3.0\n%%%%BoundingBox: 0 0 %d %d\n",w,h);
244 mgl_printf(fp, gz, "%%%%Created by MathGL library\n%%%%Title: %s\n", fname);
245 mgl_printf(fp, gz, "%%%%CreationDate: %s\n",ctime(&now));
246 mgl_printf(fp, gz, "%d %d 8 [1 0 0 1 0 0] {currentfile %d string readhexstring pop} false 3 colorimage\n",
247 w,h,w*h/40);
248 for(long j=0;j<h;j++) for(long i=0;i<w;i++)
249 {
250 if((i+w*j)%40==0 && i+j>0) mgl_printf(fp, gz, "\n");
251 long jj=h-1-j;
252 mgl_printf(fp, gz, "%02x%02x%02x",p[jj][3*i],p[jj][3*i+1],p[jj][3*i+2]);
253 }
254 mgl_printf(fp, gz, "\n\nshowpage\n%%%%EOF\n");
255 if(strcmp(fname,"-")) { if(gz) gzclose((gzFile)fp); else fclose((FILE *)fp); }
256 return 0;
257 }
258 //-----------------------------------------------------------------------------
mgl_gif_save(const char * fname,int w,int h,unsigned char ** l)259 int MGL_NO_EXPORT mgl_gif_save(const char *fname, int w, int h, unsigned char **l)
260 {
261 #if MGL_HAVE_GIF
262 #if GIFLIB_MAJOR>=5
263 GifFileType *fg = EGifOpenFileName(fname, 0, 0);
264 #else
265 GifFileType *fg = EGifOpenFileName(fname, 0);
266 #endif
267 // define colormap
268 GifColorType col[256];
269 memset(col,0,256*sizeof(GifColorType));
270 for(int i=0;i<6;i++) for(int j=0;j<6;j++) for(int k=0;k<6;k++)
271 {
272 long m = i+6*(j+6*k); // part 1
273 col[m].Red = 51*i;
274 col[m].Green=51*j;
275 col[m].Blue =51*k;
276 }
277 // write header
278 #if GIFLIB_MAJOR>=5
279 ColorMapObject *gmap = GifMakeMapObject(256, col);
280 EGifPutScreenDesc(fg, w, h, 256,0,gmap);
281 GifFreeMapObject(gmap);
282 #else
283 ColorMapObject *gmap = MakeMapObject(256, col);
284 EGifPutScreenDesc(fg, w, h, 256,0,gmap);
285 FreeMapObject(gmap);
286 #endif
287 // write frame
288 EGifPutImageDesc(fg, 0, 0, w, h, 0, 0);
289 GifPixelType *line = new GifPixelType[w*h];
290 for(long m=0;m<w*h;m++)
291 {
292 long ii = 3*(m%w), k = m/w;
293 int i = (l[k][ii]+25)/51;
294 int j = (l[k][ii+1]+25)/51;
295 k = (l[k][ii+2]+25)/51;
296 line[m] = i+6*(j+6*k);
297 }
298 EGifPutLine(fg, line, w*h);
299 #if GIFLIB_MAJOR>5 || (GIFLIB_MAJOR==5 && GIFLIB_MINOR>0)
300 EGifCloseFile(fg,0);
301 #else
302 EGifCloseFile(fg);
303 #endif
304 delete []line; return 0;
305 #else
306 mgl_set_global_warn(_("GIF support was disabled. Please, enable it and rebuild MathGL."));
307 return 1;
308 #endif
309 }
310 //-----------------------------------------------------------------------------
311 //
312 // Save animation
313 //
314 //-----------------------------------------------------------------------------
StartGIF(const char * fname,int ms)315 void mglCanvas::StartGIF(const char *fname, int ms)
316 {
317 #if MGL_HAVE_GIF
318 std::string fn=fname;
319 if(fn.empty()) { fn=PlotId+".gif"; fname = fn.c_str(); }
320 #if GIFLIB_MAJOR>5 || (GIFLIB_MAJOR==5 && GIFLIB_MINOR>0)
321 if(gif) EGifCloseFile(gif,0);
322 #else
323 if(gif) EGifCloseFile(gif);
324 #endif
325 #if GIFLIB_MAJOR>=5
326 gif = EGifOpenFileName(fname, 0, 0);
327 EGifSetGifVersion(gif,true);
328 #else
329 EGifSetGifVersion("89a");
330 gif = EGifOpenFileName(fname, 0);
331 #endif
332 // get picture sizes
333 // NOTE: you shouldn't call SetSize() after StartGIF() !!!
334 long width, height;
335 unsigned char *f=0, **l=GetRGBLines(width, height, f);
336 if(f) free(f);
337 if(l) free(l);
338 // define colormap
339 GifColorType col[256];
340 memset(col,0,256*sizeof(GifColorType));
341 for(int i=0;i<6;i++) for(int j=0;j<6;j++) for(int k=0;k<6;k++)
342 {
343 long m = i+6*(j+6*k); // part 1
344 col[m].Red = 51*i;
345 col[m].Green=51*j;
346 col[m].Blue =51*k;
347 }
348 // write header
349 #if GIFLIB_MAJOR>=5
350 ColorMapObject *gmap = GifMakeMapObject(256, col);
351 EGifPutScreenDesc(gif, width, height, 256,0,gmap);
352 GifFreeMapObject(gmap);
353 #else
354 ColorMapObject *gmap = MakeMapObject(256, col);
355 EGifPutScreenDesc(gif, width, height, 256,0,gmap);
356 FreeMapObject(gmap);
357 #endif
358 // put animation parameters
359 ms /= 10;
360 unsigned char ext1[11] = {0x4E, 0x45, 0x54, 0x53, 0x43, 0x41, 0x50, 0x45, 0x32, 0x2E, 0x30};
361 unsigned char ext2[9] = {0x08, (unsigned char)(ms%256), (unsigned char)(ms/256), 0xff};
362 unsigned char ext3[3] = {0x01, 0xff, 0xff};
363 #if GIFLIB_MAJOR>=5
364 EGifPutExtensionLeader(gif,0xff);
365 EGifPutExtensionBlock(gif,11,ext1);
366 EGifPutExtensionBlock(gif,3,ext3);
367 EGifPutExtensionTrailer(gif);
368 EGifPutExtension(gif,0xf9,4,ext2);
369 #else
370 EGifPutExtensionFirst(gif,0xff,11,ext1);
371 EGifPutExtensionLast(gif,0xff,3,ext3);
372 EGifPutExtension(gif,0xf9,4,ext2);
373 #endif
374 #else
375 mgl_set_global_warn(_("GIF support was disabled. Please, enable it and rebuild MathGL."));
376 #endif
377 }
378 //-----------------------------------------------------------------------------
CloseGIF()379 void mglCanvas::CloseGIF()
380 {
381 #if MGL_HAVE_GIF
382 #if GIFLIB_MAJOR>5 || (GIFLIB_MAJOR==5 && GIFLIB_MINOR>0)
383 if(gif) EGifCloseFile(gif,0);
384 #else
385 if(gif) EGifCloseFile(gif);
386 #endif
387 #else
388 mgl_set_global_warn(_("GIF support was disabled. Please, enable it and rebuild MathGL."));
389 #endif
390 gif = 0;
391 }
392 //-----------------------------------------------------------------------------
NewFrame()393 int mglCanvas::NewFrame()
394 {
395 Clf(); Identity(); CurFrameId++;
396 return CurFrameId-1;
397 }
398 //-----------------------------------------------------------------------------
EndFrame()399 void mglCanvas::EndFrame()
400 {
401 Finish();
402 if(get(MGL_VECT_FRAME)) PushDrwDat();
403 #if MGL_HAVE_GIF
404 if(!gif) return;
405 long width, height, n;
406 unsigned char *f=0, **l=GetRGBLines(width, height, f);
407 n = width*height;
408 if(!l) return;
409 EGifPutImageDesc(gif, 0, 0, width, height, 0, 0);
410 GifPixelType *line = new GifPixelType[n];
411 for(long m=0;m<n;m++)
412 {
413 long ii = 3*(m%width), k = m/width;
414 int i = (l[k][ii]+25)/51;
415 int j = (l[k][ii+1]+25)/51;
416 k = (l[k][ii+2]+25)/51;
417 line[m] = i+6*(j+6*k);
418 }
419 EGifPutLine(gif, line, n);
420 delete []line; free(l);
421 if(f) free(f);
422 #endif
423 }
424 //-----------------------------------------------------------------------------
DelFrame(long i)425 void mglCanvas::DelFrame(long i)
426 {
427 #if MGL_HAVE_PTHREAD
428 pthread_mutex_lock(&mutexDrw);
429 if(get(MGL_VECT_FRAME)) DrwDat.erase(DrwDat.begin()+i);
430 pthread_mutex_unlock(&mutexDrw);
431 #else
432 #pragma omp critical(drw)
433 if(get(MGL_VECT_FRAME)) DrwDat.erase(DrwDat.begin()+i);
434 #endif
435 CurFrameId--;
436 }
437 //-----------------------------------------------------------------------------
438 #undef _GR_
439 #define _GR_ ((mglCanvas *)(*gr))
440 #define _Gr_ ((mglCanvas *)(gr))
441 //-----------------------------------------------------------------------------
mgl_write_png(HMGL gr,const char * fname,const char *)442 void MGL_EXPORT mgl_write_png(HMGL gr, const char *fname,const char *)
443 {
444 long w,h; unsigned char *f=0, **p=0;
445 p =_Gr_->GetRGBLines(w,h,f,true);
446 if(p)
447 {
448 std::string fn=fname;
449 if(fn.empty()) { fn=gr->PlotId+".png"; fname = fn.c_str(); }
450 if(mgl_pnga_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
451 free(p); if(f) free(f);
452 }
453 }
mgl_write_png_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)454 void MGL_EXPORT mgl_write_png_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
455 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
456 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
457 mgl_write_png(_GR_,s,f); delete []s; delete []f; }
458 //-----------------------------------------------------------------------------
mgl_write_png_solid(HMGL gr,const char * fname,const char *)459 void MGL_EXPORT mgl_write_png_solid(HMGL gr, const char *fname,const char *)
460 {
461 long w,h; unsigned char *f=0, **p=0;
462 p =_Gr_->GetRGBLines(w,h,f);
463 if(p)
464 {
465 std::string fn=fname;
466 if(fn.empty()) { fn=gr->PlotId+".png"; fname = fn.c_str(); }
467 if(mgl_png_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
468 free(p); if(f) free(f);
469 }
470 }
mgl_write_png_solid_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)471 void MGL_EXPORT mgl_write_png_solid_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
472 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
473 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
474 mgl_write_png_solid(_GR_,s,f); delete []s; delete []f; }
475 //-----------------------------------------------------------------------------
mgl_write_jpg(HMGL gr,const char * fname,const char *)476 void MGL_EXPORT mgl_write_jpg(HMGL gr, const char *fname,const char *)
477 {
478 long w,h; unsigned char *f=0, **p=0;
479 p =_Gr_->GetRGBLines(w,h,f);
480 if(p)
481 {
482 std::string fn=fname;
483 if(fn.empty()) { fn=gr->PlotId+".jpg"; fname = fn.c_str(); }
484 if(mgl_jpeg_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
485 free(p); if(f) free(f);
486 }
487 }
mgl_write_jpg_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)488 void MGL_EXPORT mgl_write_jpg_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
489 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
490 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
491 mgl_write_jpg(_GR_,s,f); delete []s; delete []f; }
492 //-----------------------------------------------------------------------------
mgl_write_tga(HMGL gr,const char * fname,const char *)493 void MGL_EXPORT mgl_write_tga(HMGL gr, const char *fname,const char *)
494 {
495 long w,h; unsigned char *f=0, **p=0;
496 p =_Gr_->GetRGBLines(w,h,f,true);
497 if(p)
498 {
499 std::string fn=fname;
500 if(fn.empty()) { fn=gr->PlotId+".tga"; fname = fn.c_str(); }
501 if(mgl_tga_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
502 free(p); if(f) free(f);
503 }
504 }
mgl_write_tga_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)505 void MGL_EXPORT mgl_write_tga_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
506 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
507 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
508 mgl_write_tga(_GR_,s,f); delete []s; delete []f; }
509 //-----------------------------------------------------------------------------
mgl_write_bmp(HMGL gr,const char * fname,const char *)510 void MGL_EXPORT mgl_write_bmp(HMGL gr, const char *fname,const char *)
511 {
512 long w,h; unsigned char *f=0, **p=0;
513 p =_Gr_->GetRGBLines(w,h,f);
514 if(p)
515 {
516 std::string fn=fname;
517 if(fn.empty()) { fn=gr->PlotId+".bmp"; fname = fn.c_str(); }
518 if(mgl_bmp_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
519 free(p); if(f) free(f);
520 }
521 }
mgl_write_bmp_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)522 void MGL_EXPORT mgl_write_bmp_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
523 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
524 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
525 mgl_write_bmp(_GR_,s,f); delete []s; delete []f; }
526 //-----------------------------------------------------------------------------
mgl_write_bps(HMGL gr,const char * fname,const char *)527 void MGL_EXPORT mgl_write_bps(HMGL gr, const char *fname,const char *)
528 {
529 long w,h; unsigned char *f=0, **p=0;
530 p =_Gr_->GetRGBLines(w,h,f);
531 if(p)
532 {
533 std::string fn=fname;
534 if(fn.empty()) { fn=gr->PlotId+".eps"; fname = fn.c_str(); }
535 if(mgl_bps_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
536 free(p); if(f) free(f);
537 }
538 }
mgl_write_bps_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)539 void MGL_EXPORT mgl_write_bps_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
540 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
541 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
542 mgl_write_bps(_GR_,s,f); delete []s; delete []f; }
543 //-----------------------------------------------------------------------------
mgl_write_gif(HMGL gr,const char * fname,const char *)544 void MGL_EXPORT mgl_write_gif(HMGL gr, const char *fname,const char *)
545 {
546 long w,h; unsigned char *f=0, **p=0;
547 p =_Gr_->GetRGBLines(w,h,f);
548 if(p)
549 {
550 std::string fn=fname;
551 if(fn.empty()) { fn=gr->PlotId+".gif"; fname = fn.c_str(); }
552 if(mgl_gif_save(fname,w,h,p)) gr->SetWarn(mglWarnOpen,fname);
553 free(p); if(f) free(f);
554 }
555 }
mgl_write_gif_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)556 void MGL_EXPORT mgl_write_gif_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
557 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
558 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
559 mgl_write_gif(_GR_,s,f); delete []s; delete []f; }
560 //-----------------------------------------------------------------------------
mgl_start_gif(HMGL gr,const char * fname,int ms)561 void MGL_EXPORT mgl_start_gif(HMGL gr, const char *fname,int ms)
562 { _Gr_->StartGIF(fname,ms); }
mgl_start_gif_(uintptr_t * gr,const char * fname,int * ms,int l)563 void MGL_EXPORT mgl_start_gif_(uintptr_t *gr, const char *fname,int *ms,int l)
564 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
565 mgl_start_gif(_GR_,s,*ms); delete []s; }
566 //-----------------------------------------------------------------------------
mgl_close_gif(HMGL gr)567 void MGL_EXPORT mgl_close_gif(HMGL gr) { _Gr_->CloseGIF(); }
mgl_close_gif_(uintptr_t * gr)568 void MGL_EXPORT mgl_close_gif_(uintptr_t *gr) { mgl_close_gif(_GR_); }
569 //-----------------------------------------------------------------------------
mgl_write_frame(HMGL gr,const char * fname,const char * descr)570 void MGL_EXPORT mgl_write_frame(HMGL gr, const char *fname,const char *descr)
571 {
572 char buf[64];
573 if(!fname || !fname[0])
574 { snprintf(buf,64,"%s%04d.jpg",_Gr_->PlotId.c_str(),_Gr_->GetNumFrame()); buf[63]=0; fname = buf; }
575 int len=strlen(fname);
576 if(!strcmp(fname+len-4,".jpg")) mgl_write_jpg(gr,fname,descr);
577 else if(!strcmp(fname+len-5,".jpeg")) mgl_write_jpg(gr,fname,descr);
578 else if(!strcmp(fname+len-4,".prc")) mgl_write_prc(gr,fname,descr,1);
579 else if(!strcmp(fname+len-4,".pdf")) mgl_write_prc(gr,fname,descr,1);
580 else if(!strcmp(fname+len-4,".png")) mgl_write_png(gr,fname,descr);
581 else if(!strcmp(fname+len-4,".eps")) mgl_write_eps(gr,fname,descr);
582 else if(!strcmp(fname+len-5,".epsz")) mgl_write_eps(gr,fname,descr);
583 else if(!strcmp(fname+len-7,".eps.gz")) mgl_write_eps(gr,fname,descr);
584 else if(!strcmp(fname+len-4,".bps")) mgl_write_bps(gr,fname,descr);
585 else if(!strcmp(fname+len-5,".bpsz")) mgl_write_bps(gr,fname,descr);
586 else if(!strcmp(fname+len-7,".bps.gz")) mgl_write_bps(gr,fname,descr);
587 else if(!strcmp(fname+len-4,".svg")) mgl_write_svg(gr,fname,descr);
588 else if(!strcmp(fname+len-5,".svgz")) mgl_write_svg(gr,fname,descr);
589 else if(!strcmp(fname+len-7,".svg.gz")) mgl_write_svg(gr,fname,descr);
590 else if(!strcmp(fname+len-4,".gif")) mgl_write_gif(gr,fname,descr);
591 else if(!strcmp(fname+len-4,".bmp")) mgl_write_bmp(gr,fname,descr);
592 else if(!strcmp(fname+len-4,".tga")) mgl_write_tga(gr,fname,descr);
593 else if(!strcmp(fname+len-5,".mgld")) mgl_export_mgld(gr,fname,descr);
594 else if(!strcmp(fname+len-5,".json")) mgl_write_json(gr,fname,descr);
595 else if(!strcmp(fname+len-6,".jsonz")) mgl_write_json(gr,fname,descr);
596 else if(!strcmp(fname+len-4,".obj")) mgl_write_obj(gr,fname,descr,1);
597 else if(!strcmp(fname+len-4,".tex")) mgl_write_tex(gr,fname,descr);
598 else if(!strcmp(fname+len-4,".xyz")) mgl_write_xyz(gr,fname,descr);
599 else if(!strcmp(fname+len-4,".stl")) mgl_write_stl(gr,fname,descr);
600 else if(!strcmp(fname+len-4,".off")) mgl_write_off(gr,fname,descr,0);
601 // else if(!strcmp(fname+len-4,".x3d")) mgl_write_x3d(gr,fname,descr,1);
602 }
mgl_write_frame_(uintptr_t * gr,const char * fname,const char * descr,int l,int n)603 void MGL_EXPORT mgl_write_frame_(uintptr_t *gr, const char *fname,const char *descr,int l,int n)
604 { char *s=new char[l+1]; memcpy(s,fname,l); s[l]=0;
605 char *f=new char[n+1]; memcpy(f,descr,n); f[n]=0;
606 mgl_write_frame(_GR_,s,f); delete []s; delete []f;}
607 //-----------------------------------------------------------------------------
608 #ifdef WIN32
609 #include <io.h>
610 #include <direct.h>
611 #endif
mgl_show_image(HMGL gr,const char * viewer,int keep)612 void MGL_EXPORT mgl_show_image(HMGL gr, const char *viewer, int keep)
613 {
614 static size_t counter=size_t(0xffffffff*mgl_rnd());
615 char *fname = new char[256], *cmd = new char [288];
616 #if defined(_MSC_VER)
617 snprintf(fname,128,"%s.png", tmpnam(NULL));
618 #else
619 snprintf(fname,256,"%s/mathgl%lu.png", P_tmpdir, counter);
620 #endif
621 fname[255]=0; counter++;
622 mgl_write_png_solid(gr,fname,"MathGL ShowImage file");
623 if(!viewer || !viewer[0])
624 viewer = MGL_DEF_VIEWER;
625 #ifdef WIN32
626 if(keep)
627 {
628 snprintf(cmd,288,"%s %s &", viewer,fname); cmd[287]=0;
629 if(system(cmd)==-1) printf(_("Error to call external viewer\n"));
630 Sleep(2000);
631 snprintf(cmd,288,"del %s", fname);
632 }
633 else snprintf(cmd,288,"%s %s; del %s", viewer,fname,fname);
634 #else
635 if(keep)
636 {
637 snprintf(cmd,288,"%s %s &", viewer,fname); cmd[287]=0;
638 if(system(cmd)==-1) printf(_("Error to call external viewer\n"));
639 sleep(2);
640 snprintf(cmd,288,"rm %s", fname);
641 }
642 else snprintf(cmd,288,"%s %s; rm %s", viewer,fname,fname);
643 #endif
644 cmd[287] = 0;
645 if(system(cmd)==-1) printf(_("Error to call external viewer\n"));
646 delete []cmd; delete []fname;
647 }
mgl_show_image_(uintptr_t * gr,const char * viewer,int * keep,int l)648 void MGL_EXPORT mgl_show_image_(uintptr_t *gr, const char *viewer, int *keep, int l)
649 { char *s=new char[l+1]; memcpy(s,viewer,l); s[l]=0;
650 mgl_show_image(_GR_,s,*keep); delete []s; }
651 //-----------------------------------------------------------------------------
652