15c6c1daeSBarry Smith 25c6c1daeSBarry Smith /* 35c6c1daeSBarry Smith This file contains routines to open an X window display and window 45c6c1daeSBarry Smith This consists of a number of routines that set the various 55c6c1daeSBarry Smith fields in the Window structure, which is passed to 65c6c1daeSBarry Smith all of these routines. 75c6c1daeSBarry Smith 85c6c1daeSBarry Smith Note that if you use the default visual and colormap, then you 95c6c1daeSBarry Smith can use these routines with any X toolkit that will give you the 105c6c1daeSBarry Smith Window id of the window that it is managing. Use that instead of the 115c6c1daeSBarry Smith call to PetscDrawXiCreateWindow . Similarly for the Display. 125c6c1daeSBarry Smith */ 135c6c1daeSBarry Smith 145c6c1daeSBarry Smith #include <../src/sys/classes/draw/impls/x/ximpl.h> 155c6c1daeSBarry Smith 165c6c1daeSBarry Smith extern PetscErrorCode PetscDrawXi_wait_map(PetscDraw_X*); 175c6c1daeSBarry Smith extern PetscErrorCode PetscDrawXiFontFixed(PetscDraw_X*,int,int,PetscDrawXiFont**); 185c6c1daeSBarry Smith extern PetscErrorCode PetscDrawXiInitCmap(PetscDraw_X*); 19*15d5bc79SLisandro Dalcin extern PetscErrorCode PetscDrawSetColormap_X(PetscDraw_X*,Colormap); 205c6c1daeSBarry Smith 215c6c1daeSBarry Smith /* 22*15d5bc79SLisandro Dalcin PetscDrawXiOpenDisplay - Open and setup a display 235c6c1daeSBarry Smith */ 245c6c1daeSBarry Smith #undef __FUNCT__ 255c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiOpenDisplay" 26*15d5bc79SLisandro Dalcin PetscErrorCode PetscDrawXiOpenDisplay(PetscDraw_X *XiWin,const char display[]) 275c6c1daeSBarry Smith { 285c6c1daeSBarry Smith PetscFunctionBegin; 29*15d5bc79SLisandro Dalcin XiWin->disp = XOpenDisplay(display); 305c6c1daeSBarry Smith if (!XiWin->disp) { 31*15d5bc79SLisandro Dalcin SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_LIB,"Unable to open display on %s\n\ 32*15d5bc79SLisandro Dalcin Make sure your COMPUTE NODES are authorized to connect \n\ 335c6c1daeSBarry Smith to this X server and either your DISPLAY variable\n\ 34*15d5bc79SLisandro Dalcin is set or you use the -display name option\n",display); 355c6c1daeSBarry Smith } 365c6c1daeSBarry Smith XiWin->screen = DefaultScreen(XiWin->disp); 37481cee7bSLisandro Dalcin XiWin->vis = DefaultVisual(XiWin->disp,XiWin->screen); 38481cee7bSLisandro Dalcin XiWin->depth = DefaultDepth(XiWin->disp,XiWin->screen); 39*15d5bc79SLisandro Dalcin XiWin->cmap = DefaultColormap(XiWin->disp,XiWin->screen); 40*15d5bc79SLisandro Dalcin XiWin->background = WhitePixel(XiWin->disp,XiWin->screen); 41*15d5bc79SLisandro Dalcin XiWin->foreground = BlackPixel(XiWin->disp,XiWin->screen); 425c6c1daeSBarry Smith PetscFunctionReturn(0); 435c6c1daeSBarry Smith } 445c6c1daeSBarry Smith 455c6c1daeSBarry Smith /* 46*15d5bc79SLisandro Dalcin PetscDrawXiSetGC - setup the GC structure 475c6c1daeSBarry Smith */ 485c6c1daeSBarry Smith #undef __FUNCT__ 495c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiSetGC" 505c6c1daeSBarry Smith PetscErrorCode PetscDrawXiSetGC(PetscDraw_X *XiWin,PetscDrawXiPixVal fg) 515c6c1daeSBarry Smith { 525c6c1daeSBarry Smith XGCValues gcvalues; /* window graphics context values */ 535c6c1daeSBarry Smith 545c6c1daeSBarry Smith PetscFunctionBegin; 555c6c1daeSBarry Smith /* Set the graphics contexts */ 565c6c1daeSBarry Smith /* create a gc for the ROP_SET operation (writing the fg value to a pixel) */ 575c6c1daeSBarry Smith /* (do this with function GXcopy; GXset will automatically write 1) */ 585c6c1daeSBarry Smith gcvalues.function = GXcopy; 595c6c1daeSBarry Smith gcvalues.foreground = fg; 605c6c1daeSBarry Smith XiWin->gc.cur_pix = fg; 615c6c1daeSBarry Smith XiWin->gc.set = XCreateGC(XiWin->disp,RootWindow(XiWin->disp,XiWin->screen),GCFunction|GCForeground,&gcvalues); 62*15d5bc79SLisandro Dalcin if (!XiWin->gc.set) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_LIB,"Unable to create X graphics context"); 63*15d5bc79SLisandro Dalcin PetscFunctionReturn(0); 64*15d5bc79SLisandro Dalcin } 65*15d5bc79SLisandro Dalcin 66*15d5bc79SLisandro Dalcin /* 67*15d5bc79SLisandro Dalcin PetscDrawXiInitialize - basic setup the draw (display, graphics context, font) 68*15d5bc79SLisandro Dalcin */ 69*15d5bc79SLisandro Dalcin #undef __FUNCT__ 70*15d5bc79SLisandro Dalcin #define __FUNCT__ "PetscDrawXiInitialize" 71*15d5bc79SLisandro Dalcin PetscErrorCode PetscDrawXiInitialize(PetscDraw_X *XiWin,char display[]) 72*15d5bc79SLisandro Dalcin { 73*15d5bc79SLisandro Dalcin PetscErrorCode ierr; 74*15d5bc79SLisandro Dalcin PetscFunctionBegin; 75*15d5bc79SLisandro Dalcin ierr = PetscDrawXiOpenDisplay(XiWin,display);CHKERRQ(ierr); 76*15d5bc79SLisandro Dalcin ierr = PetscDrawXiSetGC(XiWin,XiWin->foreground);CHKERRQ(ierr); 77*15d5bc79SLisandro Dalcin ierr = PetscDrawXiFontFixed(XiWin,6,10,&XiWin->font);CHKERRQ(ierr); 785c6c1daeSBarry Smith PetscFunctionReturn(0); 795c6c1daeSBarry Smith } 805c6c1daeSBarry Smith 815c6c1daeSBarry Smith /* 825c6c1daeSBarry Smith Actually display a window at [x,y] with sizes (w,h) 835c6c1daeSBarry Smith */ 845c6c1daeSBarry Smith #undef __FUNCT__ 855c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiDisplayWindow" 86*15d5bc79SLisandro Dalcin PetscErrorCode PetscDrawXiDisplayWindow(PetscDraw_X *XiWin,char *label,int x,int y,int w,int h) 875c6c1daeSBarry Smith { 885c6c1daeSBarry Smith unsigned int wavail,havail; 895c6c1daeSBarry Smith XSizeHints size_hints; 905c6c1daeSBarry Smith XWindowAttributes in_window_attributes; 915c6c1daeSBarry Smith XSetWindowAttributes window_attributes; 92*15d5bc79SLisandro Dalcin unsigned int border_width = 0; 93*15d5bc79SLisandro Dalcin unsigned long backgnd_pixel = WhitePixel(XiWin->disp,XiWin->screen); 945c6c1daeSBarry Smith unsigned long wmask; 955c6c1daeSBarry Smith 965c6c1daeSBarry Smith PetscFunctionBegin; 975c6c1daeSBarry Smith /* get the available widths */ 985c6c1daeSBarry Smith wavail = DisplayWidth(XiWin->disp,XiWin->screen); 995c6c1daeSBarry Smith havail = DisplayHeight(XiWin->disp,XiWin->screen); 1005c6c1daeSBarry Smith if (w <= 0 || h <= 0) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_LIB,"X Window display has invalid height or width"); 1015c6c1daeSBarry Smith if ((unsigned int)w > wavail) w = wavail; 1025c6c1daeSBarry Smith if ((unsigned int)h > havail) h = havail; 1035c6c1daeSBarry Smith 104*15d5bc79SLisandro Dalcin if (x < 0) x = (int)(wavail - (unsigned int)w + (unsigned int)x); 105*15d5bc79SLisandro Dalcin if (y < 0) y = (int)(havail - (unsigned int)h + (unsigned int)y); 106*15d5bc79SLisandro Dalcin x = ((unsigned int)x + w > wavail) ? (int)(wavail - (unsigned int)w) : x; 107*15d5bc79SLisandro Dalcin y = ((unsigned int)y + h > havail) ? (int)(havail - (unsigned int)h) : y; 1085c6c1daeSBarry Smith 1095c6c1daeSBarry Smith /* We need XCreateWindow since we may need an visual other than the default one */ 1105c6c1daeSBarry Smith XGetWindowAttributes(XiWin->disp,RootWindow(XiWin->disp,XiWin->screen),&in_window_attributes); 1115c6c1daeSBarry Smith window_attributes.background_pixmap = None; 1125c6c1daeSBarry Smith window_attributes.background_pixel = backgnd_pixel; 1135c6c1daeSBarry Smith /* No border for now */ 1145c6c1daeSBarry Smith window_attributes.border_pixmap = None; 1155c6c1daeSBarry Smith /* 1165c6c1daeSBarry Smith window_attributes.border_pixel = border_pixel; 1175c6c1daeSBarry Smith */ 1185c6c1daeSBarry Smith window_attributes.bit_gravity = in_window_attributes.bit_gravity; 1195c6c1daeSBarry Smith window_attributes.win_gravity = in_window_attributes.win_gravity; 1205c6c1daeSBarry Smith /* Backing store is too slow in color systems */ 121*15d5bc79SLisandro Dalcin window_attributes.backing_store = NotUseful; 1225c6c1daeSBarry Smith window_attributes.backing_pixel = backgnd_pixel; 1235c6c1daeSBarry Smith window_attributes.save_under = 1; 1245c6c1daeSBarry Smith window_attributes.event_mask = 0; 1255c6c1daeSBarry Smith window_attributes.do_not_propagate_mask = 0; 1265c6c1daeSBarry Smith window_attributes.override_redirect = 0; 1275c6c1daeSBarry Smith window_attributes.colormap = XiWin->cmap; 1285c6c1daeSBarry Smith /* None for cursor does NOT mean none, it means cursor of Parent */ 1295c6c1daeSBarry Smith window_attributes.cursor = None; 130a297a907SKarl Rupp 1315c6c1daeSBarry Smith wmask = CWBackPixmap | CWBackPixel | CWBorderPixmap | CWBitGravity | 1325c6c1daeSBarry Smith CWWinGravity | CWBackingStore | CWBackingPixel | CWOverrideRedirect | 1335c6c1daeSBarry Smith CWSaveUnder | CWEventMask | CWDontPropagate | 1345c6c1daeSBarry Smith CWCursor | CWColormap; 1355c6c1daeSBarry Smith 136*15d5bc79SLisandro Dalcin XiWin->win = XCreateWindow(XiWin->disp,RootWindow(XiWin->disp,XiWin->screen),x,y,w,h,border_width,XiWin->depth,InputOutput,XiWin->vis,wmask,&window_attributes); 1375c6c1daeSBarry Smith if (!XiWin->win) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_LIB,"Unable to open X window"); 1385c6c1daeSBarry Smith 1395c6c1daeSBarry Smith /* set window manager hints */ 1405c6c1daeSBarry Smith { 1415c6c1daeSBarry Smith XWMHints wm_hints; 1425c6c1daeSBarry Smith XClassHint class_hints; 1435c6c1daeSBarry Smith XTextProperty windowname,iconname; 1445c6c1daeSBarry Smith 145a297a907SKarl Rupp if (label) XStringListToTextProperty(&label,1,&windowname); 146a297a907SKarl Rupp else XStringListToTextProperty(&label,0,&windowname); 147a297a907SKarl Rupp if (label) XStringListToTextProperty(&label,1,&iconname); 148a297a907SKarl Rupp else XStringListToTextProperty(&label,0,&iconname); 1495c6c1daeSBarry Smith 1505c6c1daeSBarry Smith wm_hints.initial_state = NormalState; 1515c6c1daeSBarry Smith wm_hints.input = True; 1525c6c1daeSBarry Smith wm_hints.flags = StateHint|InputHint; 1535c6c1daeSBarry Smith 1545c6c1daeSBarry Smith /* These properties can be used by window managers to decide how to display a window */ 1555c6c1daeSBarry Smith class_hints.res_name = (char*)"petsc"; 1565c6c1daeSBarry Smith class_hints.res_class = (char*)"PETSc"; 1575c6c1daeSBarry Smith 1585c6c1daeSBarry Smith size_hints.x = x; 1595c6c1daeSBarry Smith size_hints.y = y; 1605c6c1daeSBarry Smith size_hints.min_width = 4*border_width; 1615c6c1daeSBarry Smith size_hints.min_height = 4*border_width; 1625c6c1daeSBarry Smith size_hints.width = w; 1635c6c1daeSBarry Smith size_hints.height = h; 1645c6c1daeSBarry Smith size_hints.flags = USPosition | USSize | PMinSize; 1655c6c1daeSBarry Smith 1665c6c1daeSBarry Smith XSetWMProperties(XiWin->disp,XiWin->win,&windowname,&iconname,0,0,&size_hints,&wm_hints,&class_hints); 1675c6c1daeSBarry Smith XFree((void*)windowname.value); 1685c6c1daeSBarry Smith XFree((void*)iconname.value); 1695c6c1daeSBarry Smith } 170481cee7bSLisandro Dalcin 1715c6c1daeSBarry Smith /* make the window visible */ 1725c6c1daeSBarry Smith XSelectInput(XiWin->disp,XiWin->win,ExposureMask|StructureNotifyMask); 1735c6c1daeSBarry Smith XMapWindow(XiWin->disp,XiWin->win); 1745c6c1daeSBarry Smith 1755c6c1daeSBarry Smith /* some window systems are cruel and interfere with the placement of 1765c6c1daeSBarry Smith windows. We wait here for the window to be created or to die */ 1775c6c1daeSBarry Smith if (PetscDrawXi_wait_map(XiWin)) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_LIB,"Wait for X window failed"); 1785c6c1daeSBarry Smith PetscFunctionReturn(0); 1795c6c1daeSBarry Smith } 1805c6c1daeSBarry Smith 1815c6c1daeSBarry Smith #undef __FUNCT__ 1825c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiQuickWindow" 183*15d5bc79SLisandro Dalcin PetscErrorCode PetscDrawXiQuickWindow(PetscDraw_X *XiWin,char *name,int x,int y,int nx,int ny) 1845c6c1daeSBarry Smith { 185*15d5bc79SLisandro Dalcin Window root; 186*15d5bc79SLisandro Dalcin unsigned int w,h,dummy; 1875c6c1daeSBarry Smith PetscErrorCode ierr; 1885c6c1daeSBarry Smith 1895c6c1daeSBarry Smith PetscFunctionBegin; 190*15d5bc79SLisandro Dalcin ierr = PetscDrawSetColormap_X(XiWin,(Colormap)0);CHKERRQ(ierr); 191*15d5bc79SLisandro Dalcin ierr = PetscDrawXiDisplayWindow(XiWin,name,x,y,nx,ny);CHKERRQ(ierr); 192*15d5bc79SLisandro Dalcin XSetWindowBackground(XiWin->disp,XiWin->win,XiWin->background); 193*15d5bc79SLisandro Dalcin XClearWindow(XiWin->disp,XiWin->win); 1945c6c1daeSBarry Smith 195*15d5bc79SLisandro Dalcin XGetGeometry(XiWin->disp,XiWin->win,&root,&x,&y,&w,&h,&dummy,&dummy); 196*15d5bc79SLisandro Dalcin XiWin->x = x; 197*15d5bc79SLisandro Dalcin XiWin->y = y; 198*15d5bc79SLisandro Dalcin XiWin->w = (int)w; 199*15d5bc79SLisandro Dalcin XiWin->h = (int)h; 2005c6c1daeSBarry Smith PetscFunctionReturn(0); 2015c6c1daeSBarry Smith } 2025c6c1daeSBarry Smith 2035c6c1daeSBarry Smith /* 2045c6c1daeSBarry Smith A version from an already defined window 2055c6c1daeSBarry Smith */ 2065c6c1daeSBarry Smith #undef __FUNCT__ 2075c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiQuickWindowFromWindow" 208*15d5bc79SLisandro Dalcin PetscErrorCode PetscDrawXiQuickWindowFromWindow(PetscDraw_X *XiWin,Window win) 2095c6c1daeSBarry Smith { 2105c6c1daeSBarry Smith Window root; 211*15d5bc79SLisandro Dalcin int x,y; 212*15d5bc79SLisandro Dalcin unsigned int w,h,dummy; 2135c6c1daeSBarry Smith XWindowAttributes attributes; 214*15d5bc79SLisandro Dalcin PetscErrorCode ierr; 2155c6c1daeSBarry Smith 2165c6c1daeSBarry Smith PetscFunctionBegin; 217*15d5bc79SLisandro Dalcin XiWin->win = win; 218*15d5bc79SLisandro Dalcin XGetWindowAttributes(XiWin->disp,XiWin->win,&attributes); 219*15d5bc79SLisandro Dalcin ierr = PetscDrawSetColormap_X(XiWin,attributes.colormap);CHKERRQ(ierr); 220481cee7bSLisandro Dalcin 221*15d5bc79SLisandro Dalcin XGetGeometry(XiWin->disp,XiWin->win,&root,&x,&y,&w,&h,&dummy,&dummy); 222*15d5bc79SLisandro Dalcin XiWin->x = x; 223*15d5bc79SLisandro Dalcin XiWin->y = y; 224*15d5bc79SLisandro Dalcin XiWin->w = (int)w; 225*15d5bc79SLisandro Dalcin XiWin->h = (int)h; 2265c6c1daeSBarry Smith PetscFunctionReturn(0); 2275c6c1daeSBarry Smith } 2285c6c1daeSBarry Smith 2295c6c1daeSBarry Smith /* 2305c6c1daeSBarry Smith PetscDrawXiSetWindowLabel - Sets new label in open window. 2315c6c1daeSBarry Smith */ 2325c6c1daeSBarry Smith #undef __FUNCT__ 2335c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiSetWindowLabel" 234*15d5bc79SLisandro Dalcin PetscErrorCode PetscDrawXiSetWindowLabel(PetscDraw_X *XiWin,char *label) 2355c6c1daeSBarry Smith { 2365c6c1daeSBarry Smith XTextProperty prop; 2375c6c1daeSBarry Smith size_t len; 2385c6c1daeSBarry Smith PetscErrorCode ierr; 2395c6c1daeSBarry Smith 2405c6c1daeSBarry Smith PetscFunctionBegin; 2415c6c1daeSBarry Smith ierr = PetscStrlen(label,&len);CHKERRQ(ierr); 242*15d5bc79SLisandro Dalcin XGetWMName(XiWin->disp,XiWin->win,&prop); 243*15d5bc79SLisandro Dalcin prop.value = (unsigned char*)label; 2445c6c1daeSBarry Smith prop.nitems = (long)len; 245*15d5bc79SLisandro Dalcin XSetWMName(XiWin->disp,XiWin->win,&prop); 2465c6c1daeSBarry Smith PetscFunctionReturn(0); 2475c6c1daeSBarry Smith } 2485c6c1daeSBarry Smith 2495c6c1daeSBarry Smith #undef __FUNCT__ 2505c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawXiSetToBackground" 2515c6c1daeSBarry Smith PetscErrorCode PetscDrawXiSetToBackground(PetscDraw_X *XiWin) 2525c6c1daeSBarry Smith { 2535c6c1daeSBarry Smith PetscFunctionBegin; 2545c6c1daeSBarry Smith if (XiWin->gc.cur_pix != XiWin->background) { 2555c6c1daeSBarry Smith XSetForeground(XiWin->disp,XiWin->gc.set,XiWin->background); 2565c6c1daeSBarry Smith XiWin->gc.cur_pix = XiWin->background; 2575c6c1daeSBarry Smith } 2585c6c1daeSBarry Smith PetscFunctionReturn(0); 2595c6c1daeSBarry Smith 2605c6c1daeSBarry Smith } 2615c6c1daeSBarry Smith 2625c6c1daeSBarry Smith #undef __FUNCT__ 2635c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawSetSave_X" 2645c6c1daeSBarry Smith PetscErrorCode PetscDrawSetSave_X(PetscDraw draw,const char *filename) 2655c6c1daeSBarry Smith { 2665c6c1daeSBarry Smith PetscErrorCode ierr; 2675c6c1daeSBarry Smith #if defined(PETSC_HAVE_POPEN) 2685c6c1daeSBarry Smith PetscMPIInt rank; 2695c6c1daeSBarry Smith #endif 2705c6c1daeSBarry Smith 2715c6c1daeSBarry Smith PetscFunctionBegin; 2725c6c1daeSBarry Smith PetscValidHeaderSpecific(draw,PETSC_DRAW_CLASSID,1); 2735c6c1daeSBarry Smith #if defined(PETSC_HAVE_POPEN) 274ce94432eSBarry Smith ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)draw),&rank);CHKERRQ(ierr); 2755c6c1daeSBarry Smith if (!rank) { 276d45a07a7SBarry Smith char command[PETSC_MAX_PATH_LEN]; 277d45a07a7SBarry Smith FILE *fd; 278d45a07a7SBarry Smith int err; 279d45a07a7SBarry Smith 280d45a07a7SBarry Smith ierr = PetscMemzero(command,sizeof(command));CHKERRQ(ierr); 2819982bd17SBarry Smith ierr = PetscSNPrintf(command,PETSC_MAX_PATH_LEN,"rm -fr %s %s.m4v",draw->savefilename,draw->savefilename);CHKERRQ(ierr); 282e97f6855SBarry Smith ierr = PetscPOpen(PETSC_COMM_SELF,NULL,command,"r",&fd);CHKERRQ(ierr); 2830076e027SBarry Smith ierr = PetscPClose(PETSC_COMM_SELF,fd,&err);CHKERRQ(ierr); 2849982bd17SBarry Smith ierr = PetscSNPrintf(command,PETSC_MAX_PATH_LEN,"mkdir %s",draw->savefilename);CHKERRQ(ierr); 285e97f6855SBarry Smith ierr = PetscPOpen(PETSC_COMM_SELF,NULL,command,"r",&fd);CHKERRQ(ierr); 2860076e027SBarry Smith ierr = PetscPClose(PETSC_COMM_SELF,fd,&err);CHKERRQ(ierr); 2875c6c1daeSBarry Smith } 2885c6c1daeSBarry Smith #endif 2895c6c1daeSBarry Smith PetscFunctionReturn(0); 2905c6c1daeSBarry Smith } 2915c6c1daeSBarry Smith 2921cda70a7SBarry Smith 2935c6c1daeSBarry Smith #if defined(PETSC_HAVE_AFTERIMAGE) 2945c6c1daeSBarry Smith #include <afterimage.h> 295aee23540SBarry Smith 29676f01e85SBarry Smith /* String names of possible Afterimage formats */ 29776f01e85SBarry Smith const char *PetscAfterImageFormats[] = { 29876f01e85SBarry Smith ".Xpm", 29976f01e85SBarry Smith ".Xpm.Z", 30076f01e85SBarry Smith ".Xpm.gz", 30176f01e85SBarry Smith ".Png", 30276f01e85SBarry Smith ".Jpeg", 303f140b876SBarry Smith ".Xcf", /* Gimp format */ 30476f01e85SBarry Smith ".Ppm", 30576f01e85SBarry Smith ".Pnm", 306f140b876SBarry Smith "MS Windows Bitmap", 307f140b876SBarry Smith "MS Windows Icon", 308f140b876SBarry Smith "MS Windows Cursor", 30976f01e85SBarry Smith ".Gif", 31076f01e85SBarry Smith ".Tiff", 311f140b876SBarry Smith "Afterstep XMLScript", 312f140b876SBarry Smith "Scalable Vector Graphics (SVG)", 31376f01e85SBarry Smith ".Xbm", 31476f01e85SBarry Smith "Targa", 31576f01e85SBarry Smith ".Pcx", 31676f01e85SBarry Smith ".HTML", 31776f01e85SBarry Smith "XML", 31876f01e85SBarry Smith "Unknown" 319aee23540SBarry Smith }; 320aee23540SBarry Smith 321aee23540SBarry Smith #undef __FUNCT__ 32276f01e85SBarry Smith #define __FUNCT__ "PetscAfterimageStringToFormat" 32376f01e85SBarry Smith static PetscErrorCode PetscAfterimageStringToFormat(const char *ext,ASImageFileTypes *format) 324aee23540SBarry Smith { 32576f01e85SBarry Smith PetscInt i; 326aee23540SBarry Smith PetscErrorCode ierr; 32776f01e85SBarry Smith PetscBool flg; 328aee23540SBarry Smith 329aee23540SBarry Smith PetscFunctionBegin; 330f140b876SBarry Smith ierr = PetscStrcasecmp(".Jpg",ext,&flg);CHKERRQ(ierr); 331f140b876SBarry Smith if (flg) ext = ".Jpeg"; 33276f01e85SBarry Smith for (i=0; i<sizeof(PetscAfterImageFormats)/sizeof(char**); i++) { 33376f01e85SBarry Smith ierr = PetscStrcasecmp(PetscAfterImageFormats[i],ext,&flg);CHKERRQ(ierr); 33476f01e85SBarry Smith if (flg) { 33576f01e85SBarry Smith *format = (ASImageFileTypes)i; 33676f01e85SBarry Smith PetscFunctionReturn(0); 33776f01e85SBarry Smith } 33876f01e85SBarry Smith } 33976f01e85SBarry Smith *format = ASIT_Unknown; 34076f01e85SBarry Smith PetscFunctionReturn(0); 34176f01e85SBarry Smith } 34276f01e85SBarry Smith 34376f01e85SBarry Smith #if defined(PETSC_HAVE_SAWS) 34476f01e85SBarry Smith #include <petscviewersaws.h> 34576f01e85SBarry Smith /* 34676f01e85SBarry Smith The PetscAfterimage object and functions are used to maintain a list of file images created by Afterimage that can 34776f01e85SBarry Smith be displayed by the SAWs webserver. 34876f01e85SBarry Smith */ 34976f01e85SBarry Smith typedef struct _P_PetscAfterimage *PetscAfterimage; 35076f01e85SBarry Smith struct _P_PetscAfterimage { 35176f01e85SBarry Smith PetscAfterimage next; 35276f01e85SBarry Smith char *filename; 35376f01e85SBarry Smith char *ext; 35476f01e85SBarry Smith PetscInt cnt; 35576f01e85SBarry Smith } ; 35676f01e85SBarry Smith 35776f01e85SBarry Smith static PetscAfterimage afterimages = 0; 35876f01e85SBarry Smith 35976f01e85SBarry Smith #undef __FUNCT__ 36076f01e85SBarry Smith #define __FUNCT__ "PetscAfterimageDestroy" 36176f01e85SBarry Smith static PetscErrorCode PetscAfterimageDestroy(void) 36276f01e85SBarry Smith { 36376f01e85SBarry Smith PetscErrorCode ierr; 36476f01e85SBarry Smith PetscAfterimage afterimage,oafterimage = afterimages; 36576f01e85SBarry Smith 36676f01e85SBarry Smith PetscFunctionBegin; 36776f01e85SBarry Smith while (oafterimage) { 36876f01e85SBarry Smith afterimage = oafterimage->next; 36976f01e85SBarry Smith ierr = PetscFree(oafterimage->filename);CHKERRQ(ierr); 37076f01e85SBarry Smith ierr = PetscFree(oafterimage->ext);CHKERRQ(ierr); 37176f01e85SBarry Smith ierr = PetscFree(oafterimage);CHKERRQ(ierr); 37276f01e85SBarry Smith oafterimage = afterimage; 373aee23540SBarry Smith } 374aee23540SBarry Smith PetscFunctionReturn(0); 375aee23540SBarry Smith } 376aee23540SBarry Smith 377aee23540SBarry Smith #undef __FUNCT__ 37876f01e85SBarry Smith #define __FUNCT__ "PetscAfterimageAdd" 37976f01e85SBarry Smith static PetscErrorCode PetscAfterimageAdd(const char *filename,const char *ext,PetscInt cnt) 380aee23540SBarry Smith { 381aee23540SBarry Smith PetscErrorCode ierr; 38276f01e85SBarry Smith PetscAfterimage afterimage,oafterimage = afterimages; 383aee23540SBarry Smith PetscBool flg; 384aee23540SBarry Smith 385aee23540SBarry Smith PetscFunctionBegin; 38676f01e85SBarry Smith if (oafterimage){ 38776f01e85SBarry Smith ierr = PetscStrcmp(filename,oafterimage->filename,&flg);CHKERRQ(ierr); 38876f01e85SBarry Smith if (flg) { 38976f01e85SBarry Smith oafterimage->cnt = cnt; 39076f01e85SBarry Smith PetscFunctionReturn(0); 391aee23540SBarry Smith } 39276f01e85SBarry Smith while (oafterimage->next) { 39376f01e85SBarry Smith oafterimage = oafterimage->next; 39476f01e85SBarry Smith ierr = PetscStrcmp(filename,oafterimage->filename,&flg);CHKERRQ(ierr); 39576f01e85SBarry Smith if (flg) { 39676f01e85SBarry Smith oafterimage->cnt = cnt; 39776f01e85SBarry Smith PetscFunctionReturn(0); 39876f01e85SBarry Smith } 39976f01e85SBarry Smith } 40076f01e85SBarry Smith ierr = PetscNew(&afterimage);CHKERRQ(ierr); 40176f01e85SBarry Smith oafterimage->next = afterimage; 402aee23540SBarry Smith } else { 40376f01e85SBarry Smith ierr = PetscNew(&afterimage);CHKERRQ(ierr); 40476f01e85SBarry Smith afterimages = afterimage; 405aee23540SBarry Smith } 40676f01e85SBarry Smith ierr = PetscStrallocpy(filename,&afterimage->filename);CHKERRQ(ierr); 40776f01e85SBarry Smith ierr = PetscStrallocpy(ext,&afterimage->ext);CHKERRQ(ierr); 40876f01e85SBarry Smith afterimage->cnt = cnt; 40976f01e85SBarry Smith ierr = PetscRegisterFinalize(PetscAfterimageDestroy);CHKERRQ(ierr); 410aee23540SBarry Smith PetscFunctionReturn(0); 411aee23540SBarry Smith } 412aee23540SBarry Smith 413aee23540SBarry Smith #endif 414aee23540SBarry Smith 4155c6c1daeSBarry Smith #undef __FUNCT__ 4165c6c1daeSBarry Smith #define __FUNCT__ "PetscDrawSave_X" 4175c6c1daeSBarry Smith PetscErrorCode PetscDrawSave_X(PetscDraw draw) 4185c6c1daeSBarry Smith { 4195c6c1daeSBarry Smith PetscDraw_X *drawx = (PetscDraw_X*)draw->data; 4205c6c1daeSBarry Smith XImage *image; 4215c6c1daeSBarry Smith ASImage *asimage; 422681455b2SBarry Smith struct ASVisual *asv; 4235c6c1daeSBarry Smith char filename[PETSC_MAX_PATH_LEN]; 4245c6c1daeSBarry Smith PetscErrorCode ierr; 4255c6c1daeSBarry Smith PetscMPIInt rank; 426681455b2SBarry Smith int depth; 42776f01e85SBarry Smith ASImageFileTypes format; 4285c6c1daeSBarry Smith 4295c6c1daeSBarry Smith PetscFunctionBegin; 430ce94432eSBarry Smith ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)draw),&rank);CHKERRQ(ierr); 4315c6c1daeSBarry Smith if (rank) PetscFunctionReturn(0); 4325c6c1daeSBarry Smith if (!draw->savefilename) PetscFunctionReturn(0); 4335c6c1daeSBarry Smith if (draw->savefilecount == -1) { 4345c6c1daeSBarry Smith /* The first PetscDrawClear() should happen before any drawing has been done, hence do not save at the first PetscDrawClear() */ 4355c6c1daeSBarry Smith draw->savefilecount++; 4365c6c1daeSBarry Smith PetscFunctionReturn(0); 4375c6c1daeSBarry Smith } 438681455b2SBarry Smith XSynchronize(drawx->disp, True); 439681455b2SBarry Smith depth = DefaultDepth( drawx->disp, drawx->screen ); 440681455b2SBarry Smith asv = create_asvisual(drawx->disp, drawx->screen, depth, NULL);if (!asv) SETERRQ(PetscObjectComm((PetscObject)draw),PETSC_ERR_PLIB,"Cannot create AfterImage ASVisual"); 4415c6c1daeSBarry Smith 4429982bd17SBarry Smith image = XGetImage(drawx->disp, drawx->drw ? drawx->drw : drawx->win, 0, 0, drawx->w, drawx->h, AllPlanes, ZPixmap); 44376f01e85SBarry Smith if (!image) SETERRQ(PetscObjectComm((PetscObject)draw),PETSC_ERR_PLIB,"Cannot XGetImage()"); 444ce94432eSBarry Smith asimage = picture_ximage2asimage (asv,image,0,0);if (!asimage) SETERRQ(PetscObjectComm((PetscObject)draw),PETSC_ERR_PLIB,"Cannot create AfterImage ASImage"); 4458b7fcac6SBarry Smith if (draw->savesinglefile) { 44676f01e85SBarry Smith ierr = PetscSNPrintf(filename,PETSC_MAX_PATH_LEN,"%s/%s%s",draw->savefilename,draw->savefilename,draw->savefilenameext);CHKERRQ(ierr); 4478b7fcac6SBarry Smith } else { 44876f01e85SBarry Smith ierr = PetscSNPrintf(filename,PETSC_MAX_PATH_LEN,"%s/%s_%d%s",draw->savefilename,draw->savefilename,draw->savefilecount++,draw->savefilenameext);CHKERRQ(ierr); 4498b7fcac6SBarry Smith } 45076f01e85SBarry Smith ierr = PetscAfterimageStringToFormat(draw->savefilenameext,&format);CHKERRQ(ierr); 45176f01e85SBarry Smith ASImage2file(asimage, 0, filename,format,0); 4521cda70a7SBarry Smith #if defined(PETSC_HAVE_SAWS) 4531cda70a7SBarry Smith { 454aee23540SBarry Smith char body[4096]; 45576f01e85SBarry Smith PetscAfterimage afterimage; 456aee23540SBarry Smith size_t len = 0; 457aee23540SBarry Smith 45876f01e85SBarry Smith ierr = PetscAfterimageAdd(draw->savefilename,draw->savefilenameext,draw->savefilecount-1);CHKERRQ(ierr); 45976f01e85SBarry Smith afterimage = afterimages; 46076f01e85SBarry Smith while (afterimage) { 46176f01e85SBarry Smith if (draw->savesinglefile) { 46276f01e85SBarry Smith ierr = PetscSNPrintf(body+len,4086-len,"<img src=\"%s/%s%s\" alt=\"None\">",afterimage->filename,afterimage->filename,afterimage->ext);CHKERRQ(ierr); 46376f01e85SBarry Smith } else { 46476f01e85SBarry Smith ierr = PetscSNPrintf(body+len,4086-len,"<img src=\"%s/%s_%d%s\" alt=\"None\">",afterimage->filename,afterimage->filename,afterimage->cnt,afterimage->ext);CHKERRQ(ierr); 46576f01e85SBarry Smith } 466aee23540SBarry Smith ierr = PetscStrlen(body,&len);CHKERRQ(ierr); 46776f01e85SBarry Smith afterimage = afterimage->next; 468aee23540SBarry Smith } 469aee23540SBarry Smith ierr = PetscStrcat(body,"<br>\n");CHKERRQ(ierr); 47043da4ab2SBarry Smith if (draw->savefilecount > 0) PetscStackCallSAWs(SAWs_Pop_Body,("index.html",1)); 47143da4ab2SBarry Smith PetscStackCallSAWs(SAWs_Push_Body,("index.html",1,body)); 4721cda70a7SBarry Smith } 4731cda70a7SBarry Smith #endif 4745c6c1daeSBarry Smith 4755c6c1daeSBarry Smith XDestroyImage(image); 476681455b2SBarry Smith destroy_asvisual(asv,0); 4775c6c1daeSBarry Smith PetscFunctionReturn(0); 4785c6c1daeSBarry Smith } 4795c6c1daeSBarry Smith /* 4805c6c1daeSBarry Smith There are routines wanted by AfterImage for PNG files 4815c6c1daeSBarry Smith */ 4825c6c1daeSBarry Smith void crc32(void) {;} 4835c6c1daeSBarry Smith void inflateReset(void) {;} 4845c6c1daeSBarry Smith void deflateReset(void) {;} 4855c6c1daeSBarry Smith void deflateInit2(void) {;} 4865c6c1daeSBarry Smith void deflateInit2_(void) {;} 4875c6c1daeSBarry Smith void deflate(void) {;} 4885c6c1daeSBarry Smith void deflateEnd(void) {;} 4895c6c1daeSBarry Smith 4905c6c1daeSBarry Smith #endif 4915c6c1daeSBarry Smith 4925c6c1daeSBarry Smith 4935c6c1daeSBarry Smith 494