Actual source code: drawimage.c
petsc-3.7.7 2017-09-25
1: #include <../src/sys/classes/draw/impls/image/drawimage.h> /*I "petscdraw.h" I*/
2: #include <petsc/private/drawimpl.h> /*I "petscdraw.h" I*/
4: #if defined(PETSC_USE_DEBUG)
5: #define PetscDrawValidColor(color) \
6: do { if (PetscUnlikely((color)<0||(color)>=256)) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Color value %D out of range [0..255]",(PetscInt)(color)); } while (0)
7: #else
8: #define PetscDrawValidColor(color) do {} while (0)
9: #endif
11: #define XTRANS(draw,img,x) ((int)(((img)->w-1)*((draw)->port_xl + ((((x) - (draw)->coor_xl)*((draw)->port_xr - (draw)->port_xl))/((draw)->coor_xr - (draw)->coor_xl)))))
12: #define YTRANS(draw,img,y) (((img)->h-1) - (int)(((img)->h-1)*((draw)->port_yl + ((((y) - (draw)->coor_yl)*((draw)->port_yr - (draw)->port_yl))/((draw)->coor_yr - (draw)->coor_yl)))))
14: #define ITRANS(draw,img,i) ((draw)->coor_xl + (((PetscReal)(i))*((draw)->coor_xr - (draw)->coor_xl)/((img)->w-1) - (draw)->port_xl)/((draw)->port_xr - (draw)->port_xl))
15: #define JTRANS(draw,img,j) ((draw)->coor_yl + (((PetscReal)(j))/((img)->h-1) + (draw)->port_yl - 1)*((draw)->coor_yr - (draw)->coor_yl)/((draw)->port_yl - (draw)->port_yr))
20: static PetscErrorCode PetscDrawSetViewport_Image(PetscDraw draw,PetscReal xl,PetscReal yl,PetscReal xr,PetscReal yr)
21: {
22: PetscImage img = (PetscImage)draw->data;
24: {
25: int xmax = img->w - 1, ymax = img->h - 1;
26: int xa = (int)(xl*xmax), ya = ymax - (int)(yr*ymax);
27: int xb = (int)(xr*xmax), yb = ymax - (int)(yl*ymax);
28: PetscImageSetClip(img,xa,ya,xb+1-xa,yb+1-ya);
29: }
30: return(0);
31: }
33: /*
36: static PetscErrorCode PetscDrawSetCoordinates_Image(PetscDraw draw,PetscReal xl,PetscReal yl,PetscReal xr,PetscReal yr)
37: {
39: return(0);
40: }*/
41: #define PetscDrawSetCoordinates_Image NULL
45: static PetscErrorCode PetscDrawCoordinateToPixel_Image(PetscDraw draw,PetscReal x,PetscReal y,int *i,int *j)
46: {
47: PetscImage img = (PetscImage)draw->data;
49: if (i) *i = XTRANS(draw,img,x);
50: if (j) *j = YTRANS(draw,img,y);
51: return(0);
52: }
56: static PetscErrorCode PetscDrawPixelToCoordinate_Image(PetscDraw draw,int i,int j,PetscReal *x,PetscReal *y)
57: {
58: PetscImage img = (PetscImage)draw->data;
60: if (x) *x = ITRANS(draw,img,i);
61: if (y) *y = JTRANS(draw,img,j);
62: return(0);
63: }
65: /*
68: static PetscErrorCode PetscDrawPointSetSize_Image(PetscDraw draw,PetscReal width)
69: {
71: return(0);
72: }*/
73: #define PetscDrawPointSetSize_Image NULL
77: static PetscErrorCode PetscDrawPoint_Image(PetscDraw draw,PetscReal x,PetscReal y,int c)
78: {
79: PetscImage img = (PetscImage)draw->data;
81: PetscDrawValidColor(c);
82: {
83: int j, xx = XTRANS(draw,img,x);
84: int i, yy = YTRANS(draw,img,y);
85: for (i=-1; i<=1; i++)
86: for (j=-1; j<=1; j++)
87: PetscImageDrawPixel(img,xx+j,yy+i,c);
88: }
89: return(0);
90: }
94: static PetscErrorCode PetscDrawPointPixel_Image(PetscDraw draw,int x,int y,int c)
95: {
96: PetscImage img = (PetscImage)draw->data;
98: PetscDrawValidColor(c);
99: {
100: PetscImageDrawPixel(img,x,y,c);
101: }
102: return(0);
103: }
105: /*
108: static PetscErrorCode PetscDrawLineSetWidth_Image(PetscDraw draw,PetscReal width)
109: {
111: return(0);
112: }*/
113: #define PetscDrawLineSetWidth_Image NULL
117: static PetscErrorCode PetscDrawLineGetWidth_Image(PetscDraw draw,PetscReal *width)
118: {
119: PetscImage img = (PetscImage)draw->data;
121: {
122: int lw = 1;
123: *width = lw*(draw->coor_xr - draw->coor_xl)/(img->w*(draw->port_xr - draw->port_xl));
124: }
125: return(0);
126: }
130: static PetscErrorCode PetscDrawLine_Image(PetscDraw draw,PetscReal xl,PetscReal yl,PetscReal xr,PetscReal yr,int c)
131: {
132: PetscImage img = (PetscImage)draw->data;
134: {
135: int x_1 = XTRANS(draw,img,xl), x_2 = XTRANS(draw,img,xr);
136: int y_1 = YTRANS(draw,img,yl), y_2 = YTRANS(draw,img,yr);
137: PetscImageDrawLine(img,x_1,y_1,x_2,y_2,c);
138: }
139: return(0);
140: }
144: static PetscErrorCode PetscDrawArrow_Image(PetscDraw draw,PetscReal xl,PetscReal yl,PetscReal xr,PetscReal yr,int c)
145: {
146: PetscImage img = (PetscImage)draw->data;
148: PetscDrawValidColor(c);
149: {
150: int x_1 = XTRANS(draw,img,xl), x_2 = XTRANS(draw,img,xr);
151: int y_1 = YTRANS(draw,img,yl), y_2 = YTRANS(draw,img,yr);
152: if (x_1 == x_2 && y_1 == y_2) return(0);
153: PetscImageDrawLine(img,x_1,y_1,x_2,y_2,c);
154: if (x_1 == x_2 && PetscAbs(y_1 - y_2) > 7) {
155: if (y_2 > y_1) {
156: PetscImageDrawLine(img,x_2,y_2,x_2-3,y_2-3,c);
157: PetscImageDrawLine(img,x_2,y_2,x_2+3,y_2-3,c);
158: } else {
159: PetscImageDrawLine(img,x_2,y_2,x_2-3,y_2+3,c);
160: PetscImageDrawLine(img,x_2,y_2,x_2+3,y_2+3,c);
161: }
162: }
163: if (y_1 == y_2 && PetscAbs(x_1 - x_2) > 7) {
164: if (x_2 > x_1) {
165: PetscImageDrawLine(img,x_2-3,y_2-3,x_2,y_2,c);
166: PetscImageDrawLine(img,x_2-3,y_2+3,x_2,y_2,c);
167: } else {
168: PetscImageDrawLine(img,x_2,y_2,x_2+3,y_2-3,c);
169: PetscImageDrawLine(img,x_2,y_2,x_2+3,y_2+3,c);
170: }
171: }
172: }
173: return(0);
174: }
178: static PetscErrorCode PetscDrawRectangle_Image(PetscDraw draw,PetscReal xl,PetscReal yl,PetscReal xr,PetscReal yr,int c1,int c2,int c3,int c4)
179: {
180: PetscImage img = (PetscImage)draw->data;
182: PetscDrawValidColor(c1);
183: PetscDrawValidColor(c2);
184: PetscDrawValidColor(c3);
185: PetscDrawValidColor(c4);
186: {
187: int x = XTRANS(draw,img,xl), w = XTRANS(draw,img,xr) + 1 - x;
188: int y = YTRANS(draw,img,yr), h = YTRANS(draw,img,yl) + 1 - y;
189: int c = (c1 + c2 + c3 + c4)/4;
190: PetscImageDrawRectangle(img,x,y,w,h,c);
191: }
192: return(0);
193: }
197: static PetscErrorCode PetscDrawEllipse_Image(PetscDraw draw,PetscReal x,PetscReal y,PetscReal a,PetscReal b,int c)
198: {
199: PetscImage img = (PetscImage)draw->data;
201: PetscDrawValidColor(c);
202: a = PetscAbsReal(a);
203: b = PetscAbsReal(b);
204: {
205: int xc = XTRANS(draw,img,x), w = XTRANS(draw,img,x + a/2) + 0 - xc;
206: int yc = YTRANS(draw,img,y), h = YTRANS(draw,img,y - b/2) + 0 - yc;
207: if (PetscAbsReal(a-b) <= 0) w = h = PetscMin(w,h); /* workaround truncation errors */
208: PetscImageDrawEllipse(img,xc,yc,w,h,c);
209: }
210: return(0);
211: }
215: static PetscErrorCode PetscDrawTriangle_Image(PetscDraw draw,PetscReal X_1,PetscReal Y_1,PetscReal X_2,PetscReal Y_2,PetscReal X_3,PetscReal Y_3,int c1,int c2,int c3)
216: {
217: PetscImage img = (PetscImage)draw->data;
219: PetscDrawValidColor(c1);
220: PetscDrawValidColor(c2);
221: PetscDrawValidColor(c3);
222: {
223: int x_1 = XTRANS(draw,img,X_1), x_2 = XTRANS(draw,img,X_2), x_3 = XTRANS(draw,img,X_3);
224: int y_1 = YTRANS(draw,img,Y_1), y_2 = YTRANS(draw,img,Y_2), y_3 = YTRANS(draw,img,Y_3);
225: PetscImageDrawTriangle(img,x_1,y_1,c1,x_2,y_2,c2,x_3,y_3,c3);
226: }
227: return(0);
228: }
230: /*
233: static PetscErrorCode PetscDrawStringSetSize_Image(PetscDraw draw,PetscReal w,PetscReal h)
234: {
236: return(0);
237: }*/
238: #define PetscDrawStringSetSize_Image NULL
242: static PetscErrorCode PetscDrawStringGetSize_Image(PetscDraw draw,PetscReal *w,PetscReal *h)
243: {
244: PetscImage img = (PetscImage)draw->data;
246: {
247: int tw = PetscImageFontWidth;
248: int th = PetscImageFontHeight;
249: if (w) *w = tw*(draw->coor_xr - draw->coor_xl)/(img->w*(draw->port_xr - draw->port_xl));
250: if (h) *h = th*(draw->coor_yr - draw->coor_yl)/(img->h*(draw->port_yr - draw->port_yl));
251: }
252: return(0);
253: }
257: static PetscErrorCode PetscDrawString_Image(PetscDraw draw,PetscReal x,PetscReal y,int c,const char text[])
258: {
259: PetscImage img = (PetscImage)draw->data;
260: PetscToken token;
261: char *subtext;
264: PetscDrawValidColor(c);
265: {
266: int xx = XTRANS(draw,img,x);
267: int yy = YTRANS(draw,img,y);
268: PetscTokenCreate(text,'\n',&token);
269: PetscTokenFind(token,&subtext);
270: while (subtext) {
271: PetscImageDrawText(img,xx,yy,c,subtext);
272: yy += PetscImageFontHeight;
273: PetscTokenFind(token,&subtext);
274: }
275: PetscTokenDestroy(&token);
276: }
277: return(0);
278: }
282: static PetscErrorCode PetscDrawStringVertical_Image(PetscDraw draw,PetscReal x,PetscReal y,int c,const char text[])
283: {
284: PetscImage img = (PetscImage)draw->data;
286: PetscDrawValidColor(c);
287: {
288: char chr[2] = {0, 0};
289: int xx = XTRANS(draw,img,x);
290: int yy = YTRANS(draw,img,y);
291: int offset = PetscImageFontHeight;
292: while ((chr[0] = *text++)) {
293: PetscImageDrawText(img,xx,yy+offset,c,chr);
294: yy += PetscImageFontHeight;
295: }
296: }
297: return(0);
298: }
300: /*
303: static PetscErrorCode PetscDrawStringBoxed_Image(PetscDraw draw,PetscReal sxl,PetscReal syl,int sc,int bc,const char text[],PetscReal *w,PetscReal *h)
304: {
306: if (w) *w = 0;
307: if (h) *h = 0;
308: return(0);
309: */
310: #define PetscDrawStringBoxed_Image NULL
312: /*
315: static PetscErrorCode PetscDrawFlush_Image(PetscDraw draw)
316: {
318: return(0);
319: }*/
320: #define PetscDrawFlush_Image NULL
324: static PetscErrorCode PetscDrawClear_Image(PetscDraw draw)
325: {
326: PetscImage img = (PetscImage)draw->data;
328: {
329: PetscImageClear(img);
330: }
331: return(0);
332: }
334: /*
337: static PetscErrorCode PetscDrawSetDoubleBuffer_Image(PetscDraw draw)
338: {
340: return(0);
341: }*/
342: #define PetscDrawSetDoubleBuffer_Image NULL
346: static PetscErrorCode PetscDrawGetPopup_Image(PetscDraw draw,PetscDraw *popup)
347: {
348: PetscBool flg = PETSC_FALSE;
352: PetscOptionsGetBool(((PetscObject)draw)->options,((PetscObject)draw)->prefix,"-draw_popup",&flg,NULL);
353: if (!flg) {*popup = NULL; return(0);}
354: PetscDrawCreate(PetscObjectComm((PetscObject)draw),NULL,NULL,0,0,220,220,popup);
355: PetscDrawSetType(*popup,PETSC_DRAW_IMAGE);
356: PetscObjectSetOptionsPrefix((PetscObject)*popup,"popup_");
357: PetscObjectAppendOptionsPrefix((PetscObject)*popup,((PetscObject)draw)->prefix);
358: draw->popup = *popup;
359: return(0);
360: }
362: /*
365: static PetscErrorCode PetscDrawSetTitle_Image(PetscDraw draw,const char title[])
366: {
368: return(0);
369: }*/
370: #define PetscDrawSetTitle_Image NULL
372: /*
375: static PetscErrorCode PetscDrawCheckResizedWindow_Image(PetscDraw draw)
376: {
378: return(0);
379: }*/
380: #define PetscDrawCheckResizedWindow_Image NULL
384: static PetscErrorCode PetscDrawResizeWindow_Image(PetscDraw draw,int w,int h)
385: {
386: PetscImage img = (PetscImage)draw->data;
390: if (w == img->w && h == img->h) return(0);
391: PetscFree(img->buffer);
393: img->w = w; img->h = h;
394: PetscCalloc1((size_t)(img->w*img->h),&img->buffer);
395: PetscDrawSetViewport_Image(draw,draw->port_xl,draw->port_yl,draw->port_xr,draw->port_yr);
396: return(0);
397: }
401: static PetscErrorCode PetscDrawDestroy_Image(PetscDraw draw)
402: {
403: PetscImage img = (PetscImage)draw->data;
407: PetscDrawDestroy(&draw->popup);
408: PetscFree(img->buffer);
409: PetscFree(draw->data);
410: return(0);
411: }
413: /*
416: static PetscErrorCode PetscDrawView_Image(PetscDraw draw,PetscViewer viewer)
417: {
419: return(0);
420: }*/
421: #define PetscDrawView_Image NULL
423: /*
426: static PetscErrorCode PetscDrawGetMouseButton_Image(PetscDraw draw,PetscDrawButton *button,PetscReal *x_user,PetscReal *y_user,PetscReal *x_phys,PetscReal *y_phys)
427: {
429: *button = PETSC_BUTTON_NONE;
430: if (x_user) *x_user = 0;
431: if (y_user) *y_user = 0;
432: if (x_phys) *x_phys = 0;
433: if (y_phys) *y_phys = 0;
434: return(0);
435: }*/
436: #define PetscDrawGetMouseButton_Image NULL
438: /*
441: static PetscErrorCode PetscDrawPause_Image(PetscDraw draw)
442: {
444: return(0);
445: }*/
446: #define PetscDrawPause_Image NULL
448: /*
451: static PetscErrorCode PetscDrawBeginPage_Image(PetscDraw draw)
452: {
454: return(0);
455: }*/
456: #define PetscDrawBeginPage_Image NULL
458: /*
461: static PetscErrorCode PetscDrawEndPage_Image(PetscDraw draw)
462: {
464: return(0);
465: }*/
466: #define PetscDrawEndPage_Image NULL
470: static PetscErrorCode PetscDrawGetSingleton_Image(PetscDraw draw,PetscDraw *sdraw)
471: {
472: PetscImage pimg = (PetscImage)draw->data;
473: PetscImage simg;
477: PetscDrawCreate(PETSC_COMM_SELF,NULL,NULL,0,0,draw->w,draw->h,sdraw);
478: PetscDrawSetType(*sdraw,PETSC_DRAW_IMAGE);
479: (*sdraw)->ops->resizewindow = NULL;
480: simg = (PetscImage)(*sdraw)->data;
481: PetscMemcpy(simg->buffer,pimg->buffer,(size_t)(pimg->w*pimg->h));
482: return(0);
483: }
487: static PetscErrorCode PetscDrawRestoreSingleton_Image(PetscDraw draw,PetscDraw *sdraw)
488: {
489: PetscImage pimg = (PetscImage)draw->data;
490: PetscImage simg = (PetscImage)(*sdraw)->data;
494: PetscMemcpy(pimg->buffer,simg->buffer,(size_t)(pimg->w*pimg->h));
495: PetscDrawDestroy(sdraw);
496: return(0);
497: }
499: /*
502: static PetscErrorCode PetscDrawSave_Image(PetscDraw draw)
503: {
505: return(0);
506: }*/
507: #define PetscDrawSave_Image NULL
511: static PetscErrorCode PetscDrawGetImage_Image(PetscDraw draw,unsigned char palette[256][3],unsigned int *w,unsigned int *h,unsigned char *pixels[])
512: {
513: PetscImage img = (PetscImage)draw->data;
514: unsigned char *buffer = NULL;
515: PetscMPIInt rank,size;
519: if (w) *w = (unsigned int)img->w;
520: if (h) *h = (unsigned int)img->h;
521: if (pixels) *pixels = NULL;
522: MPI_Comm_rank(PetscObjectComm((PetscObject)draw),&rank);
523: if (!rank) {
524: PetscMemcpy(palette,img->palette,sizeof(img->palette));
525: PetscMalloc1((size_t)(img->w*img->h),&buffer);
526: if (pixels) *pixels = buffer;
527: }
528: MPI_Comm_size(PetscObjectComm((PetscObject)draw),&size);
529: if (size == 1) {
530: PetscMemcpy(buffer,img->buffer,(size_t)(img->w*img->h));
531: } else {
532: MPI_Reduce(img->buffer,buffer,img->w*img->h,MPI_UNSIGNED_CHAR,MPI_MAX,0,PetscObjectComm((PetscObject)draw));
533: }
534: return(0);
535: }
537: static struct _PetscDrawOps DvOps = {
538: PetscDrawSetDoubleBuffer_Image,
539: PetscDrawFlush_Image,
540: PetscDrawLine_Image,
541: PetscDrawLineSetWidth_Image,
542: PetscDrawLineGetWidth_Image,
543: PetscDrawPoint_Image,
544: PetscDrawPointSetSize_Image,
545: PetscDrawString_Image,
546: PetscDrawStringVertical_Image,
547: PetscDrawStringSetSize_Image,
548: PetscDrawStringGetSize_Image,
549: PetscDrawSetViewport_Image,
550: PetscDrawClear_Image,
551: PetscDrawRectangle_Image,
552: PetscDrawTriangle_Image,
553: PetscDrawEllipse_Image,
554: PetscDrawGetMouseButton_Image,
555: PetscDrawPause_Image,
556: PetscDrawBeginPage_Image,
557: PetscDrawEndPage_Image,
558: PetscDrawGetPopup_Image,
559: PetscDrawSetTitle_Image,
560: PetscDrawCheckResizedWindow_Image,
561: PetscDrawResizeWindow_Image,
562: PetscDrawDestroy_Image,
563: PetscDrawView_Image,
564: PetscDrawGetSingleton_Image,
565: PetscDrawRestoreSingleton_Image,
566: PetscDrawSave_Image,
567: PetscDrawGetImage_Image,
568: PetscDrawSetCoordinates_Image,
569: PetscDrawArrow_Image,
570: PetscDrawCoordinateToPixel_Image,
571: PetscDrawPixelToCoordinate_Image,
572: PetscDrawPointPixel_Image,
573: PetscDrawStringBoxed_Image
574: };
576: static const unsigned char BasicColors[PETSC_DRAW_BASIC_COLORS][3] = {
577: { 255, 255, 255 }, /* white */
578: { 0, 0, 0 }, /* black */
579: { 255, 0, 0 }, /* red */
580: { 0, 255, 0 }, /* green */
581: { 0, 255, 255 }, /* cyan */
582: { 0, 0, 255 }, /* blue */
583: { 255, 0, 255 }, /* magenta */
584: { 127, 255, 212 }, /* aquamarine */
585: { 34, 139, 34 }, /* forestgreen */
586: { 255, 165, 0 }, /* orange */
587: { 238, 130, 238 }, /* violet */
588: { 165, 42, 42 }, /* brown */
589: { 255, 192, 203 }, /* pink */
590: { 255, 127, 80 }, /* coral */
591: { 190, 190, 190 }, /* gray */
592: { 255, 255, 0 }, /* yellow */
593: { 255, 215, 0 }, /* gold */
594: { 255, 182, 193 }, /* lightpink */
595: { 72, 209, 204 }, /* mediumturquoise */
596: { 240, 230, 140 }, /* khaki */
597: { 105, 105, 105 }, /* dimgray */
598: { 54, 205, 50 }, /* yellowgreen */
599: { 135, 206, 235 }, /* skyblue */
600: { 0, 100, 0 }, /* darkgreen */
601: { 0, 0, 128 }, /* navyblue */
602: { 244, 164, 96 }, /* sandybrown */
603: { 95, 158, 160 }, /* cadetblue */
604: { 176, 224, 230 }, /* powderblue */
605: { 255, 20, 147 }, /* deeppink */
606: { 216, 191, 216 }, /* thistle */
607: { 50, 205, 50 }, /* limegreen */
608: { 255, 240, 245 }, /* lavenderblush */
609: { 221, 160, 221 }, /* plum */
610: };
613: /*MC
614: PETSC_DRAW_IMAGE - PETSc graphics device that uses a raster buffer
616: Options Database Keys:
617: . -draw_size w,h - size of image in pixels
619: Level: beginner
621: .seealso: PetscDrawOpenImage(), PetscDrawSetFromOptions()
622: M*/
623: PETSC_EXTERN PetscErrorCode PetscDrawCreate_Image(PetscDraw);
627: PETSC_EXTERN PetscErrorCode PetscDrawCreate_Image(PetscDraw draw)
628: {
629: PetscImage img;
630: int w = draw->w, h = draw->h;
631: PetscInt size[2], nsize = 2;
632: PetscBool set;
636: draw->pause = 0;
637: draw->coor_xl = 0; draw->coor_xr = 1;
638: draw->coor_yl = 0; draw->coor_yr = 1;
639: draw->port_xl = 0; draw->port_xr = 1;
640: draw->port_yl = 0; draw->port_yr = 1;
642: size[0] = w; if (size[0] < 1) size[0] = 300;
643: size[1] = h; if (size[1] < 1) size[1] = size[0];
644: PetscOptionsGetIntArray(((PetscObject)draw)->options,((PetscObject)draw)->prefix,"-draw_size",size,&nsize,&set);
645: if (set && nsize == 1) size[1] = size[0];
646: if (size[0] < 1) size[0] = 300;
647: if (size[1] < 1) size[1] = size[0];
648: draw->w = w = size[0]; draw->x = 0;
649: draw->h = h = size[1]; draw->x = 0;
651: PetscNewLog(draw,&img);
652: PetscMemcpy(draw->ops,&DvOps,sizeof(DvOps));
653: draw->data = (void*)img;
655: img->w = w; img->h = h;
656: PetscCalloc1((size_t)(img->w*img->h),&img->buffer);
657: PetscImageSetClip(img,0,0,img->w,img->h);
658: {
659: int i,k,ncolors = 256-PETSC_DRAW_BASIC_COLORS;
660: unsigned char R[256-PETSC_DRAW_BASIC_COLORS];
661: unsigned char G[256-PETSC_DRAW_BASIC_COLORS];
662: unsigned char B[256-PETSC_DRAW_BASIC_COLORS];
663: PetscDrawUtilitySetCmap(NULL,ncolors,R,G,B);
664: for (k=0; k<PETSC_DRAW_BASIC_COLORS; k++) {
665: img->palette[k][0] = BasicColors[k][0];
666: img->palette[k][1] = BasicColors[k][1];
667: img->palette[k][2] = BasicColors[k][2];
668: }
669: for (i=0; i<ncolors; i++, k++) {
670: img->palette[k][0] = R[i];
671: img->palette[k][1] = G[i];
672: img->palette[k][2] = B[i];
673: }
674: }
676: if (!draw->savefilename ){PetscDrawSetSave(draw,"");}
677: return(0);
678: }
682: /*@C
683: PetscDrawOpenImage - Opens an image for use with the PetscDraw routines.
685: Collective on MPI_Comm
687: Input Parameters:
688: + comm - the communicator that will share image
689: - filename - optional name of the file
690: - w, h - the image width and height in pixels
692: Output Parameters:
693: . draw - the drawing context.
695: Level: beginner
697: .seealso: PetscDrawSetSave(), PetscDrawSetFromOptions(), PetscDrawCreate(), PetscDrawDestroy()
698: @*/
699: PetscErrorCode PetscDrawOpenImage(MPI_Comm comm,const char filename[],int w,int h,PetscDraw *draw)
700: {
704: PetscDrawCreate(comm,NULL,NULL,0,0,w,h,draw);
705: PetscDrawSetType(*draw,PETSC_DRAW_IMAGE);
706: PetscDrawSetSave(*draw,filename);
707: return(0);
708: }