xref: /petsc/src/sys/classes/draw/interface/draw.c (revision 4683183ff602abad4ed575829633a91c06c87c27)
1 
2 /*
3        Provides the calling sequences for all the basic PetscDraw routines.
4 */
5 #include <petsc/private/drawimpl.h>  /*I "petscdraw.h" I*/
6 #include <petscviewer.h>
7 
8 PetscClassId PETSC_DRAW_CLASSID;
9 
10 static PetscBool PetscDrawPackageInitialized = PETSC_FALSE;
11 #undef __FUNCT__
12 #define __FUNCT__ "PetscDrawFinalizePackage"
13 /*@C
14   PetscDrawFinalizePackage - This function destroys everything in the Petsc interface to the Draw package. It is
15   called from PetscFinalize().
16 
17   Level: developer
18 
19 .keywords: Petsc, destroy, package, mathematica
20 .seealso: PetscFinalize()
21 @*/
22 PetscErrorCode  PetscDrawFinalizePackage(void)
23 {
24   PetscErrorCode ierr;
25 
26   PetscFunctionBegin;
27   ierr = PetscFunctionListDestroy(&PetscDrawList);CHKERRQ(ierr);
28   PetscDrawPackageInitialized = PETSC_FALSE;
29   PetscDrawRegisterAllCalled  = PETSC_FALSE;
30   PetscFunctionReturn(0);
31 }
32 
33 #undef __FUNCT__
34 #define __FUNCT__ "PetscDrawInitializePackage"
35 /*@C
36   PetscInitializeDrawPackage - This function initializes everything in the PetscDraw package. It is called
37   from PetscDLLibraryRegister() when using dynamic libraries, and on the call to PetscInitialize()
38   when using static libraries.
39 
40   Level: developer
41 
42 .keywords: Petsc, initialize, package
43 .seealso: PetscInitialize()
44 @*/
45 PetscErrorCode  PetscDrawInitializePackage(void)
46 {
47   char           logList[256];
48   char           *className;
49   PetscBool      opt;
50   PetscErrorCode ierr;
51 
52   PetscFunctionBegin;
53   if (PetscDrawPackageInitialized) PetscFunctionReturn(0);
54   PetscDrawPackageInitialized = PETSC_TRUE;
55   /* Register Classes */
56   ierr = PetscClassIdRegister("Draw",&PETSC_DRAW_CLASSID);CHKERRQ(ierr);
57   ierr = PetscClassIdRegister("Draw Axis",&PETSC_DRAWAXIS_CLASSID);CHKERRQ(ierr);
58   ierr = PetscClassIdRegister("Line Graph",&PETSC_DRAWLG_CLASSID);CHKERRQ(ierr);
59   ierr = PetscClassIdRegister("Histogram",&PETSC_DRAWHG_CLASSID);CHKERRQ(ierr);
60   ierr = PetscClassIdRegister("Bar Graph",&PETSC_DRAWBAR_CLASSID);CHKERRQ(ierr);
61   ierr = PetscClassIdRegister("Scatter Plot",&PETSC_DRAWSP_CLASSID);CHKERRQ(ierr);
62   /* Register Constructors */
63   ierr = PetscDrawRegisterAll();CHKERRQ(ierr);
64   /* Process info exclusions */
65   ierr = PetscOptionsGetString(NULL,NULL, "-info_exclude", logList, 256, &opt);CHKERRQ(ierr);
66   if (opt) {
67     ierr = PetscStrstr(logList, "draw", &className);CHKERRQ(ierr);
68     if (className) {
69       ierr = PetscInfoDeactivateClass(0);CHKERRQ(ierr);
70     }
71   }
72   /* Process summary exclusions */
73   ierr = PetscOptionsGetString(NULL,NULL, "-log_exclude", logList, 256, &opt);CHKERRQ(ierr);
74   if (opt) {
75     ierr = PetscStrstr(logList, "draw", &className);CHKERRQ(ierr);
76     if (className) {
77       ierr = PetscLogEventDeactivateClass(0);CHKERRQ(ierr);
78     }
79   }
80   ierr = PetscRegisterFinalize(PetscDrawFinalizePackage);CHKERRQ(ierr);
81   PetscFunctionReturn(0);
82 }
83 
84 #undef __FUNCT__
85 #define __FUNCT__ "PetscDrawResizeWindow"
86 /*@
87    PetscDrawResizeWindow - Allows one to resize a window from a program.
88 
89    Collective on PetscDraw
90 
91    Input Parameter:
92 +  draw - the window
93 -  w,h - the new width and height of the window
94 
95    Level: intermediate
96 
97 .seealso: PetscDrawCheckResizedWindow()
98 @*/
99 PetscErrorCode  PetscDrawResizeWindow(PetscDraw draw,int w,int h)
100 {
101   PetscErrorCode ierr;
102 
103   PetscFunctionBegin;
104   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
105   PetscValidLogicalCollectiveInt(draw,w,2);
106   PetscValidLogicalCollectiveInt(draw,h,3);
107   if (draw->ops->resizewindow) {
108     ierr = (*draw->ops->resizewindow)(draw,w,h);CHKERRQ(ierr);
109   }
110   PetscFunctionReturn(0);
111 }
112 
113 #undef __FUNCT__
114 #define __FUNCT__ "PetscDrawGetWindowSize"
115 /*@
116    PetscDrawGetWindowSize - Gets the size of the window.
117 
118    Not collective
119 
120    Input Parameter:
121 .  draw - the window
122 
123    Output Parameters:
124 .  w,h - the window width and height
125 
126    Level: intermediate
127 
128 .seealso: PetscDrawResizeWindow(), PetscDrawCheckResizedWindow()
129 @*/
130 PetscErrorCode  PetscDrawGetWindowSize(PetscDraw draw,int *w,int *h)
131 {
132   PetscFunctionBegin;
133   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
134   if (w) PetscValidPointer(w,2);
135   if (h) PetscValidPointer(h,3);
136   if (w) *w = draw->w;
137   if (h) *h = draw->h;
138   PetscFunctionReturn(0);
139 }
140 
141 #undef __FUNCT__
142 #define __FUNCT__ "PetscDrawCheckResizedWindow"
143 /*@
144    PetscDrawCheckResizedWindow - Checks if the user has resized the window.
145 
146    Collective on PetscDraw
147 
148    Input Parameter:
149 .  draw - the window
150 
151    Level: advanced
152 
153 .seealso: PetscDrawResizeWindow()
154 
155 @*/
156 PetscErrorCode  PetscDrawCheckResizedWindow(PetscDraw draw)
157 {
158   PetscErrorCode ierr;
159 
160   PetscFunctionBegin;
161   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
162   if (draw->ops->checkresizedwindow) {
163     ierr = (*draw->ops->checkresizedwindow)(draw);CHKERRQ(ierr);
164   }
165   PetscFunctionReturn(0);
166 }
167 
168 #undef __FUNCT__
169 #define __FUNCT__ "PetscDrawGetTitle"
170 /*@C
171    PetscDrawGetTitle - Gets pointer to title of a PetscDraw context.
172 
173    Not collective
174 
175    Input Parameter:
176 .  draw - the graphics context
177 
178    Output Parameter:
179 .  title - the title
180 
181    Level: intermediate
182 
183 .seealso: PetscDrawSetTitle()
184 @*/
185 PetscErrorCode  PetscDrawGetTitle(PetscDraw draw,char **title)
186 {
187   PetscFunctionBegin;
188   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
189   PetscValidPointer(title,2);
190   *title = draw->title;
191   PetscFunctionReturn(0);
192 }
193 
194 #undef __FUNCT__
195 #define __FUNCT__ "PetscDrawSetTitle"
196 /*@C
197    PetscDrawSetTitle - Sets the title of a PetscDraw context.
198 
199    Collective on PetscDraw
200 
201    Input Parameters:
202 +  draw - the graphics context
203 -  title - the title
204 
205    Level: intermediate
206 
207    Note: The title is positioned in the windowing system title bar for the window. Hence it will not be saved with -draw_save
208    in the image.
209 
210    A copy of the string is made, so you may destroy the
211    title string after calling this routine.
212 
213    You can use PetscDrawAxisSetLabels() to indicate a title within the window
214 
215 .seealso: PetscDrawGetTitle(), PetscDrawAppendTitle()
216 @*/
217 PetscErrorCode  PetscDrawSetTitle(PetscDraw draw,const char title[])
218 {
219   PetscErrorCode ierr;
220 
221   PetscFunctionBegin;
222   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
223   PetscValidCharPointer(title,2);
224   ierr = PetscFree(draw->title);CHKERRQ(ierr);
225   ierr = PetscStrallocpy(title,&draw->title);CHKERRQ(ierr);
226   if (draw->ops->settitle) {
227     ierr = (*draw->ops->settitle)(draw,draw->title);CHKERRQ(ierr);
228   }
229   PetscFunctionReturn(0);
230 }
231 
232 #undef __FUNCT__
233 #define __FUNCT__ "PetscDrawAppendTitle"
234 /*@C
235    PetscDrawAppendTitle - Appends to the title of a PetscDraw context.
236 
237    Collective on PetscDraw
238 
239    Input Parameters:
240 +  draw - the graphics context
241 -  title - the title
242 
243    Note:
244    A copy of the string is made, so you may destroy the
245    title string after calling this routine.
246 
247    Level: advanced
248 
249 .seealso: PetscDrawSetTitle(), PetscDrawGetTitle()
250 @*/
251 PetscErrorCode  PetscDrawAppendTitle(PetscDraw draw,const char title[])
252 {
253   PetscErrorCode ierr;
254 
255   PetscFunctionBegin;
256   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
257   if (title) PetscValidCharPointer(title,2);
258   if (!title || !title[0]) PetscFunctionReturn(0);
259 
260   if (draw->title) {
261     size_t len1,len2;
262     char   *newtitle;
263     ierr = PetscStrlen(title,&len1);CHKERRQ(ierr);
264     ierr = PetscStrlen(draw->title,&len2);CHKERRQ(ierr);
265     ierr = PetscMalloc1(len1 + len2 + 1,&newtitle);CHKERRQ(ierr);
266     ierr = PetscStrcpy(newtitle,draw->title);CHKERRQ(ierr);
267     ierr = PetscStrcat(newtitle,title);CHKERRQ(ierr);
268     ierr = PetscFree(draw->title);CHKERRQ(ierr);
269     draw->title = newtitle;
270   } else {
271     ierr = PetscStrallocpy(title,&draw->title);CHKERRQ(ierr);
272   }
273   if (draw->ops->settitle) {
274     ierr = (*draw->ops->settitle)(draw,draw->title);CHKERRQ(ierr);
275   }
276   PetscFunctionReturn(0);
277 }
278 
279 #undef __FUNCT__
280 #define __FUNCT__ "PetscDrawDestroy_Private"
281 static PetscErrorCode PetscDrawDestroy_Private(PetscDraw draw)
282 {
283   PetscErrorCode ierr;
284 
285   PetscFunctionBegin;
286   if (!draw->ops->save && !draw->ops->getimage) PetscFunctionReturn(0);
287   ierr = PetscDrawSaveMovie(draw);CHKERRQ(ierr);
288   if (draw->savefinalfilename) {
289     draw->savesinglefile = PETSC_TRUE;
290     ierr = PetscDrawSetSave(draw,draw->savefinalfilename);CHKERRQ(ierr);
291     ierr = PetscDrawSave(draw);CHKERRQ(ierr);
292   }
293   ierr = PetscBarrier((PetscObject)draw);CHKERRQ(ierr);
294   PetscFunctionReturn(0);
295 }
296 
297 #undef __FUNCT__
298 #define __FUNCT__ "PetscDrawDestroy"
299 /*@
300    PetscDrawDestroy - Deletes a draw context.
301 
302    Collective on PetscDraw
303 
304    Input Parameters:
305 .  draw - the drawing context
306 
307    Level: beginner
308 
309 .seealso: PetscDrawCreate()
310 
311 @*/
312 PetscErrorCode  PetscDrawDestroy(PetscDraw *draw)
313 {
314   PetscErrorCode ierr;
315 
316   PetscFunctionBegin;
317   if (!*draw) PetscFunctionReturn(0);
318   PetscValidHeaderSpecific(*draw,PETSC_DRAW_CLASSID,1);
319   if (--((PetscObject)(*draw))->refct > 0) PetscFunctionReturn(0);
320 
321   if ((*draw)->pause == -2) {
322     (*draw)->pause = -1;
323     ierr = PetscDrawPause(*draw);CHKERRQ(ierr);
324   }
325 
326   /* if memory was published then destroy it */
327   ierr = PetscObjectSAWsViewOff((PetscObject)*draw);CHKERRQ(ierr);
328 
329   ierr = PetscDrawDestroy_Private(*draw);CHKERRQ(ierr);
330 
331   if ((*draw)->ops->destroy) {
332     ierr = (*(*draw)->ops->destroy)(*draw);CHKERRQ(ierr);
333   }
334   ierr = PetscDrawDestroy(&(*draw)->popup);CHKERRQ(ierr);
335   ierr = PetscFree((*draw)->title);CHKERRQ(ierr);
336   ierr = PetscFree((*draw)->display);CHKERRQ(ierr);
337   ierr = PetscFree((*draw)->savefilename);CHKERRQ(ierr);
338   ierr = PetscFree((*draw)->saveimageext);CHKERRQ(ierr);
339   ierr = PetscFree((*draw)->savemovieext);CHKERRQ(ierr);
340   ierr = PetscFree((*draw)->savefinalfilename);CHKERRQ(ierr);
341   ierr = PetscHeaderDestroy(draw);CHKERRQ(ierr);
342   PetscFunctionReturn(0);
343 }
344 
345 #undef __FUNCT__
346 #define __FUNCT__ "PetscDrawGetPopup"
347 /*@
348    PetscDrawGetPopup - Creates a popup window associated with a PetscDraw window.
349 
350    Collective on PetscDraw
351 
352    Input Parameter:
353 .  draw - the original window
354 
355    Output Parameter:
356 .  popup - the new popup window
357 
358    Level: advanced
359 
360 .seealso: PetscDrawScalePopup(), PetscDrawCreate()
361 
362 @*/
363 PetscErrorCode  PetscDrawGetPopup(PetscDraw draw,PetscDraw *popup)
364 {
365   PetscErrorCode ierr;
366 
367   PetscFunctionBegin;
368   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
369   PetscValidPointer(popup,2);
370 
371   if (draw->popup) *popup = draw->popup;
372   else if (draw->ops->getpopup) {
373     ierr = (*draw->ops->getpopup)(draw,popup);CHKERRQ(ierr);
374     if (*popup) {
375       ierr = PetscObjectSetOptionsPrefix((PetscObject)*popup,"popup_");CHKERRQ(ierr);
376       (*popup)->pause = 0.0;
377       ierr = PetscDrawSetFromOptions(*popup);CHKERRQ(ierr);
378     }
379   } else *popup = NULL;
380   PetscFunctionReturn(0);
381 }
382 
383 #undef __FUNCT__
384 #define __FUNCT__ "PetscDrawSetDisplay"
385 /*@
386   PetscDrawSetDisplay - Sets the display where a PetscDraw object will be displayed
387 
388   Input Parameter:
389 + draw - the drawing context
390 - display - the X windows display
391 
392   Level: advanced
393 
394 .seealso: PetscDrawCreate()
395 
396 @*/
397 PetscErrorCode  PetscDrawSetDisplay(PetscDraw draw,const char display[])
398 {
399   PetscErrorCode ierr;
400 
401   PetscFunctionBegin;
402   ierr = PetscFree(draw->display);CHKERRQ(ierr);
403   ierr = PetscStrallocpy(display,&draw->display);CHKERRQ(ierr);
404   PetscFunctionReturn(0);
405 }
406 
407 
408 #undef __FUNCT__
409 #define __FUNCT__ "PetscDrawSetDoubleBuffer"
410 /*@
411    PetscDrawSetDoubleBuffer - Sets a window to be double buffered.
412 
413    Logically Collective on PetscDraw
414 
415    Input Parameter:
416 .  draw - the drawing context
417 
418    Level: intermediate
419 
420    Concepts: drawing^double buffer
421    Concepts: graphics^double buffer
422    Concepts: double buffer
423 
424 @*/
425 PetscErrorCode  PetscDrawSetDoubleBuffer(PetscDraw draw)
426 {
427   PetscErrorCode ierr;
428 
429   PetscFunctionBegin;
430   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
431   if (draw->ops->setdoublebuffer) {
432     ierr = (*draw->ops->setdoublebuffer)(draw);CHKERRQ(ierr);
433   }
434   PetscFunctionReturn(0);
435 }
436 
437 #undef __FUNCT__
438 #define __FUNCT__ "PetscDrawGetSingleton"
439 /*@C
440    PetscDrawGetSingleton - Gain access to a PetscDraw object as if it were owned
441         by the one process.
442 
443    Collective on PetscDraw
444 
445    Input Parameter:
446 .  draw - the original window
447 
448    Output Parameter:
449 .  sdraw - the singleton window
450 
451    Level: advanced
452 
453 .seealso: PetscDrawRestoreSingleton(), PetscViewerGetSingleton(), PetscViewerRestoreSingleton()
454 
455 @*/
456 PetscErrorCode  PetscDrawGetSingleton(PetscDraw draw,PetscDraw *sdraw)
457 {
458   PetscErrorCode ierr;
459   PetscMPIInt    size;
460 
461   PetscFunctionBegin;
462   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
463   PetscValidPointer(sdraw,2);
464 
465   ierr = MPI_Comm_size(PetscObjectComm((PetscObject)draw),&size);CHKERRQ(ierr);
466   if (size == 1) {
467     ierr = PetscObjectReference((PetscObject)draw);CHKERRQ(ierr);
468     *sdraw = draw;
469   } else {
470     if (draw->ops->getsingleton) {
471       ierr = (*draw->ops->getsingleton)(draw,sdraw);CHKERRQ(ierr);
472     } else SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Cannot get singleton for this type %s of draw object",((PetscObject)draw)->type_name);
473   }
474   PetscFunctionReturn(0);
475 }
476 
477 #undef __FUNCT__
478 #define __FUNCT__ "PetscDrawRestoreSingleton"
479 /*@C
480    PetscDrawRestoreSingleton - Remove access to a PetscDraw object as if it were owned
481         by the one process.
482 
483    Collective on PetscDraw
484 
485    Input Parameters:
486 +  draw - the original window
487 -  sdraw - the singleton window
488 
489    Level: advanced
490 
491 .seealso: PetscDrawGetSingleton(), PetscViewerGetSingleton(), PetscViewerRestoreSingleton()
492 
493 @*/
494 PetscErrorCode  PetscDrawRestoreSingleton(PetscDraw draw,PetscDraw *sdraw)
495 {
496   PetscErrorCode ierr;
497   PetscMPIInt    size;
498 
499   PetscFunctionBegin;
500   PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1);
501   PetscValidPointer(sdraw,2);
502   PetscValidHeaderSpecific(*sdraw,PETSC_DRAW_CLASSID,2);
503 
504   ierr = MPI_Comm_size(PetscObjectComm((PetscObject)draw),&size);CHKERRQ(ierr);
505   if (size == 1) {
506     if (draw == *sdraw) {
507       ierr = PetscObjectDereference((PetscObject)draw);CHKERRQ(ierr);
508       *sdraw = NULL;
509     } else SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Cannot restore singleton, it is not the parent draw");
510   } else {
511     if (draw->ops->restoresingleton) {
512       ierr = (*draw->ops->restoresingleton)(draw,sdraw);CHKERRQ(ierr);
513     } else SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Cannot restore singleton for this type %s of draw object",((PetscObject)draw)->type_name);
514   }
515   PetscFunctionReturn(0);
516 }
517