1 /*****************************************************************************
2 Major portions of this software are copyrighted by the Medical College
3 of Wisconsin, 1994-2000, and are released under the Gnu General Public
4 License, Version 2. See the file README.Copyright for details.
5 ******************************************************************************/
6
7 #define MAIN
8
9 #include <X11/Intrinsic.h>
10 #include <X11/StringDefs.h>
11 #include <X11/Shell.h>
12 #include <stdio.h>
13
14 #include <Xm/XmAll.h>
15 #include "mrilib.h"
16
17 static char * vcl[] = { "StaticGray" , "GrayScale" , "StaticColor" ,
18 "PseudoColor" , "TrueColor" , "DirectColor" } ;
19
20 static XImage * xim = NULL ;
21 static int xim_ww = 0 ;
22 static int xim_hh = 0 ;
23
24 #undef USE_TRUECOLOR
25
26 #define USE_PIXMAP
27 #ifdef USE_PIXMAP
28 # define WANT_LOGO_BITMAP
29 # include "logo.h"
30 #endif
31
32 XImage * rgb_to_XImage( Display * dis , XVisualInfo * vin , MRI_IMAGE * im ) ;
33
fred_CB(Widget w,XtPointer cd,XtPointer cb)34 void fred_CB( Widget w , XtPointer cd , XtPointer cb ){ exit(0); }
35
elvis_CB(Widget w,XtPointer cd,XtPointer cb)36 void elvis_CB( Widget w , XtPointer cd , XtPointer cb )
37 {
38 static int needGC = 1 ;
39 static GC myGC ;
40 XmDrawingAreaCallbackStruct * cbs = (XmDrawingAreaCallbackStruct *) cb ;
41 XExposeEvent * ev = (XExposeEvent *) cbs->event ;
42 Dimension nx=0 , ny=0 ;
43 int ii , jj ;
44
45 if( cbs->reason != XmCR_EXPOSE || ev->count > 0 ) return ;
46
47 if( needGC ){
48 XGCValues gcv;
49 gcv.function = GXcopy ;
50 myGC = XCreateGC( XtDisplay(w) , XtWindow(w) , GCFunction , &gcv ) ;
51 needGC = 0 ;
52 }
53
54 XtVaGetValues( w , XmNwidth , &nx , XmNheight , &ny , NULL ) ;
55
56 #ifdef USE_TRUECOLOR
57 ii = 0 ;
58 do{
59 jj = 0 ;
60 do{
61 XPutImage( XtDisplay(w),XtWindow(w),myGC,xim,0,0,ii,jj,xim_ww,xim_hh) ;
62 jj += xim_hh + 4 ;
63 } while( jj < ny ) ;
64 ii += xim_ww ;
65 } while( ii < nx ) ;
66 #else
67 # ifdef USE_PIXMAP
68 ii = 0 ;
69 do{ jj = 0 ;
70 do{
71 XCopyArea( XtDisplay(w),logo_pixmap , XtWindow(w),myGC ,
72 0,0,logo_width,logo_height , ii,jj ) ;
73 jj += logo_height + 4 ;
74 } while( jj < ny ) ;
75 ii += logo_width ;
76 } while( ii < nx ) ;
77 # endif /* USE_PIXMAP */
78 #endif /* USE_TRUECOLOR */
79
80 return ;
81 }
82
main(int argc,char * argv[])83 int main( int argc , char * argv[] )
84 {
85 XtAppContext app; /* the application context */
86 Widget top; /* toplevel widget */
87 Display *dpy; /* display */
88 Colormap colormap; /* created colormap */
89 XVisualInfo vinfo; /* template for find visual */
90 Visual *vis ; /* the Visual itself */
91 XVisualInfo *vinfo_list; /* returned list of visuals */
92 int count; /* number of matchs (only 1?) */
93 int vid , stat ;
94 Widget fred , fff ;
95
96 top = XtVaAppInitialize( &app , "test" , NULL , 0 , &argc , argv , NULL , NULL ) ;
97 dpy = XtDisplay (top);
98
99 #ifndef USE_TRUECOLOR
100 stat = XMatchVisualInfo( dpy,XScreenNumberOfScreen(XtScreen(top)),
101 8,PseudoColor,&vinfo ) ;
102 if( stat == 0 ){ printf("no 8 bit visual\n") ; exit(1) ; }
103 #else
104 vid = strtol( argv[1] , NULL , 0 ) ;
105 vinfo.visualid = (VisualID) vid ;
106 vinfo_list = XGetVisualInfo (dpy, VisualIDMask, &vinfo, &count);
107 if( count == 0 || vinfo_list == NULL ){fprintf(stderr,"no match\n");exit(1);}
108 vinfo = vinfo_list[0] ;
109 #endif
110 vid = vinfo.visualid ;
111 vis = vinfo.visual ;
112
113 colormap = XCreateColormap( dpy, RootWindowOfScreen(XtScreen(top)) ,
114 vis , AllocNone ) ;
115
116 XtVaSetValues( top ,
117 XtNborderColor , 0 ,
118 XtNbackground , 0 ,
119 XtNdepth , vinfo.depth ,
120 XtNcolormap , colormap ,
121 XtNvisual , vis ,
122 NULL ) ;
123
124 fff = XtVaCreateWidget( "dialog" , xmFormWidgetClass , top ,
125 XmNborderWidth , 0 ,
126 NULL ) ;
127
128 #ifndef LABEL_ARG
129 #define LABEL_ARG(str) \
130 XtVaTypedArg , XmNlabelString , XmRString , (str) , strlen(str)+1
131 #endif
132
133 fred = XtVaCreateManagedWidget( "dialog" , xmPushButtonWidgetClass , fff ,
134 LABEL_ARG("Jumpback") ,
135 XmNtopAttachment , XmATTACH_FORM ,
136 XmNleftAttachment , XmATTACH_FORM ,
137 XmNrightAttachment , XmATTACH_FORM ,
138 NULL ) ;
139 XtAddCallback( fred , XmNactivateCallback , fred_CB , NULL ) ;
140
141 fred = XtVaCreateManagedWidget( "dialog" , xmDrawingAreaWidgetClass , fff ,
142 XmNtopAttachment , XmATTACH_WIDGET ,
143 XmNtopWidget , fred ,
144 XmNleftAttachment , XmATTACH_FORM ,
145 XmNrightAttachment , XmATTACH_FORM ,
146 XmNbottomAttachment , XmATTACH_FORM ,
147 NULL ) ;
148
149 XtAddCallback( fred , XmNexposeCallback , elvis_CB , NULL ) ;
150
151 #ifdef USE_TRUECOLOR
152 { MRI_IMAGE * im ;
153 im = mri_read_ppm( "bob.ppm" ) ;
154 xim = rgb_to_XImage( XtDisplay(top) , &vinfo , im ) ;
155 xim_ww = im->nx ; xim_hh = im->ny ;
156 mri_free(im) ;
157 }
158 #else
159 xim_ww = xim_hh = 77 ;
160 #endif
161
162 XtVaSetValues( top ,
163 XmNwidth , xim_ww ,
164 XmNheight , xim_hh+40 ,
165 NULL ) ;
166
167 #ifdef USE_PIXMAP
168 { Pixel bg_pix=0 , fg_pix=0 ;
169 # define ICON_bg bg_pix
170 # define ICON_fg fg_pix
171
172 XtVaGetValues( fred ,
173 XmNforeground , &bg_pix , /* note reversal of roles here! */
174 XmNbackground , &fg_pix ,
175 NULL ) ;
176
177 logo_pixmap = XCreatePixmapFromBitmapData(
178 XtDisplay(top) ,
179 RootWindowOfScreen(XtScreen(top)) ,
180 logo_bits , logo_width , logo_height ,
181 fg_pix , bg_pix ,
182 DefaultDepthOfScreen(XtScreen(top)) ) ;
183
184 XtVaSetValues( top , XmNiconPixmap , logo_pixmap , NULL ) ;
185 }
186 #endif
187
188
189 XtManageChild(fff) ;
190 XtRealizeWidget(top); NI_sleep(1);
191 XtAppMainLoop(app);
192
193 exit(0); /* never reached */
194 }
195
196 #ifdef USE_TRUECOLOR
197 /*---------------------------------------------------------------------------
198 Create an XImage from an RGB image. Adapted from program "xv".
199 The output of this can be XPutImage-d to a window.
200 -----------------------------------------------------------------------------*/
201
202 static int highbit(unsigned long ul) ; /* prototype */
203
rgb_to_XImage(Display * dis,XVisualInfo * vin,MRI_IMAGE * im)204 XImage * rgb_to_XImage( Display * dis , XVisualInfo * vin , MRI_IMAGE * im )
205 {
206 unsigned long r, g, b, rmask, gmask, bmask ;
207 int rshift, gshift, bshift, bperpix, bperline, border, i,j ;
208 int wide, high ;
209 byte *imagedata, *lip, *ip, *pp ;
210 XImage *xim = NULL ;
211 int *xcol ;
212
213 /* check inputs */
214
215 #if defined(__cplusplus) || defined(c_plusplus)
216 if( vin==NULL || vin->c_class!=TrueColor || im==NULL || im->kind!=MRI_rgb ){
217 #else
218 if( vin==NULL || vin->class!=TrueColor || im==NULL || im->kind!=MRI_rgb ){
219 #endif
220 fprintf(stderr,"\a\n*** ILLEGAL input to rgb_to_XImage\n") ;
221 sleep(1) ; exit(1) ;
222 }
223
224 /* get color masks and shifts to put high bit of color byte into place */
225
226 rmask = vin->red_mask ; rshift = 7 - highbit(rmask) ;
227 gmask = vin->green_mask ; gshift = 7 - highbit(gmask) ;
228 bmask = vin->blue_mask ; bshift = 7 - highbit(bmask) ;
229
230 /* input image dimensions */
231
232 wide = im->nx ;
233 high = im->ny ;
234
235 /* make output XImage */
236
237 xim = XCreateImage( dis , vin->visual , vin->depth , ZPixmap, 0, NULL,
238 wide, high, 32, 0) ;
239
240 bperline = xim->bytes_per_line ;
241 bperpix = xim->bits_per_pixel ;
242 border = xim->byte_order ;
243
244 if(bperpix != 8 && bperpix != 16 && bperpix != 24 && bperpix != 32){
245 fprintf(stderr,"\a\n*** rgb_to_XImage: can't use %d-bit TrueColor\n",bperpix) ;
246 sleep(1) ; exit(1) ;
247 }
248
249 /* make output image array */
250
251 imagedata = (byte *) XtMalloc((size_t) (high * bperline)) ;
252 xim->data = (char *) imagedata ;
253
254 lip = imagedata ; /* pointer to row of output image array */
255 pp = MRI_RGB_PTR(im) ; /* pointer to input image data */
256
257 xcol = (int *) malloc(sizeof(int) * wide) ; /* row of output colors */
258
259 /*-- loop over image --*/
260
261 for (i=0; i<high; i++, lip+=bperline) { /* loop over rows */
262
263 for (j=0, ip=lip; j<wide; j++) { /* load color for row #i */
264
265 r = *pp++ ; g = *pp++ ; b = *pp++ ; /* get input RGB byte values */
266
267 /* shift each component to the correct position, and mask it off */
268
269 r = (rshift<0) ? (r<<(-rshift)) : (r>>rshift) ; r = r & rmask ;
270 g = (gshift<0) ? (g<<(-gshift)) : (g>>gshift) ; g = g & gmask ;
271 b = (bshift<0) ? (b<<(-bshift)) : (b>>bshift) ; b = b & bmask ;
272
273 xcol[j] = r | g | b ; /* assemble color for this pixel */
274 }
275
276 /* now put all colors for row #i into output image array,
277 allowing for most possible bytes/pixel and byte ordering stupidities */
278
279 switch( bperpix ){
280 case 32:
281 if (border == MSBFirst)
282 for( j=0 ; j < wide ; j++ ){
283 *ip++ = (xcol[j]>>24) & 0xff ;
284 *ip++ = (xcol[j]>>16) & 0xff ;
285 *ip++ = (xcol[j]>>8) & 0xff ;
286 *ip++ = xcol[j] & 0xff ;
287 }
288 else
289 for( j=0 ; j < wide ; j++ ){
290 *ip++ = xcol[j] & 0xff ;
291 *ip++ = (xcol[j]>>8) & 0xff ;
292 *ip++ = (xcol[j]>>16) & 0xff ;
293 *ip++ = (xcol[j]>>24) & 0xff ;
294 }
295 break ;
296
297 case 24:
298 if (border == MSBFirst)
299 for( j=0 ; j < wide ; j++ ){
300 *ip++ = (xcol[j]>>16) & 0xff ;
301 *ip++ = (xcol[j]>>8) & 0xff ;
302 *ip++ = xcol[j] & 0xff ;
303 }
304 else
305 for( j=0 ; j < wide ; j++ ){
306 *ip++ = xcol[j] & 0xff ;
307 *ip++ = (xcol[j]>>8) & 0xff ;
308 *ip++ = (xcol[j]>>16) & 0xff ;
309 }
310 break ;
311
312 case 16:
313 if (border == MSBFirst)
314 for( j=0 ; j < wide ; j++ ){
315 *ip++ = (xcol[j]>>8) & 0xff ;
316 *ip++ = xcol[j] & 0xff ;
317 }
318 else
319 for( j=0 ; j < wide ; j++ ){
320 *ip++ = xcol[j] & 0xff ;
321 *ip++ = (xcol[j]>>8) & 0xff ;
322 }
323 break ;
324
325 case 8:
326 for( j=0 ; j < wide ; j++ )
327 *ip++ = xcol[j] & 0xff ;
328 break ;
329 }
330 } /* end of loop over rows */
331
332 free(xcol) ;
333 return xim ;
334 }
335
336 /*------------------------------------------------------------------------
337 Returns position of highest set bit in 'ul' as an integer (0-31),
338 or returns -1 if no bit is set.
339 --------------------------------------------------------------------------*/
340
341 static int highbit(unsigned long ul)
342 {
343 int i; unsigned long hb;
344
345 hb = 0x80; hb = hb << 24; /* hb = 0x80000000UL */
346 for (i=31; ((ul & hb) == 0) && i>=0; i--, ul<<=1);
347 return i;
348 }
349 #endif
350
351 /*---------- Fix a Linux stupidity ------------------------------------*/
352
353 #include "machdep.h"
354 #ifdef NEED_XSETLOCALE
355 #include <locale.h>
356 char * _Xsetlocale( int category, const char * locale)
357 { return setlocale(category,locale) ; }
358 #endif
359