1 /*! File to contain functions for creating interface
2 for mapping data to color maps. Lots of functions from
3 xim.c display.c and pbar.c*/
4
5 #include "SUMA_suma.h"
6 #include "SUMA_plot.h"
7
8 /*!
9 \brief Reads a ppm image and turns i into an rgba vector for ease of
10 use with OpenGL.
11 Depends heavily on afni's mri_read_ppm
12 */
SUMA_read_ppm(char * fname,int * width,int * height,int verb)13 unsigned char *SUMA_read_ppm(char *fname, int *width, int *height, int verb)
14 {
15 static char FuncName[]={"SUMA_read_ppm"};
16 char stmp[500];
17 unsigned char *imar = NULL;
18 byte * rgb , *cp=NULL;
19 float alf = 0;
20 MRI_IMAGE * im=NULL;
21 int ir, ic, i1d, i1df, imx, i1d3, i1d4;
22 SUMA_Boolean LocalHead = NOPE;
23
24 SUMA_ENTRY;
25
26 if (!fname) { if (verb) SUMA_SL_Err("NULL fname"); SUMA_RETURN(imar); }
27 im = mri_read_ppm( fname ) ;
28 if (!im) {
29 if (verb) {
30 SUMA_SL_Err("Failed to read %s", fname); }
31 SUMA_RETURN(imar);
32 }
33
34 rgb = MRI_RGB_PTR(im) ;
35 *height = im->ny ;
36 *width = im->nx ;
37 imx = im->ny * im->nx;
38
39 if (LocalHead)
40 fprintf (SUMA_STDERR,"%s:\nNx (width) = %d, Ny (height) = %d\n",
41 FuncName, im->nx, im->ny);
42
43 imar = (unsigned char *)
44 SUMA_malloc(sizeof(unsigned char) * im->nx * im->ny * 4);
45 if (!imar) {
46 SUMA_SL_Crit("Failed to allocate.");
47 mri_free(im) ;
48 SUMA_RETURN(imar);
49 }
50
51 for (ir = 0; ir < im->ny; ++ir) {
52 for (ic = 0; ic < im->nx; ++ic) {
53 i1d = ic + ir * im->nx; /* equiv. 1d index into row major image data */
54 i1df = ic + (im->ny - ir - 1) * im->nx; /* column flipped index */
55 i1d4 = 4 * i1d; i1d3 = 3*i1df;
56 imar[i1d4] = (unsigned char)rgb[i1d3];
57 alf = (float)imar[i1d4]; ++i1d3; ++i1d4;
58 imar[i1d4] = (unsigned char)rgb[i1d3];
59 alf += (float)imar[i1d4]; ++i1d3; ++i1d4;
60 imar[i1d4] = (unsigned char)rgb[i1d3];
61 alf += (float)imar[i1d4]; ++i1d4;
62 imar[i1d4] = (unsigned char)(alf/3.0);
63 }
64 }
65
66 mri_free(im) ; im = NULL;
67
68 SUMA_RETURN(imar);
69 }
70
SUMA_cmap_wid_graphicsInit(Widget w,XtPointer clientData,XtPointer call)71 void SUMA_cmap_wid_graphicsInit (Widget w, XtPointer clientData, XtPointer call)
72 {
73 static char FuncName[]={"SUMA_cmap_wid_graphicsInit"};
74 XVisualInfo *SUMAg_cVISINFO=NULL;
75 SUMA_ALL_DO *ado=NULL;
76 SUMA_X_SurfCont *SurfCont=NULL;
77 SUMA_Boolean LocalHead = NOPE;
78
79 SUMA_ENTRY;
80
81 SUMA_LH("called");
82
83 ado = (SUMA_ALL_DO *)clientData;
84 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
85 if (!(SurfCont=SUMA_ADO_Cont(ado))) {
86 SUMA_S_Err("NULL Cont!!!"); SUMA_RETURNe;
87 }
88
89 XtVaGetValues(w, GLwNvisualInfo, &SUMAg_cVISINFO, NULL);
90 SurfCont->cmp_ren->cmap_context =
91 glXCreateContext( XtDisplay(w), SUMAg_cVISINFO,
92 0, /* No sharing. */
93 True); /* Direct rendering if possible. */
94
95 /* Setup OpenGL state. */
96 if (!SUMA_glXMakeCurrent( XtDisplay(w), XtWindow(w),
97 SurfCont->cmp_ren->cmap_context,
98 FuncName, "some cmap init", 1)) {
99 fprintf (SUMA_STDERR,
100 "Error %s: Failed in SUMA_glXMakeCurrent.\n \tContinuing ...\n",
101 FuncName);
102 SUMA_GL_ERRS;
103 SUMA_RETURNe;
104 }
105
106 /* call context_Init to setup colors and lighting */
107 SUMA_cmap_context_Init(ado);
108
109 SUMA_RETURNe;
110 }
111
112 /*!
113 Originally intended to setup for an Ortho2D mode for an image display
114 But we don't like 2D. So this ends up being very much like
115 SUMA_context_Init, lookt here for reference if need be.
116 */
SUMA_cmap_context_Init(SUMA_ALL_DO * ado)117 void SUMA_cmap_context_Init(SUMA_ALL_DO *ado)
118 {
119 static char FuncName[]={"SUMA_cmap_context_Init"};
120 GLfloat mat_specular[] = { 0.0, 0.0, 0.0, 1.0};
121 GLfloat mat_shininess[] = { 0 };
122 GLfloat mat_ambient[] = { 0.0, 0.0, 0.0, 1.0};
123 GLfloat mat_diffuse[] = { 1.0, 1.0, 1.0, 1.0 };
124 GLfloat mat_emission[] = { SUMA_MAT_EMISSION_INIT };
125 GLfloat clear_color[] = { 0.0, 0.0, 0.0, 0.0};
126 GLfloat light0_color[] = { 1.0, 1.0, 1.0, 1.0};
127 GLfloat lmodel_ambient[] = {1.0, 1.0, 1.0, 1.0};
128 GLfloat light0_position[] = {0.0, 0.0, -1.0, 0.0};
129 GLfloat ViewFrom[]={0.0, 0.0, 300};
130 GLfloat ViewCenter[]={0.0, 0.0, 0.0};
131 GLfloat ViewCamUp[]={0.0, 1.0, 0.0};
132 GLfloat CmapOrig[]={SUMA_CMAP_ORIGIN};
133 GLfloat CmapTL[]={SUMA_CMAP_TOPLEFT};
134 int i;
135
136 SUMA_ENTRY;
137
138 glClearColor (clear_color[0], clear_color[1], clear_color[2], clear_color[3]);
139 glShadeModel (GL_SMOOTH);
140
141 SUMA_SET_GL_RENDER_MODE(SRM_Fill);
142
143
144 /* Set the material properties*/
145 glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular);
146 glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient);
147 glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse);
148 glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess);
149 glMaterialfv(GL_FRONT, GL_EMISSION, mat_emission);
150
151 /* set the directional light properties */
152 glLightfv(GL_LIGHT0, GL_POSITION, light0_position);
153 glLightfv(GL_LIGHT0, GL_DIFFUSE, light0_color);
154 glLightfv(GL_LIGHT0, GL_SPECULAR, light0_color);
155
156 /* set the ambient light */
157 glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient);
158
159 glEnable(GL_LIGHTING); /* prepare GL to perform lighting calculations */
160 glEnable(GL_LIGHT0); /*Turn lights ON */
161 glEnable(GL_DEPTH_TEST);
162
163 /*setup the view point and then setup the lights.
164 Those lights will remain in place regardless of the rotations/translations
165 done on the surface */
166 for (i=0; i<2; ++i) { ViewCenter[i] = (CmapTL[i] - CmapOrig[i]) / 2.0; }
167 ViewFrom[0] = ViewCenter[0];
168 ViewFrom[1] = ViewCenter[1]; ViewFrom[2] =
169 SUMA_CMAP_VIEW_FROM;
170
171 glMatrixMode(GL_MODELVIEW);
172 glLoadIdentity();
173 gluLookAt ( ViewFrom[0], ViewFrom[1], ViewFrom[2],
174 ViewCenter[0], ViewCenter[1], ViewCenter[2],
175 ViewCamUp[0], ViewCamUp[1], ViewCamUp[2] );
176
177
178 SUMA_RETURNe;
179
180 }
181
SUMA_DrawCmap(SUMA_COLOR_MAP * Cmap)182 void SUMA_DrawCmap(SUMA_COLOR_MAP *Cmap)
183 {
184 static char FuncName[]={"SUMA_DrawCmap"};
185 float orig[3]={ SUMA_CMAP_ORIGIN };
186 float topright[3] = { SUMA_CMAP_TOPLEFT };
187 int i;
188 SUMA_Boolean LocalHead = NOPE;
189
190 SUMA_ENTRY;
191
192 SUMA_LH("called");
193
194 if (!Cmap->SO) {
195 SUMA_LH("Creating Cmap's SO");
196 Cmap->SO = SUMA_Cmap_To_SO(Cmap, orig, topright, 0);
197 if (!Cmap->SO) { SUMA_SL_Err("Failed to create SO"); }
198 }
199
200 /* initialize the context to be safe;
201 sometimes there is conflict with the viewer's context
202 and that causes the colormaps to be absent... ZSS Nov. 28 06
203 But that is too radical and kills translation toys ZSS Mar. 06 08*/
204 /* Turned off, may no longer cause trouble... ZSS Mar. 07 08*/
205 /* SUMA_cmap_context_Init((SUMA_ALL_DO*)Cmap->SO); */
206
207 /* This allows each node to follow the color specified when it was drawn */
208 glColorMaterial(GL_FRONT, GL_AMBIENT_AND_DIFFUSE);
209 glEnable(GL_COLOR_MATERIAL);
210
211 /*Now setup various pointers*/
212 glEnableClientState (GL_COLOR_ARRAY);
213 glEnableClientState (GL_VERTEX_ARRAY);
214 glEnableClientState (GL_NORMAL_ARRAY);
215 glColorPointer (4, GL_FLOAT, 0, Cmap->SO->PermCol);
216 glVertexPointer (3, GL_FLOAT, 0, Cmap->SO->glar_NodeList);
217 glNormalPointer (GL_FLOAT, 0, Cmap->SO->glar_NodeNormList);
218
219 SUMA_SET_GL_RENDER_MODE(SRM_Fill);
220 glDrawElements (GL_TRIANGLES, (GLsizei)Cmap->SO->N_FaceSet*3,
221 GL_UNSIGNED_INT, Cmap->SO->glar_FaceSetList);
222
223 /* Here you could draw a contour around the color cells.
224 But you'll need to raise the contour over the filled polygons
225 because they'll get
226 covered otherwise */
227 #if 0
228 {
229 GLfloat *LineCol=NULL;
230 LineCol = (GLfloat *)SUMA_calloc(Cmap->SO->N_Node*4, sizeof(GLfloat));
231 for (i=0; i<Cmap->SO->N_Node; ++i) {
232 LineCol[4*i] = LineCol[4*i+1] = LineCol[4*i+2] = 0.1;
233 LineCol[4*i+3] = 1.0; }
234 glColorPointer (4, GL_FLOAT, 0, LineCol);
235 SUMA_SET_GL_RENDER_MODE(SRM_Line);
236 glDrawElements ( GL_TRIANGLES, (GLsizei)Cmap->SO->N_FaceSet*3,
237 GL_UNSIGNED_INT, Cmap->SO->glar_FaceSetList);
238 SUMA_free(LineCol); LineCol = NULL;
239 }
240 #endif
241
242 SUMA_RETURNe;
243 }
244
SUMA_cmap_wid_display(SUMA_ALL_DO * ado)245 void SUMA_cmap_wid_display(SUMA_ALL_DO *ado)
246 {
247 static char FuncName[]={"SUMA_cmap_wid_display"};
248 int i;
249 GLfloat rotationMatrix[4][4];
250 float currentQuat[]={0.0, 0.0, 0.0, 1.0};
251 GLfloat clear_color[] = { 0.8, 0.8, 0.8, 0.0};
252 GLfloat RotaCenter[]={0.0, 0.0, 0.0};
253 SUMA_COLOR_MAP *Cmap = NULL;
254 SUMA_X_SurfCont *SurfCont=NULL;
255 SUMA_OVERLAYS *curColPlane=NULL;
256 SUMA_Boolean LocalHead = NOPE; /* local headline debugging messages */
257
258 SUMA_ENTRY;
259
260 SUMA_LH("in, lots of inefficiencies here, make sure you revisit");
261
262 SurfCont = SUMA_ADO_Cont(ado);
263 curColPlane = SUMA_ADO_CurColPlane(ado);
264
265 /* is surface controller closed? */
266 if (!SurfCont->Open) {
267 SUMA_LHv("SurfCont closed for %s, trying to open it\n",
268 SUMA_ADO_Label(ado));
269 if (!SUMA_viewSurfaceCont(NULL, ado, SUMA_BestViewerForADO(ado))) {
270 SUMA_S_Warn("No SurfCont");
271 SUMA_DUMP_TRACE("No SurfCont");
272 SUMA_RETURNe;
273 }
274 }
275 /* now you need to set the clear_color since it can be
276 changed per viewer Thu Dec 12 2002 */
277 glClearColor (clear_color[0], clear_color[1],clear_color[2],clear_color[3]);
278
279 if (LocalHead)
280 fprintf (SUMA_STDOUT,"%s: Building Rotation matrix ...\n", FuncName);
281 SUMA_build_rotmatrix(rotationMatrix, currentQuat);
282
283 if (LocalHead)
284 fprintf (SUMA_STDOUT,"%s: performing glClear ...\n", FuncName);
285 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); /* clear the Color Buffer and the depth buffer */
286
287 /* careful here, you might want to turn
288 the next block into a macro like SUMA_SET_GL_PROJECTION */
289 if (LocalHead)
290 fprintf (SUMA_STDOUT,
291 "%s: Setting up matrix mode and perspective ...\nFOV=%f\n"
292 "Translation is %f %f %f\n",
293 FuncName, SUMA_CMAP_FOV_INITIAL,
294 SurfCont->cmp_ren->translateVec[0],
295 SurfCont->cmp_ren->translateVec[1],
296 SurfCont->cmp_ren->translateVec[2] );
297 glMatrixMode (GL_PROJECTION);
298 glLoadIdentity ();
299 gluPerspective(SurfCont->cmp_ren->FOV,
300 (double)SUMA_CMAP_WIDTH/SUMA_CMAP_HEIGHT,
301 SUMA_PERSPECTIVE_NEAR, SUMA_PERSPECTIVE_FAR);
302 /*lower angle is larger zoom,*/
303
304 glMatrixMode(GL_MODELVIEW);
305 glPushMatrix();
306 glTranslatef ( SurfCont->cmp_ren->translateVec[0],
307 SurfCont->cmp_ren->translateVec[1],
308 SurfCont->cmp_ren->translateVec[2] );
309 if (0){
310 SUMA_SL_Note("no need for shananigans\n"
311 "But to illustrate ...\n");
312 glTranslatef (RotaCenter[0], RotaCenter[1], RotaCenter[2]);
313 glMultMatrixf(&rotationMatrix[0][0]);
314 glTranslatef (-RotaCenter[0], -RotaCenter[1], -RotaCenter[2]);
315 }
316
317
318 /* find out what colormap is to be displayed */
319 if (curColPlane) {
320 /* what's the Cmap for that plane ? */
321 Cmap = SUMA_CmapOfPlane (curColPlane );
322 if (Cmap) SUMA_DrawCmap(Cmap); /* create the colormap */
323 } else {
324 SUMA_SL_Err("NULL curColPlane");
325 }
326 glPopMatrix();
327
328 if (LocalHead)
329 fprintf (SUMA_STDERR,
330 "%s: Flushing or swapping ...\n"
331 "cmp_ren %p, cmap_wid %p\n",
332 FuncName,
333 SurfCont ? SurfCont->cmp_ren : NULL,
334 (SurfCont && SurfCont->cmp_ren ) ?
335 SurfCont->cmp_ren->cmap_wid : NULL );
336
337 if (SUMAg_SVv[0].X->DOUBLEBUFFER)
338 glXSwapBuffers(XtDisplay(SurfCont->cmp_ren->cmap_wid),
339 XtWindow(SurfCont->cmp_ren->cmap_wid));
340 else
341 glFlush();
342
343 /* Avoid indirect rendering latency from queuing. */
344
345 if (!glXIsDirect( XtDisplay(SurfCont->cmp_ren->cmap_wid),
346 SurfCont->cmp_ren->cmap_context)) {
347 SUMA_LH("GLfinish time");
348 glFinish();
349 } else {
350 SUMA_LH("No finish call");
351 }
352
353 SUMA_RETURNe;
354 }
355
SUMA_cmap_wid_handleRedisplay(XtPointer clientData)356 Boolean SUMA_cmap_wid_handleRedisplay(XtPointer clientData)
357 {
358 static char FuncName[]={"SUMA_cmap_wid_handleRedisplay"};
359 SUMA_ALL_DO *ado=NULL;
360 SUMA_X_SurfCont *SurfCont=NULL;
361 SUMA_Boolean LocalHead = NOPE;
362
363 SUMA_ENTRY;
364
365 SUMA_LH("Called");
366
367 ado = (SUMA_ALL_DO *)clientData;
368 if (!ado) { SUMA_SL_Err("NULL DO"); SUMA_RETURN(NOPE); }
369
370 SurfCont = SUMA_ADO_Cont(ado);
371 SUMA_LHv("Called with ado %s, SurfCont->Open: %d\n",
372 SUMA_ADO_Label(ado), SurfCont->Open);
373 if (SurfCont->Open) { /* Otherwise it causes a crash on linux
374 when yoking L/R stuff */
375 SUMA_LHv("Making cmap_wid current %p %p\n",
376 SurfCont->cmp_ren->cmap_wid,
377 SurfCont->cmp_ren->cmap_context);
378 if (!SUMA_glXMakeCurrent( XtDisplay(SurfCont->cmp_ren->cmap_wid),
379 XtWindow(SurfCont->cmp_ren->cmap_wid),
380 SurfCont->cmp_ren->cmap_context, FuncName, "some cmap resize", 1)) {
381 SUMA_S_Err("Failed in SUMA_glXMakeCurrent.\n \tContinuing ...");
382 }
383 SUMA_LH("Calling wid display");
384 SUMA_cmap_wid_display(ado);
385 glFinish();
386
387 /* insist on a glXMakeCurrent for surface viewer */
388 SUMA_LH("Making sv's GLXAREA current\n");
389 SUMA_SiSi_I_Insist();
390 }
391
392 SUMA_RETURN(YUP);
393 }
394
SUMA_cmap_wid_postRedisplay(Widget w,XtPointer clientData,XtPointer call)395 void SUMA_cmap_wid_postRedisplay(Widget w, XtPointer clientData, XtPointer call)
396 {
397 static char FuncName[]={"SUMA_cmap_wid_postRedisplay"};
398 static XtPointer elvis;
399 int isv;
400 SUMA_ALL_DO *ado=NULL;
401 SUMA_Boolean LocalHead = NOPE;
402
403 SUMA_ENTRY;
404
405 SUMA_LH("cold");
406
407 ado = (SUMA_ALL_DO *)clientData;
408 if (!ado) { SUMA_SL_Err("NULL DO"); SUMA_RETURNe; }
409
410 SUMA_register_workproc(SUMA_cmap_wid_handleRedisplay , (XtPointer)ado );
411
412 SUMA_RETURNe;
413 }
414
SUMA_cmap_wid_expose(Widget w,XtPointer clientData,XtPointer call)415 void SUMA_cmap_wid_expose(Widget w, XtPointer clientData, XtPointer call)
416 {
417 static char FuncName[]={"SUMA_cmap_wid_expose"};
418 SUMA_ALL_DO *ado=NULL;
419 SUMA_Boolean LocalHead = NOPE;
420
421 SUMA_ENTRY;
422
423 SUMA_LH("called");
424 ado = (SUMA_ALL_DO *)clientData;
425 if (!ado) { SUMA_SL_Err("NULL DO"); SUMA_RETURNe; }
426
427 SUMA_cmap_wid_postRedisplay(w, (XtPointer)ado, NULL);
428
429 SUMA_RETURNe;
430 }
431
432 /* An attempt to render colormap using X11 and Motif rather than openGL.
433 This is only for the purpose of taking an autosnapshot of the whole widget
434 Based on AFNI's PBAR_bigexpose_CB()*/
SUMA_PBAR_bigexpose_CB(Widget wiw,XtPointer clientData,XtPointer calliw)435 void SUMA_PBAR_bigexpose_CB(Widget wiw, XtPointer clientData, XtPointer calliw)
436 {
437 static char FuncName[]={"SUMA_PBAR_bigexpose_CB"};
438 SUMA_ALL_DO *ado=NULL;
439 XVisualInfo *SUMAg_cVISINFO=NULL;
440 static MCW_DC *dc = NULL;
441 static XImage *bigxim = NULL;
442 SUMA_X_SurfCont *SurfCont = NULL;
443 int ww = SUMA_CMAP_WIDTH, hh = SUMA_CMAP_HEIGHT;
444 int ii , jj , kk;
445 MRI_IMAGE *cim, *dim;
446 byte *car , r,g,b ;
447 static SUMA_COLOR_MAP *CMd=NULL;
448 SUMA_COLOR_MAP *CM=NULL;
449 SUMA_OVERLAYS *curColPlane=NULL;
450 SUMA_Boolean LocalHead = NOPE;
451
452 SUMA_ENTRY;
453
454 SUMA_LH("called");
455 ado = (SUMA_ALL_DO *)clientData;
456 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) {
457 SUMA_SL_Err("NULL DO or Cont"); SUMA_RETURNe;
458 }
459
460 /* Get colormap of plane, if possible */
461 if ((curColPlane = SUMA_ADO_CurColPlane(ado))) {
462 CM = SUMA_CmapOfPlane (curColPlane );
463 }
464 /* get some default */
465 if (!CM) {
466 if (!(CM = SUMA_FindNamedColMap("byr64"))) {
467 SUMA_S_Err("Failed to get byr64");
468 SUMA_RETURNe;
469 }
470 }
471
472 if (!CMd || CM != CMd) {
473 SUMA_LH("Setting CMd");
474 CMd = CM;
475 if (bigxim) {
476 SUMA_LH("Killing bigxim");
477 MCW_kill_XImage( bigxim ); bigxim = NULL;
478 }
479 }
480
481 if (!bigxim) {
482 float fac; int mm;
483 cim = mri_new( ww, 256 , MRI_rgb ) ;
484 car = MRI_RGB_PTR(cim) ;
485 fac = (float)CM->N_M[0]/256.0;
486 for( kk=ii=0 ; ii < 256 ; ii++ ){
487 mm = CM->N_M[0]-1-(int)((float)ii*fac);
488 if (mm>=CM->N_M[0]) mm = CM->N_M[0]-1;
489 if (mm<0) mm = 0;
490 r=(byte)(CM->M[mm][0]*255.0);
491 g=(byte)(CM->M[mm][1]*255.0);
492 b=(byte)(CM->M[mm][2]*255.0);
493 if( CM->M[mm][0] >= 0 || CM->M[mm][1] >= 0 || CM->M[mm][2] >= 0 ){
494 for( jj=0 ; jj < ww ; jj++ ){
495 car[kk++] = r; car[kk++] = g; car[kk++] = b;
496 }
497 } else {
498 for( jj=0 ; jj < ww ; jj++ ){
499 car[kk++]=128; car[kk++]=128; car[kk++]=128;
500 }
501 }
502 }
503 dim = mri_resize( cim , ww,hh ) ;
504 if (!dc) {
505 dc = MCW_new_DC( SurfCont->Fake_pbar, 4,0, NULL,NULL, 1.0,0 );
506 }
507 bigxim = mri_to_XImage( dc , dim ) ;
508 mri_free(dim) ;
509 }
510
511 /* actually show the image to the window pane */
512 if( XtIsManaged(SurfCont->Fake_pbar) )
513 XPutImage( SUMAg_CF->X->DPY_controller1 ,
514 XtWindow(SurfCont->Fake_pbar) ,
515 dc->origGC , bigxim , 0,0,0,0 ,
516 ww , hh ) ;
517
518 SUMA_RETURNe;
519 }
520
SUMA_PBAR_biginput_CB(Widget w,XtPointer clientData,XtPointer call)521 void SUMA_PBAR_biginput_CB(Widget w, XtPointer clientData, XtPointer call)
522 {
523 static char FuncName[]={"SUMA_PBAR_biginput_CB"};
524 SUMA_ALL_DO *ado=NULL;
525 SUMA_X_SurfCont *SurfCont = NULL;
526 SUMA_Boolean LocalHead = NOPE;
527
528 SUMA_ENTRY;
529
530 SUMA_LH("called");
531 ado = (SUMA_ALL_DO *)clientData;
532 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) {
533 SUMA_SL_Err("NULL DO or Cont"); SUMA_RETURNe;
534 }
535 SUMA_RETURNe;
536 }
537
SUMA_PBAR_bigresize_CB(Widget w,XtPointer clientData,XtPointer call)538 void SUMA_PBAR_bigresize_CB(Widget w, XtPointer clientData, XtPointer call)
539 {
540 static char FuncName[]={"SUMA_PBAR_bigresize_CB"};
541 SUMA_ALL_DO *ado=NULL;
542 SUMA_X_SurfCont *SurfCont = NULL;
543 SUMA_Boolean LocalHead = NOPE;
544
545 SUMA_ENTRY;
546
547 SUMA_LH("called");
548 ado = (SUMA_ALL_DO *)clientData;
549 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) {
550 SUMA_SL_Err("NULL DO or Cont"); SUMA_RETURNe;
551 }
552 SUMA_RETURNe;
553 }
554
555
SUMA_cmap_wid_resize(Widget w,XtPointer clientData,XtPointer call)556 void SUMA_cmap_wid_resize(Widget w, XtPointer clientData, XtPointer call)
557 {
558 static char FuncName[]={"SUMA_cmap_wid_resize"};
559 SUMA_ALL_DO *ado=NULL;
560 SUMA_Boolean LocalHead = NOPE;
561
562 SUMA_ENTRY;
563
564 SUMA_LH("called");
565 ado = (SUMA_ALL_DO *)clientData;
566 if (!ado) { SUMA_SL_Err("NULL DO"); SUMA_RETURNe; }
567
568 SUMA_RETURNe;
569 }
570
SUMA_cmap_wid_input(Widget w,XtPointer clientData,XtPointer callData)571 void SUMA_cmap_wid_input(Widget w, XtPointer clientData, XtPointer callData)
572 {
573 static char FuncName[]={"SUMA_cmap_wid_input"};
574 GLwDrawingAreaCallbackStruct *cd;
575 KeySym keysym;
576 XKeyEvent Kev;
577 XButtonEvent Bev;
578 XMotionEvent Mev;
579 char buffer[10], cbuf = '\0', cbuf2='\0';
580 SUMA_ALL_DO *ado=NULL;
581 int xls;
582 static Time B1time = 0;
583 static int pButton, mButton, rButton;
584 static SUMA_Boolean DoubleClick = NOPE;
585 DList *list = NULL;
586 SUMA_EngineData *ED = NULL;
587 static float height_two_col, width;
588 int ncol;
589 SUMA_COLOR_MAP *ColMap = NULL;
590 static float fov_lim = -1.0;
591 static SUMA_SurfaceObject *SOcmap=NULL;
592 SUMA_X_SurfCont *SurfCont=NULL;
593 SUMA_OVERLAYS *curColPlane=NULL;
594 SUMA_Boolean LocalHead = NOPE;
595
596 SUMA_ENTRY;
597
598 SUMA_LH("called");
599 ado = (SUMA_ALL_DO *)clientData;
600 /* THIS ado is for the main surface/DO, NOT THE colormap's */
601 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
602
603 SurfCont = SUMA_ADO_Cont(ado);
604 curColPlane = SUMA_ADO_CurColPlane(ado);
605
606 ColMap = SUMA_CmapOfPlane (curColPlane );
607 if (!ColMap) { SUMA_SL_Err("No Cmap"); SUMA_RETURNe; };
608 if (ColMap->SO != SOcmap) {
609 SUMA_LH("New colormap SO");
610 /* calculate FOV limit for zooming in */
611 SOcmap = ColMap->SO;
612 ncol = SOcmap->N_FaceSet / 2;
613 height_two_col = (SOcmap->MaxDims[1] - SOcmap->MinDims[1]) /
614 (float)ncol * 2.0;
615 /* no need to show more than 2 cols */
616 width = (SOcmap->MaxDims[0] - SOcmap->MinDims[0]);
617 fov_lim = 2.0 * atan( (double)height_two_col /
618 ( 2.0 * (double)SUMA_CMAP_VIEW_FROM ) ) * 180 / SUMA_PI;
619 if (LocalHead) {
620 SUMA_Print_Surface_Object(SOcmap, NULL);
621 fprintf( SUMA_STDERR,
622 "%s: ncol=%d, height = %f, height of 2 col =%f\n"
623 ", width=%f, d = %d, fov_lim = %f\n",
624 FuncName, ncol, (SOcmap->MaxDims[1] - SOcmap->MinDims[1]),
625 height_two_col, width, SUMA_CMAP_VIEW_FROM, fov_lim);
626 }
627 }
628
629 /* make sure the color map is the current context */
630 if (!SUMA_glXMakeCurrent( XtDisplay(w),
631 XtWindow(w),
632 SurfCont->cmp_ren->cmap_context, FuncName, "some cmap input", 1)) {
633 SUMA_S_Err("Failed in SUMA_glXMakeCurrent.\n ");
634 SUMA_RETURNe;
635 }
636
637 /* get the callData pointer */
638 cd = (GLwDrawingAreaCallbackStruct *) callData;
639
640 Kev = *(XKeyEvent *) &cd->event->xkey; /* RickR's suggestion to comply with
641 ANSI C, no type casting of
642 structures July 04*/
643 Bev = *(XButtonEvent *) &cd->event->xbutton;
644 Mev = *(XMotionEvent *) &cd->event->xmotion;
645
646 switch (Kev.type) { /* switch event type */
647 case KeyPress:
648 xls = XLookupString((XKeyEvent *) cd->event, buffer, 8, &keysym, NULL);
649
650 /* XK_* are found in keysymdef.h */
651 switch (keysym) { /* keysym */
652 case XK_h:
653 if (Kev.state & ControlMask){
654 if (!list) list = SUMA_CreateList();
655 ED = SUMA_InitializeEngineListData (SE_Help_Cmap);
656 SUMA_RegisterEngineListCommand ( list, ED,
657 SEF_vp, (void *)ColMap,
658 SES_SumaWidget, NULL, NOPE,
659 SEI_Head, NULL);
660 if (!SUMA_Engine (&list)) {
661 fprintf(stderr,
662 "Error %s: SUMA_Engine call failed.\n", FuncName);
663 }
664 }
665 break;
666 case XK_f:
667 {
668 if (1) {
669 SUMA_LH("Flipping colormap");
670 SUMA_Flip_Color_Map(
671 SUMA_CmapOfPlane(curColPlane));
672 SUMA_LH("Switching colormap");
673 SUMA_SwitchCmap(ado,
674 SUMA_CmapOfPlane(curColPlane), 0);
675 }
676 }
677 break;
678 case XK_r:
679 {
680 GLvoid *pixels;
681 SUMA_LH("Recording");
682 if (SUMAg_SVv[0].X->DOUBLEBUFFER)
683 glXSwapBuffers(XtDisplay(SurfCont->cmp_ren->cmap_wid),
684 XtWindow(SurfCont->cmp_ren->cmap_wid));
685 pixels = SUMA_grabPixels(3, SUMA_CMAP_WIDTH, SUMA_CMAP_HEIGHT);
686 if (SUMAg_SVv[0].X->DOUBLEBUFFER)
687 glXSwapBuffers(XtDisplay(SurfCont->cmp_ren->cmap_wid),
688 XtWindow(SurfCont->cmp_ren->cmap_wid));
689 if (pixels) {
690 ISQ_snapsave (SUMA_CMAP_WIDTH, -SUMA_CMAP_HEIGHT,
691 (unsigned char *)pixels,
692 SurfCont->cmp_ren->cmap_wid );
693 SUMA_free(pixels);
694 }else {
695 SUMA_SLP_Err("Failed to record image.");
696 }
697 }
698 break;
699 case XK_w:
700 {
701 char *sss=NULL;
702 SUMA_COLOR_MAP * ColMap =
703 SUMA_CmapOfPlane(curColPlane);
704 if (LocalHead) {
705 if ((sss = SUMA_ColorMapVec_Info(&ColMap, 1, 1))) {
706 SUMA_LHv("To be written:\n%s\n", sss);
707 SUMA_free(sss); sss = NULL;
708 }
709 }
710 if (!SUMA_Write_Color_Map_1D(ColMap, NULL)) {
711 SUMA_S_Errv("Failed to write colmap %s\n",
712 curColPlane->Name);
713 }else {
714 SUMA_S_Notev("Wrote colormap %s to file.\n",
715 curColPlane->Name);
716 }
717 }
718 break;
719 case XK_Z:
720 {
721 static SUMA_Boolean BeepedAlready = NOPE;
722 SurfCont->cmp_ren->FOV /= FOV_IN_FACT;
723 if (SurfCont->cmp_ren->FOV < fov_lim) {
724 if (!BeepedAlready) {
725 SUMA_BEEP; BeepedAlready = YUP;
726 }
727 SurfCont->cmp_ren->FOV = fov_lim;
728 } else BeepedAlready = NOPE;
729 if (LocalHead)
730 fprintf(SUMA_STDERR,
731 "%s: Zoom in FOV = %f\n",
732 FuncName, SurfCont->cmp_ren->FOV);
733 SUMA_cmap_wid_postRedisplay(w, (XtPointer)ado, NULL);
734 }
735 break;
736
737 case XK_z:
738 {
739 static SUMA_Boolean BeepedAlready = NOPE;
740 SurfCont->cmp_ren->FOV /= FOV_OUT_FACT;
741 if (SurfCont->cmp_ren->FOV > SUMA_CMAP_FOV_INITIAL) {
742 if (!BeepedAlready) {
743 SUMA_BEEP; BeepedAlready = YUP;
744 }
745 SurfCont->cmp_ren->FOV = SUMA_CMAP_FOV_INITIAL;
746 } else BeepedAlready = NOPE;
747 if (LocalHead)
748 fprintf( SUMA_STDERR,
749 "%s: Zoom out FOV = %f\n",
750 FuncName, SurfCont->cmp_ren->FOV);
751 SUMA_cmap_wid_postRedisplay(w, (XtPointer)ado, NULL);
752 }
753 break;
754 case XK_Home:
755 SurfCont->cmp_ren->FOV = SUMA_CMAP_FOV_INITIAL;
756 SurfCont->cmp_ren->translateVec[0] =
757 SurfCont->cmp_ren->translateVec[1] =
758 SurfCont->cmp_ren->translateVec[2] = 0.0;
759 {
760 SUMA_COLOR_MAP *CM = SUMA_CmapOfPlane(curColPlane);
761 if (SUMA_Rotate_Color_Map(CM, 0) % CM->N_M[0]) {
762 SUMA_SwitchCmap(ado,
763 SUMA_CmapOfPlane(curColPlane), 0);
764 } else {
765 SUMA_cmap_wid_postRedisplay(w, (XtPointer)ado, NULL);
766 }
767 }
768 break;
769 case XK_Up: /*KEY_UP:*/
770 {
771 if (Kev.state & ShiftMask){
772 static SUMA_Boolean BeepedAlready = NOPE;
773 float tstep = height_two_col / 2.0 *
774 SurfCont->cmp_ren->FOV /
775 (float)SUMA_CMAP_FOV_INITIAL;
776 SurfCont->cmp_ren->translateVec[1] += tstep ;
777 if (LocalHead)
778 fprintf(SUMA_STDERR,
779 "%s: translateVec[1] = %f (%d)\n",
780 FuncName,
781 SurfCont->cmp_ren->translateVec[1],
782 SUMA_CMAP_HEIGHT - 20);
783 if ( SurfCont->cmp_ren->translateVec[1] >
784 SUMA_CMAP_HEIGHT - 20) {
785 if (!BeepedAlready) {
786 SUMA_BEEP; BeepedAlready = YUP;
787 }
788 SurfCont->cmp_ren->translateVec[1] -= tstep;
789 } else BeepedAlready = NOPE;
790 SUMA_cmap_wid_postRedisplay(w, (XtPointer)ado, NULL);
791 } else {
792 float frac = 0.0;
793 if (Kev.state & ControlMask) {
794 frac = 1;
795 }else {
796 frac = SUMAg_CF->CmapRotaFrac;
797 }
798 SUMA_LH("Rotating colormap");
799 SUMA_Rotate_Color_Map(
800 SUMA_CmapOfPlane(curColPlane), frac);
801 SUMA_LH("Switching colormap");
802 SUMA_SwitchCmap(ado,
803 SUMA_CmapOfPlane(curColPlane), 0);
804 }
805 }
806 break;
807 case XK_Down: /*KEY_DOWN:*/
808 {
809 if (Kev.state & ShiftMask){
810 static SUMA_Boolean BeepedAlready = NOPE;
811 float tstep = height_two_col / 2.0 *
812 SurfCont->cmp_ren->FOV /
813 (float)SUMA_CMAP_FOV_INITIAL;
814 SurfCont->cmp_ren->translateVec[1] -= tstep;
815 if ( SurfCont->cmp_ren->translateVec[1] <
816 -SUMA_CMAP_HEIGHT + 20) {
817 if (!BeepedAlready) {
818 SUMA_BEEP; BeepedAlready = YUP;
819 }
820 SurfCont->cmp_ren->translateVec[1] += tstep;
821 } else BeepedAlready = NOPE;
822 SUMA_cmap_wid_postRedisplay(w, (XtPointer)ado, NULL);
823 } else {
824 float frac = 0.0;
825 if (Kev.state & ControlMask) {
826 frac = 1;
827 }else {
828 frac = SUMAg_CF->CmapRotaFrac;
829 }
830 SUMA_Rotate_Color_Map(
831 SUMA_CmapOfPlane(curColPlane), -frac);
832 SUMA_SwitchCmap(ado,
833 SUMA_CmapOfPlane(curColPlane), 0);
834 }
835 }
836 break;
837
838 } /* keysym */
839 break;
840
841 case ButtonPress:
842 if (LocalHead) fprintf(stdout,"In ButtonPress\n");
843 pButton = Bev.button;
844 if (SUMAg_CF->SwapButtons_1_3 ||
845 (SUMAg_CF->ROI_mode && SUMAg_CF->Pen_mode)) {
846 if (pButton == Button1) pButton = Button3;
847 else if (pButton == Button3) pButton = Button1;
848 }
849
850 /* trap for double click */
851 if (Bev.time - B1time < SUMA_DOUBLE_CLICK_MAX_DELAY) {
852 if (LocalHead) fprintf(SUMA_STDERR, "%s: Double click.\n", FuncName);
853 DoubleClick = YUP;
854 } else {
855 DoubleClick = NOPE;
856 }
857 B1time = Bev.time;
858
859 switch (pButton) { /* switch type of button Press */
860 case Button1:
861 break;
862 default:
863 break;
864 } /* switch type of button Press */
865 break;
866
867 case ButtonRelease:
868 if (LocalHead) fprintf(SUMA_STDERR,"%s: In ButtonRelease\n", FuncName);
869 rButton = Bev.button;
870 if (SUMAg_CF->SwapButtons_1_3 ||
871 (SUMAg_CF->ROI_mode && SUMAg_CF->Pen_mode) ) {
872 if (rButton == Button1) rButton = Button3;
873 else if (rButton == Button3) rButton = Button1;
874 }
875 switch (rButton) { /* switch type of button Press */
876 case Button3:
877 break;
878 default:
879 break;
880 } /* switch type of button Press */
881 break;
882
883 case MotionNotify:
884 if (LocalHead) fprintf(stdout,"In MotionNotify\n");
885 if (SUMAg_CF->SwapButtons_1_3 ||
886 (SUMAg_CF->ROI_mode && SUMAg_CF->Pen_mode)) {
887 if (((Mev.state & Button3MotionMask) && (Mev.state & Button2MotionMask))
888 || ((Mev.state & Button2MotionMask) && (Mev.state & ShiftMask))) {
889 mButton = SUMA_Button_12_Motion;
890 } else if(Mev.state & Button3MotionMask) {
891 mButton = SUMA_Button_1_Motion;
892 }else if(Mev.state & Button2MotionMask) {
893 mButton = SUMA_Button_2_Motion;
894 }else if(Mev.state & Button1MotionMask) {
895 mButton = SUMA_Button_3_Motion;
896 }else {
897 break;
898 }
899 } else {
900 if (((Mev.state & Button1MotionMask) && (Mev.state & Button2MotionMask)) || ((Mev.state & Button2MotionMask) && (Mev.state & ShiftMask))) {
901 mButton = SUMA_Button_12_Motion;
902 } else if(Mev.state & Button1MotionMask) {
903 mButton = SUMA_Button_1_Motion;
904 }else if(Mev.state & Button2MotionMask) {
905 mButton = SUMA_Button_2_Motion;
906 } else if(Mev.state & Button3MotionMask) {
907 mButton = SUMA_Button_3_Motion;
908 }else {
909 break;
910 }
911 }
912
913 switch (mButton) {
914 case SUMA_Button_12_Motion:
915 case SUMA_Button_2_Shift_Motion:
916 break;
917 default:
918 break;
919 }
920
921
922 break;
923 }/* switch event type */
924
925 /* set up flag to make sure sv regains context */
926 SUMA_SiSi_I_Insist();
927
928 SUMA_RETURNe;
929 }
930
SUMA_set_threshold_label(SUMA_ALL_DO * ado,float val,float val2)931 int SUMA_set_threshold_label(SUMA_ALL_DO *ado, float val, float val2)
932 {
933 static char FuncName[]={"SUMA_set_threshold_label"};
934 char slabel[100];
935 SUMA_X_SurfCont *SurfCont=NULL;
936 SUMA_OVERLAYS *curColPlane=NULL;
937 SUMA_Boolean LocalHead = NOPE;
938
939 SUMA_ENTRY;
940
941 SUMA_LH("called");
942
943 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURN(0); }
944
945 SurfCont = SUMA_ADO_Cont(ado);
946 curColPlane = SUMA_ADO_CurColPlane(ado);
947
948 switch (curColPlane->OptScl->ThrMode) {
949 case SUMA_LESS_THAN:
950 sprintf(slabel, "%5s", MV_format_fval(val));
951 break;
952 case SUMA_ABS_LESS_THAN:
953 /* used to use this:
954 sprintf(slabel, "|%5s|", ....
955 but that does not work in the editable field ... */
956 sprintf(slabel, "%5s", MV_format_fval(val));
957 break;
958 case SUMA_THRESH_INSIDE_RANGE:
959 /* This is just a place holder for now */
960 sprintf(slabel, "<%5s..%5s>",
961 MV_format_fval(val), MV_format_fval(val2));
962 break;
963 case SUMA_THRESH_OUTSIDE_RANGE:
964 /* This is just a place holder for now */
965 sprintf(slabel, ">%5s..%5s<",
966 MV_format_fval(val), MV_format_fval(val2));
967 break;
968 case SUMA_NO_THRESH:
969 break;
970 default:
971 /* This is just a place holder for now */
972 sprintf(slabel, "?%5s??%5s?<",
973 MV_format_fval(val), MV_format_fval(val2));
974 break;
975 }
976 /* SUMA_SET_LABEL(SurfCont->thr_lb, slabel);*/
977 SUMA_INSERT_CELL_STRING(SurfCont->SetThrScaleTable, 0,0,slabel);
978
979
980 /* You must use the line below if you are calling this function on the fly */
981 /* SUMA_FORCE_SCALE_HEIGHT(SUMA_ADO_Cont(ado)); */
982
983 #if SUMA_SEPARATE_SURF_CONTROLLERS
984 SUMA_UpdateColPlaneShellAsNeeded(ado);
985 #endif
986
987 /* Will need to ponder Pvalue field when I start using
988 SUMA_THRESH_INSIDE_RANGE and SUMA_THRESH_OUTSIDE_RANGE.
989 Also, should also consider one tail versus two tail...*/
990 SUMA_UpdatePvalueField (ado, val);
991
992 SUMA_RETURN(1);
993 }
994
SUMA_cb_set_threshold_label(Widget w,XtPointer clientData,XtPointer call)995 void SUMA_cb_set_threshold_label(Widget w, XtPointer clientData, XtPointer call)
996 {
997 static char FuncName[]={"SUMA_cb_set_threshold_label"};
998 SUMA_ALL_DO *ado=NULL;
999 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
1000 float fff ;
1001 int dec=0;
1002 char slabel[100];
1003 SUMA_Boolean LocalHead = NOPE;
1004
1005 SUMA_ENTRY;
1006
1007 SUMA_LH("called");
1008 ado = (SUMA_ALL_DO *)clientData;
1009 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
1010
1011 XtVaGetValues(w, XmNuserData, &dec, NULL);
1012 fff = (float)cbs->value / pow(10.0, dec);
1013
1014 SUMA_set_threshold_label(ado, fff, 0.0);
1015
1016 SUMA_RETURNe;
1017 }
1018
SUMA_set_threshold(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,float * val)1019 int SUMA_set_threshold(SUMA_ALL_DO *ado, SUMA_OVERLAYS *colp,
1020 float *val)
1021 {
1022 static char FuncName[]={"SUMA_set_threshold"};
1023 SUMA_SurfaceObject *SOC=NULL, *SO=NULL;
1024 SUMA_OVERLAYS *colpC=NULL;
1025 SUMA_Boolean LocalHead = NOPE;
1026
1027 SUMA_ENTRY;
1028
1029 if (!SUMA_set_threshold_one(ado, colp, val)) SUMA_RETURN(0);
1030 if (!colp) colp = SUMA_ADO_CurColPlane(ado);
1031 if (!colp) SUMA_RETURN(0);
1032
1033 if (ado->do_type == SO_type) {
1034 /* do we have a contralateral SO and overlay? */
1035 SO = (SUMA_SurfaceObject *)ado;
1036 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
1037 if (colpC && SOC) {
1038 SUMA_LHv("Found contralateral equivalent to:\n"
1039 " %s and %s in\n"
1040 " %s and %s\n",
1041 SO->Label, CHECK_NULL_STR(colp->Label),
1042 SOC->Label, CHECK_NULL_STR(colpC->Label));
1043 if (!SUMA_SetScaleThr_one((SUMA_ALL_DO *)SOC, colpC, val, 1, 1)) {
1044 SUMA_S_Warn("Failed in contralateral");
1045 SUMA_RETURN(0);
1046 }
1047 }
1048 }
1049
1050 /* CIFTI yoking outline
1051
1052 if (colp->dset_link) is CIFTI subdomain (see a. below)
1053 Look up the parent cifti dset (cdset) by using MD_parent_ID
1054
1055 Look up also the CIFTI DO (CO) that goes with cdset using
1056 SUMA_Fetch_OverlayPointerByDset()
1057
1058 For each subdomain in CO and each corresponding dset and color plane
1059
1060 If the subdomain and the colorplane are different from ado , adoC (that
1061 would be (SUMA_ALL_DO *)SOC above), colp and colpC
1062
1063 call SUMA_SetScaleThr_one() as per above
1064
1065
1066
1067 a. One way to find out if a dset is a subdomain would be to look for one of the MD_* attribute of dset->ngr that are created in SUMA_CIFTI_2_edset()
1068
1069 */
1070
1071 SUMA_RETURN(1);
1072 }
1073
SUMA_set_threshold_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,float * valp)1074 int SUMA_set_threshold_one(SUMA_ALL_DO *ado, SUMA_OVERLAYS *colp,
1075 float *valp)
1076 {
1077 static char FuncName[]={"SUMA_set_threshold_one"};
1078 float oval, val;
1079 SUMA_X_SurfCont *SurfCont=NULL;
1080 SUMA_Boolean LocalHead = NOPE;
1081
1082 SUMA_ENTRY;
1083
1084 if (!ado) SUMA_RETURN(0);
1085 SurfCont = SUMA_ADO_Cont(ado);
1086 if (!colp) colp = SUMA_ADO_CurColPlane(ado);
1087 if (!colp) SUMA_RETURN(0);
1088
1089 oval = colp->OptScl->ThreshRange[0];
1090 if (!valp) val = oval; /* a dirty trick to force scale height */
1091 else val = *valp;
1092 colp->OptScl->ThreshRange[0] = val;
1093
1094 if (LocalHead) {
1095 fprintf( SUMA_STDERR,
1096 "%s:\nThreshold set to %f\n",
1097 FuncName,
1098 colp->OptScl->ThreshRange[0]);
1099 }
1100
1101 if ( colp->OptScl->UseThr &&
1102 colp->OptScl->tind >=0) {
1103 if (oval != colp->OptScl->ThreshRange[0] &&
1104 colp->OptScl->Clusterize) {
1105 /* Need a new clusterizing effort*/
1106 colp->OptScl->RecomputeClust = 1;
1107 }
1108 SUMA_ColorizePlane(colp);
1109 SUMA_Remixedisplay(ado);
1110 }
1111
1112 /* call this one since it is not being called as the slider is dragged. */
1113 SUMA_set_threshold_label(ado, val, 0.0);
1114
1115 /* sad as it is */
1116 SUMA_FORCE_SCALE_HEIGHT(SUMA_ADO_Cont(ado));
1117
1118 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
1119
1120 #if SUMA_SEPARATE_SURF_CONTROLLERS
1121 SUMA_UpdateColPlaneShellAsNeeded(ado);
1122 #endif
1123
1124 SUMA_UpdateNodeValField(ado);
1125 SUMA_UpdateNodeLblField(ado);
1126 SUMA_UpdatePvalueField (ado, colp->OptScl->ThreshRange[0]);
1127
1128 SUMA_RETURN(1);
1129 }
1130
SUMA_cb_set_threshold(Widget w,XtPointer clientData,XtPointer call)1131 void SUMA_cb_set_threshold(Widget w, XtPointer clientData, XtPointer call)
1132 {
1133 static char FuncName[]={"SUMA_cb_set_threshold"};
1134 SUMA_ALL_DO *ado=NULL;
1135 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
1136 float fff=0.0;
1137 int dec=-1;
1138 SUMA_Boolean LocalHead = NOPE;
1139
1140 SUMA_ENTRY;
1141
1142 SUMA_LH("called");
1143 ado = (SUMA_ALL_DO *)clientData;
1144 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
1145 XtVaGetValues(w, XmNuserData, &dec, NULL);
1146 fff = (float)cbs->value / pow(10.0, dec);
1147 SUMA_LHv("Have %f\n", fff);
1148 SUMA_set_threshold(ado, NULL, &fff);
1149
1150 SUMA_RETURNe;
1151 }
1152
SUMA_SwitchColPlaneIntensity(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int ind,int setmen)1153 int SUMA_SwitchColPlaneIntensity(
1154 SUMA_ALL_DO *ado,
1155 SUMA_OVERLAYS *colp,
1156 int ind, int setmen)
1157 {
1158 static char FuncName[]={"SUMA_SwitchColPlaneIntensity"};
1159 char srange[500];
1160 double range[2];
1161 int loc[2];
1162 SUMA_Boolean LocalHead = NOPE;
1163
1164 SUMA_ENTRY;
1165
1166 if (!SUMA_SwitchColPlaneIntensity_one(ado, colp, ind, setmen)) {
1167 SUMA_S_Err("Failed in _one");
1168 SUMA_RETURN(0);
1169 }
1170
1171 if (ado->do_type == SO_type) {
1172 SUMA_SurfaceObject *SOC=NULL, *SO=NULL;
1173 SUMA_OVERLAYS *colpC=NULL;
1174 /* do we have a contralateral SO and overlay? */
1175 SO = (SUMA_SurfaceObject *)ado;
1176 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
1177 if (colpC && SOC) {
1178 SUMA_LHv("Found contralateral equivalent to:\n"
1179 " %s and %s in\n"
1180 " %s and %s\n",
1181 SO->Label, CHECK_NULL_STR(colp->Label),
1182 SOC->Label, CHECK_NULL_STR(colpC->Label));
1183 if (!SUMA_SwitchColPlaneIntensity_one(
1184 (SUMA_ALL_DO *)SOC, colpC, ind, 1)) {
1185 SUMA_S_Warn("Failed in contralateral");
1186 }
1187 }
1188 }
1189
1190 SUMA_RETURN(1);
1191 }
1192
1193
1194 /* changes you do here should be reflected under SE_SetSurfCont in SUMA_Engine*/
SUMA_SwitchColPlaneIntensity_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int ind,int setmen)1195 int SUMA_SwitchColPlaneIntensity_one (
1196 SUMA_ALL_DO *ado,
1197 SUMA_OVERLAYS *colp,
1198 int ind, int setmen)
1199 {
1200 static char FuncName[]={"SUMA_SwitchColPlaneIntensity_one"};
1201 char srange[500];
1202 double range[2];
1203 int loc[2];
1204 float pp = 0.0;
1205 SUMA_DSET *dset=NULL;
1206 char *Label=NULL;
1207 SUMA_X_SurfCont *SurfCont=NULL;
1208 SUMA_OVERLAYS *curColPlane=NULL;
1209 SUMA_Boolean LocalHead = NOPE;
1210
1211 SUMA_ENTRY;
1212
1213
1214 SurfCont = SUMA_ADO_Cont(ado);
1215 curColPlane = SUMA_ADO_CurColPlane(ado);
1216 Label = SUMA_ADO_Label(ado);
1217
1218 if ( !ado || !SurfCont ||
1219 !curColPlane ||
1220 !colp || !colp->dset_link || !colp->OptScl) { SUMA_RETURN(0); }
1221
1222 if (ind < 0) {
1223 if (ind == SUMA_BACK_ONE_SUBBRICK) {/* --1 */
1224 ind = colp->OptScl->find-1;
1225 if (ind < 0 || ind >= SDSET_VECNUM(colp->dset_link)) {
1226 SUMA_LH("Reached end");
1227 SUMA_BEEP;
1228 SUMA_RETURN(1);
1229 }
1230 } else if (ind == SUMA_FORWARD_ONE_SUBBRICK) {/* ++1 */
1231 ind = colp->OptScl->find+1;
1232 if (ind < 0 || ind >= SDSET_VECNUM(colp->dset_link)) {
1233 SUMA_LH("Reached end, return without complaint");
1234 SUMA_BEEP;
1235 SUMA_RETURN(1);
1236 }
1237 } else { SUMA_RETURN(0); }
1238 }
1239
1240 if (LocalHead) {
1241 fprintf( SUMA_STDERR,
1242 "%s:\n request to switch intensity to col. %d\n",
1243 FuncName, ind);
1244 fprintf(SUMA_STDERR, "ADO->Label = %s\n", Label);
1245 }
1246
1247 if (SDSET_TYPE(colp->dset_link) == SUMA_NODE_RGB) {
1248 SUMA_S_Err("This is a NODE_RGB dataset, cannot switch columns.\n");
1249 SUMA_RETURN(0);
1250 }
1251 if (ind >= SDSET_VECNUM(colp->dset_link)) {
1252 SUMA_S_Errv("Col. Index of %d exceeds maximum of %d for this dset.\n",
1253 ind, SDSET_VECNUM(colp->dset_link)-1);
1254 SUMA_RETURN(0);
1255 }
1256 if (ind != colp->OptScl->find &&
1257 colp->OptScl->Clusterize) {
1258 /* Need a new clusterizing effort*/
1259 colp->OptScl->RecomputeClust = 1;
1260 }
1261 colp->OptScl->find = ind;
1262 if (setmen && colp == curColPlane && SurfCont->SwitchIntMenu) {
1263 SUMA_LHv("Setting menu values, %d\n", colp->OptScl->find+1);
1264 SUMA_Set_Menu_Widget(SurfCont->SwitchIntMenu, colp->OptScl->find+1);
1265 }
1266
1267
1268 dset=colp->dset_link;
1269 switch(curColPlane->LinkMode) {/* corresponding threshold sb */
1270 case SW_LinkMode_Stat:
1271 {
1272 char *lab=SUMA_DsetColLabelCopy(dset, ind, 0), *lab2=NULL, *ext=NULL;
1273 int ind2=-1, ipair=0;
1274 static char *exta[50]={ "_Coef", "_Tstat", /* 3dDeconvolve */
1275 "_mean", "_Tstat", /* 3dttest++ */
1276 ":Mean", ":t-stat", /* 3dANOVA */
1277 ":Contr", ":t-stat", /* 3dANOVA */
1278 ":Inten", ":F-stat", /* 3dANOVA */
1279 ":Diff", ":t-stat", /* 3dANOVA */
1280 ":b", ":t", /* 3dMEMA */
1281 "_mean", "_Zscr", /* GICOR */
1282 "_meanNC", "_ZscrNC", /* GICOR */
1283 "", " t", /* 3dMVM */
1284 NULL, NULL }; /* leave always at the bottom*/
1285 SUMA_LHv("Looking for decent match for %s\n", lab);
1286 if (lab) {
1287 ipair=0;
1288 while(ind2 < 0 && (ext = exta[ipair*2])) {
1289 if ((strcmp(ext, "")==0) || STRING_HAS_SUFFIX(lab,ext)) {
1290 lab[strlen(lab)-strlen(ext)]='\0';
1291 lab2 = SUMA_append_string(lab,exta[ipair*2+1]);
1292 SUMA_LHv(" Looking for %s\n", lab2);
1293 if ((ind2 = SUMA_FindDsetColLabeled(dset, lab2)) >= 0) {
1294 SUMA_LHv("Sub-brick %s%s has %s go with it.\n",
1295 lab, ext, lab2);
1296 colp->OptScl->tind = ind2;
1297 if (colp == curColPlane && SurfCont->SwitchThrMenu){
1298 /* must set this
1299 regardless of setmen, but not if
1300 SwitchThrMenu has not be been set yet */
1301 SUMA_LH("Setting threshold values");
1302 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
1303 colp->OptScl->tind+1);
1304 if (SUMA_GetDsetColRange(colp->dset_link,
1305 colp->OptScl->tind, range, loc)) {
1306 SUMA_SetScaleRange(ado, range );
1307 SUMA_InitRangeTable(ado, -1) ;
1308 SUMA_UpdateNodeValField(ado);
1309 }else {
1310 SUMA_S_Err("Failed to get range");
1311 }
1312 if ((pp=SUMA_floatEnv("SUMA_pval_at_switch", -1.0))
1313 >= 0) {
1314 pp = (float)SUMA_Pval2ThreshVal (ado, (double)pp);
1315 /* This function will cause undue redisplays, but
1316 keeps code clean */
1317 if ( pp != 0.0) {
1318 SUMA_set_threshold_one(ado, colp, &pp);
1319 }
1320 }
1321 }
1322 } SUMA_free(lab2); lab2=NULL;
1323 /* put lab back together */
1324 lab[strlen(lab)]=ext[0];
1325 }
1326 ++ipair;
1327 }
1328 }
1329 }
1330 break;
1331 case SW_LinkMode_Same:
1332 colp->OptScl->tind = ind;
1333 if (colp == curColPlane ) {/* must set this
1334 regardless of setmen */
1335 SUMA_LH("Setting threshold values");
1336 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
1337 colp->OptScl->tind+1) ;
1338 if (SUMA_GetDsetColRange(colp->dset_link,
1339 colp->OptScl->tind, range, loc)) {
1340 SUMA_SetScaleRange(ado, range );
1341 SUMA_InitRangeTable(ado, -1) ;
1342 SUMA_UpdateNodeValField(ado);
1343 }else {
1344 SUMA_S_Err("Failed to get range");
1345 }
1346 if ((pp=SUMA_floatEnv("SUMA_pval_at_switch", -1.0)) >= 0) {
1347 pp = (float)SUMA_Pval2ThreshVal (ado, (double)pp);
1348 /* This function will cause undue redisplays, but
1349 keeps code clean */
1350 if ( pp != 0.0) {
1351 SUMA_set_threshold_one(ado, colp, &pp);
1352 }
1353 }
1354 }
1355 break;
1356 case SW_LinkMode_Pls1:
1357 {
1358 if (ind+1 >= SDSET_VECNUM(dset)) break;
1359 colp->OptScl->tind = ind+1;
1360 if (colp == curColPlane ) {/* must set this
1361 regardless of setmen */
1362 SUMA_LH("Setting threshold values");
1363 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
1364 colp->OptScl->tind+1) ;
1365 if (SUMA_GetDsetColRange(colp->dset_link,
1366 colp->OptScl->tind, range, loc)) {
1367 SUMA_SetScaleRange(ado, range );
1368 SUMA_InitRangeTable(ado, -1) ;
1369 SUMA_UpdateNodeValField(ado);
1370 }else {
1371 SUMA_S_Err("Failed to get range");
1372 }
1373 if ((pp=SUMA_floatEnv("SUMA_pval_at_switch", -1.0)) >= 0) {
1374 pp = (float)SUMA_Pval2ThreshVal (ado, (double)pp);
1375 /* This function will cause undue redisplays, but
1376 keeps code clean */
1377 if ( pp != 0.0) {
1378 SUMA_set_threshold_one(ado, colp, &pp);
1379 }
1380 }
1381 }
1382 }
1383 break;
1384 default:
1385 break;
1386 }
1387
1388
1389 SUMA_LH("Setting Range, Intensity change");
1390 SUMA_InitRangeTable(ado, 0) ;
1391 SUMA_UpdateCrossHairNodeLabelFieldForDO(ado);
1392
1393 if (colp->ShowMode < 0) { SUMA_RETURN(1); } /* nothing else to do */
1394
1395 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
1396
1397 if (!SUMA_ColorizePlane (colp)) {
1398 SUMA_SLP_Err("Failed to colorize plane.\n");
1399 SUMA_RETURN(0);
1400 }
1401
1402
1403 SUMA_Remixedisplay(ado);
1404
1405 #if SUMA_SEPARATE_SURF_CONTROLLERS
1406 SUMA_UpdateColPlaneShellAsNeeded(ado);
1407 #endif
1408
1409 SUMA_UpdateNodeValField(ado);
1410 SUMA_UpdateNodeLblField(ado);
1411
1412 SUMA_RETURN(1);
1413 }
1414
SUMA_cb_SwitchIntensity(Widget w,XtPointer client_data,XtPointer call)1415 void SUMA_cb_SwitchIntensity(Widget w, XtPointer client_data, XtPointer call)
1416 {
1417 static char FuncName[]={"SUMA_cb_SwitchIntensity"};
1418 int imenu = 0;
1419 SUMA_MenuCallBackData *datap=NULL;
1420 SUMA_ALL_DO *ado=NULL;
1421 SUMA_OVERLAYS *curColPlane=NULL;
1422 SUMA_Boolean LocalHead = NOPE;
1423
1424 SUMA_ENTRY;
1425
1426 /* get the surface object that the setting belongs to */
1427 datap = (SUMA_MenuCallBackData *)client_data;
1428 ado = (SUMA_ALL_DO *)datap->ContID;
1429 curColPlane = SUMA_ADO_CurColPlane(ado);
1430 imenu = (INT_CAST)datap->callback_data;
1431
1432 if (imenu-1 == curColPlane->OptScl->find) {
1433 SUMA_RETURNe; /* nothing to be done */
1434 }
1435
1436 SUMA_SwitchColPlaneIntensity(ado, curColPlane, imenu -1, 0);
1437
1438 SUMA_RETURNe;
1439 }
1440
SUMA_SwitchColPlaneThreshold(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int ind,int setmen)1441 int SUMA_SwitchColPlaneThreshold(
1442 SUMA_ALL_DO *ado,
1443 SUMA_OVERLAYS *colp,
1444 int ind, int setmen)
1445 {
1446 static char FuncName[]={"SUMA_SwitchColPlaneThreshold"};
1447 char srange[500];
1448 double range[2];
1449 int loc[2];
1450 SUMA_DSET *dset=NULL;
1451 SUMA_SurfaceObject *SOC=NULL, *SO=NULL;
1452 SUMA_OVERLAYS *colpC=NULL;
1453 SUMA_Boolean LocalHead = NOPE;
1454
1455 SUMA_ENTRY;
1456
1457 if (!SUMA_SwitchColPlaneThreshold_one(ado, colp, ind, setmen)) {
1458 SUMA_S_Err("Failed in _one");
1459 SUMA_RETURN(0);
1460 }
1461
1462 if (ado->do_type == SO_type) {
1463 SO = (SUMA_SurfaceObject *)ado;
1464 /* do we have a contralateral SO and overlay? */
1465 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
1466 if (colpC && SOC) {
1467 SUMA_LHv("Found contralateral equivalent to:\n"
1468 " %s and %s in\n"
1469 " %s and %s\n",
1470 SO->Label, CHECK_NULL_STR(colp->Label),
1471 SOC->Label, CHECK_NULL_STR(colpC->Label));
1472 if (!SUMA_SwitchColPlaneThreshold_one(ado, colpC, ind, 1)) {
1473 SUMA_S_Warn("Failed in contralateral");
1474 }
1475 }
1476 }
1477
1478 SUMA_RETURN(1);
1479 }
1480
SUMA_SwitchColPlaneThreshold_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int ind,int setmen)1481 int SUMA_SwitchColPlaneThreshold_one(
1482 SUMA_ALL_DO *ado, SUMA_OVERLAYS *colp,
1483 int ind, int setmen)
1484 {
1485 static char FuncName[]={"SUMA_SwitchColPlaneThreshold_one"};
1486 char srange[500];
1487 double range[2]; int loc[2];
1488 float pp=0.0;
1489 SUMA_X_SurfCont *SurfCont=NULL;
1490 SUMA_OVERLAYS *curColPlane=NULL;
1491 SUMA_Boolean LocalHead = NOPE;
1492
1493 SUMA_ENTRY;
1494
1495
1496 SurfCont = SUMA_ADO_Cont(ado);
1497 curColPlane = SUMA_ADO_CurColPlane(ado);
1498 if (!ado || !SurfCont || !curColPlane ||
1499 !colp || ind < -1 || !colp->dset_link) { SUMA_RETURN(0); }
1500
1501
1502 if (LocalHead) {
1503 fprintf(SUMA_STDERR, "%s:\n request to switch threshold to col. %d\n",
1504 FuncName, ind);
1505 }
1506 if (ind < 0) {
1507 /* turn threshold off */
1508 XmToggleButtonSetState (SurfCont->Thr_tb, NOPE, YUP);
1509 SUMA_RETURN(1);
1510 }
1511
1512 if (ind >= SDSET_VECNUM(colp->dset_link)) {
1513 SUMA_S_Errv("Col. Index of %d exceeds maximum of %d for this dset.\n",
1514 ind, SDSET_VECNUM(colp->dset_link)-1);
1515 SUMA_RETURN(0);
1516 }
1517
1518 if (ind != colp->OptScl->tind &&
1519 colp->OptScl->Clusterize) {
1520 /* Need a new clusterizing effort*/
1521 colp->OptScl->RecomputeClust = 1;
1522 }
1523 colp->OptScl->tind = ind;
1524
1525
1526 /* make sure threshold is on if command is not from the interface*/
1527 if (setmen && !colp->OptScl->UseThr && colp->OptScl->tind >= 0) {
1528 colp->OptScl->UseThr = YUP;
1529 XmToggleButtonSetState (SurfCont->Thr_tb, YUP, NOPE);
1530 }
1531
1532 if (setmen && colp == curColPlane) {
1533 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
1534 colp->OptScl->tind+1) ;
1535 }
1536
1537 if (SUMA_GetDsetColRange(colp->dset_link, colp->OptScl->tind, range, loc)) {
1538 SUMA_SetScaleRange(ado, range );
1539 }else {
1540 SUMA_SLP_Err("Failed to get range");
1541 SUMA_RETURN(0);
1542 }
1543
1544 /* threshold sub-brick change */
1545 SUMA_InitRangeTable(ado, -1) ;
1546 SUMA_UpdateCrossHairNodeLabelFieldForDO(ado);
1547 SUMA_UpdateNodeValField(ado);
1548
1549 if (!colp->OptScl->UseThr) { SUMA_RETURN(1); } /* nothing else to do */
1550
1551 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
1552
1553 if (!SUMA_ColorizePlane (colp)) {
1554 SUMA_SLP_Err("Failed to colorize plane.\n");
1555 SUMA_RETURN(0);
1556 }
1557
1558 SUMA_Remixedisplay(ado);
1559
1560 #if SUMA_SEPARATE_SURF_CONTROLLERS
1561 SUMA_UpdateColPlaneShellAsNeeded(ado);
1562 #endif
1563
1564 SUMA_UpdateNodeLblField(ado);
1565
1566 if ((pp=SUMA_floatEnv("SUMA_pval_at_switch", -1.0)) >= 0) {
1567 pp = (float)SUMA_Pval2ThreshVal (ado, (double)pp);
1568 /* This function will cause undue redisplays, but keeps code clean */
1569 if ( pp != 0.0) {
1570 SUMA_set_threshold_one(ado, colp, &pp);
1571 }
1572 }
1573
1574 SUMA_RETURN(1);
1575 }
1576
SUMA_cb_SwitchThreshold(Widget w,XtPointer client_data,XtPointer call)1577 void SUMA_cb_SwitchThreshold(Widget w, XtPointer client_data, XtPointer call)
1578 {
1579 static char FuncName[]={"SUMA_cb_SwitchThreshold"};
1580 int imenu = 0;
1581 SUMA_MenuCallBackData *datap=NULL;
1582 SUMA_ALL_DO *ado=NULL;
1583 SUMA_OVERLAYS *curColPlane=NULL;
1584 SUMA_Boolean LocalHead = NOPE;
1585
1586 SUMA_ENTRY;
1587
1588 /* get the surface object that the setting belongs to */
1589 datap = (SUMA_MenuCallBackData *)client_data;
1590 ado = (SUMA_ALL_DO *)datap->ContID;
1591 imenu = (INT_CAST)datap->callback_data;
1592
1593 curColPlane = SUMA_ADO_CurColPlane(ado);
1594 if (imenu-1 == curColPlane->OptScl->tind) {
1595 SUMA_RETURNe; /* nothing to be done */
1596 }
1597
1598 SUMA_SwitchColPlaneThreshold(ado, curColPlane, imenu -1, 0);
1599 SUMA_RETURNe;
1600 }
1601
SUMA_SwitchColPlaneBrightness(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int ind,int setmen)1602 int SUMA_SwitchColPlaneBrightness(
1603 SUMA_ALL_DO *ado,
1604 SUMA_OVERLAYS *colp,
1605 int ind, int setmen)
1606 {
1607 static char FuncName[]={"SUMA_SwitchColPlaneBrightness"};
1608 char srange[500];
1609 double range[2];
1610 int loc[2];
1611 SUMA_DSET *dset=NULL;
1612 SUMA_OVERLAYS *colpC=NULL;
1613 SUMA_Boolean LocalHead = NOPE;
1614
1615 SUMA_ENTRY;
1616
1617 if (LocalHead) {
1618 fprintf(SUMA_STDERR,
1619 "%s:\n request to switch brightness to col. %d\n", FuncName, ind);
1620 }
1621
1622 if (ind == colp->OptScl->bind) {
1623 SUMA_RETURN(0); /* nothing to be done */
1624 }
1625
1626 if (!SUMA_SwitchColPlaneBrightness_one(ado, colp, ind, setmen)) {
1627 SUMA_S_Err("Failed in _one");
1628 SUMA_RETURN(0);
1629 }
1630
1631 if (ado->do_type == SO_type) {
1632 SUMA_SurfaceObject *SOC=NULL;
1633 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
1634 /* do we have a contralateral SO and overlay? */
1635 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
1636 if (colpC && SOC) {
1637 SUMA_LHv("Found contralateral equivalent to:\n"
1638 " %s and %s in\n"
1639 " %s and %s\n",
1640 SO->Label, CHECK_NULL_STR(colp->Label),
1641 SOC->Label, CHECK_NULL_STR(colpC->Label));
1642 if (!SUMA_SwitchColPlaneBrightness_one((SUMA_ALL_DO *)SOC,
1643 colpC, ind, 1)) {
1644 SUMA_S_Warn("Failed in contralateral");
1645 }
1646 }
1647 }
1648 SUMA_RETURN(1);
1649 }
1650
SUMA_SwitchColPlaneBrightness_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int ind,int setmen)1651 int SUMA_SwitchColPlaneBrightness_one(
1652 SUMA_ALL_DO *ado, SUMA_OVERLAYS *colp,
1653 int ind, int setmen)
1654 {
1655 static char FuncName[]={"SUMA_SwitchColPlaneBrightness_one"};
1656 char srange[500];
1657 double range[2]; int loc[2];
1658 SUMA_X_SurfCont *SurfCont=NULL;
1659 SUMA_OVERLAYS *curColPlane=NULL;
1660 SUMA_Boolean LocalHead = NOPE;
1661
1662 SUMA_ENTRY;
1663
1664 if (!ado) {
1665 SUMA_SL_Err("NULL ado");
1666 SUMA_RETURN(0);
1667 }
1668 SurfCont = SUMA_ADO_Cont(ado);
1669 curColPlane = SUMA_ADO_CurColPlane(ado);
1670
1671 if ( !SurfCont || !curColPlane ||
1672 !colp || ind < -1 || !colp->dset_link) {
1673 SUMA_S_Err("NULLity");
1674 SUMA_RETURN(0);
1675 }
1676
1677
1678 if (LocalHead) {
1679 fprintf(SUMA_STDERR,
1680 "%s:\n request to switch brightness to col. %d, currently %d\n",
1681 FuncName, ind, colp->OptScl->bind);
1682 }
1683
1684 if (ind < 0) {
1685 /* turn brightness off */
1686 XmToggleButtonSetState (SurfCont->Brt_tb, NOPE, YUP);
1687 SUMA_RETURN(1);
1688 }
1689
1690 if (ind >= SDSET_VECNUM(colp->dset_link)) {
1691 SUMA_S_Errv("Col. Index of %d exceeds maximum of %d for this dset.\n",
1692 ind, SDSET_VECNUM(colp->dset_link)-1);
1693 SUMA_RETURN(0);
1694 }
1695 colp->OptScl->bind = ind;
1696
1697 /* make sure brightness is on if command is not from the interface*/
1698 if (setmen && !colp->OptScl->UseBrt && colp->OptScl->bind >= 0) {
1699 colp->OptScl->UseBrt = YUP;
1700 XmToggleButtonSetState (SurfCont->Brt_tb, YUP, NOPE);
1701 }
1702
1703 if (setmen && colp == curColPlane) {
1704 SUMA_Set_Menu_Widget(SurfCont->SwitchBrtMenu,
1705 colp->OptScl->bind+1);
1706 }
1707
1708 if (SUMA_GetDsetColRange(colp->dset_link, colp->OptScl->bind, range, loc)) {
1709 SUMA_SetScaleRange(ado, range );
1710 }else {
1711 SUMA_SLP_Err("Failed to get range");
1712 SUMA_RETURN(0);
1713 }
1714
1715 /* brightness change */
1716 SUMA_InitRangeTable(ado, -1) ;
1717 SUMA_UpdateCrossHairNodeLabelFieldForDO(ado);
1718 SUMA_UpdateNodeValField(ado);
1719
1720 if (!colp->OptScl->UseBrt) { SUMA_RETURN(1); } /* nothing else to do */
1721
1722 if (!SUMA_ColorizePlane (colp)) {
1723 SUMA_SLP_Err("Failed to colorize plane.\n");
1724 SUMA_RETURN(0);
1725 }
1726
1727 SUMA_Remixedisplay(ado);
1728
1729 #if SUMA_SEPARATE_SURF_CONTROLLERS
1730 SUMA_UpdateColPlaneShellAsNeeded(ado);
1731 #endif
1732
1733 SUMA_UpdateNodeLblField(ado);
1734
1735 SUMA_RETURN(1);
1736 }
1737
1738
SUMA_cb_SwitchBrightness(Widget w,XtPointer client_data,XtPointer call)1739 void SUMA_cb_SwitchBrightness(Widget w, XtPointer client_data, XtPointer call)
1740 {
1741 static char FuncName[]={"SUMA_cb_SwitchBrightness"};
1742 int imenu = 0;
1743 SUMA_MenuCallBackData *datap=NULL;
1744 SUMA_ALL_DO *ado = NULL;
1745 SUMA_OVERLAYS *curColPlane=NULL;
1746 SUMA_Boolean LocalHead = NOPE;
1747
1748 SUMA_ENTRY;
1749
1750 /* get the surface object that the setting belongs to */
1751 datap = (SUMA_MenuCallBackData *)client_data;
1752 ado = (SUMA_ALL_DO *)datap->ContID;
1753 curColPlane = SUMA_ADO_CurColPlane(ado);
1754 imenu = (INT_CAST)datap->callback_data;
1755
1756 if (imenu-1 == curColPlane->OptScl->bind) {
1757 SUMA_RETURNe; /* nothing to be done */
1758 }
1759 SUMA_SwitchColPlaneBrightness(ado, curColPlane, imenu -1, 0);
1760
1761 #if 0 /* Obsolete, now all handled in SUMA_SwitchColPlaneBrightness above*/
1762 if (LocalHead) {
1763 fprintf( SUMA_STDERR,
1764 "%s:\n request to switch brightness to col. %d\n",
1765 FuncName, imenu - 1);
1766 }
1767
1768 curColPlane->OptScl->bind = imenu - 1;
1769
1770 SUMA_InitRangeTable(ado, 1) ;
1771
1772 SUMA_UpdateNodeValField(ado);
1773 if (!curColPlane->OptScl->UseBrt) {
1774 SUMA_RETURNe;
1775 } /* nothing else to do */
1776
1777 if (!SUMA_ColorizePlane (curColPlane)) {
1778 SUMA_SLP_Err("Failed to colorize plane.\n");
1779 SUMA_RETURNe;
1780 }
1781
1782
1783 SUMA_Remixedisplay(ado);
1784
1785 #if SUMA_SEPARATE_SURF_CONTROLLERS
1786 SUMA_UpdateColPlaneShellAsNeeded(ado);
1787 #endif
1788
1789 SUMA_UpdateNodeLblField(ado);
1790 #endif
1791
1792 SUMA_RETURNe;
1793 }
1794
SUMA_SwitchCmap_one(SUMA_ALL_DO * ado,SUMA_COLOR_MAP * CM,int setmenu)1795 int SUMA_SwitchCmap_one(SUMA_ALL_DO *ado,
1796 SUMA_COLOR_MAP *CM, int setmenu)
1797 {
1798 static char FuncName[]={"SUMA_SwitchCmap_one"};
1799 SUMA_Boolean LocalHead = NOPE;
1800
1801 SUMA_ENTRY;
1802
1803 if (!ado || !CM) SUMA_RETURN(0);
1804
1805 if (LocalHead) {
1806 fprintf(SUMA_STDERR, "%s:\n request to switch colormap to (%s)\n",
1807 FuncName, CM->Name);
1808 }
1809
1810 if (setmenu) {
1811 if (!SUMA_SetCmapMenuChoice (ado, CM->Name)) {
1812 SUMA_SL_Err("Failed in SUMA_SetCmapMenuChoice");
1813 }
1814 }
1815
1816 if (!SUMA_SwitchColPlaneCmap(ado, CM)) {
1817 SUMA_SL_Err("Failed in SUMA_SwitchColPlaneCmap");
1818 }
1819
1820 /* Now you'll need to close the list widget if a choice has been made */
1821 if (SUMAg_CF->X->SwitchCmapLst) {
1822 if (!SUMAg_CF->X->SwitchCmapLst->isShaded)
1823 SUMA_cb_CloseSwitchCmap( NULL, (XtPointer)SUMAg_CF->X->SwitchCmapLst,
1824 NULL);
1825 }
1826
1827 #if SUMA_SEPARATE_SURF_CONTROLLERS
1828 SUMA_UpdateColPlaneShellAsNeeded(ado);
1829 #endif
1830
1831 /* update Lbl fields */
1832 SUMA_UpdateNodeLblField(ado);
1833
1834 if (SUMAg_CF->Fake_Cmap) {
1835 SUMA_LH("Attempting to keep up appearances");
1836 SUMA_PBAR_bigexpose_CB(NULL, (XtPointer)ado, NULL);
1837 }
1838
1839 SUMA_RETURN(1);
1840 }
1841
SUMA_SwitchCmap(SUMA_ALL_DO * ado,SUMA_COLOR_MAP * CM,int setmenu)1842 int SUMA_SwitchCmap(SUMA_ALL_DO *ado,
1843 SUMA_COLOR_MAP *CM, int setmenu)
1844 {
1845 static char FuncName[]={"SUMA_SwitchCmap"};
1846 SUMA_Boolean LocalHead = NOPE;
1847
1848 SUMA_ENTRY;
1849
1850 SUMA_LH("Called");
1851 if (!ado || !CM) SUMA_RETURN(0);
1852
1853 if (!SUMA_SwitchCmap_one(ado, CM, setmenu)) SUMA_RETURN(0);
1854
1855 if (ado->do_type == SO_type) {
1856 SUMA_SurfaceObject *SOC=NULL, *SO=(SUMA_SurfaceObject *)ado;
1857 SUMA_OVERLAYS *colp=NULL, *colpC=NULL;
1858 /* do we have a contralateral SO and overlay? */
1859 colp = SO->SurfCont->curColPlane;
1860 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
1861 if (colpC && SOC) {
1862 SUMA_LHv("Found contralateral equivalent to:\n"
1863 " %s and %s in\n"
1864 " %s and %s\n",
1865 SO->Label, CHECK_NULL_STR(colp->Label),
1866 SOC->Label, CHECK_NULL_STR(colpC->Label));
1867 if (!SUMA_SwitchCmap_one((SUMA_ALL_DO *)SOC, CM, 1)) {
1868 SUMA_S_Warn("Failed in contralateralination");
1869 }
1870 }
1871 }
1872 SUMA_RETURN(1);
1873 }
1874
1875 /*!
1876 \brief function that handlges switching colormap from the menu widget
1877 \sa SUMA_cb_SelectSwitchCmap
1878 */
SUMA_cb_SwitchCmap(Widget w,XtPointer client_data,XtPointer call)1879 void SUMA_cb_SwitchCmap(Widget w, XtPointer client_data, XtPointer call)
1880 {
1881 static char FuncName[]={"SUMA_cb_SwitchCmap"};
1882 SUMA_MenuCallBackData *datap=NULL;
1883 SUMA_ALL_DO *ado = NULL;
1884 SUMA_COLOR_MAP *CM = NULL;
1885 SUMA_Boolean LocalHead = NOPE;
1886
1887 SUMA_ENTRY;
1888
1889 /* get the surface object that the setting belongs to */
1890 datap = (SUMA_MenuCallBackData *)client_data;
1891 ado = (SUMA_ALL_DO *)datap->ContID;
1892 CM = (SUMA_COLOR_MAP *)datap->callback_data;
1893
1894 SUMA_SwitchCmap(ado, CM, 0);
1895
1896 SUMA_RETURNe;
1897 }
1898
SUMA_cb_ShowZero_tb_toggled(Widget w,XtPointer data,XtPointer client_data)1899 void SUMA_cb_ShowZero_tb_toggled (Widget w, XtPointer data,
1900 XtPointer client_data)
1901 {
1902 static char FuncName[]={"SUMA_cb_ShowZero_tb_toggled"};
1903 SUMA_ALL_DO *ado = NULL;
1904 SUMA_TABLE_FIELD *TF=NULL;
1905 SUMA_X_SurfCont *SurfCont=NULL;
1906 SUMA_OVERLAYS *curColPlane=NULL;
1907 SUMA_Boolean LocalHead = NOPE;
1908
1909 SUMA_ENTRY;
1910
1911 SUMA_LH("Called");
1912
1913 ado = (SUMA_ALL_DO *)data;
1914
1915 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
1916 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
1917 curColPlane = SUMA_ADO_CurColPlane(ado);
1918 if ( !curColPlane ||
1919 !curColPlane->OptScl ) {
1920 SUMA_S_Warn("NULL input 2"); SUMA_RETURNe;
1921 }
1922
1923 curColPlane->OptScl->MaskZero =
1924 !curColPlane->OptScl->MaskZero;
1925
1926 /* seems the '!' were remnants - */
1927 /* revert to original logic, but avoid warnings
1928 * (to later evaluate changes) todo: apply ShowMode
1929 * original : if (!curColPlane->ShowMode < 0)
1930 * fix?? : if (curColPlane->ShowMode < 0)
1931 * temp.as.orig : if ( 0 )
1932 *
1933 * comments : orig/temp would never show
1934 * : we probably want to RETURN if not showing ( < 0 )
1935 * : so '!' was just a remnant typo
1936 * : might be unclear when == 0
1937 * 19 Feb 2021 [rickr] */
1938 if ( 0 ) {
1939 /* nothing else to do */
1940 SUMA_RETURNe;
1941 }
1942
1943 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
1944
1945 if (!SUMA_ColorizePlane (curColPlane)) {
1946 SUMA_SLP_Err("Failed to colorize plane.\n");
1947 SUMA_RETURNe;
1948 }
1949
1950 SUMA_Remixedisplay(ado);
1951
1952 SUMA_UpdateNodeLblField(ado);
1953
1954 SUMA_RETURNe;
1955 }
1956
1957
SUMA_cb_SymIrange_tb_toggled(Widget w,XtPointer data,XtPointer client_data)1958 void SUMA_cb_SymIrange_tb_toggled (Widget w, XtPointer data,
1959 XtPointer client_data)
1960 {
1961 static char FuncName[]={"SUMA_cb_SymIrange_tb_toggled"};
1962 SUMA_ALL_DO *ado = NULL;
1963 SUMA_X_SurfCont *SurfCont=NULL;
1964 SUMA_OVERLAYS *curColPlane=NULL;
1965 SUMA_TABLE_FIELD *TF=NULL;
1966 SUMA_Boolean LocalHead = NOPE;
1967
1968 SUMA_ENTRY;
1969
1970 SUMA_LH("Called");
1971
1972 ado = (SUMA_ALL_DO *)data;
1973
1974 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
1975 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
1976 curColPlane = SUMA_ADO_CurColPlane(ado);
1977 if ( !curColPlane ) {
1978 SUMA_S_Warn("NULL input 2"); SUMA_RETURNe;
1979 }
1980
1981 curColPlane->SymIrange = !curColPlane->SymIrange;
1982
1983 if (curColPlane->SymIrange) {
1984 /* manual setting of range.
1985 DO NOT Call SUMA_InitRangeTable because it will
1986 automatically update the I range under certain conditions*/
1987 TF = SurfCont->SetRangeTable;
1988 curColPlane->OptScl->IntRange[1] =
1989 SUMA_LARG_ABS(curColPlane->OptScl->IntRange[0],
1990 curColPlane->OptScl->IntRange[1]);
1991 curColPlane->OptScl->IntRange[0] =
1992 -curColPlane->OptScl->IntRange[1];
1993 SUMA_INSERT_CELL_VALUE(TF, 1, 1,
1994 curColPlane->OptScl->IntRange[0]);
1995 SUMA_INSERT_CELL_VALUE(TF, 1, 2,
1996 curColPlane->OptScl->IntRange[1]);
1997 }
1998
1999 /* seems the '!' were remnants - */
2000 /* revert to original logic, but avoid warnings
2001 * (to later evaluate changes) todo: apply ShowMode
2002 * original : if (!curColPlane->ShowMode < 0)
2003 * fix?? : if (curColPlane->ShowMode < 0)
2004 * temp.as.orig : if ( 0 )
2005 *
2006 * comments : orig/temp would never RETURN
2007 * : seems we should return if < 0
2008 * 19 Feb 2021 [rickr] */
2009 if ( 0 ) { SUMA_RETURNe; }
2010
2011 if (!SUMA_ColorizePlane (curColPlane)) {
2012 SUMA_SLP_Err("Failed to colorize plane.\n");
2013 SUMA_RETURNe;
2014 }
2015
2016 SUMA_Remixedisplay(ado);
2017
2018 SUMA_UpdateNodeValField(ado);
2019 SUMA_UpdateNodeLblField(ado);
2020
2021
2022 SUMA_RETURNe;
2023 }
2024
SUMA_cb_AbsThresh_tb_toggled(Widget w,XtPointer data,XtPointer client_data)2025 void SUMA_cb_AbsThresh_tb_toggled (Widget w, XtPointer data,
2026 XtPointer client_data)
2027 {
2028 static char FuncName[]={"SUMA_cb_AbsThresh_tb_toggled"};
2029 SUMA_ALL_DO *ado = NULL;
2030 SUMA_X_SurfCont *SurfCont=NULL;
2031 SUMA_OVERLAYS *curColPlane=NULL;
2032 char slabel[100];
2033 double range[2]; int loc[2];
2034 SUMA_Boolean LocalHead = NOPE;
2035
2036 SUMA_ENTRY;
2037
2038 SUMA_LH("Called");
2039
2040 ado = (SUMA_ALL_DO *)data;
2041
2042 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
2043 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
2044 curColPlane = SUMA_ADO_CurColPlane(ado);
2045 if ( !curColPlane ) {
2046 SUMA_S_Warn("NULL input 2"); SUMA_RETURNe;
2047 }
2048
2049 if (curColPlane->OptScl->ThrMode == SUMA_LESS_THAN) {
2050 curColPlane->OptScl->ThrMode = SUMA_ABS_LESS_THAN;
2051 } else if (curColPlane->OptScl->ThrMode == SUMA_ABS_LESS_THAN){
2052 curColPlane->OptScl->ThrMode = SUMA_LESS_THAN;
2053 } else if (curColPlane->OptScl->ThrMode == SUMA_THRESH_OUTSIDE_RANGE){
2054 curColPlane->OptScl->ThrMode = SUMA_THRESH_INSIDE_RANGE;
2055 } else if (curColPlane->OptScl->ThrMode == SUMA_THRESH_INSIDE_RANGE){
2056 curColPlane->OptScl->ThrMode = SUMA_THRESH_OUTSIDE_RANGE;
2057 } else {
2058 SUMA_S_Err("Not ready for this situation %d...",
2059 curColPlane->OptScl->ThrMode);
2060 }
2061 switch (curColPlane->OptScl->ThrMode) {
2062 case SUMA_LESS_THAN:
2063 sprintf(slabel, "%5s",
2064 MV_format_fval(curColPlane->OptScl->ThreshRange[0]));
2065 break;
2066 case SUMA_ABS_LESS_THAN:
2067 /* used to use this:
2068 sprintf(slabel, "|%5s|", ....
2069 but that does not work in the editable field ... */
2070 sprintf(slabel, "%5s",
2071 MV_format_fval(fabs(curColPlane->OptScl->ThreshRange[0])));
2072 break;
2073 case SUMA_THRESH_INSIDE_RANGE:
2074 /* This is just a place holder for now */
2075 sprintf(slabel, "<%5s..%5s>",
2076 MV_format_fval(curColPlane->OptScl->ThreshRange[0]),
2077 MV_format_fval(curColPlane->OptScl->ThreshRange[1]));
2078 break;
2079 case SUMA_THRESH_OUTSIDE_RANGE:
2080 /* This is just a place holder for now */
2081 sprintf(slabel, ">%5s..%5s<",
2082 MV_format_fval(curColPlane->OptScl->ThreshRange[0]),
2083 MV_format_fval(curColPlane->OptScl->ThreshRange[1]));
2084 break;
2085 case SUMA_NO_THRESH:
2086 break;
2087 default:
2088 /* This is just a place holder for now */
2089 sprintf(slabel, "?%5s??%5s?<",
2090 MV_format_fval(curColPlane->OptScl->ThreshRange[0]),
2091 MV_format_fval(curColPlane->OptScl->ThreshRange[1]));
2092 break;
2093 }
2094
2095 /* SUMA_SET_LABEL(SurfCont->thr_lb, slabel); */
2096 SUMA_INSERT_CELL_STRING(SurfCont->SetThrScaleTable, 0,0,slabel);
2097 if (SUMA_GetDsetColRange(curColPlane->dset_link,
2098 curColPlane->OptScl->tind, range, loc)) {
2099 SUMA_SetScaleRange(ado, range );
2100 }else {
2101 SUMA_SLP_Err("Failed to get range");
2102 SUMA_RETURNe;
2103 }
2104
2105 if (!curColPlane->OptScl->UseThr) { SUMA_RETURNe; }
2106 /* nothing else to do */
2107
2108 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
2109
2110 if (!SUMA_ColorizePlane (curColPlane)) {
2111 SUMA_SLP_Err("Failed to colorize plane.\n");
2112 SUMA_RETURNe;
2113 }
2114
2115 SUMA_Remixedisplay(ado);
2116
2117 SUMA_UpdateNodeLblField(ado);
2118
2119 SUMA_RETURNe;
2120 }
2121
SUMA_cb_SwitchInt_toggled(Widget w,XtPointer data,XtPointer client_data)2122 void SUMA_cb_SwitchInt_toggled (Widget w, XtPointer data, XtPointer client_data)
2123 {
2124 static char FuncName[]={"SUMA_cb_SwitchInt_toggled"};
2125 SUMA_ALL_DO *ado = NULL;
2126 SUMA_X_SurfCont *SurfCont=NULL;
2127 SUMA_OVERLAYS *curColPlane=NULL;
2128 SUMA_Boolean LocalHead = NOPE;
2129
2130 SUMA_ENTRY;
2131
2132 SUMA_LH("Called");
2133
2134 ado = (SUMA_ALL_DO *)data;
2135
2136 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
2137 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
2138 curColPlane = SUMA_ADO_CurColPlane(ado);
2139 if ( !curColPlane ) {
2140 SUMA_S_Warn("NULL input 2"); SUMA_RETURNe;
2141 }
2142
2143 /* make sure ok to turn on */
2144 if (curColPlane->OptScl->find < 0) {
2145 SUMA_BEEP;
2146 SUMA_SLP_Note("no intensity column set");
2147 XmToggleButtonSetState (SurfCont->Int_tb, NOPE, NOPE);
2148 SUMA_RETURNe;
2149 }
2150
2151 /* this button's the same as the Show button */
2152 if (XmToggleButtonGetState (SurfCont->Int_tb)) {
2153 curColPlane->ShowMode =
2154 SUMA_ABS(curColPlane->ShowMode);
2155 } else {
2156 curColPlane->ShowMode =
2157 -SUMA_ABS(curColPlane->ShowMode);
2158 }
2159 if (SurfCont->DsetViewModeMenu) {
2160 SUMA_Set_Menu_Widget(SurfCont->DsetViewModeMenu,
2161 SUMA_ShowMode2ShowModeMenuItem(
2162 curColPlane->ShowMode));
2163 }
2164
2165 SUMA_ColorizePlane(curColPlane);
2166 SUMA_Remixedisplay(ado);
2167 SUMA_UpdateNodeLblField(ado);
2168
2169 #if SUMA_SEPARATE_SURF_CONTROLLERS
2170 SUMA_UpdateColPlaneShellAsNeeded(ado);
2171 #endif
2172 SUMA_RETURNe;
2173 }
2174
SUMA_cb_SwitchThr_toggled(Widget w,XtPointer data,XtPointer client_data)2175 void SUMA_cb_SwitchThr_toggled (Widget w, XtPointer data, XtPointer client_data)
2176 {
2177 static char FuncName[]={"SUMA_cb_SwitchThr_toggled"};
2178 SUMA_ALL_DO *ado = NULL;
2179 SUMA_X_SurfCont *SurfCont=NULL;
2180 SUMA_OVERLAYS *curColPlane=NULL;
2181 SUMA_Boolean LocalHead = NOPE;
2182
2183 SUMA_ENTRY;
2184
2185 SUMA_LH("Called");
2186
2187 ado = (SUMA_ALL_DO *)data;
2188
2189 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
2190 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
2191 curColPlane = SUMA_ADO_CurColPlane(ado);
2192 if ( !curColPlane ) {
2193 SUMA_S_Warn("NULL input 2"); SUMA_RETURNe;
2194 }
2195
2196
2197 /* make sure ok to turn on */
2198 if (curColPlane->OptScl->tind < 0) {
2199 SUMA_BEEP;
2200 SUMA_SLP_Note("no threshold column set");
2201 XmToggleButtonSetState (SurfCont->Thr_tb, NOPE, NOPE);
2202 SUMA_RETURNe;
2203 }
2204
2205 curColPlane->OptScl->UseThr =
2206 XmToggleButtonGetState (SurfCont->Thr_tb);
2207
2208 SUMA_ColorizePlane(curColPlane);
2209 SUMA_Remixedisplay(ado);
2210
2211 SUMA_UpdateNodeLblField(ado);
2212
2213 #if SUMA_SEPARATE_SURF_CONTROLLERS
2214 SUMA_UpdateColPlaneShellAsNeeded(ado);
2215 #endif
2216 SUMA_RETURNe;
2217 }
2218
SUMA_cb_SwitchBrt_toggled(Widget w,XtPointer data,XtPointer client_data)2219 void SUMA_cb_SwitchBrt_toggled (Widget w, XtPointer data, XtPointer client_data)
2220 {
2221 static char FuncName[]={"SUMA_cb_SwitchBrt_toggled"};
2222 SUMA_ALL_DO *ado = NULL;
2223 SUMA_X_SurfCont *SurfCont=NULL;
2224 SUMA_OVERLAYS *curColPlane=NULL;
2225 SUMA_Boolean LocalHead = NOPE;
2226
2227 SUMA_ENTRY;
2228
2229 SUMA_LH("Called");
2230
2231 ado = (SUMA_ALL_DO *)data;
2232
2233 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
2234 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
2235 curColPlane = SUMA_ADO_CurColPlane(ado);
2236 if ( !curColPlane ) {
2237 SUMA_S_Warn("NULL input 2"); SUMA_RETURNe;
2238 }
2239
2240 /* make sure ok to turn on */
2241 if (curColPlane->OptScl->bind < 0) {
2242 SUMA_BEEP;
2243 SUMA_SLP_Note("no brightness column set");
2244 XmToggleButtonSetState (SurfCont->Brt_tb, NOPE, NOPE);
2245 SUMA_RETURNe;
2246 }
2247
2248 curColPlane->OptScl->UseBrt =
2249 XmToggleButtonGetState (SurfCont->Brt_tb);
2250
2251 SUMA_ColorizePlane(curColPlane);
2252 SUMA_Remixedisplay(ado);
2253 SUMA_UpdateNodeLblField(ado);
2254
2255 #if SUMA_SEPARATE_SURF_CONTROLLERS
2256 SUMA_UpdateColPlaneShellAsNeeded(ado);
2257 #endif
2258 SUMA_RETURNe;
2259 }
2260
2261 SUMA_MenuItem CoordBias_Menu[] = {
2262 { "-", &xmPushButtonWidgetClass,
2263 '\0', NULL, NULL,
2264 SUMA_cb_SetCoordBias, (XtPointer) SW_CoordBias_None, NULL},
2265
2266 { "x", &xmPushButtonWidgetClass,
2267 '\0', NULL, NULL,
2268 SUMA_cb_SetCoordBias, (XtPointer) SW_CoordBias_X, NULL},
2269
2270 { "y", &xmPushButtonWidgetClass,
2271 '\0', NULL, NULL,
2272 SUMA_cb_SetCoordBias, (XtPointer) SW_CoordBias_Y, NULL},
2273
2274 { "z", &xmPushButtonWidgetClass,
2275 '\0', NULL, NULL,
2276 SUMA_cb_SetCoordBias, (XtPointer) SW_CoordBias_Z, NULL},
2277
2278 { "n", &xmPushButtonWidgetClass,
2279 '\0', NULL, NULL,
2280 SUMA_cb_SetCoordBias, (XtPointer) SW_CoordBias_N, NULL},
2281
2282 {NULL},
2283 };
2284
2285 SUMA_MenuItem CmapMode_Menu[] = {
2286 { "Dir", &xmPushButtonWidgetClass,
2287 '\0', NULL, NULL,
2288 SUMA_cb_SetCmapMode, (XtPointer) SW_Direct, NULL},
2289
2290 { "NN", &xmPushButtonWidgetClass,
2291 '\0', NULL, NULL,
2292 SUMA_cb_SetCmapMode, (XtPointer) SW_NN, NULL},
2293
2294 { "Int", &xmPushButtonWidgetClass,
2295 '\0', NULL, NULL,
2296 SUMA_cb_SetCmapMode, (XtPointer) SW_Interp, NULL},
2297
2298 {NULL},
2299 };
2300
2301 SUMA_MenuItem LinkMode_Menu[] = {
2302 { "None", &xmPushButtonWidgetClass,
2303 '\0', NULL, NULL,
2304 SUMA_cb_SetLinkMode, (XtPointer) SW_LinkMode_None, NULL},
2305
2306 { "Pls1", &xmPushButtonWidgetClass,
2307 '\0', NULL, NULL,
2308 SUMA_cb_SetLinkMode, (XtPointer) SW_LinkMode_Pls1, NULL},
2309
2310 { "Same", &xmPushButtonWidgetClass,
2311 '\0', NULL, NULL,
2312 SUMA_cb_SetLinkMode, (XtPointer) SW_LinkMode_Same, NULL},
2313
2314 { "Stat", &xmPushButtonWidgetClass,
2315 '\0', NULL, NULL,
2316 SUMA_cb_SetLinkMode, (XtPointer) SW_LinkMode_Stat, NULL},
2317
2318 {NULL},
2319 };
2320
2321
2322 /*!
2323 \brief sets the colormap interpolation mode
2324 - expects a SUMA_MenuCallBackData * in client_data
2325 with SO as client_data->ContID and Menubutton in client_data->callback_data
2326 */
SUMA_cb_SetCmapMode(Widget widget,XtPointer client_data,XtPointer call_data)2327 void SUMA_cb_SetCmapMode(Widget widget, XtPointer client_data,
2328 XtPointer call_data)
2329 {
2330 static char FuncName[]={"SUMA_cb_SetCmapMode"};
2331 SUMA_MenuCallBackData *datap=NULL;
2332 int imenu;
2333 SUMA_ALL_DO *ado=NULL;
2334 SUMA_Boolean LocalHead = NOPE;
2335
2336 SUMA_ENTRY;
2337
2338 /* get the surface object that the setting belongs to */
2339 datap = (SUMA_MenuCallBackData *)client_data;
2340 ado = (SUMA_ALL_DO *)datap->ContID;
2341 imenu = (INT_CAST)datap->callback_data;
2342
2343 SUMA_SetCmapMode(ado, imenu);
2344
2345 SUMA_RETURNe;
2346 }
2347
SUMA_SetCmapMode(SUMA_ALL_DO * ado,int imenu)2348 SUMA_Boolean SUMA_SetCmapMode(SUMA_ALL_DO *ado, int imenu)
2349 {
2350 static char FuncName[]={"SUMA_SetCmapMode"};
2351 SUMA_Boolean NewDisp = NOPE;
2352 SUMA_X_SurfCont *SurfCont=NULL;
2353 SUMA_OVERLAYS *curColPlane=NULL;
2354 SUMA_Boolean LocalHead = NOPE;
2355
2356 SUMA_ENTRY;
2357
2358 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado)) ||
2359 !(curColPlane = SUMA_ADO_CurColPlane(ado)) ||
2360 imenu < 1) SUMA_RETURN(NOPE);
2361
2362 /* get the surface object that the setting belongs to */
2363 NewDisp = NOPE;
2364 switch (imenu) {
2365 case SW_Interp:
2366 if (curColPlane->OptScl->interpmode != SUMA_INTERP) {
2367 curColPlane->OptScl->interpmode = SUMA_INTERP;
2368 NewDisp = YUP;
2369 }
2370 break;
2371 case SW_NN:
2372 if (curColPlane->OptScl->interpmode != SUMA_NO_INTERP) {
2373 curColPlane->OptScl->interpmode = SUMA_NO_INTERP;
2374 NewDisp = YUP;
2375 }
2376 break;
2377 case SW_Direct:
2378 if (curColPlane->OptScl->interpmode != SUMA_DIRECT) {
2379 curColPlane->OptScl->interpmode = SUMA_DIRECT;
2380 NewDisp = YUP;
2381 }
2382 break;
2383 default:
2384 fprintf (SUMA_STDERR,
2385 "Error %s: Unexpected widget index.\n", FuncName);
2386 SUMA_RETURN(NOPE);
2387 break;
2388
2389 }
2390
2391 /* redisplay all viewers showing SO*/
2392 if (NewDisp) {
2393 SUMA_ColorizePlane(curColPlane);
2394 SUMA_Remixedisplay(ado);
2395 }
2396
2397 SUMA_UpdateNodeNodeField(ado);
2398 SUMA_UpdateNodeLblField(ado);
2399
2400 SUMA_RETURN(YUP);
2401 }
2402
2403 /*!
2404 \brief sets the linking between I & T mode
2405 - expects a SUMA_MenuCallBackData * in client_data
2406 with SO as client_data->ContID and Menubutton in client_data->callback_data
2407 */
SUMA_cb_SetLinkMode(Widget widget,XtPointer client_data,XtPointer call_data)2408 void SUMA_cb_SetLinkMode(Widget widget, XtPointer client_data,
2409 XtPointer call_data)
2410 {
2411 static char FuncName[]={"SUMA_cb_SetLinkMode"};
2412 SUMA_MenuCallBackData *datap=NULL;
2413 int imenu;
2414 SUMA_ALL_DO *ado = NULL;
2415 SUMA_OVERLAYS *curColPlane=NULL;
2416 SUMA_Boolean NewDisp = NOPE;
2417 SUMA_Boolean LocalHead = NOPE;
2418
2419 SUMA_ENTRY;
2420
2421 /* get the surface object that the setting belongs to */
2422 datap = (SUMA_MenuCallBackData *)client_data;
2423 ado = (SUMA_ALL_DO *)datap->ContID;
2424 curColPlane = SUMA_ADO_CurColPlane(ado);
2425 imenu = (INT_CAST)datap->callback_data;
2426 NewDisp = NOPE;
2427 switch (imenu) { /* There is really no need for this
2428 switching block... */
2429 case SW_LinkMode_None:
2430 if (curColPlane->LinkMode != imenu) {
2431 curColPlane->LinkMode = imenu;
2432 NewDisp = YUP;
2433 }
2434 break;
2435 case SW_LinkMode_Pls1:
2436 if (curColPlane->LinkMode != imenu) {
2437 curColPlane->LinkMode = imenu;
2438 NewDisp = YUP;
2439 }
2440 break;
2441 case SW_LinkMode_Same:
2442 if (curColPlane->LinkMode != imenu) {
2443 curColPlane->LinkMode = imenu;
2444 NewDisp = YUP;
2445 }
2446 break;
2447 case SW_LinkMode_Stat:
2448 if (curColPlane->LinkMode != imenu) {
2449 curColPlane->LinkMode = imenu;
2450 NewDisp = YUP;
2451 }
2452 break;
2453 default:
2454 fprintf (SUMA_STDERR, "Error %s: Unexpected widget index %d.\n",
2455 FuncName, imenu);
2456 break;
2457 }
2458 SUMA_LHv("LinkMode now %d\n", curColPlane->LinkMode);
2459 /* redisplay all viewers showing SO*/
2460 if (NewDisp) {
2461 SUMA_ColorizePlane(curColPlane);
2462 SUMA_Remixedisplay(ado);
2463 }
2464
2465 SUMA_UpdateNodeNodeField(ado);
2466 SUMA_UpdateNodeLblField(ado);
2467
2468 SUMA_RETURNe;
2469 }
2470
2471 /*!
2472 \brief sets the coordinate bias mode
2473 - expects a SUMA_MenuCallBackData * in client_data
2474 with SO as client_data->ContID and Menubutton in client_data->callback_data
2475 */
SUMA_cb_SetCoordBias(Widget widget,XtPointer client_data,XtPointer call_data)2476 void SUMA_cb_SetCoordBias(Widget widget, XtPointer client_data,
2477 XtPointer call_data)
2478 {
2479 static char FuncName[]={"SUMA_cb_SetCoordBias"};
2480 SUMA_MenuCallBackData *datap=NULL;
2481 int imenu;
2482 SUMA_ALL_DO *ado = NULL;
2483 SUMA_OVERLAYS *curColPlane=NULL;
2484 SUMA_X_SurfCont *SurfCont=NULL;
2485 SUMA_Boolean NewDisp = NOPE;
2486 SUMA_VIS_XFORM_DATUM *x0=NULL;
2487 SUMA_Boolean LocalHead = NOPE;
2488
2489 SUMA_ENTRY;
2490 /* get the surface object that the setting belongs to */
2491 datap = (SUMA_MenuCallBackData *)client_data;
2492 ado = (SUMA_ALL_DO *)datap->ContID;
2493 imenu = (INT_CAST)datap->callback_data;
2494 curColPlane = SUMA_ADO_CurColPlane(ado);
2495 SurfCont = SUMA_ADO_Cont(ado);
2496
2497 /* if CoordBias is to be added, it should be before Prying */
2498 switch(ado->do_type) {
2499 case SO_type: {
2500 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
2501 x0 = SUMA_Fetch_VisX_Datum ("CoordBias", SO->VisX.Xchain,
2502 ADD_BEFORE, "Prying");
2503 break; }
2504 case GDSET_type: {
2505 SUMA_S_Warn("Not sure what to do here");
2506 break; }
2507 case CDOM_type: {
2508 SUMA_S_Warn("Not sure what to do here");
2509 break; }
2510 default:
2511 SUMA_S_Errv("Not ready for type %s\n",
2512 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
2513 break;
2514 }
2515
2516 NewDisp = NOPE;
2517 switch (imenu) {
2518 case SW_CoordBias_None:
2519 if (curColPlane->OptScl->DoBias != SW_CoordBias_None) {
2520 if (curColPlane->OptScl->BiasVect) {
2521 SUMA_RemoveCoordBias(curColPlane);
2522 }
2523 NewDisp = YUP;
2524 }
2525 break;
2526 case SW_CoordBias_X:
2527 if (curColPlane->OptScl->DoBias != SW_CoordBias_X) {
2528 /* something needs to be done */
2529 /* bias other than on other dimension exists, transfer it to
2530 new dimension*/
2531 SUMA_TransferCoordBias(curColPlane, SW_CoordBias_X);
2532 NewDisp = YUP;
2533 }
2534 break;
2535 case SW_CoordBias_Y:
2536 if (curColPlane->OptScl->DoBias != SW_CoordBias_Y) {
2537 /* something needs to be done */
2538 /* bias other than on other dimension exists, transfer it to
2539 new dimension*/
2540 SUMA_TransferCoordBias(curColPlane, SW_CoordBias_Y);
2541 NewDisp = YUP;
2542 }
2543 break;
2544 case SW_CoordBias_Z:
2545 if (curColPlane->OptScl->DoBias != SW_CoordBias_Z) {
2546 /* something needs to be done */
2547 /* bias other than on other dimension exists, transfer it to
2548 new dimension*/
2549 SUMA_TransferCoordBias(curColPlane, SW_CoordBias_Z);
2550 NewDisp = YUP;
2551 }
2552 break;
2553 case SW_CoordBias_N:
2554 if (curColPlane->OptScl->DoBias != SW_CoordBias_N) {
2555 /* something needs to be done */
2556 /* bias other than on other dimension exists, transfer it to
2557 new dimension*/
2558 SUMA_TransferCoordBias(curColPlane, SW_CoordBias_N);
2559 NewDisp = YUP;
2560 }
2561 break;
2562 default:
2563 fprintf (SUMA_STDERR, "Error %s: Unexpected widget index.\n", FuncName);
2564 break;
2565 }
2566
2567 /* redisplay all viewers showing DO*/
2568 if (NewDisp) {
2569 SUMA_ColorizePlane(curColPlane);
2570 SUMA_Remixedisplay(ado);
2571 }
2572
2573 SUMA_UpdateNodeNodeField(ado);
2574
2575 #if SUMA_SEPARATE_SURF_CONTROLLERS
2576 SUMA_UpdateColPlaneShellAsNeeded(ado);
2577 #endif
2578 SUMA_RETURNe;
2579 }
2580
2581 /*!
2582 \brief Function to call a redisplay of all viewers showing SO
2583 */
SUMA_RedisplayAllShowing(char * SO_idcode_str,SUMA_SurfaceViewer * SVv,int N_SVv)2584 SUMA_Boolean SUMA_RedisplayAllShowing(char *SO_idcode_str,
2585 SUMA_SurfaceViewer *SVv, int N_SVv)
2586 {
2587 static char FuncName[]={"SUMA_RedisplayAllShowing"};
2588 SUMA_SurfaceViewer *sv;
2589 void *pp=NULL;
2590 SUMA_ALL_DO *ado=NULL;
2591 SUMA_DO_Types tp;
2592 SUMA_SurfaceObject *SO1 = NULL, *SO2 = NULL;
2593 SUMA_DSET *dset=NULL;
2594 int i, k;
2595 DList *list=NULL;
2596 SUMA_Boolean LocalHead = NOPE;
2597
2598 SUMA_ENTRY;
2599
2600 if (!SVv) {
2601 SVv = SUMAg_SVv;
2602 N_SVv = SUMAg_N_SVv;
2603 }
2604 if (!SO_idcode_str || !SVv) {
2605 SUMA_S_Err("NULL SVv or SO_idcode_str. BAD");
2606 SUMA_RETURN (NOPE);
2607 }
2608 if (!(pp = SUMA_find_any_object(SO_idcode_str, &tp))) {
2609 SUMA_S_Errv("Failed to find object with idcode %s.\n", SO_idcode_str);
2610 SUMA_RETURN(NOPE);
2611 }
2612 ado = (SUMA_ALL_DO*)pp;
2613 switch (tp) {
2614 case SO_type:
2615 SO1 = (SUMA_SurfaceObject *)pp;
2616 /* search all viewers */
2617 for (i=0; i < N_SVv; ++i) {
2618 SUMA_LHv("Searching viewer %d.\n", i);
2619 sv = &(SVv[i]);
2620 /* search for SO in RegisteredDO */
2621 for (k=0; k < sv->N_DO; ++k) {
2622 if (SUMA_isSO(SUMAg_DOv[sv->RegistDO[k].dov_ind])) {
2623 SO2 = (SUMA_SurfaceObject *)
2624 SUMAg_DOv[sv->RegistDO[k].dov_ind].OP;
2625 if (SUMA_WhatAreYouToMe(SO1, SO2) == SUMA_SO1_is_SO2) {
2626 /* Get a redisplay for that puppy */
2627 if (!list) list = SUMA_CreateList ();
2628 SUMA_REGISTER_HEAD_COMMAND_NO_DATA(list, SE_Redisplay,
2629 SES_SumaWidget, sv);
2630 }
2631 }
2632 }
2633 }
2634 break;
2635 case MASK_type:
2636 case GDSET_type:
2637 case CDOM_type:
2638 case VO_type:
2639 case TRACT_type:
2640 case GRAPH_LINK_type:
2641 for (i=0; i < N_SVv; ++i) {
2642 sv = &(SVv[i]);
2643 if (SUMA_ADO_isRegistered(sv, ado)) {
2644 if (!list) list = SUMA_CreateList ();
2645 SUMA_REGISTER_HEAD_COMMAND_NO_DATA(list, SE_Redisplay,
2646 SES_SumaWidget, sv);
2647 }
2648 }
2649 break;
2650 default:
2651 SUMA_S_Errv("Type %d (%s) is not welcome here\n",
2652 tp, SUMA_ObjectTypeCode2ObjectTypeName(tp));
2653 SUMA_RETURN(NOPE);
2654 }
2655
2656 if (!SUMA_Engine(&list)) {
2657 SUMA_SLP_Err("Failed to redisplay.");
2658 SUMA_RETURN(NOPE);
2659 }
2660
2661 SUMA_RETURN(YUP);
2662 }
2663
SUMA_AllocTableField(char * wname)2664 SUMA_TABLE_FIELD * SUMA_AllocTableField(char *wname)
2665 {
2666 static char FuncName[]={"SUMA_AllocTableField"};
2667 SUMA_TABLE_FIELD *TF = NULL;
2668
2669 SUMA_ENTRY;
2670 TF = (SUMA_TABLE_FIELD *)SUMA_calloc(1,sizeof(SUMA_TABLE_FIELD));
2671 if (!TF) {
2672 SUMA_SL_Crit("Failed to allocate");
2673 SUMA_RETURN(TF);
2674 }
2675 TF->Ni = -1;
2676 TF->Nj = -1;
2677 TF->rc = NULL;
2678 TF->cells = NULL;
2679 TF->cwidth = NULL;
2680 TF->editable = NOPE;
2681 TF->type = SUMA_string;
2682 TF->NewValueCallback = NULL;
2683 TF->NewValueCallbackData = NULL;
2684 TF->TitLabelEVHandler = NULL;
2685 TF->TitLabelEVHandlerData = NULL;
2686 TF->CellEVHandler = NULL;
2687 TF->CellEVHandlerData = NULL;
2688 TF->cell_modified = -1;
2689 TF->num_value = NULL;
2690 TF->str_value = NULL;
2691 TF->rowobject_id = NULL;
2692 if (wname) snprintf(TF->wname,63,"%s", wname);
2693 else snprintf(TF->wname,63,"UNNAMED");
2694 SUMA_RETURN(TF);
2695 }
2696
SUMA_AllocSliceField(char * wname)2697 SUMA_SLICE_FIELD * SUMA_AllocSliceField(char *wname)
2698 {
2699 static char FuncName[]={"SUMA_AllocSliceField"};
2700 SUMA_SLICE_FIELD *SF = NULL;
2701
2702 SUMA_ENTRY;
2703 SF = (SUMA_SLICE_FIELD *)SUMA_calloc(1,sizeof(SUMA_SLICE_FIELD));
2704 if (!SF) {
2705 SUMA_SL_Crit("Failed to allocate");
2706 SUMA_RETURN(SF);
2707 }
2708 SF->Nslc = -1;
2709 SF->sl = NULL;
2710 SF->tb = NULL;
2711 SF->text = NULL;
2712 SF->mont = NULL;
2713 SF->NewValueCallback = NULL;
2714 SF->NewValueCallbackData = NULL;
2715 SF->slice_num_str = NULL;
2716 SF->mont_str = NULL;
2717 SF->slice_units = SUMA_NO_NUM_UNITS;
2718 SF->mont_units = SUMA_NO_NUM_UNITS;
2719 SF->slice_num = 0;
2720 SF->mont_num = 1;
2721 SF->mont_inc = 10;
2722 SF->variant = NULL;
2723 if (wname) snprintf(SF->wname,63,"%s", wname);
2724 else snprintf(SF->wname,63,"UNNAMED");
2725 SUMA_RETURN(SF);
2726 }
2727
SUMA_FreeSliceField(SUMA_SLICE_FIELD * SF)2728 SUMA_SLICE_FIELD * SUMA_FreeSliceField(SUMA_SLICE_FIELD *SF)
2729 {
2730 static char FuncName[]={"SUMA_FreeSliceField"};
2731 int i;
2732
2733 SUMA_ENTRY;
2734
2735 if (!SF) SUMA_RETURN(NULL);
2736
2737 if (SF->slice_num_str) SUMA_free(SF->slice_num_str);
2738 if (SF->mont_str) SUMA_free(SF->mont_str);
2739 if (SF->variant) SUMA_free(SF->variant);
2740 SUMA_free(SF);
2741
2742 SUMA_RETURN(NULL);
2743
2744 }
2745
SUMA_AllocVRField(char * wname)2746 SUMA_VR_FIELD * SUMA_AllocVRField(char *wname)
2747 {
2748 static char FuncName[]={"SUMA_AllocVRField"};
2749 SUMA_VR_FIELD *VrF = NULL;
2750
2751 SUMA_ENTRY;
2752
2753 VrF = (SUMA_VR_FIELD *)SUMA_calloc(1,sizeof(SUMA_VR_FIELD));
2754 if (!VrF) {
2755 SUMA_SL_Crit("Failed to allocate");
2756 SUMA_RETURN(VrF);
2757 }
2758 VrF->Nslc = -1;
2759 VrF->tb = NULL;
2760 VrF->text = NULL;
2761 VrF->NewValueCallback = NULL;
2762 VrF->NewValueCallbackData = NULL;
2763 VrF->N_slice_num_str = NULL;
2764 VrF->N_slice_units = SUMA_NO_NUM_UNITS;
2765 VrF->N_slice_num = -1;
2766 if (wname) snprintf(VrF->wname,63,"%s", wname);
2767 else snprintf(VrF->wname,63,"UNNAMED");
2768 SUMA_RETURN(VrF);
2769 }
2770
SUMA_FreeVRField(SUMA_VR_FIELD * VrF)2771 SUMA_VR_FIELD * SUMA_FreeVRField(SUMA_VR_FIELD *VrF)
2772 {
2773 static char FuncName[]={"SUMA_FreeVRField"};
2774 int i;
2775
2776 SUMA_ENTRY;
2777
2778 if (!VrF) SUMA_RETURN(NULL);
2779
2780 if (VrF->N_slice_num_str) SUMA_free(VrF->N_slice_num_str);
2781 SUMA_free(VrF);
2782
2783 SUMA_RETURN(NULL);
2784
2785 }
2786
2787 /*!
2788 Called when user clicks on range table cell
2789 Expect SO in cd
2790 */
SUMA_RangeTableCell_EV(Widget w,XtPointer cd,XEvent * ev,Boolean * continue_to_dispatch)2791 void SUMA_RangeTableCell_EV ( Widget w , XtPointer cd ,
2792 XEvent *ev , Boolean *continue_to_dispatch )
2793 {
2794 static char FuncName[]={"SUMA_RangeTableCell_EV"};
2795 SUMA_ALL_DO *ado = (SUMA_ALL_DO *)cd, *curDO=NULL;
2796 SUMA_X_SurfCont *SurfCont=NULL;
2797 SUMA_OVERLAYS *curColPlane=NULL;
2798 XButtonEvent * bev = (XButtonEvent *) ev ;
2799 int i, j, n, Found;
2800 void *cv=NULL;
2801 SUMA_TABLE_FIELD *TF = NULL;
2802 SUMA_Boolean LocalHead = NOPE;
2803
2804 SUMA_ENTRY;
2805
2806 SUMA_LH("Called");
2807
2808
2809 SurfCont = SUMA_ADO_Cont(ado);
2810 curColPlane = SUMA_ADO_CurColPlane(ado);
2811 curDO = SUMA_Cont_ADO(SurfCont);
2812 TF = SurfCont->RangeTable;
2813
2814 /* see note in bbox.c optmenu_EV for the condition below*/
2815 if( bev->button == Button2 ) {
2816 XUngrabPointer( bev->display , CurrentTime ) ;
2817 SUMA_RETURNe ;
2818 }
2819
2820 if( w == NULL || TF == NULL || ado == NULL ) { SUMA_RETURNe ; }
2821
2822 switch (bev->button) {
2823 case Button1:
2824 SUMA_LH("Button 1");
2825 break;
2826 case Button2:
2827 SUMA_LH("Button 2");
2828 break;
2829 case Button3:
2830 SUMA_LH("Button 3");
2831 break;
2832 default:
2833 SUMA_RETURNe;
2834 }
2835
2836 /* which cell is calling? */
2837 n = 0;
2838 Found = -1;
2839 while (n<TF->Nj*TF->Ni && Found == -1) {
2840 if (TF->cells[n] == w) {
2841 Found = n;
2842 } else ++n;
2843 }
2844
2845 if (Found <0) {
2846 SUMA_SL_Err("Widget not found ????");
2847 SUMA_RETURNe;
2848 }
2849
2850 /* find out widget's place in table*/
2851 i = Found % TF->Ni; j = Found / TF->Ni ;
2852 n = Found;
2853
2854 switch (j) {
2855 case 0:
2856 case 1:
2857 case 3:
2858 break;
2859 case 2:
2860 case 4:
2861 SUMA_LH("Call to jump to a node");
2862 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
2863 if (LocalHead) {
2864 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s, node = %d\n",
2865 FuncName, i, j, (char *)cv, atoi((char *)cv));
2866 }
2867
2868 /* look for a viewer that is showing this surface
2869 and has this surface in focus*/
2870 for (i=0; i<SUMAg_N_SVv; ++i) {
2871 SUMA_LHv("Checking viewer %d.\n", i);
2872 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
2873 /* is this viewer showing curDO ? */
2874 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv,
2875 curDO)) {
2876 if (SUMA_SV_Focus_ADO(&(SUMAg_SVv[i])) == curDO) {
2877 SUMA_JumpIndex((char *)cv, (void *)(&(SUMAg_SVv[i])));
2878 } else {
2879 SUMA_LHv("Seeking DO, %p, %s\n",
2880 curDO,
2881 SUMA_CHECK_NULL_STR(SUMA_ADO_idcode(curDO)));
2882 SUMAg_SVv[i].Focus_DO_ID =
2883 SUMA_whichDO(SUMA_ADO_idcode(curDO),
2884 SUMAg_DOv, SUMAg_N_DOv );
2885 if (SUMA_isADO_Cont_Realized(curDO)) {
2886 SUMA_Init_SurfCont_SurfParam(curDO);
2887 } else {
2888 SUMA_S_Err("How did this happen?");
2889 }
2890 SUMA_JumpIndex((char *)cv, (void *)(&(SUMAg_SVv[i])));
2891 SUMA_UpdateViewerTitle(SUMAg_SVv+i);
2892 }
2893 }
2894 }
2895 }
2896
2897 break;
2898 default:
2899 SUMA_SL_Err("Did not know you had so many");
2900 break;
2901 }
2902
2903 SUMA_RETURNe;
2904 }
2905
2906 /*!
2907 Called when user clicks on table title
2908 Expects SUMA_SRV_DATA in TF->NewValueCallbackData
2909 */
SUMA_SetRangeTableTit_EV(Widget w,XtPointer cd,XEvent * ev,Boolean * continue_to_dispatch)2910 void SUMA_SetRangeTableTit_EV ( Widget w , XtPointer cd ,
2911 XEvent *ev , Boolean *continue_to_dispatch )
2912 {
2913 static char FuncName[]={"SUMA_SetRangeTableTit_EV"};
2914 Dimension lw ;
2915 Widget * children , wl = NULL;
2916 XButtonEvent * bev = (XButtonEvent *) ev ;
2917 int num_children , i, j, Found, AutoHist;
2918 SUMA_TABLE_FIELD *TF = (SUMA_TABLE_FIELD *)cd;
2919 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)TF->NewValueCallbackData;
2920 SUMA_ALL_DO *ado = srvd->ado;
2921 SUMA_X_SurfCont *SurfCont=NULL;
2922 SUMA_OVERLAYS *curColPlane=NULL;
2923 SUMA_Boolean LocalHead = NOPE;
2924
2925 SUMA_ENTRY;
2926
2927 SUMA_LH("Called");
2928
2929 /* see note in bbox.c optmenu_EV for the condition below*/
2930 if( bev->button == Button2 ){
2931 XUngrabPointer( bev->display , CurrentTime ) ;
2932 SUMA_RETURNe ;
2933 }
2934
2935 if( w == NULL || TF == NULL ) SUMA_RETURNe ;
2936
2937 switch (bev->button) {
2938 case Button1:
2939 SUMA_LH("Button 1");
2940 break;
2941 case Button2:
2942 SUMA_LH("Button 2");
2943 break;
2944 case Button3:
2945 SUMA_LH("Button 3");
2946 break;
2947 default:
2948 SUMA_RETURNe;
2949 }
2950
2951 /* which column title (i == 0) widget is calling ? */
2952 /* check the first column */
2953 i = 0; j = 0;
2954 Found = 0;
2955 while (j<TF->Nj && !Found) {
2956 if (TF->cells[j*TF->Ni+i] == w) {
2957 Found = 1;
2958 } else ++j;
2959 }
2960
2961 if (!Found) { /* maybe it is a row title */
2962 i = 0; j = 0;
2963 Found = 0;
2964 while (i<TF->Ni && !Found) {
2965 if (TF->cells[j*TF->Ni+i] == w) {
2966 Found = 1;
2967 } else ++i;
2968 }
2969 }
2970
2971 if (Found >= 0) {
2972 SUMA_LHv("Click on cell [%d %d]\n", i, j);
2973 } else {
2974 SUMA_SL_Err("CEll not found!");
2975 SUMA_RETURNe;
2976 }
2977
2978 SurfCont = SUMA_ADO_Cont(ado);
2979 curColPlane = SUMA_ADO_CurColPlane(ado);
2980
2981 if (!ado || !SurfCont || !curColPlane) {
2982 SUMA_SL_Err("No curColPlane!");
2983 SUMA_RETURNe;
2984 }
2985
2986 /* Now do something */
2987 if (j == 0) { /* clicked on one of the row's titles */
2988 switch (i) {
2989 case 1:
2990 if (bev->button == Button1) { /* toggle lock */
2991 curColPlane->OptScl->AutoIntRange =
2992 !curColPlane->OptScl->AutoIntRange;
2993 SurfCont->IntRangeLocked = !SurfCont->IntRangeLocked;
2994 MCW_invert_widget(w);
2995 }else if (bev->button == Button3) { /* reset to autorange values */
2996 AutoHist = curColPlane->OptScl->AutoIntRange;
2997 curColPlane->OptScl->AutoIntRange = 1;
2998 SUMA_InitRangeTable(ado, 0); /* overkill but little overhead */
2999 SUMA_ColorizePlane(curColPlane);
3000 SUMA_Remixedisplay(ado);
3001 curColPlane->OptScl->AutoIntRange = AutoHist;
3002 }
3003 break;
3004 case 2:
3005 if (bev->button == Button1) { /* toggle lock */
3006 curColPlane->OptScl->AutoBrtRange =
3007 !curColPlane->OptScl->AutoBrtRange;
3008 SurfCont->BrtRangeLocked = !SurfCont->BrtRangeLocked;
3009 MCW_invert_widget(w);
3010 }else if (bev->button == Button3) { /* reset to autorange values */
3011 AutoHist = curColPlane->OptScl->AutoBrtRange;
3012 curColPlane->OptScl->AutoBrtRange = 1;
3013 SUMA_InitRangeTable(ado, 1); /* overkill but little overhead */
3014 SUMA_ColorizePlane(curColPlane);
3015 SUMA_Remixedisplay(ado);
3016 curColPlane->OptScl->AutoBrtRange = AutoHist;
3017 }
3018 break;
3019 case 3:
3020 break;
3021 default:
3022 break;
3023 }
3024 }
3025 if (i == 0) { /* clicked on one of the column's titles */
3026 switch (j) {
3027 case 1:
3028 break;
3029 case 2:
3030 break;
3031 case 3:
3032 break;
3033 default:
3034 break;
3035 }
3036 }
3037
3038 /* update the Xhair Info block */
3039 if (curColPlane->OptScl->DoBias != SW_CoordBias_None) {
3040 SUMA_UpdateNodeNodeField(ado);
3041 }
3042 SUMA_UpdateNodeLblField(ado);
3043
3044 SUMA_RETURNe;
3045
3046 }
3047
SUMA_SetClustTableTit_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int i,int j,int Button)3048 SUMA_Boolean SUMA_SetClustTableTit_one (SUMA_ALL_DO *ado,
3049 SUMA_OVERLAYS *colp, int i, int j, int Button)
3050 {
3051 static char FuncName[]={"SUMA_SetClustTableTit_one"};
3052 SUMA_TABLE_FIELD *TF = NULL;
3053 SUMA_X_SurfCont *SurfCont=NULL;
3054 SUMA_OVERLAYS *curColPlane=NULL;
3055 SUMA_Boolean LocalHead = NOPE;
3056
3057 SUMA_ENTRY;
3058
3059 SUMA_LH("Called");
3060
3061 if (!ado) SUMA_RETURN(0);
3062
3063 SurfCont = SUMA_ADO_Cont(ado);
3064 curColPlane = SUMA_ADO_CurColPlane(ado);
3065
3066 if (colp && colp != curColPlane) SUMA_RETURN(0);
3067 colp = curColPlane;
3068 if (!colp) SUMA_RETURN(0);
3069 if (!(TF = SurfCont->SetClustTable)) SUMA_RETURN(0);
3070
3071 /* Now do something */
3072 if (j == 0) { /* clicked on one of the row's titles */
3073 switch (i) {
3074 case 1:
3075 if (Button == Button1) { /* toggle lock */
3076 TF->but_flag[j*TF->Ni+i] = !TF->but_flag[j*TF->Ni+i];
3077 MCW_invert_widget(TF->cells[j*TF->Ni+i]);
3078 colp->OptScl->Clusterize = TF->but_flag[j*TF->Ni+i];
3079 colp->OptScl->RecomputeClust = YUP;
3080 SUMA_ColorizePlane(colp);
3081 SUMA_Remixedisplay((SUMA_ALL_DO*)ado);
3082 }else if (Button == Button3) { /* nothing to do */
3083
3084 }
3085 break;
3086 default:
3087 break;
3088 }
3089 }
3090 if (i == 0) { /* clicked on one of the column's titles */
3091 switch (j) {
3092 case 1:
3093 break;
3094 case 2:
3095 break;
3096 case 3:
3097 break;
3098 default:
3099 break;
3100 }
3101 }
3102
3103 /* update the Xhair Info block */
3104 SUMA_UpdateNodeLblField(ado);
3105
3106 SUMA_RETURN(YUP);
3107 }
3108
3109 /* Set the button flag for a table cell (usually for titles only),
3110 based on flag. Inverts widget if need be. */
SUMA_SetTableTitleButton1(SUMA_TABLE_FIELD * TF,int i,int j,byte flag)3111 SUMA_Boolean SUMA_SetTableTitleButton1(SUMA_TABLE_FIELD *TF, int i, int j,
3112 byte flag)
3113 {
3114 static char FuncName[]={"SUMA_SetTableTitleButton1"};
3115
3116 SUMA_ENTRY;
3117
3118 if (!TF) SUMA_RETURN(NOPE);
3119
3120 if (flag == TF->but_flag[j*TF->Ni+i]) {
3121 /* Nothing to do, return*/
3122 } else {
3123 TF->but_flag[j*TF->Ni+i] = !TF->but_flag[j*TF->Ni+i];
3124 MCW_invert_widget(TF->cells[j*TF->Ni+i]);
3125 }
3126
3127 SUMA_RETURN(YUP);
3128 }
3129
SUMA_SetClustTableTit(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int i,int j,int Button)3130 SUMA_Boolean SUMA_SetClustTableTit (SUMA_ALL_DO *ado,
3131 SUMA_OVERLAYS *colp, int i, int j, int Button)
3132 {
3133 static char FuncName[]={"SUMA_SetClustTableTit"};
3134 SUMA_X_SurfCont *SurfCont=NULL;
3135 SUMA_OVERLAYS *curColPlane=NULL;
3136
3137 SUMA_Boolean LocalHead = NOPE;
3138
3139 SUMA_ENTRY;
3140
3141 SUMA_LH("Called");
3142
3143 if (!ado) SUMA_RETURN(0);
3144 SurfCont = SUMA_ADO_Cont(ado);
3145 curColPlane = SUMA_ADO_CurColPlane(ado);
3146
3147 if (colp && colp != curColPlane) SUMA_RETURN(0);
3148 colp = curColPlane;
3149 if (!colp) SUMA_RETURN(0);
3150
3151 if (!SUMA_SetClustTableTit_one (ado, colp, i, j, Button)) SUMA_RETURN(0);
3152
3153 if (ado->do_type == SO_type) {
3154 SUMA_SurfaceObject *SOC=NULL, *SO = (SUMA_SurfaceObject *)ado;
3155 SUMA_OVERLAYS *colpC=NULL;
3156 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
3157 if (colpC && SOC) {
3158 SUMA_LHv("Found contralateral equivalent to:\n"
3159 " %s and %s in\n"
3160 " %s and %s\n",
3161 SO->Label, CHECK_NULL_STR(colp->Label),
3162 SOC->Label, CHECK_NULL_STR(colpC->Label));
3163 if (!SUMA_SetClustTableTit_one ((SUMA_ALL_DO *)SOC,
3164 colpC, i, j, Button)) SUMA_RETURN(0);
3165 }
3166 }
3167
3168 SUMA_RETURN(YUP);
3169 }
3170
3171 /*!
3172 Called when user clicks on table title
3173 Expects SUMA_SRV_DATA in TF->NewValueCallbackData
3174 */
SUMA_SetClustTableTit_EV(Widget w,XtPointer cd,XEvent * ev,Boolean * continue_to_dispatch)3175 void SUMA_SetClustTableTit_EV ( Widget w , XtPointer cd ,
3176 XEvent *ev , Boolean *continue_to_dispatch )
3177 {
3178 static char FuncName[]={"SUMA_SetClustTableTit_EV"};
3179 Dimension lw ;
3180 Widget * children , wl = NULL;
3181 XButtonEvent * bev = (XButtonEvent *) ev ;
3182 int num_children , i, j, Found;
3183 SUMA_TABLE_FIELD *TF = (SUMA_TABLE_FIELD *)cd;
3184 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)TF->NewValueCallbackData;
3185 SUMA_ALL_DO *ado = srvd->ado;
3186 SUMA_X_SurfCont *SurfCont=NULL;
3187 SUMA_OVERLAYS *curColPlane=NULL;
3188 SUMA_Boolean LocalHead = NOPE;
3189
3190 SUMA_ENTRY;
3191
3192 SUMA_LH("Called");
3193
3194 SurfCont = SUMA_ADO_Cont(ado);
3195 curColPlane = SUMA_ADO_CurColPlane(ado);
3196
3197 /* see note in bbox.c optmenu_EV for the condition below*/
3198 if( bev->button == Button2 ){
3199 XUngrabPointer( bev->display , CurrentTime ) ;
3200 SUMA_RETURNe ;
3201 }
3202
3203 if( w == NULL || TF == NULL ) SUMA_RETURNe ;
3204
3205 switch (bev->button) {
3206 case Button1:
3207 SUMA_LH("Button 1");
3208 break;
3209 case Button2:
3210 SUMA_LH("Button 2");
3211 break;
3212 case Button3:
3213 SUMA_LH("Button 3");
3214 break;
3215 default:
3216 SUMA_RETURNe;
3217 }
3218
3219 /* which column title (i == 0) widget is calling ? */
3220 /* check the first column */
3221 i = 0; j = 0;
3222 Found = 0;
3223 while (j<TF->Nj && !Found) {
3224 if (TF->cells[j*TF->Ni+i] == w) {
3225 Found = 1;
3226 } else ++j;
3227 }
3228
3229 if (!Found) { /* maybe it is a row title */
3230 i = 0; j = 0;
3231 Found = 0;
3232 while (i<TF->Ni && !Found) {
3233 if (TF->cells[j*TF->Ni+i] == w) {
3234 Found = 1;
3235 } else ++i;
3236 }
3237 }
3238
3239 if (Found >= 0) {
3240 SUMA_LHv("Click on cell [%d %d]\n", i, j);
3241 } else {
3242 SUMA_SL_Err("CEll not found!");
3243 SUMA_RETURNe;
3244 }
3245 if (!curColPlane) {
3246 SUMA_SL_Err("No curColPlane!");
3247 SUMA_RETURNe;
3248 }
3249
3250
3251 if (!SUMA_SetClustTableTit(ado, curColPlane, i, j, bev->button)){
3252 SUMA_S_Err("Failed, weird");
3253 }
3254
3255 SUMA_RETURNe;
3256
3257 }
3258
SUMA_SetClustTableCell_EV(Widget w,XtPointer cd,XEvent * ev,Boolean * continue_to_dispatch)3259 void SUMA_SetClustTableCell_EV ( Widget w , XtPointer cd ,
3260 XEvent *ev , Boolean *continue_to_dispatch )
3261 {
3262 static char FuncName[]={"SUMA_SetClustTableCell_EV"};
3263 Dimension lw ;
3264 Widget * children , wl = NULL;
3265 XButtonEvent * bev = (XButtonEvent *) ev ;
3266 int num_children , i, j, Found, incr=0, an, n;
3267 float reset, newv;
3268 SUMA_TABLE_FIELD *TF = (SUMA_TABLE_FIELD *)cd;
3269 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)TF->NewValueCallbackData;
3270 SUMA_ALL_DO *ado = srvd->ado;
3271 SUMA_X_SurfCont *SurfCont=NULL;
3272 SUMA_OVERLAYS *curColPlane=NULL;
3273 DList *list = NULL;
3274 SUMA_Boolean LocalHead = NOPE;
3275
3276 SUMA_ENTRY;
3277
3278 SUMA_LH("Called Button %d", bev->button);
3279
3280 SurfCont = SUMA_ADO_Cont(ado);
3281 curColPlane = SUMA_ADO_CurColPlane(ado);
3282
3283 /* see note in bbox.c optmenu_EV for the condition below*/
3284 if( bev->button == Button2 ){
3285 XUngrabPointer( bev->display , CurrentTime ) ;
3286 SUMA_RETURNe ;
3287 }
3288
3289 if( w == NULL || TF == NULL ) SUMA_RETURNe ;
3290
3291 incr = 0;
3292 switch (bev->button) {
3293 case Button1:
3294 SUMA_LH("Button 1");
3295 break;
3296 case Button2:
3297 SUMA_LH("Button 2");
3298 break;
3299 case Button3:
3300 SUMA_LH("Button 3");
3301 break;
3302 case Button4:
3303 case 6: /* This is shift and wheel on mac, Button6 is not in X.h ! */
3304 SUMA_LH("Button 4/6 %d", bev->button);
3305 incr = -1;
3306 break;
3307 case Button5:
3308 case 7:
3309 SUMA_LH("Button 5/7 %d", bev->button);
3310 incr = 1;
3311 break;
3312 default:
3313 SUMA_RETURNe;
3314 }
3315
3316 /* which cell is calling? */
3317 n = 0;
3318 Found = -1;
3319 while (n<TF->Nj*TF->Ni && Found == -1) {
3320 if (TF->cells[n] == w) {
3321 Found = n;
3322 } else ++n;
3323 }
3324
3325 if (Found <0) {
3326 SUMA_SL_Err("Widget not found ????");
3327 SUMA_RETURNe;
3328 }
3329
3330 /* find out widget's place in table*/
3331 i = Found % TF->Ni; j = Found / TF->Ni ;
3332 n = Found;
3333
3334 switch (j) {
3335 case 0:
3336 break;
3337 case 1:/* radius */
3338 case 2: /* area */
3339 if (incr) {
3340 if (TF->num_value[n]>1000) incr = incr*100;
3341 else if (TF->num_value[n]>100) incr = incr*10;
3342 else if (TF->num_value[n]>50) incr = incr*5;
3343 newv = TF->num_value[n]+incr;
3344 SUMA_MODIFY_CELL_VALUE(TF, i, j, newv);
3345 an = SUMA_SetClustValue(ado, curColPlane, i, j,
3346 TF->num_value[n], 0.0,
3347 0, 1, &reset);
3348 if (an < 0) {
3349 SUMA_S_Warn("Error checking not handled yet.\n"
3350 "This upcoming code chunk is from\n"
3351 "sister function: SUMA_cb_SetRangeValueNew\n");
3352 if (an == -1 || an == -2) {
3353 SUMA_BEEP;
3354 TF->num_value[n] = reset;
3355 SUMA_TableF_SetString(TF);
3356 if (an == -1) { SUMA_SLP_Err("Doh"); }
3357 else { SUMA_SLP_Err("Duh"); }
3358 SUMA_RETURNe;
3359 } else {
3360 SUMA_S_Err("Erriositation");
3361 SUMA_RETURNe;
3362 }
3363 }
3364 /* redisplay */
3365 if (!list) list = SUMA_CreateList ();
3366 SUMA_REGISTER_TAIL_COMMAND_NO_DATA(list, SE_Redisplay_AllVisible,
3367 SES_Suma, NULL);
3368 if (!SUMA_Engine(&list)) SUMA_SLP_Err("Failed to redisplay.");
3369 }
3370 break;
3371 default:
3372 SUMA_SL_Err("Did not know you had so many");
3373 break;
3374 }
3375
3376 SUMA_RETURNe;
3377 }
3378
SUMA_FreeTableField(SUMA_TABLE_FIELD * TF)3379 SUMA_TABLE_FIELD * SUMA_FreeTableField(SUMA_TABLE_FIELD *TF)
3380 {
3381 static char FuncName[]={"SUMA_FreeTableField"};
3382 int i;
3383
3384 SUMA_ENTRY;
3385
3386 if (!TF) SUMA_RETURN(NULL);
3387
3388 if (TF->cells) SUMA_free(TF->cells);
3389 if (TF->cwidth) SUMA_free(TF->cwidth);
3390 if (TF->num_value) SUMA_free(TF->num_value);
3391 if (TF->but_flag) SUMA_free(TF->but_flag);
3392 if (TF->str_value) {
3393 for (i=0; i<TF->Nj*TF->Ni; ++i)
3394 if (TF->str_value[i]) SUMA_free(TF->str_value[i]);
3395 SUMA_free(TF->str_value);
3396 }
3397 if (TF->rowobject_id) {
3398 for (i=0; i<TF->Ni; ++i)
3399 if (TF->rowobject_id[i]) SUMA_free(TF->rowobject_id[i]);
3400 SUMA_free(TF->rowobject_id);
3401 }
3402 SUMA_free(TF);
3403
3404 SUMA_RETURN(NULL);
3405
3406 }
3407
3408 /*!
3409 \brief sets a cell entry widget to be in Edit or No Edit modes
3410 \param TF
3411 \param i (int) the row index
3412 \param j (int) the col index
3413 \param Mode (int) 0 no edit, 1 yes edit
3414 */
SUMA_SetCellEditMode(SUMA_TABLE_FIELD * TF,int i,int j,int Mode)3415 void SUMA_SetCellEditMode(SUMA_TABLE_FIELD *TF, int i, int j, int Mode)
3416 {
3417 static char FuncName[]={"SUMA_SetCellEditMode"};
3418 int n;
3419 SUMA_Boolean LocalHead = NOPE;
3420
3421 SUMA_ENTRY;
3422
3423 if (!TF) { SUMA_SL_Err("NULL TF"); SUMA_RETURNe; }
3424 n = j * TF->Ni + i;
3425
3426 /* remove calls anyway */
3427 XtRemoveCallback (TF->cells[n], XmNactivateCallback,
3428 SUMA_TableF_cb_label_change, (XtPointer)TF);
3429 XtRemoveCallback (TF->cells[n], XmNmodifyVerifyCallback,
3430 SUMA_TableF_cb_label_Modify, (XtPointer)TF);
3431 /* remove event handlers */
3432 XtRemoveEventHandler( TF->cells[n] ,
3433 LeaveWindowMask ,
3434 FALSE ,
3435 SUMA_leave_TableField,
3436 (XtPointer) TF);
3437 switch (Mode) {
3438 case 0:
3439 /* non edit */
3440 XtVaSetValues(TF->cells[n],
3441 XmNeditable, False,
3442 XmNshadowThickness , 1, /* hide the border */
3443 XmNcursorPositionVisible, False, /* hide the cursor */
3444 NULL);
3445 break;
3446 case 1:
3447 /* si edit */
3448 XtVaSetValues(TF->cells[n],
3449 XmNeditable, True,
3450 XmNshadowThickness , 2,
3451 XmNcursorPositionVisible, True,
3452 NULL);
3453
3454 XtAddCallback (TF->cells[n], XmNactivateCallback,
3455 SUMA_TableF_cb_label_change, (XtPointer)TF);
3456 XtAddCallback (TF->cells[n], XmNmodifyVerifyCallback,
3457 SUMA_TableF_cb_label_Modify, (XtPointer)TF);
3458 /* add event handler to notify when widget was left */
3459 XtInsertEventHandler( TF->cells[n] , /* notify when */
3460 LeaveWindowMask , /* pointer leaves */
3461 FALSE , /* this window */
3462 SUMA_leave_TableField,
3463 (XtPointer) TF ,
3464 XtListTail ) ; /* last in queue */
3465 break;
3466 default:
3467 SUMA_SL_Err("What?");
3468 break;
3469 }
3470 SUMA_RETURNe;
3471 }
3472
3473 /*
3474 Appends a font of a some name to a fontlist.
3475 You'll almost always want to call the function with the same 1st argument and
3476 the returned variable. The function will free the old one and return a new one.
3477 Read function for more detail.
3478
3479 fontlist = SUMA_AppendToFontList(fontlist, w, "6x10", NULL);
3480
3481 Font lesson from http://www-h.eng.cam.ac.uk/help/tpl/graphics/Motif/mt3 :
3482 -------------------------------------------------------------------------
3483 """Begin quote
3484 [How do you find out which font names are valid on your system? Generally,
3485 type the command:
3486
3487 xlsfonts -fn "*" > out,
3488
3489 and then look at "out". All the font names will be in the file. Some of
3490 them are short, like "6x10" used above, but some are monsters, as shown
3491 in the fragment of my "out" file copied below:
3492
3493 -adobe-times-bold-i-normal--24-240-75-75-p-128-iso8859-1
3494 -adobe-times-bold-i-normal--25-180-100-100-p-128-iso8859-1
3495 -adobe-times-bold-i-normal--34-240-100-100-p-170-iso8859-1
3496
3497 To use one of these fonts, I can say:
3498
3499 namestring="*times*-25-*";
3500
3501 in the above code. This will get a 25 point times font. If I want a specific
3502 times font I can be more specific, like "*times*bold*-25-*". The "*" is
3503 a wildcard like it is in a file name.]
3504 """End quote
3505
3506 */
SUMA_AppendToFontList(XmFontList fontlisti,Widget w,char * fontname,char * tag)3507 XmFontList SUMA_AppendToFontList(XmFontList fontlisti, Widget w,
3508 char *fontname, char *tag)
3509 {
3510 static char FuncName[]={"SUMA_AppendToFontList"};
3511 XFontStruct *font = NULL;
3512 XmFontList fontlist = NULL;
3513 XmFontListEntry entry = NULL;
3514
3515 SUMA_ENTRY;
3516
3517 if (!tag) tag = XmFONTLIST_DEFAULT_TAG;
3518
3519 if (!(font = XLoadQueryFont(XtDisplay(w), fontname))) {
3520 SUMA_S_Errv("Failed to get font named %s\n", fontname);
3521 SUMA_RETURN(fontlist);
3522 }
3523 #if 0
3524 /* OBSOLETE, do not use. If you use it, you'll also need to take care
3525 of clean up */
3526 fontlist = XmFontListCreate(font, XmSTRING_DEFAULT_CHARSET);
3527 #else
3528 entry = XmFontListEntryCreate(tag,
3529 XmFONT_IS_FONT, font);
3530 /* Do not free font after this call.
3531 Unless all other lists referencing it are feed */
3532 fontlist = XmFontListAppendEntry(fontlisti, entry);
3533 /* fontlisti is taken care of inside XmFontListAppendEntry */
3534 XmFontListEntryFree(&entry); entry = NULL;
3535 #endif
3536
3537 SUMA_RETURN(fontlist);
3538 }
3539
3540 /*!
3541 \brief create a table widget
3542 \param parent (Widget)
3543 \param Ni (int) number of entries in column (including title, if any)
3544 \param Nj (int) number of entries in row (including title, if any)
3545 \param col_tit (char **) if not NULL then this should be Nj strings
3546 to appear as titles above each column
3547 \param row_tit (char **) if not NULL then this should be Ni strings
3548 to appear as titles before each row
3549 \param cwidth (int *) number of characters to allow for each column. No auto sizing allowed
3550 \param editable (SUMA_Boolean) if YUP then fields are editable by user
3551 \param NewValueCallback(void * data) (void) function called when user changes value
3552 \param cb_data (void *) pointer to data sent back to call back
3553 \param TF (SUMA_TABLE_FIELD *) structure containing table info and the index
3554 for the newly modified field.
3555 */
SUMA_CreateTable(Widget parent,int Ni,int Nj,char * iwname,char ** row_tit,char ** col_tit,char ** row_hint,char ** col_hint,char ** row_help,char ** col_help,int * cwidth,SUMA_Boolean editable,SUMA_VARTYPE type,void (* NewValueCallback)(void * data),void * cb_data,void (* TitLabelEVHandler)(Widget w,XtPointer cd,XEvent * ev,Boolean * ctd),void * TitLabelEVHandlerData,void (* CellEVHandler)(Widget w,XtPointer cd,XEvent * ev,Boolean * ctd),void * CellEVHandlerData,SUMA_TABLE_FIELD * TF)3556 void SUMA_CreateTable( Widget parent,
3557 int Ni, int Nj,
3558 char *iwname,
3559 char **row_tit, char **col_tit,
3560 char **row_hint, char **col_hint,
3561 char **row_help, char **col_help,
3562 int *cwidth, SUMA_Boolean editable, SUMA_VARTYPE type,
3563 void (*NewValueCallback)(void * data), void *cb_data,
3564 void (*TitLabelEVHandler)
3565 ( Widget w , XtPointer cd , XEvent *ev ,
3566 Boolean *ctd ),
3567 void *TitLabelEVHandlerData,
3568 void (*CellEVHandler)
3569 ( Widget w , XtPointer cd , XEvent *ev ,
3570 Boolean *ctd),
3571 void *CellEVHandlerData,
3572 SUMA_TABLE_FIELD *TF)
3573 {
3574 static char FuncName[]={"SUMA_CreateTable"};
3575 int i, j, n, titw, xmw, shad;
3576 char *tmp, wname[64]={"NeedToSetMe"};
3577 Widget rcc;
3578 XtPointer cd;
3579 SUMA_Boolean LocalHead = NOPE;
3580
3581 SUMA_ENTRY;
3582
3583 if (!parent) { SUMA_SL_Err("NULL parent"); SUMA_RETURNe; }
3584
3585 /* initialize font list if need be */
3586 if (!SUMAg_CF->X->TableTextFontList) {
3587 if (SUMA_isEnv("SUMA_SurfContFontSize", "BIG")) {
3588 SUMAg_CF->X->TableTextFontList =
3589 SUMA_AppendToFontList( SUMAg_CF->X->TableTextFontList,
3590 parent, "*9x15*", NULL);
3591 } else {
3592 SUMAg_CF->X->TableTextFontList =
3593 SUMA_AppendToFontList( SUMAg_CF->X->TableTextFontList,
3594 parent, "*8x13*", NULL);
3595 }
3596 }
3597
3598 if (!TF) { SUMA_SL_Err("NULL TF"); SUMA_RETURNe; }
3599 /* looks like wname is the "useless default" 17 Feb 2021 [rickr] */
3600 if (iwname) { /* override useless default */
3601 snprintf(TF->wname,63,"%s", iwname);
3602 } else {
3603 snprintf(TF->wname,63,"%s", wname);
3604 }
3605 TF->Ni = Ni; TF->Nj = Nj; TF->editable = editable;
3606 TF->cwidth = (int *)SUMA_calloc(TF->Nj, sizeof(int));
3607 TF->rowobject_id = (char **)SUMA_calloc(TF->Ni, sizeof(char *));
3608 for (j=0; j<TF->Nj; ++j) TF->cwidth[j] = cwidth[j];
3609 if(col_tit) TF->HasColTit = YUP; else TF->HasColTit = NOPE;
3610 if(row_tit) TF->HasRowTit = YUP; else TF->HasRowTit = NOPE;
3611 TF->cells = (Widget *)SUMA_calloc(TF->Ni*TF->Nj,sizeof(Widget));
3612 TF->but_flag = (byte *)SUMA_calloc(TF->Ni*TF->Nj,sizeof(byte));
3613 if (!TF->cells) { SUMA_SL_Crit("Failed to allocate"); SUMA_RETURNe; }
3614 TF->NewValueCallback = NewValueCallback;
3615 TF->NewValueCallbackData = cb_data;
3616 TF->TitLabelEVHandler = TitLabelEVHandler;
3617 TF->TitLabelEVHandlerData = TitLabelEVHandlerData;
3618 TF->CellEVHandler = CellEVHandler;
3619 TF->CellEVHandlerData = CellEVHandlerData;
3620 TF->type = type;
3621 TF->num_units = SUMA_NO_NUM_UNITS;
3622 switch (TF->type) {
3623 case SUMA_int:
3624 case SUMA_float:
3625 TF->num_value= (float *)SUMA_calloc(TF->Nj*TF->Ni, sizeof(float));
3626 break;
3627 case SUMA_string:
3628 TF->str_value= (char **)SUMA_malloc(TF->Nj*TF->Ni * sizeof(char *));
3629 for (i=0; i<TF->Nj*TF->Ni; ++i) TF->str_value[i] = NULL;
3630 break;
3631 default:
3632 SUMA_SL_Err("Comme tu es bete!");
3633 SUMA_RETURNe;
3634 break;
3635 }
3636 /* An outer row column to keep the inner one from resizing with parent
3637 YOU COULD HAVE SET XmNadjustLast to False, instead ....*/
3638 TF->rc = XtVaCreateManagedWidget ("rowcolumn",
3639 xmRowColumnWidgetClass, parent,
3640 XmNorientation , XmHORIZONTAL ,
3641 XmNpacking, XmPACK_TIGHT,
3642 XmNmarginHeight, 0,
3643 XmNmarginWidth, 0,
3644 NULL);
3645
3646
3647 /* Le row column to contain the table's columns*/
3648 TF->rco = XtVaCreateManagedWidget ("rowcolumn",
3649 xmRowColumnWidgetClass, TF->rc,
3650 XmNorientation , XmVERTICAL ,
3651 XmNpacking, XmPACK_TIGHT,
3652 XmNnumColumns, 1,
3653 XmNmarginHeight, 0,
3654 XmNmarginWidth, 0,
3655 NULL);
3656
3657 /* must fill up row by row, each column is a separate bloody rc
3658 to allow for alignments */
3659 for (i=0; i<TF->Ni; ++i) { /* for each row */
3660 rcc = XtVaCreateManagedWidget ("rowcolumn",
3661 xmRowColumnWidgetClass, TF->rco,
3662 XmNorientation , XmHORIZONTAL ,
3663 XmNmarginHeight, 0,
3664 XmNmarginHeight, 0,
3665 XmNmarginWidth, 0,
3666 NULL);
3667
3668 if (i == 0 && TF->HasColTit) {
3669 /* This is left here to show that I
3670 tried using different packing methods
3671 to get the title to appear centered with the cell entries below.
3672 That did nothing. Setting packing to tight in all cases and padding
3673 the titles to fit the cell entry widths works fine */
3674 XtVaSetValues (rcc, XmNpacking, XmPACK_TIGHT, NULL);
3675 } else {
3676 XtVaSetValues (rcc, XmNpacking, XmPACK_TIGHT, NULL);
3677 }
3678
3679 /* Create what would become a table URI in the html help */
3680 snprintf(wname, 63, "%s", TF->wname);
3681 SUMA_Register_Widget_Help(NULL, 2, wname, NULL, NULL);
3682
3683 for (j=0; j<TF->Nj; ++j) { /* for each column */
3684 n = j * TF->Ni + i;
3685 switch (SUMA_cellvariety(TF, n)) {
3686 case SUMA_ROW_TIT_CELL: /* row's title */
3687 if (LocalHead)
3688 fprintf( SUMA_STDERR,
3689 "%s:\nAdding RT [%d %d] (%d) %s\n",
3690 FuncName, i, j, n, row_tit[i] );
3691 #if 0
3692 TF->cells[n] = XtVaCreateManagedWidget(row_tit[i],
3693 xmLabelWidgetClass, rcc,
3694 NULL);
3695 #else
3696 TF->cells[n] =
3697 XtVaCreateManagedWidget("table",
3698 xmTextFieldWidgetClass, rcc,
3699 XmNvalue, row_tit[i],
3700 XmNmarginHeight, 0,
3701 XmNmarginWidth, 0,
3702 XmNmarginTop, 0,
3703 XmNmarginBottom, 0,
3704 XmNmarginLeft, 0,
3705 XmNmarginRight, 0,
3706 XmNeditable, False,
3707 XmNshadowThickness , 0, /* hide the border */
3708 XmNcursorPositionVisible, False, /* hide the cursor */
3709 XmNcolumns, strlen(row_tit[i]),
3710 NULL);
3711 XtVaSetValues( TF->cells[n],
3712 XmNfontList,
3713 SUMAg_CF->X->TableTextFontList, NULL);
3714
3715 #endif
3716 if (!TF->TitLabelEVHandlerData)
3717 cd = (XtPointer) TF;
3718 else cd = (XtPointer)TF->TitLabelEVHandlerData;
3719 if (TF->TitLabelEVHandler) {
3720 /* insert handler to catch clicks on titles */
3721 XtInsertEventHandler(
3722 TF->cells[n] , /* handle events in title cell */
3723 ButtonPressMask , /* button presses */
3724 FALSE , /* nonmaskable events? */
3725 TF->TitLabelEVHandler, /* handler */
3726 cd , /* client data */
3727 XtListTail ) ;
3728 }
3729 if (0 && TF->HasRowTit && row_tit[i]) { /* Much better name, but
3730 Cannot use it before updating
3731 help generating functions which now call for help on .c00,
3732 .c01, or .r00 .r01, etc. */
3733 snprintf(wname, 63, "%s.%s", TF->wname, row_tit[i]);
3734 } else {
3735 snprintf(wname, 63, "%s.r%02d", TF->wname, i);
3736 }
3737 SUMA_Register_Widget_Help(TF->cells[n], 1, wname,
3738 row_hint?row_hint[i]:NULL,
3739 row_help?row_help[i]:NULL ) ;
3740 break;
3741
3742 case SUMA_COL_TIT_CELL: /* column's title */
3743 if (LocalHead)
3744 fprintf( SUMA_STDERR,
3745 "%s:\nAdding CT [%d %d] (%d) %s\n",
3746 FuncName, i, j, n, col_tit[j]);
3747 /* padd to fit cell entry fields*/
3748 if (i == 0 && j != 0 && TF->HasColTit) {
3749 titw = TF->cwidth[j];
3750 /* set the margins to meet those of cell entries */
3751 xmw = 6;
3752 shad = 1;
3753 } else {
3754 titw = TF->cwidth[j];
3755 /* set the margins to meet those of Labels */
3756 xmw = 0;
3757 shad = 0;
3758 }
3759 #if 0
3760 TF->cells[n] = XtVaCreateManagedWidget(tmp,
3761 xmLabelWidgetClass, rcc,
3762 NULL);
3763 #else
3764 TF->cells[n] =
3765 XtVaCreateManagedWidget("table",
3766 xmTextFieldWidgetClass, rcc,
3767 XmNvalue, col_tit[j],
3768 XmNmarginHeight, 0,
3769 XmNmarginWidth, xmw+shad,/*include shadow size
3770 of text entry cells*/
3771 XmNmarginTop, 0,
3772 XmNmarginBottom, 0,
3773 XmNmarginLeft, 0,
3774 XmNmarginRight, 0,
3775 XmNeditable, False,
3776 XmNshadowThickness , 0, /* hide the border */
3777 XmNcursorPositionVisible, False, /* hide the cursor */
3778 /* Keep these two out: See warning below ...
3779 XmNfontList, SUMAg_CF->X->TableTextFontList,
3780 XmNcolumns, titw,
3781 */
3782 NULL);
3783
3784 /* WARNING: At least with LESSTIF:
3785 The order in which one sets XmNfontList
3786 and XmNcolumns matters. For example, adding:
3787 XmNfontList, SUMAg_CF->X->TableTextFontList,
3788 XmNcolumns, titw,
3789 to XtVaCreateManagedWidget above does not
3790 work. You need to call XtVaSetValues for these
3791 variables separately.
3792
3793 Also, simply adding the XtVaSetValues lines
3794 below WITHOUT removing the two lines:
3795 XmNfontList, SUMAg_CF->X->TableTextFontList,
3796 XmNcolumns, titw,
3797 from XtVaCreateManagedWidget does not work quite well.
3798
3799 Also, note that the shadow adds to the size of the
3800 TextFieldWdiget, it does not eat 'into' it. So to
3801 improve title alignment, I added the shadow thickness
3802 into the margin width. */
3803
3804 XtVaSetValues( TF->cells[n],
3805 XmNfontList,
3806 SUMAg_CF->X->TableTextFontList, NULL);
3807 XtVaSetValues( TF->cells[n], XmNcolumns, titw,
3808 NULL);
3809
3810 #endif
3811 if (i == 0 && j != 0) {
3812 XtVaSetValues( TF->cells[n],
3813 XmNalignment, XmALIGNMENT_BEGINNING, NULL);
3814 }
3815
3816 /* insert handler to catch clicks on titles */
3817 if (!TF->TitLabelEVHandlerData)
3818 cd = (XtPointer) TF;
3819 else cd = (XtPointer)TF->TitLabelEVHandlerData;
3820 if (TF->TitLabelEVHandler) {
3821 /* insert handler to catch clicks on titles */
3822 XtInsertEventHandler(
3823 TF->cells[n] , /* handle events in title cell */
3824 ButtonPressMask , /* button presses */
3825 FALSE , /* nonmaskable events? */
3826 TF->TitLabelEVHandler, /* handler */
3827 cd , /* client data */
3828 XtListTail ) ;
3829 }
3830 if (0 && TF->HasColTit && col_tit[j]) {/* Much better name, but
3831 Cannot use it before updating
3832 help generating functions which now call for help on .c00,
3833 .c01, or .r00 .r01, etc. */
3834 snprintf(wname, 63, "%s.%s", TF->wname, col_tit[j]);
3835 } else {
3836 snprintf(wname, 63, "%s.c%02d", TF->wname, j);
3837 }
3838 SUMA_Register_Widget_Help(TF->cells[n], 1, wname,
3839 col_hint?col_hint[j]:NULL,
3840 col_help?col_help[j]:NULL ) ;
3841 break;
3842 case SUMA_ENTRY_CELL: /* entry cell */
3843 if (LocalHead)
3844 fprintf( SUMA_STDERR,
3845 "%s:\nAdding [%d %d] (%d) entry cell\n",
3846 FuncName, i, j, n);
3847 TF->cells[n] = XtVaCreateManagedWidget(
3848 "entry",
3849 xmTextFieldWidgetClass, rcc,
3850 XmNuserData, (XTP_CAST)n,
3851 XmNvalue, "-",
3852 XmNmarginHeight, 0,
3853 XmNmarginTop, 0,
3854 XmNmarginBottom, 0,
3855 XmNmarginWidth, 5,
3856 NULL);
3857 XtVaSetValues( TF->cells[n],
3858 XmNfontList,
3859 SUMAg_CF->X->TableTextFontList, NULL);
3860 if (col_help || col_hint || row_help || row_hint) {
3861 if (TF->Ni>1) {
3862 snprintf(wname, 63, "%s[%d,%d]", TF->wname, i, j);
3863 } else {
3864 snprintf(wname, 63, "%s[%d]", TF->wname, n);
3865 }
3866 if (!row_tit && !col_tit && TF->Ni == 1 && TF->Nj == 1) {
3867 char *shh=NULL, *sii=NULL;
3868 if (col_help) shh = col_help[0] ;
3869 else if (row_help) shh = row_help[0] ;
3870 if (col_hint) sii = col_hint[0] ;
3871 else if (row_hint) sii = row_hint[0] ;
3872 if (shh || sii) {
3873 SUMA_Register_Widget_Help(TF->cells[n],1,wname,sii, shh);
3874 }
3875 } else {
3876 SUMA_Register_Widget_Help(TF->cells[n], 1, wname,
3877 NULL,
3878 "Use BHelp on table's column and row titles"
3879 "for usage information.") ;
3880 }
3881 }
3882 if (TF->cwidth[j] > 0) {
3883 XtVaSetValues(TF->cells[n], XmNcolumns, TF->cwidth[j], NULL);
3884 }
3885 if (!TF->editable) {
3886 SUMA_SetCellEditMode(TF, i, j, 0);
3887 } else {
3888 SUMA_SetCellEditMode(TF, i, j, 1);
3889 }
3890
3891 /* insert handlers if any */
3892 if (!TF->CellEVHandlerData) cd = (XtPointer) TF;
3893 else cd = (XtPointer)TF->CellEVHandlerData;
3894 if (TF->CellEVHandler) {
3895 /* insert handler to catch clicks on cells */
3896 XtInsertEventHandler(
3897 TF->cells[n] , /* handle events in cell */
3898 ButtonPressMask , /* button presses */
3899 FALSE , /* nonmaskable events? */
3900 TF->CellEVHandler, /* handler */
3901 cd , /* client data */
3902 XtListTail ) ;
3903 }
3904 break;
3905 default:
3906 SUMA_SL_Err("Bad cell type");
3907 SUMA_RETURNe;
3908 break;
3909 }
3910 } /* for j */
3911 } /* for i */
3912
3913 SUMA_RETURNe;
3914 }
3915
SUMA_set_slice_label(SUMA_ALL_DO * ado,char * variant,float val)3916 int SUMA_set_slice_label(SUMA_ALL_DO *ado, char *variant, float val)
3917 {
3918 static char FuncName[]={"SUMA_set_slice_label"};
3919 char slabel[100];
3920 SUMA_X_SurfCont *SurfCont=NULL;
3921 SUMA_Boolean LocalHead = NOPE;
3922
3923 SUMA_ENTRY;
3924
3925 SUMA_LH("called");
3926
3927 SurfCont = SUMA_ADO_Cont(ado);
3928 if (!ado || !variant || !SurfCont) {
3929 SUMA_SL_Err("NULL input"); SUMA_RETURN(0); }
3930
3931 if (!SurfCont->Ax_slc || !SurfCont->Ax_slc->text ||
3932 !SurfCont->Sa_slc || !SurfCont->Sa_slc->text ||
3933 !SurfCont->Co_slc || !SurfCont->Co_slc->text) {
3934 SUMA_LH("No GUI yet"); SUMA_RETURN(1);
3935 }
3936
3937 sprintf(slabel, "%3s", MV_format_fval(val));
3938 if (variant[0] == 'A') {
3939 SUMA_STRING_REPLACE(SurfCont->Ax_slc->slice_num_str, slabel);
3940 XtVaSetValues (SurfCont->Ax_slc->text, XmNvalue, slabel, NULL);
3941 } else if (variant[0] == 'S') {
3942 SUMA_STRING_REPLACE(SurfCont->Sa_slc->slice_num_str, slabel);
3943 XtVaSetValues (SurfCont->Sa_slc->text, XmNvalue, slabel, NULL);
3944 } else if (variant[0] == 'C') {
3945 SUMA_STRING_REPLACE(SurfCont->Co_slc->slice_num_str, slabel);
3946 XtVaSetValues (SurfCont->Co_slc->text, XmNvalue, slabel, NULL);
3947 }
3948
3949 SUMA_RETURN(1);
3950 }
3951
SUMA_set_slice_scale(SUMA_ALL_DO * ado,char * variant,float val)3952 int SUMA_set_slice_scale(SUMA_ALL_DO *ado, char *variant, float val)
3953 {
3954 static char FuncName[]={"SUMA_set_slice_scale"};
3955 char slabel[100];
3956 int cv;
3957 SUMA_X_SurfCont *SurfCont=NULL;
3958 SUMA_Boolean LocalHead = NOPE;
3959
3960 SUMA_ENTRY;
3961
3962 SUMA_LH("called");
3963
3964 SurfCont = SUMA_ADO_Cont(ado);
3965 if (!ado || !variant || !SurfCont) {
3966 SUMA_SL_Err("NULL input"); SUMA_RETURN(0); }
3967
3968 if (!SurfCont->Ax_slc || !SurfCont->Ax_slc->sl ||
3969 !SurfCont->Sa_slc || !SurfCont->Sa_slc->sl ||
3970 !SurfCont->Co_slc || !SurfCont->Co_slc->sl) {
3971 SUMA_LH("No GUI yet"); SUMA_RETURN(1);
3972 }
3973
3974 cv = SUMA_SliceVal2ScalePos (ado, variant, &val );
3975
3976 if (variant[0] == 'A') {
3977 XtVaSetValues(SurfCont->Ax_slc->sl, XmNvalue, cv, NULL);
3978 } else if (variant[0] == 'S') {
3979 XtVaSetValues(SurfCont->Sa_slc->sl, XmNvalue, cv, NULL);
3980 } else if (variant[0] == 'C') {
3981 XtVaSetValues(SurfCont->Co_slc->sl, XmNvalue, cv, NULL);
3982 }
3983
3984 SUMA_RETURN(1);
3985 }
3986
SUMA_cb_set_Ax_slice_label(Widget w,XtPointer clientData,XtPointer call)3987 void SUMA_cb_set_Ax_slice_label(Widget w, XtPointer clientData, XtPointer call)
3988 {
3989 static char FuncName[]={"SUMA_cb_set_Ax_slice_label"};
3990 SUMA_ALL_DO *ado=NULL;
3991 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
3992 float fff ;
3993 int dec=0;
3994 char slabel[100];
3995 SUMA_Boolean LocalHead = NOPE;
3996
3997 SUMA_ENTRY;
3998
3999 SUMA_LH("called");
4000 ado = (SUMA_ALL_DO *)clientData;
4001 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
4002
4003 XtVaGetValues(w, XmNuserData, &dec, NULL);
4004 fff = (float)cbs->value / pow(10.0, dec);
4005
4006 SUMA_set_slice(ado, "Ax", &fff, "text_field", 1);
4007
4008 SUMA_RETURNe;
4009 }
4010
SUMA_cb_set_Sa_slice_label(Widget w,XtPointer clientData,XtPointer call)4011 void SUMA_cb_set_Sa_slice_label(Widget w, XtPointer clientData, XtPointer call)
4012 {
4013 static char FuncName[]={"SUMA_cb_set_Sa_slice_label"};
4014 SUMA_ALL_DO *ado=NULL;
4015 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
4016 float fff ;
4017 int dec=0;
4018 char slabel[100];
4019 SUMA_Boolean LocalHead = NOPE;
4020
4021 SUMA_ENTRY;
4022
4023 SUMA_LH("called");
4024 ado = (SUMA_ALL_DO *)clientData;
4025 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
4026
4027 XtVaGetValues(w, XmNuserData, &dec, NULL);
4028 fff = (float)cbs->value / pow(10.0, dec);
4029
4030 SUMA_set_slice(ado, "Sa", &fff, "text_field", 1);
4031
4032 SUMA_RETURNe;
4033 }
4034
SUMA_cb_set_Co_slice_label(Widget w,XtPointer clientData,XtPointer call)4035 void SUMA_cb_set_Co_slice_label(Widget w, XtPointer clientData, XtPointer call)
4036 {
4037 static char FuncName[]={"SUMA_cb_set_Co_slice_label"};
4038 SUMA_ALL_DO *ado=NULL;
4039 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
4040 float fff ;
4041 int dec=0;
4042 char slabel[100];
4043 SUMA_Boolean LocalHead = NOPE;
4044
4045 SUMA_ENTRY;
4046
4047 SUMA_LH("called");
4048 ado = (SUMA_ALL_DO *)clientData;
4049 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
4050
4051 XtVaGetValues(w, XmNuserData, &dec, NULL);
4052 fff = (float)cbs->value / pow(10.0, dec);
4053
4054 SUMA_set_slice(ado, "Co", &fff, "text_field", 1);
4055
4056 SUMA_RETURNe;
4057 }
4058
SUMA_cb_set_Ax_slice(Widget w,XtPointer clientData,XtPointer call)4059 void SUMA_cb_set_Ax_slice(Widget w, XtPointer clientData, XtPointer call)
4060 {
4061 static char FuncName[]={"SUMA_cb_set_Ax_slice"};
4062 SUMA_ALL_DO *ado=NULL;
4063 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
4064 float fff=0.0;
4065 int dec=-1;
4066 SUMA_Boolean LocalHead = NOPE;
4067
4068 SUMA_ENTRY;
4069 ado = (SUMA_ALL_DO *)clientData;
4070 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
4071 XtVaGetValues(w, XmNuserData, &dec, NULL);
4072 fff = (float)cbs->value / pow(10.0, dec);
4073 SUMA_LHv("Have %f\n", fff);
4074 SUMA_set_slice(ado, "Ax", &fff, "scale", 1);
4075
4076 SUMA_RETURNe;
4077 }
4078
SUMA_cb_set_Sa_slice(Widget w,XtPointer clientData,XtPointer call)4079 void SUMA_cb_set_Sa_slice(Widget w, XtPointer clientData, XtPointer call)
4080 {
4081 static char FuncName[]={"SUMA_cb_set_Sa_slice"};
4082 SUMA_ALL_DO *ado=NULL;
4083 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
4084 float fff=0.0;
4085 int dec=-1;
4086 SUMA_Boolean LocalHead = NOPE;
4087
4088 SUMA_ENTRY;
4089 ado = (SUMA_ALL_DO *)clientData;
4090 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
4091 XtVaGetValues(w, XmNuserData, &dec, NULL);
4092 fff = (float)cbs->value / pow(10.0, dec);
4093 SUMA_LHv("Have %f\n", fff);
4094 SUMA_set_slice(ado, "Sa", &fff, "scale", 1);
4095
4096 SUMA_RETURNe;
4097 }
4098
SUMA_cb_set_Co_slice(Widget w,XtPointer clientData,XtPointer call)4099 void SUMA_cb_set_Co_slice(Widget w, XtPointer clientData, XtPointer call)
4100 {
4101 static char FuncName[]={"SUMA_cb_set_Co_slice"};
4102 SUMA_ALL_DO *ado=NULL;
4103 XmScaleCallbackStruct * cbs = (XmScaleCallbackStruct *) call ;
4104 float fff=0.0;
4105 int dec=-1;
4106 SUMA_Boolean LocalHead = NOPE;
4107
4108 SUMA_ENTRY;
4109 ado = (SUMA_ALL_DO *)clientData;
4110 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURNe; }
4111 XtVaGetValues(w, XmNuserData, &dec, NULL);
4112 fff = (float)cbs->value / pow(10.0, dec);
4113 SUMA_LHv("Have %f\n", fff);
4114 SUMA_set_slice(ado, "Co", &fff, "scale", 1);
4115
4116 SUMA_RETURNe;
4117 }
4118
SUMA_set_slice(SUMA_ALL_DO * ado,char * variant,float * valp,char * caller,int redisp)4119 int SUMA_set_slice(SUMA_ALL_DO *ado, char *variant, float *valp,
4120 char *caller, int redisp)
4121 {
4122 static char FuncName[]={"SUMA_set_slice"};
4123 float oval, val;
4124 SUMA_X_SurfCont *SurfCont=NULL;
4125 SUMA_VolumeObject *VO=(SUMA_VolumeObject *)ado;
4126 SUMA_Boolean LocalHead = NOPE;
4127
4128 SUMA_ENTRY;
4129
4130 if (!ado || !variant) SUMA_RETURN(0);
4131 if (!caller) caller = "XXX"; /* Don't update other input sources */
4132
4133 SurfCont = SUMA_ADO_Cont(ado);
4134
4135 if (!valp) {
4136 val = SUMA_VO_N_Slices(VO, variant);/* dirty trick to force scale height */
4137 } else val = *valp;
4138
4139 SUMA_LH("Slice %s set to %f", variant, val);
4140
4141 if (caller[0] == 'i') { /* incrementor */
4142 /* calculate val to reflect increment */
4143 if (variant[0] == 'A') {
4144 val += SurfCont->Ax_slc->slice_num;
4145 } else if (variant[0] == 'S') {
4146 val += SurfCont->Sa_slc->slice_num;
4147 } else if (variant[0] == 'C') {
4148 val += SurfCont->Co_slc->slice_num;
4149 } else if (variant[0] == 'V') {
4150 val += SurfCont->VR_fld->N_slice_num;
4151 }
4152 }
4153
4154 if (val < 0) val = 0;
4155 else if (val >= SUMA_VO_N_Slices(VO, variant) &&
4156 variant[0] != 'V')
4157 val = SUMA_VO_N_Slices(VO, variant)-1;
4158
4159 /* call this one since it is not being called as the slider is dragged. */
4160 if (caller[0] != 'X' && variant[0] != 'V') { /* Update equivalent */
4161 if (caller[0] != 't') { /* Caller not from text field so set that*/
4162 SUMA_set_slice_label(ado, variant, val);
4163 }
4164 if (caller[0] != 's') { /* Caller not from slider, so update that too */
4165 SUMA_set_slice_scale(ado, variant, val);
4166 }
4167 }
4168
4169 if (variant[0] == 'A') {
4170 SurfCont->Ax_slc->slice_num = val;
4171 } else if (variant[0] == 'S') {
4172 SurfCont->Sa_slc->slice_num = val;
4173 } else if (variant[0] == 'C') {
4174 SurfCont->Co_slc->slice_num = val;
4175 } else if (variant[0] == 'V') {
4176 SurfCont->VR_fld->N_slice_num = val;
4177 }
4178
4179 if (redisp) SUMA_Remixedisplay(ado);
4180
4181 /* sad as it is */
4182 if (variant[0] != 'V') SUMA_FORCE_SLICE_SCALE_WIDTH(SUMA_ADO_Cont(ado));
4183
4184 #if 0 /* I don't think this will be necessary */
4185 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
4186 #endif
4187
4188 /* And this?
4189 #if SUMA_SEPARATE_SURF_CONTROLLERS
4190 SUMA_UpdateColPlaneShellAsNeeded(ado);
4191 #endif
4192 */
4193
4194 if (0) {
4195 static int ncnt=0;
4196 /* Do nothing about selection. Not sure what would be of use
4197 One could supposedly move the selection - if the selection
4198 was on the slice being moved. Something to ponder for the
4199 future
4200 Remember selection could be on any of the slices in the
4201 montage, or even elsewhere in space....
4202 */
4203 if (!ncnt) {
4204 SUMA_S_Warn("What to do about selected voxels here? Move them along?");
4205 ++ncnt;
4206 }
4207 SUMA_UpdateNodeValField(ado);
4208 SUMA_UpdateNodeLblField(ado);
4209 }
4210
4211 SUMA_RETURN(1);
4212 }
4213
SUMA_set_mont(SUMA_ALL_DO * ado,char * variant,float * val1p,float * val2p,char * caller,int redisp)4214 int SUMA_set_mont(SUMA_ALL_DO *ado, char *variant,
4215 float *val1p, float *val2p,
4216 char *caller, int redisp)
4217 {
4218 static char FuncName[]={"SUMA_set_mont"};
4219 float oval, val1, val2;
4220 SUMA_X_SurfCont *SurfCont=NULL;
4221 SUMA_VolumeObject *VO=(SUMA_VolumeObject *)ado;
4222 SUMA_Boolean LocalHead = NOPE;
4223
4224 SUMA_ENTRY;
4225
4226 if (!ado || !variant) SUMA_RETURN(0);
4227 if (!caller) caller = "XXX"; /* Don't update other input sources */
4228
4229 SurfCont = SUMA_ADO_Cont(ado);
4230
4231 if (!val1p) {
4232 val1 = 1;
4233 } else val1 = *val1p;
4234 if (!val2p) {
4235 val2 = 1;
4236 } else val2 = *val2p;
4237
4238 if (val1 < 1) val1 = 1;
4239 else if (val1 > SUMA_VO_N_Slices(VO, variant))
4240 val1 = SUMA_VO_N_Slices(VO, variant);
4241 if (val2 < 1) val2 = 1;
4242 else if (val2 > SUMA_VO_N_Slices(VO, variant))
4243 val2 = SUMA_VO_N_Slices(VO, variant);
4244
4245 val1 = (int)val1; val2 = (int)val2;
4246 SUMA_LH("Slice %s mont set to %d %d", variant, (int)val1, (int)val2);
4247
4248
4249 if (variant[0] == 'A') {
4250 SurfCont->Ax_slc->mont_num = val1;
4251 SurfCont->Ax_slc->mont_inc = val2;
4252 } else if (variant[0] == 'S') {
4253 SurfCont->Sa_slc->mont_num = val1;
4254 SurfCont->Sa_slc->mont_inc = val2;
4255 } else if (variant[0] == 'C') {
4256 SurfCont->Co_slc->mont_num = val1;
4257 SurfCont->Co_slc->mont_inc = val2;
4258 }
4259
4260 if (redisp) SUMA_Remixedisplay(ado);
4261
4262 SUMA_RETURN(1);
4263 }
4264
4265 /*!
4266 \brief create slice selection widgets
4267 */
SUMA_CreateSliceFields(Widget parent,char * tit,char * hint,char * help,int Nslc,char * var,SUMA_ALL_DO * ado,void (* NewValueCallback)(void * data),void * cb_data,SUMA_SLICE_FIELD * SF)4268 void SUMA_CreateSliceFields( Widget parent,
4269 char *tit, char *hint, char *help,
4270 int Nslc, char *var, SUMA_ALL_DO *ado,
4271 void (*NewValueCallback)(void * data), void *cb_data,
4272 SUMA_SLICE_FIELD *SF)
4273 {
4274 static char FuncName[]={"SUMA_CreateSliceFields"};
4275 int i, j, n, titw, xmw, shad, mult;
4276 char *tmp, sbuf[12], wname[64]={"SetMePlease"};
4277 XtPointer cd;
4278 XtVarArgsList arglist=NULL;
4279 XtCallbackProc slcb, sllbcb, slcactcb, shwslccb;
4280 int shw_init = 0;
4281 SUMA_VOL_SAUX *VSaux=NULL;
4282 SUMA_Boolean LocalHead = NOPE;
4283
4284 SUMA_ENTRY;
4285
4286 if (!parent) { SUMA_SL_Err("NULL parent"); SUMA_RETURNe; }
4287 if (!ado) { SUMA_S_Err("NULL ado"); SUMA_RETURNe; }
4288 if (!(VSaux = SUMA_ADO_VSaux(ado))) { SUMA_S_Err("No VSaux"); SUMA_RETURNe; }
4289 if (!tit) tit = var;
4290
4291 if (LocalHead) {
4292 SUMA_S_Warn("Are NewValueCallback and its data needed at all?");
4293 }
4294 /* initialize font list if need be */
4295 if (!SUMAg_CF->X->TableTextFontList) {
4296 if (SUMA_isEnv("SUMA_SurfContFontSize", "BIG")) {
4297 SUMAg_CF->X->TableTextFontList =
4298 SUMA_AppendToFontList( SUMAg_CF->X->TableTextFontList,
4299 parent, "*9x15*", NULL);
4300 } else {
4301 SUMAg_CF->X->TableTextFontList =
4302 SUMA_AppendToFontList( SUMAg_CF->X->TableTextFontList,
4303 parent, "*8x13*", NULL);
4304 }
4305 }
4306
4307 if (!SF) { SUMA_SL_Err("NULL SF"); SUMA_RETURNe; }
4308 if (!var){ SUMA_S_Err("Bad var format"); SUMA_RETURNe; }
4309 SUMA_LH("Init");
4310 if (!strcmp(var,"Ax")) {
4311 slcb = SUMA_cb_set_Ax_slice;
4312 sllbcb = SUMA_cb_set_Ax_slice_label;
4313 slcactcb = SUMA_SliceF_cb_label_change;
4314 shwslccb = SUMA_cb_ShowAxSlice_toggled;
4315 shw_init = VSaux->ShowAxSlc;
4316 } else if (!strcmp(var,"Sa")) {
4317 slcb = SUMA_cb_set_Sa_slice;
4318 sllbcb = SUMA_cb_set_Sa_slice_label;
4319 slcactcb = SUMA_SliceF_cb_label_change;
4320 shwslccb = SUMA_cb_ShowSaSlice_toggled;
4321 shw_init = VSaux->ShowSaSlc;
4322 } else if (!strcmp(var,"Co")) {
4323 slcb = SUMA_cb_set_Co_slice;
4324 sllbcb = SUMA_cb_set_Co_slice_label;
4325 slcactcb = SUMA_SliceF_cb_label_change;
4326 shwslccb = SUMA_cb_ShowCoSlice_toggled;
4327 shw_init = VSaux->ShowCoSlc;
4328 } else {
4329 SUMA_S_Err("Bad var %s", var);
4330 SUMA_RETURNe;
4331 }
4332 SF->variant = SUMA_copy_string(var);
4333 SF->Nslc = Nslc;
4334 SF->NewValueCallback = NewValueCallback;
4335 SF->NewValueCallbackData = cb_data;
4336 /* An outer row column to keep the inner one from resizing with parent
4337 YOU COULD HAVE SET XmNadjustLast to False, instead ....*/
4338 SF->rc = XtVaCreateManagedWidget ("rowcolumn",
4339 xmRowColumnWidgetClass, parent,
4340 XmNorientation , XmHORIZONTAL ,
4341 XmNpacking, XmPACK_TIGHT,
4342 XmNmarginHeight, 0,
4343 XmNmarginWidth, 0,
4344 NULL);
4345
4346 SUMA_LH("Widgets, var %s, tit %s, slice num = %d, Nslc = %d, wname = %s",
4347 var, tit, (int)SF->slice_num, SF->Nslc, SF->wname);
4348 SF->lab = XtVaCreateManagedWidget(tit, xmLabelWidgetClass, SF->rc,
4349 XmNfontList, SUMAg_CF->X->TableTextFontList,
4350 NULL);
4351 if (hint || help) {
4352 snprintf(wname,63, "%s->%s", SF->wname, tit);
4353 SUMA_Register_Widget_Help( SF->lab, 1, wname, hint, help);
4354 }
4355 mult = ((int)(SF->Nslc/20.0)/5)*5; if (mult < 1) mult = 1;
4356 arglist = XtVaCreateArgsList( NULL,
4357 XmNshowValue, False,
4358 XmNmaximum, SF->Nslc,
4359 XmNvalue, (int)SF->slice_num,
4360 XmNscaleMultiple, mult,
4361 XmNheight, SUMA_SCALE_HEIGHT,
4362 XmNorientation, XmHORIZONTAL,
4363 XmNuserData, (XtPointer)0,
4364 NULL);
4365
4366 SF->sl = XtVaCreateManagedWidget(var,
4367 xmScaleWidgetClass, SF->rc,
4368 XtVaNestedList, arglist,
4369 NULL);
4370 XtAddCallback (SF->sl,
4371 XmNvalueChangedCallback,
4372 slcb,
4373 (XtPointer) ado);
4374
4375 XtAddCallback (SF->sl,
4376 XmNdragCallback,
4377 sllbcb,
4378 (XtPointer) ado);
4379
4380 if (arglist) XtFree(arglist); arglist = NULL;
4381
4382 sprintf(sbuf,"%-3d", (int)SF->slice_num);
4383 SF->text = XtVaCreateManagedWidget(
4384 "slice",
4385 xmTextFieldWidgetClass, SF->rc,
4386 XmNuserData, (XTP_CAST)ado,
4387 XmNvalue, sbuf,
4388 XmNmarginHeight, 0,
4389 XmNmarginTop, 0,
4390 XmNmarginBottom, 0,
4391 XmNmarginWidth, 5,
4392 NULL);
4393 XtVaSetValues( SF->text, XmNfontList,
4394 SUMAg_CF->X->TableTextFontList, NULL);
4395
4396 if (hint || help) {
4397 snprintf(wname, 63, "%s->%s_text", SF->wname, tit);
4398 SUMA_Register_Widget_Help( SF->text, 1, wname, hint, help);
4399 }
4400 XtVaSetValues(SF->text, XmNcolumns, 3, NULL);
4401 XtVaSetValues(SF->text, XmNeditable, True,
4402 XmNshadowThickness , 2,
4403 XmNcursorPositionVisible, True,
4404 NULL);
4405
4406 XtAddCallback (SF->text, XmNactivateCallback,
4407 SUMA_SliceF_cb_label_change, (XtPointer)SF);
4408 /* add event handler to notify when widget was left */
4409 XtInsertEventHandler( SF->text , /* notify when */
4410 LeaveWindowMask , /* pointer leaves */
4411 FALSE , /* this window */
4412 SUMA_leave_SliceField,
4413 (XtPointer) SF ,
4414 XtListTail ) ; /* last in queue */
4415
4416 sprintf(sbuf,"%d:%d", (int)SF->mont_num, (int)SF->mont_inc);
4417 SF->mont = XtVaCreateManagedWidget(
4418 "mont",
4419 xmTextFieldWidgetClass, SF->rc,
4420 XmNuserData, (XTP_CAST)ado,
4421 XmNvalue, sbuf,
4422 XmNmarginHeight, 0,
4423 XmNmarginTop, 0,
4424 XmNmarginBottom, 0,
4425 XmNmarginWidth, 5,
4426 NULL);
4427 XtVaSetValues( SF->mont, XmNfontList,
4428 SUMAg_CF->X->TableTextFontList, NULL);
4429
4430 if (hint || help) {
4431 snprintf(wname, 63, "%s->mont", SF->wname);
4432 SUMA_Register_Widget_Help( SF->mont, 1, wname, hint, help);
4433 }
4434 XtVaSetValues(SF->mont, XmNcolumns, 5, NULL);
4435 XtVaSetValues(SF->mont, XmNeditable, True,
4436 XmNshadowThickness , 2,
4437 XmNcursorPositionVisible, True,
4438 NULL);
4439
4440 XtAddCallback (SF->mont, XmNactivateCallback,
4441 SUMA_SliceF_cb_mont_change, (XtPointer)SF);
4442 /* add event handler to notify when widget was left */
4443 XtInsertEventHandler( SF->mont , /* notify when */
4444 LeaveWindowMask , /* pointer leaves */
4445 FALSE , /* this window */
4446 SUMA_leave_MontField,
4447 (XtPointer) SF ,
4448 XtListTail ) ; /* last in queue */
4449
4450
4451 /* Now for the toggle button */
4452 SF->tb = XtVaCreateManagedWidget("v",
4453 xmToggleButtonWidgetClass, SF->rc, NULL);
4454 XtAddCallback (SF->tb,
4455 XmNvalueChangedCallback, shwslccb, ado);
4456 snprintf(wname, 63, "%s->tb", SF->wname);
4457 SUMA_Register_Widget_Help(SF->tb, 1, wname,
4458 "View (ON)/Hide Slice(s)",
4459 SUMA_SurfContHelp_ShowSliceTgl);
4460
4461 SUMA_SET_SELECT_COLOR(SF->tb);
4462 XmToggleButtonSetState (SF->tb, shw_init , NOPE);
4463
4464 SUMA_RETURNe;
4465 }
4466
SUMA_cb_ShowAxSlice_toggled(Widget w,XtPointer data,XtPointer client_data)4467 void SUMA_cb_ShowAxSlice_toggled(Widget w, XtPointer data, XtPointer client_data)
4468 {
4469 static char FuncName[]={"SUMA_cb_ShowAxSlice_toggled"};
4470 SUMA_ALL_DO *ado = NULL;
4471 SUMA_X_SurfCont *SurfCont=NULL;
4472 SUMA_Boolean LocalHead = NOPE;
4473
4474 SUMA_ENTRY;
4475
4476 SUMA_LH("Called");
4477
4478 ado = (SUMA_ALL_DO *)data;
4479 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
4480 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
4481
4482 SUMA_SetShowSlice((SUMA_VolumeObject *)ado, "Ax",
4483 XmToggleButtonGetState (SurfCont->Ax_slc->tb));
4484 SUMA_RETURNe;
4485 }
4486
4487
SUMA_cb_ShowSaSlice_toggled(Widget w,XtPointer data,XtPointer client_data)4488 void SUMA_cb_ShowSaSlice_toggled(Widget w, XtPointer data, XtPointer client_data)
4489 {
4490 static char FuncName[]={"SUMA_cb_ShowSaSlice_toggled"};
4491 SUMA_ALL_DO *ado = NULL;
4492 SUMA_X_SurfCont *SurfCont=NULL;
4493 SUMA_Boolean LocalHead = NOPE;
4494
4495 SUMA_ENTRY;
4496
4497 SUMA_LH("Called");
4498
4499 ado = (SUMA_ALL_DO *)data;
4500 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
4501 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
4502
4503 SUMA_SetShowSlice((SUMA_VolumeObject *)ado, "Sa",
4504 XmToggleButtonGetState (SurfCont->Sa_slc->tb));
4505 SUMA_RETURNe;
4506 }
4507
SUMA_cb_ShowCoSlice_toggled(Widget w,XtPointer data,XtPointer client_data)4508 void SUMA_cb_ShowCoSlice_toggled(Widget w, XtPointer data, XtPointer client_data)
4509 {
4510 static char FuncName[]={"SUMA_cb_ShowCoSlice_toggled"};
4511 SUMA_ALL_DO *ado = NULL;
4512 SUMA_X_SurfCont *SurfCont=NULL;
4513 SUMA_Boolean LocalHead = NOPE;
4514
4515 SUMA_ENTRY;
4516
4517 SUMA_LH("Called");
4518
4519 ado = (SUMA_ALL_DO *)data;
4520 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado))) {
4521 SUMA_S_Warn("NULL input"); SUMA_RETURNe; }
4522
4523 SUMA_SetShowSlice((SUMA_VolumeObject *)ado, "Co",
4524 XmToggleButtonGetState (SurfCont->Co_slc->tb));
4525 SUMA_RETURNe;
4526 }
4527
SUMA_SetShowSlice(SUMA_VolumeObject * vdo,char * variant,int val)4528 int SUMA_SetShowSlice(SUMA_VolumeObject *vdo, char *variant, int val)
4529 {
4530 static char FuncName[]={"SUMA_SetShowSlice"};
4531 SUMA_ALL_DO *ado = NULL;
4532 SUMA_X_SurfCont *SurfCont=NULL;
4533 SUMA_VOL_SAUX *VSaux = NULL;
4534 SUMA_Boolean LocalHead = NOPE;
4535
4536 SUMA_ENTRY;
4537
4538 SUMA_LH("Called variant %s, val %d", variant?variant:"NULL", val);
4539
4540 ado = (SUMA_ALL_DO *)vdo;
4541 VSaux = SUMA_ADO_VSaux(ado);
4542 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado)) || !VSaux || !variant) {
4543 SUMA_S_Warn("NULL input"); SUMA_RETURN(0); }
4544
4545 if (!strcmp(variant, "Ax")) {
4546 if (VSaux->ShowAxSlc != val) {
4547 VSaux->ShowAxSlc = val;
4548 SUMA_Remixedisplay(ado);
4549 #if SUMA_SEPARATE_SURF_CONTROLLERS
4550 SUMA_UpdateColPlaneShellAsNeeded(ado);
4551 #endif
4552 }
4553 } else if (!strcmp(variant, "Sa")) {
4554 if (VSaux->ShowSaSlc != val) {
4555 VSaux->ShowSaSlc = val;
4556 SUMA_Remixedisplay(ado);
4557 #if SUMA_SEPARATE_SURF_CONTROLLERS
4558 SUMA_UpdateColPlaneShellAsNeeded(ado);
4559 #endif
4560 }
4561 } else if (!strcmp(variant, "Co")) {
4562 if (VSaux->ShowCoSlc != val) {
4563 VSaux->ShowCoSlc = val;
4564 SUMA_Remixedisplay(ado);
4565 #if SUMA_SEPARATE_SURF_CONTROLLERS
4566 SUMA_UpdateColPlaneShellAsNeeded(ado);
4567 #endif
4568 }
4569 } else if (!strcmp(variant, "Vr")) {
4570 if (VSaux->ShowVrSlc != val) {
4571 VSaux->ShowVrSlc = val;
4572 SUMA_Remixedisplay(ado);
4573 #if SUMA_SEPARATE_SURF_CONTROLLERS
4574 SUMA_UpdateColPlaneShellAsNeeded(ado);
4575 #endif
4576 }
4577 SUMA_LH("ShowVrSlc now %d", VSaux->ShowVrSlc);
4578 } else if (!strcmp(variant, "AtXYZ")) {
4579 SUMA_SurfaceViewer *sv=NULL;
4580 if (VSaux->SlicesAtCrosshair != val) {
4581 VSaux->SlicesAtCrosshair = val;
4582 if (VSaux->SlicesAtCrosshair && (sv=SUMA_OneViewerWithADOVisible(ado))
4583 && sv->Ch){
4584 SUMA_VO_set_slices_XYZ(vdo, sv->Ch->c_noVisX);
4585 }
4586 SUMA_Remixedisplay(ado);
4587 #if SUMA_SEPARATE_SURF_CONTROLLERS
4588 SUMA_UpdateColPlaneShellAsNeeded(ado);
4589 #endif
4590 }
4591 SUMA_LH("SlicesAtCrosshair now %d", VSaux->SlicesAtCrosshair);
4592 } else if (!strcmp(variant, "Sel")) {
4593 if (VSaux->VrSelect != val) {
4594 VSaux->VrSelect = val;
4595 }
4596 SUMA_LH("VrSelect now %d", VSaux->VrSelect);
4597 } else {
4598 SUMA_S_Err("And what is variant %s for?", variant);
4599 SUMA_RETURN(NOPE);
4600 }
4601 SUMA_RETURN(1);
4602 }
4603
4604
4605
SUMA_cellvariety(SUMA_TABLE_FIELD * TF,int n)4606 SUMA_CELL_VARIETY SUMA_cellvariety (SUMA_TABLE_FIELD *TF, int n)
4607 {
4608 static char FuncName[]={"SUMA_cellvariety"};
4609 int i, j;
4610 SUMA_Boolean LocalHead = NOPE;
4611
4612 SUMA_ENTRY;
4613
4614 if (!TF) SUMA_RETURN(SUMA_ERROR_CELL);
4615 i = n % TF->Ni;
4616 j = n / TF->Ni;
4617 if (TF->HasColTit && i == 0) SUMA_RETURN(SUMA_COL_TIT_CELL);
4618 if (TF->HasRowTit && j == 0) SUMA_RETURN(SUMA_ROW_TIT_CELL);
4619 SUMA_RETURN(SUMA_ENTRY_CELL);
4620 }
4621
SUMA_RowTitCell(SUMA_TABLE_FIELD * TF,int r)4622 int SUMA_RowTitCell(SUMA_TABLE_FIELD *TF, int r)
4623 {
4624 static char FuncName[]={"SUMA_RowTitCell"};
4625 SUMA_Boolean LocalHead = NOPE;
4626
4627 SUMA_ENTRY;
4628
4629 if (!TF || !TF->HasRowTit || r < 0 || r >= TF->Ni) SUMA_RETURN(-1);
4630
4631 SUMA_RETURN(r);
4632 }
4633
SUMA_ColTitCell(SUMA_TABLE_FIELD * TF,int c)4634 int SUMA_ColTitCell(SUMA_TABLE_FIELD *TF, int c)
4635 {
4636 static char FuncName[]={"SUMA_ColTitCell"};
4637 SUMA_Boolean LocalHead = NOPE;
4638
4639 SUMA_ENTRY;
4640
4641 if (!TF || !TF->HasColTit || c < 0 || c >= TF->Nj) SUMA_RETURN(-1);
4642
4643 SUMA_RETURN(c*TF->Ni);
4644 }
4645
SUMA_ObjectID_Row(SUMA_TABLE_FIELD * TF,char * id)4646 int SUMA_ObjectID_Row(SUMA_TABLE_FIELD *TF, char *id)
4647 {
4648 static char FuncName[]={"SUMA_ObjectID_Row"};
4649 int found = -1, ii=-1;
4650 SUMA_Boolean LocalHead = NOPE;
4651
4652 SUMA_ENTRY;
4653
4654 if (!TF || !TF->rowobject_id || !id) SUMA_RETURN(-1);
4655
4656 if (LocalHead) {
4657 fprintf(SUMA_STDERR, "Seeking %s\n"
4658 "in ", id);
4659 for (ii=0; ii<TF->Ni; ++ii) {
4660 fprintf(SUMA_STDERR,"%s\n ",
4661 TF->rowobject_id[ii]?TF->rowobject_id[ii]:"NULL");
4662 }
4663 fprintf(SUMA_STDERR, "\n");
4664 }
4665 found = -1; ii=0;
4666 while (found < 0 && ii < TF->Ni) {
4667 if (TF->rowobject_id[ii] &&
4668 !strcmp(id, TF->rowobject_id[ii])) {
4669 found = ii;
4670 }
4671 ++ii;
4672 }
4673
4674 SUMA_RETURN(found);
4675 }
4676
4677
4678 /*!
4679 \brief This function is called when mouse pointer leaves label field
4680 It only acts if TF->modified
4681 */
SUMA_leave_TableField(Widget w,XtPointer client_data,XEvent * ev,Boolean * continue_to_dispatch)4682 void SUMA_leave_TableField( Widget w , XtPointer client_data ,
4683 XEvent * ev , Boolean * continue_to_dispatch )
4684 {
4685 static char FuncName[]={"SUMA_leave_TableField"};
4686 SUMA_TABLE_FIELD *TF=NULL;
4687 XLeaveWindowEvent * lev = (XLeaveWindowEvent *) ev ;
4688 XmAnyCallbackStruct cbs ;
4689 SUMA_Boolean LocalHead = NOPE;
4690
4691 SUMA_ENTRY;
4692
4693 SUMA_LH("Called");
4694 TF = (SUMA_TABLE_FIELD *)client_data ;
4695 if( lev->type != LeaveNotify || TF->cell_modified < 0) SUMA_RETURNe;
4696
4697 if (LocalHead) fprintf (SUMA_STDERR, "%s: Leave notification.\n", FuncName);
4698
4699 SUMA_TableF_cb_label_change( w , (XtPointer)TF , NULL ) ;
4700
4701 SUMA_RETURNe;
4702 }
4703
4704 /*!
4705 \brief This function is called when mouse pointer leaves montage field
4706 */
SUMA_leave_MontField(Widget w,XtPointer client_data,XEvent * ev,Boolean * continue_to_dispatch)4707 void SUMA_leave_MontField( Widget w , XtPointer client_data ,
4708 XEvent * ev , Boolean * continue_to_dispatch )
4709 {
4710 static char FuncName[]={"SUMA_leave_MontField"};
4711 SUMA_SLICE_FIELD *SF=NULL;
4712 XLeaveWindowEvent * lev = (XLeaveWindowEvent *) ev ;
4713 XmAnyCallbackStruct cbs ;
4714 SUMA_Boolean LocalHead = NOPE;
4715
4716 SUMA_ENTRY;
4717
4718 SUMA_LH("Called");
4719 SF = (SUMA_SLICE_FIELD *)client_data ;
4720 if( lev->type != LeaveNotify) SUMA_RETURNe;
4721
4722 if (LocalHead) fprintf (SUMA_STDERR, "%s: Leave notification.\n", FuncName);
4723
4724 SUMA_SliceF_cb_mont_change( w , (XtPointer)SF , NULL ) ;
4725
4726 SUMA_RETURNe;
4727 }
4728
4729 /*!
4730 \brief This function is called when mouse pointer leaves slice field
4731 */
SUMA_leave_SliceField(Widget w,XtPointer client_data,XEvent * ev,Boolean * continue_to_dispatch)4732 void SUMA_leave_SliceField( Widget w , XtPointer client_data ,
4733 XEvent * ev , Boolean * continue_to_dispatch )
4734 {
4735 static char FuncName[]={"SUMA_leave_SliceField"};
4736 SUMA_SLICE_FIELD *SF=NULL;
4737 XLeaveWindowEvent * lev = (XLeaveWindowEvent *) ev ;
4738 XmAnyCallbackStruct cbs ;
4739 SUMA_Boolean LocalHead = NOPE;
4740
4741 SUMA_ENTRY;
4742
4743 SUMA_LH("Called");
4744 SF = (SUMA_SLICE_FIELD *)client_data ;
4745 if( lev->type != LeaveNotify) SUMA_RETURNe;
4746
4747 if (LocalHead) fprintf (SUMA_STDERR, "%s: Leave notification.\n", FuncName);
4748
4749 SUMA_SliceF_cb_label_change( w , (XtPointer)SF , NULL ) ;
4750
4751 SUMA_RETURNe;
4752 }
4753
4754 /*!
4755 \brief User entered new slice value
4756 */
SUMA_SliceF_cb_label_change(Widget w,XtPointer client_data,XtPointer call_data)4757 void SUMA_SliceF_cb_label_change ( Widget w, XtPointer client_data,
4758 XtPointer call_data)
4759 {
4760 static char FuncName[]={"SUMA_SliceF_cb_label_change"};
4761 SUMA_SLICE_FIELD *SF=NULL;
4762 float val;
4763 int N_words = 0;
4764 XmAnyCallbackStruct *cbs = (XmAnyCallbackStruct *) call_data;
4765 void *n=NULL;
4766 char *cs=NULL;
4767 int unt = SUMA_NO_NUM_UNITS;
4768 SUMA_Boolean DoCallBacks;
4769 SUMA_Boolean LocalHead = NOPE;
4770
4771 SUMA_ENTRY;
4772
4773 SUMA_LH("Called");
4774 /* make call to NewValue callback */
4775 SF = (SUMA_SLICE_FIELD *)client_data;
4776
4777 DoCallBacks = NOPE;
4778 if (call_data) {
4779 /* do the call backs if carriage return even if nothing is modified */
4780 if (LocalHead)
4781 fprintf (SUMA_STDERR,"%s: cbs->reason = %d (CR=%d)\n",
4782 FuncName, cbs->reason, XmCR_ACTIVATE);
4783 if (cbs->reason == XmCR_ACTIVATE) {
4784 DoCallBacks = YUP;
4785 }
4786 }
4787
4788 DoCallBacks = YUP; /* do the callbacks even if no carriage return ... */
4789 /* Check if the string is numerical, and get unit */
4790 XtVaGetValues (w, XmNvalue, &n, NULL);
4791 cs = (char *)n;
4792 if (!cs || !strlen(cs)) {/* empty cell, leave it alone */
4793 SUMA_LHv("empty %s", cs);
4794 SUMA_RETURNe;
4795 } else {
4796 SUMA_COUNT_WORDS(cs, NULL, N_words);
4797 if (!N_words) { /* no harm, go back */
4798 SUMA_LHv("spacy %s", cs);
4799 SUMA_RETURNe;
4800 }
4801 }
4802 unt = SUMA_NumStringUnits(cs, 0);
4803 if (SUMA_StringToNum(cs, (void *)&val, 1, 1) != 1) {
4804 SUMA_BEEP;
4805 /* bad syntax, reset value*/
4806 if (LocalHead) fprintf (SUMA_STDERR, "%s: Bad syntax.\n", FuncName);
4807 SUMA_RegisterMessage (SUMAg_CF->MessageList,
4808 "Bad value in text field", FuncName,
4809 SMT_Error, SMA_Log);
4810 SUMA_SliceF_SetString (SF);
4811 }else {
4812 if (SF->slice_num == val &&
4813 SF->slice_units == unt) {
4814 SUMA_LH("Same value");
4815 SUMA_RETURNe;
4816 }
4817 SUMA_LH("A new beast? %f, %f, %d %d",
4818 SF->slice_num, val, SF->slice_units, unt);
4819 SF->slice_num = val;
4820 SF->slice_units = unt;
4821 SUMA_SliceF_SetString (SF);
4822 }
4823
4824 if (DoCallBacks) {
4825 SUMA_set_slice((SUMA_ALL_DO *)SF->NewValueCallbackData, SF->variant, &val,
4826 "text_field", 1);
4827 }
4828
4829 SUMA_RETURNe;
4830 }
4831
4832 /*!
4833 \brief User entered new montage string
4834 */
SUMA_SliceF_cb_mont_change(Widget w,XtPointer client_data,XtPointer call_data)4835 void SUMA_SliceF_cb_mont_change ( Widget w, XtPointer client_data,
4836 XtPointer call_data)
4837 {
4838 static char FuncName[]={"SUMA_SliceF_cb_mont_change"};
4839 SUMA_SLICE_FIELD *SF=NULL;
4840 float val1, val2;
4841 int N_words = 0;
4842 XmAnyCallbackStruct *cbs = (XmAnyCallbackStruct *) call_data;
4843 void *n=NULL;
4844 char *cs=NULL, *ss=NULL;
4845 int unt = SUMA_NO_NUM_UNITS;
4846 SUMA_Boolean DoCallBacks;
4847 SUMA_Boolean LocalHead = NOPE;
4848
4849 SUMA_ENTRY;
4850
4851 SUMA_LH("Nothing done yet, build based on SUMA_SliceF_cb_label_change");
4852 /* make call to NewValue callback */
4853 SF = (SUMA_SLICE_FIELD *)client_data;
4854
4855 DoCallBacks = NOPE;
4856 if (call_data) {
4857 /* do the call backs if carriage return even if nothing is modified */
4858 if (LocalHead)
4859 fprintf (SUMA_STDERR,"%s: cbs->reason = %d (CR=%d)\n",
4860 FuncName, cbs->reason, XmCR_ACTIVATE);
4861 if (cbs->reason == XmCR_ACTIVATE) {
4862 DoCallBacks = YUP;
4863 }
4864 }
4865
4866 DoCallBacks = YUP; /* do the callbacks even if no carriage return ... */
4867 /* Check if the string is numerical, and get unit */
4868 XtVaGetValues (w, XmNvalue, &n, NULL);
4869 cs = (char *)n;
4870 if (!cs || !strlen(cs)) {/* empty cell, leave it alone */
4871 SUMA_LHv("empty %s", cs);
4872 SUMA_RETURNe;
4873 } else {
4874 SUMA_COUNT_WORDS(cs, NULL, N_words);
4875 if (!N_words) { /* no harm, go back */
4876 SUMA_LHv("spacy %s", cs);
4877 SUMA_RETURNe;
4878 }
4879 }
4880 val1 = -1;
4881 val2 = -1;
4882 unt = SUMA_NumStringUnits(cs, 0);
4883 /* Split based on the presence of ':' */
4884 if (!(ss = SUMA_NI_get_ith_string(cs, ":", 0))) {
4885 SUMA_LH("Nothing in cs?");
4886 SUMA_RETURNe;
4887 }
4888 if (SUMA_StringToNum(ss, (void *)&val1, 1, 1) != 1) {
4889 SUMA_BEEP;
4890 /* bad syntax, reset value*/
4891 if (LocalHead) fprintf (SUMA_STDERR, "%s: Bad syntax.\n", FuncName);
4892 SUMA_RegisterMessage (SUMAg_CF->MessageList,
4893 "Bad value in text field", FuncName,
4894 SMT_Error, SMA_Log);
4895 SUMA_SliceF_SetString (SF);
4896 val1 = SF->mont_num;
4897 } else {
4898 SUMA_ifree(ss);
4899 if (!(ss = SUMA_NI_get_ith_string(cs, ":", 1))) {
4900 SUMA_LH("No second number, assume 1");
4901 val2 = 1;
4902 } else if (SUMA_StringToNum(ss, (void *)&val2, 1, 1) != 1) {
4903 SUMA_BEEP;
4904 /* bad syntax, reset value*/
4905 if (LocalHead) fprintf (SUMA_STDERR, "%s: Bad syntax.\n", FuncName);
4906 SUMA_RegisterMessage (SUMAg_CF->MessageList,
4907 "Bad value in text field", FuncName,
4908 SMT_Error, SMA_Log);
4909 SUMA_SliceF_SetString (SF);
4910 val2 = SF->mont_inc;
4911 }
4912 }
4913 SUMA_ifree(ss);
4914
4915 if (val1 >= 0.0 && val2 >= 0.0) {
4916 if (SF->mont_num == val1 &&
4917 SF->mont_inc == val2) {
4918 SUMA_LH("Same value");
4919 SUMA_RETURNe;
4920 }
4921 SF->mont_num = val1;
4922 SF->mont_inc = val2;
4923 SUMA_SliceF_SetString (SF);
4924 }
4925
4926 if (DoCallBacks) {
4927 SUMA_set_mont((SUMA_ALL_DO *)SF->NewValueCallbackData, SF->variant,
4928 &val1, &val2, "text_field", 1);
4929 }
4930
4931 SUMA_RETURNe;
4932 }
4933
SUMA_SliceF_SetString(SUMA_SLICE_FIELD * SF)4934 void SUMA_SliceF_SetString (SUMA_SLICE_FIELD * SF)
4935 {
4936 static char FuncName[]={"SUMA_SliceF_SetString"};
4937 char buf[36];
4938
4939 SUMA_ENTRY;
4940
4941 if (SF->slice_units == SUMA_NO_NUM_UNITS) {
4942 sprintf (buf, "%-4d", (int)SF->slice_num);
4943 }else if (SF->slice_units == SUMA_MM_UNITS) {
4944 sprintf (buf, "%s",
4945 MV_format_fval2( SF->slice_num, 3));
4946 }else {
4947 /* fair enough, must be stringy */
4948 }
4949
4950 XtVaSetValues (SF->text, XmNvalue, buf, NULL);
4951 SUMA_RETURNe;
4952 }
4953
4954
4955 /*!
4956 \brief This function is called when the label field is activated by the user
4957 \*/
SUMA_TableF_cb_label_change(Widget w,XtPointer client_data,XtPointer call_data)4958 void SUMA_TableF_cb_label_change ( Widget w, XtPointer client_data,
4959 XtPointer call_data)
4960 {
4961 static char FuncName[]={"SUMA_TableF_cb_label_change"};
4962 SUMA_TABLE_FIELD *TF=NULL;
4963 float val;
4964 int N_words = 0;
4965 XmAnyCallbackStruct *cbs = (XmAnyCallbackStruct *) call_data;
4966 void *n=NULL;
4967 char *cs=NULL;
4968 int unt = SUMA_NO_NUM_UNITS;
4969 SUMA_Boolean DoCallBacks;
4970 SUMA_Boolean LocalHead = NOPE;
4971
4972 SUMA_ENTRY;
4973
4974 SUMA_LH("Called");
4975 /* make call to NewValue callback */
4976 TF = (SUMA_TABLE_FIELD *)client_data;
4977
4978 DoCallBacks = NOPE;
4979 if (call_data) {
4980 /* do the call backs if carriage return even if nothing is modified */
4981 if (LocalHead)
4982 fprintf (SUMA_STDERR,"%s: cbs->reason = %d (CR=%d)\n",
4983 FuncName, cbs->reason, XmCR_ACTIVATE);
4984 if (cbs->reason == XmCR_ACTIVATE) {
4985 DoCallBacks = YUP;
4986 }
4987 }
4988
4989 if (TF->cell_modified >= 0) {
4990 DoCallBacks = YUP; /* do the callbacks even if no carriage return ... */
4991 if (TF->type == SUMA_int || TF->type == SUMA_float) {
4992 /* Check if the string is numerical, and get unit */
4993 XtVaGetValues (w, XmNvalue, &n, NULL);
4994 cs = (char *)n;
4995 if (!cs || !strlen(cs)) {/* empty cell, leave it alone */
4996 TF->cell_modified = -1;
4997 SUMA_LHv("empty %s", cs);
4998 SUMA_RETURNe;
4999 } else {
5000 SUMA_COUNT_WORDS(cs, NULL, N_words);
5001 if (!N_words) { /* no harm, go back */
5002 TF->cell_modified = -1;
5003 SUMA_LHv("spacy %s", cs);
5004 SUMA_RETURNe;
5005 }
5006 }
5007 unt = SUMA_NumStringUnits(cs, 0);
5008 if (SUMA_StringToNum(cs, (void *)&val, 1, 1) != 1) {
5009 SUMA_BEEP;
5010 /* bad syntax, reset value*/
5011 if (LocalHead) fprintf (SUMA_STDERR, "%s: Bad syntax.\n", FuncName);
5012 SUMA_RegisterMessage (SUMAg_CF->MessageList,
5013 "Bad value in text field", FuncName,
5014 SMT_Error, SMA_Log);
5015 SUMA_TableF_SetString (TF);
5016 }else {
5017 if (TF->type == SUMA_int) {
5018 if (TF->num_value[TF->cell_modified] == (int)val &&
5019 TF->num_units == unt ) {
5020 SUMA_LH("Same value");
5021 TF->cell_modified = -1;
5022 SUMA_RETURNe;
5023 }
5024 TF->num_value[TF->cell_modified] = (int)val;
5025 } else if (TF->type == SUMA_float) {
5026 if (TF->num_value[TF->cell_modified] == val &&
5027 TF->num_units == unt) {
5028 SUMA_LH("Same value");
5029 TF->cell_modified = -1;
5030 SUMA_RETURNe;
5031 }
5032 TF->num_value[TF->cell_modified] = val;
5033 }
5034 SUMA_LH("Going to set string");
5035 TF->num_units = unt;
5036 SUMA_TableF_SetString (TF);
5037 }
5038 } else if (TF->type == SUMA_string) {
5039 XtVaGetValues (w, XmNvalue, &n, NULL);
5040 cs = (char *)n;
5041 if ( TF->str_value && TF->str_value[TF->cell_modified] &&
5042 !strcmp(TF->str_value[TF->cell_modified],cs)) {
5043 SUMA_LH("Same string");
5044 TF->cell_modified = -1;
5045 SUMA_RETURNe;
5046 }
5047 SUMA_LH("Here now, modified %d \n", TF->cell_modified);
5048 }
5049 } else {
5050 SUMA_LH("no cells modified");
5051 }
5052
5053 if (DoCallBacks) {
5054 SUMA_LH("CallBacks ...");
5055 if (TF->cell_modified < 0) {
5056 /* figure out which one, user insists on value */
5057 SUMA_WHICH_CELL(TF, w, TF->cell_modified);
5058 }
5059 if (!TF->NewValueCallbackData) {
5060 SUMA_LH("No Callback data.");
5061 if (TF->NewValueCallback) TF->NewValueCallback((void*)TF);
5062 } else {
5063 SUMA_LH("Callback data.");
5064 if (TF->NewValueCallback)
5065 TF->NewValueCallback(TF->NewValueCallbackData);
5066 }
5067 }
5068
5069 TF->cell_modified = -1;
5070 SUMA_RETURNe;
5071 }
5072
SUMA_SliceVal2ScalePos(SUMA_ALL_DO * ado,char * variant,float * val)5073 int SUMA_SliceVal2ScalePos (SUMA_ALL_DO *ado, char *variant, float *val)
5074 {
5075 static char FuncName[]={"SUMA_SliceVal2ScalePos"};
5076 int min_v=0, max_v=0, cv=0, scl=0, dec=0;
5077 float ftmp;
5078 Widget w = NULL;
5079 SUMA_X_SurfCont *SurfCont=NULL;
5080 SUMA_VOL_SAUX *VSaux=NULL;
5081 SUMA_Boolean LocalHead = NOPE;
5082
5083 SUMA_ENTRY;
5084
5085 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))
5086 || !(VSaux = SUMA_ADO_VSaux(ado)) || !variant) {
5087 SUMA_SL_Err("Null ado or no SurfCont"); SUMA_RETURN(0);
5088 }
5089 if (variant[0] == 'A') {
5090 w = SurfCont->Ax_slc->sl;
5091 } else if (variant[0] == 'S') {
5092 w = SurfCont->Sa_slc->sl;
5093 } else if (variant[0] == 'C') {
5094 w = SurfCont->Co_slc->sl;
5095 }
5096 if (!w) { SUMA_SL_Err("Null widget"); SUMA_RETURN(0); }
5097
5098 if (XtIsRealized(w)) {
5099 XtVaGetValues(w, XmNuserData, &dec, NULL);
5100 XtVaGetValues( w,
5101 XmNmaximum, &max_v,
5102 XmNminimum, &min_v,
5103 XmNvalue, &cv,
5104 XmNscaleMultiple, &scl,
5105 NULL);
5106 } else {
5107 SUMA_S_Note("Slider widget not realized"); SUMA_RETURN(0);
5108 }
5109
5110 if (*val < 0) { /* ignore sign */
5111 *val = -*val;
5112 }
5113 SUMA_LHv("min %d max %d scalemult %d decimals %d\nCurrent scale value %d\n",
5114 min_v, max_v, scl, dec, cv);
5115
5116 /* what is the new slider value to be ?*/
5117 ftmp = *val * pow(10.0, dec);
5118 if (ftmp > 0) cv = (int) (ftmp+0.5);
5119 else cv = (int) (ftmp-0.5);
5120
5121 /* Now check on the new cv */
5122 if (cv < min_v) {
5123 cv = min_v;
5124 /* must update threshold value in options structure*/
5125 *val = (float)cv / pow(10.0, dec);
5126 } else if (cv > max_v) {
5127 cv = max_v;
5128 *val = (float)cv / pow(10.0, dec);
5129 }
5130
5131 SUMA_RETURN(cv);
5132 }
5133
5134
5135 /*!
5136 threshold value to scale value (position)
5137 NOTE val's value might change if it is outside the slider range
5138 or if it is negative when the slider is in |T| mode
5139 */
SUMA_ThreshVal2ScalePos(SUMA_ALL_DO * ado,float * val)5140 int SUMA_ThreshVal2ScalePos(SUMA_ALL_DO *ado, float *val)
5141 {
5142 static char FuncName[]={"SUMA_ThreshVal2ScalePos"};
5143 int min_v=0, max_v=0, cv=0, scl=0, dec=0;
5144 float ftmp;
5145 Widget w = NULL;
5146 SUMA_X_SurfCont *SurfCont=NULL;
5147 SUMA_OVERLAYS *curColPlane=NULL;
5148 SUMA_Boolean LocalHead = NOPE;
5149
5150 SUMA_ENTRY;
5151
5152 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) {
5153 SUMA_SL_Err("Null ado or no SurfCont"); SUMA_RETURN(0);
5154 }
5155 curColPlane = SUMA_ADO_CurColPlane(ado);
5156 w = SurfCont->thr_sc;
5157 if (!w) { SUMA_SL_Err("Null widget"); SUMA_RETURN(0); }
5158
5159 if (XtIsRealized(w)) {
5160 XtVaGetValues(w, XmNuserData, &dec, NULL);
5161 XtVaGetValues( w,
5162 XmNmaximum, &max_v,
5163 XmNminimum, &min_v,
5164 XmNvalue, &cv,
5165 XmNscaleMultiple, &scl,
5166 NULL);
5167 } else {
5168 SUMA_S_Note("Slider widget not realized"); SUMA_RETURN(0);
5169 }
5170 if (*val < 0 &&
5171 curColPlane->OptScl->ThrMode == SUMA_ABS_LESS_THAN) {
5172 *val = -*val;
5173 }
5174 SUMA_LHv("min %d max %d scalemult %d decimals %d\nCurrent scale value %d\n",
5175 min_v, max_v, scl, dec, cv);
5176
5177 /* what is the new slider value to be ?*/
5178 ftmp = *val * pow(10.0, dec);
5179 if (ftmp > 0) cv = (int) (ftmp+0.5);
5180 else cv = (int) (ftmp-0.5);
5181
5182 /* Now check on the new cv */
5183 if (cv < min_v) {
5184 cv = min_v;
5185 /* must update threshold value in options structure*/
5186 *val = (float)cv / pow(10.0, dec);
5187 } else if (cv > max_v) {
5188 cv = max_v;
5189 *val = (float)cv / pow(10.0, dec);
5190 }
5191
5192 SUMA_RETURN(cv);
5193 }
5194
SUMA_Pval2ThreshVal(SUMA_ALL_DO * ado,double pval)5195 double SUMA_Pval2ThreshVal (SUMA_ALL_DO *ado, double pval)
5196 {
5197 static char FuncName[]={"SUMA_Pval2ThreshVal"};
5198 float p[3], zval = -1.0;
5199 int statcode;
5200 double val = 0.0;
5201 SUMA_X_SurfCont *SurfCont=NULL;
5202 SUMA_OVERLAYS *curColPlane=NULL;
5203 SUMA_Boolean LocalHead = NOPE;
5204
5205 SUMA_ENTRY;
5206
5207 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) {
5208 SUMA_SL_Err("Null ado or no SurfCont"); SUMA_RETURN(val);
5209 }
5210 curColPlane = SUMA_ADO_CurColPlane(ado);
5211
5212 if (!SurfCont ||
5213 !SurfCont->thr_sc ||
5214 !curColPlane ||
5215 !curColPlane->dset_link) {
5216 SUMA_SL_Err("NULL SurfCont or other things");
5217 SUMA_RETURN(val);
5218 }
5219
5220 /* see if you can get the stat codes */
5221 if (!SUMA_GetDsetColStatAttr(
5222 curColPlane->dset_link,
5223 curColPlane->OptScl->tind,
5224 &statcode,
5225 p, (p+1), (p+2))) {
5226 SUMA_LH("Error");
5227 }else if (statcode) {
5228 SUMA_LHv("Have stats at sb %d\n"
5229 "statcode %d: %f %f %f\n",
5230 curColPlane->OptScl->tind,
5231 statcode, p[0], p[1], p[2]);
5232 curColPlane->OptScl->ThreshStats[0] = pval;
5233 val = THD_pval_to_stat( pval , statcode , p ) ;
5234 SUMA_LHv("Have pval of %f\n"
5235 " val of %f\n",
5236 curColPlane->OptScl->ThreshStats[0],val);
5237 } else {
5238 /* no stats */
5239 curColPlane->OptScl->ThreshStats[0] = -1.0;
5240 curColPlane->OptScl->ThreshStats[1] = -1.0;
5241 }
5242
5243 SUMA_RETURN(val);
5244 }
5245
5246
5247 /*!
5248 set the threshold bar when a new value is entered
5249
5250 Crash note for suma in macosx_10.7_Intel_64 binaries.
5251
5252 With gcc 4.7.0 and 4.7.1, SUMA crashed when two hemispheres are loaded
5253 and the threshold level is changed for one hemisphere. Because of LR yoking
5254 the contralateral hemisphere is subject to the threshold change too.
5255 This works fine on all other binaries but with binaries from SARUMAN which use
5256 gcc 4.7.1, rather than the older gcc 4.2.1. The stack at the crash reliably pointed
5257 to SUMA_SetScaleThr_one(), right after the call to SUMA_ThreshVal2ScalePos().
5258 Debugging messages show that SUMA_ThreshVal2ScalePos() returns OK, but not even
5259 a simple statement can get printed right afterwards. Valgrind showed no relevant
5260 errors.
5261 To reproduce the problem, use the toy surfaces under std10_toy. Something like
5262 suma -spec std.10both.mini.spec , followed by ctrl+s and a few threshold adjustments
5263 is enough to cause the crash.
5264
5265 */
SUMA_SetScaleThr_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,float * val,int setmen,int redisplay)5266 int SUMA_SetScaleThr_one(SUMA_ALL_DO *ado, SUMA_OVERLAYS *colp,
5267 float *val, int setmen, int redisplay)
5268 {
5269 static char FuncName[]={"SUMA_SetScaleThr_one"};
5270 SUMA_ALL_DO *curDO = NULL;
5271 SUMA_TABLE_FIELD *TF=NULL;
5272 int cv=0;
5273 SUMA_X_SurfCont *SurfCont=NULL;
5274 SUMA_OVERLAYS *curColPlane=NULL;
5275 SUMA_Boolean LocalHead = NOPE;
5276
5277 SUMA_ENTRY;
5278
5279 SUMA_LH("Called");
5280
5281 if (!(SurfCont=SUMA_ADO_Cont(ado)) ||
5282 !SurfCont->SetThrScaleTable) SUMA_RETURN(0);
5283 curColPlane = SUMA_ADO_CurColPlane(ado);
5284 if (colp && colp != curColPlane) SUMA_RETURN(0);
5285
5286 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5287 SUMA_S_Err("Failed to get curDOp");
5288 SUMA_RETURN(0);
5289 }
5290 TF = SurfCont->SetThrScaleTable;
5291
5292 switch (TF->num_units) {
5293 case SUMA_P_VALUE_UNITS:
5294 if (LocalHead)
5295 fprintf( SUMA_STDERR,
5296 "%s:\nUnits in p value, transforming %f\n",
5297 FuncName, *val);
5298 /* transform value from P to threshold value */
5299 *val = (float)SUMA_Pval2ThreshVal (ado, (double)*val);
5300 if (LocalHead)
5301 fprintf( SUMA_STDERR,
5302 " to %f\n",
5303 *val);
5304 /* reset the units of the table to reflect new value,
5305 string containing new val is reset later on*/
5306 TF->num_units = SUMA_NO_NUM_UNITS;
5307 break;
5308 case SUMA_PERC_VALUE_UNITS:
5309 SUMA_LH("Units in percentile value, transforming %f\n", *val);
5310 *val = SUMA_OverlayPercentile(colp, 'T', *val);
5311 TF->num_units = SUMA_NO_NUM_UNITS;
5312 break;
5313 default:
5314 break;
5315 }
5316
5317 cv = SUMA_ThreshVal2ScalePos (ado, val );
5318
5319 if (LocalHead)
5320 fprintf(SUMA_STDERR,
5321 "%s:\nChecksums, new value is %f, cv to be set to %d\n"
5322 "val now %f\n",
5323 FuncName, TF->num_value[0], cv, *val);
5324
5325 /* TF->cell_modifed is not good when the call is made
5326 as a result of LR controller yoking. So don't bother using it.
5327 We only have one cell to be modified anyway. ZSS Sept 11 2012 */
5328
5329 /* check on value */
5330 if (TF->num_value[0] != *val) {
5331 /* a change in value (plateau effect) */
5332 TF->num_value[0] = *val;
5333 if (!setmen) setmen = 1;
5334 }
5335
5336 if (setmen) {
5337 SUMA_INSERT_CELL_VALUE(TF, 0, 0, *val);
5338 }
5339
5340 if (LocalHead)
5341 fprintf( SUMA_STDERR,
5342 "%s:\nSet thresholdiation, new value is %f\n",
5343 FuncName, *val);
5344 /* if value OK, set threshold bar*/
5345 curColPlane->OptScl->ThreshRange[0] = *val;
5346 XtVaSetValues(SurfCont->thr_sc,
5347 XmNvalue, cv,
5348 NULL);
5349
5350 SUMA_LHv("Colorize if necessary, redisplay=%d\n", redisplay);
5351 /* colorize if necessary */
5352 if ( redisplay == 0 ||
5353 (redisplay == 1 && !curColPlane->OptScl->UseThr) ) {
5354 SUMA_RETURN(0);
5355 } /* nothing else to do */
5356
5357
5358 SUMA_ADO_Flush_Pick_Buffer(ado, NULL);
5359
5360 SUMA_LH("Colorize");
5361 if (!SUMA_ColorizePlane (curColPlane)) {
5362 SUMA_SLP_Err("Failed to colorize plane.\n");
5363 SUMA_RETURN(0);
5364 }
5365
5366 SUMA_LH("Remix redisplay");
5367 SUMA_Remixedisplay(ado);
5368
5369 SUMA_UpdateNodeLblField(ado);
5370 SUMA_UpdatePvalueField( ado,
5371 curColPlane->OptScl->ThreshRange[0]);
5372 SUMA_RETURN(1);
5373 }
5374
SUMA_SetScaleThr(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,float * val,int setmen,int redisplay)5375 int SUMA_SetScaleThr(SUMA_ALL_DO *ado, SUMA_OVERLAYS *colp,
5376 float *val, int setmen, int redisplay)
5377 {
5378 static char FuncName[]={"SUMA_SetScaleThr"};
5379 SUMA_X_SurfCont *SurfCont=NULL;
5380 SUMA_OVERLAYS *curColPlane=NULL;
5381
5382 SUMA_Boolean LocalHead = NOPE;
5383
5384 SUMA_ENTRY;
5385
5386 SUMA_LH("Called");
5387
5388 SurfCont = SUMA_ADO_Cont(ado);
5389 curColPlane = SUMA_ADO_CurColPlane(ado);
5390 if (!ado || !SurfCont || !curColPlane) SUMA_RETURN(0);
5391
5392 if (colp && colp != curColPlane) SUMA_RETURN(0);
5393 colp = curColPlane;
5394
5395 if (!SUMA_SetScaleThr_one(ado, colp, val, setmen, redisplay)) SUMA_RETURN(0);
5396
5397 if (ado->do_type == SO_type) {
5398 SUMA_SurfaceObject *SOC=NULL, *SO = (SUMA_SurfaceObject *)ado;
5399 SUMA_OVERLAYS *colpC=NULL;
5400 /* do we have a contralateral SO and overlay? */
5401 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
5402 if (colpC && SOC) {
5403 SUMA_LHv("Found contralateral equivalent to:\n"
5404 " %s and %s in\n"
5405 " %s and %s\n",
5406 SO->Label, CHECK_NULL_STR(colp->Label),
5407 SOC->Label, CHECK_NULL_STR(colpC->Label));
5408 if (!SUMA_SetScaleThr_one((SUMA_ALL_DO *)SOC,
5409 colpC, val, 1, redisplay)) SUMA_RETURN(0);
5410 }
5411 }
5412 SUMA_RETURN(1);
5413 }
5414
SUMA_cb_SetScaleThr(void * data)5415 void SUMA_cb_SetScaleThr(void *data)
5416 {
5417 static char FuncName[]={"SUMA_cb_SetScaleThr"};
5418 SUMA_ALL_DO *ado=(SUMA_ALL_DO *)data, *curDO = NULL;
5419 SUMA_TABLE_FIELD *TF=NULL;
5420 int cv, max_v, min_v, cell_mod = -1;
5421 float val;
5422 SUMA_X_SurfCont *SurfCont=NULL;
5423 SUMA_OVERLAYS *curColPlane=NULL;
5424 SUMA_Boolean LocalHead = NOPE;
5425
5426 SUMA_ENTRY;
5427
5428 SUMA_LH("Called");
5429 if (!ado) SUMA_RETURNe;
5430 SurfCont = SUMA_ADO_Cont(ado);
5431 curColPlane = SUMA_ADO_CurColPlane(ado);
5432 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5433 SUMA_S_Err("Failed to get curDOp");
5434 SUMA_RETURNe;
5435 }
5436 TF = SurfCont->SetThrScaleTable;
5437 if (TF->cell_modified<0) SUMA_RETURNe;
5438 val = TF->num_value[TF->cell_modified];
5439
5440 SUMA_SetScaleThr(ado, NULL, &val, 0, 1);
5441
5442 SUMA_RETURNe;
5443 }
5444
5445 /*!
5446 \brief Sends the Focus triangle when new value is entered
5447 */
SUMA_TriInput(void * data)5448 void SUMA_TriInput (void *data)
5449 {
5450 static char FuncName[]={"SUMA_TriInput"};
5451 SUMA_ALL_DO *ado=(SUMA_ALL_DO *)data, *curDO=NULL;
5452 SUMA_SurfaceObject *SO=NULL, *curSO = NULL;
5453 SUMA_TABLE_FIELD *TF=NULL;
5454 int i, n, j;
5455 void *cv=NULL;
5456 float fv3[3];
5457 char str[100];
5458 SUMA_X_SurfCont *SurfCont=NULL;
5459 SUMA_Boolean LocalHead = NOPE;
5460
5461 SUMA_ENTRY;
5462
5463 SUMA_LH("Called");
5464 SurfCont = SUMA_ADO_Cont(ado);
5465 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5466 SUMA_S_Err("Failed to get curDOp");
5467 SUMA_RETURNe;
5468 }
5469
5470 if (ado->do_type != SO_type || curDO->do_type != SO_type) {
5471 SUMA_S_Err("Should not call this");
5472 SUMA_RETURNe;
5473 }
5474 SO = (SUMA_SurfaceObject *)ado;
5475 curSO = (SUMA_SurfaceObject *)curDO;
5476
5477 TF = SO->SurfCont->FaceTable;
5478 if (TF->cell_modified<0) SUMA_RETURNe;
5479 n = TF->cell_modified;
5480 i = n % TF->Ni;
5481 j = n / TF->Ni;
5482
5483 if ((int)TF->num_value[n] < 0 || (int)TF->num_value[n] >= curSO->N_FaceSet) {
5484 SUMA_SLP_Err("Triangle index n must be positive\n"
5485 "and less than the number of nodes \n"
5486 "forming the surface.\n");
5487 TF->num_value[n] = SO->SelectedFaceSet;
5488 SUMA_TableF_SetString (TF);
5489 TF->cell_modified = -1;
5490 SUMA_RETURNe;
5491 }
5492
5493 switch (j) {
5494 case 1:
5495 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
5496 if (LocalHead) {
5497 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s, Tri = %d\n",
5498 FuncName, i, j, (char *)cv, (int)TF->num_value[n]);
5499 }
5500
5501 /* look for a viewer that is showing this surface and
5502 has this surface in focus*/
5503 for (i=0; i<SUMAg_N_SVv; ++i) {
5504 SUMA_LHv("Checking viewer %d.\n", i);
5505 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
5506 /* is this viewer showing curSO ? */
5507 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv,
5508 (SUMA_ALL_DO *)curSO)) {
5509 if (SUMA_SV_Focus_SO(&(SUMAg_SVv[i])) == curSO) {
5510 SUMA_JumpFocusFace((char *)cv, (void *)(&(SUMAg_SVv[i])));
5511 }
5512 }
5513 }
5514 }
5515 break;
5516 default:
5517 SUMA_SL_Err("Should not get this input");
5518 break;
5519 }
5520 SUMA_RETURNe;
5521 }
5522 /*!
5523 \brief Sends the node/datum flying when new value is entered
5524 */
SUMA_NodeInput(void * data)5525 void SUMA_NodeInput (void *data)
5526 {
5527 static char FuncName[]={"SUMA_NodeInput"};
5528 SUMA_ALL_DO *ado=(SUMA_ALL_DO *)data, *curDO = NULL;
5529 SUMA_TABLE_FIELD *TF=NULL;
5530 int i, n, j;
5531 void *cv=NULL;
5532 float fv3[3];
5533 char str[100];
5534 SUMA_X_SurfCont *SurfCont=NULL;
5535 SUMA_Boolean LocalHead = NOPE;
5536
5537 SUMA_ENTRY;
5538
5539 SUMA_LH("Called");
5540
5541 SurfCont = SUMA_ADO_Cont(ado);
5542
5543 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5544 SUMA_S_Err("Failed to get curDOp");
5545 SUMA_RETURNe;
5546 }
5547 TF = SurfCont->NodeTable;
5548 if (TF->cell_modified<0) SUMA_RETURNe;
5549 n = TF->cell_modified;
5550 i = n % TF->Ni;
5551 j = n / TF->Ni;
5552
5553 if ((int)TF->num_value[n] < 0 ||
5554 (int)TF->num_value[n] > SUMA_ADO_Max_Datum_Index(ado)) {
5555 SUMA_SLP_Err("Node/Voxel/etc index must be positive and \n"
5556 "less than the number of nodes \n"
5557 "forming the surface.\n");
5558 TF->num_value[n] = SUMA_ADO_SelectedDatum(ado, NULL, NULL);
5559 SUMA_TableF_SetString (TF);
5560 TF->cell_modified = -1;
5561 SUMA_RETURNe;
5562 }
5563 if (ado->do_type == MASK_type) {
5564 SUMA_S_Warn("Have not dealt with masks yet");
5565 SUMA_RETURNe;
5566 }
5567 switch (j) {
5568 case 1:
5569 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
5570 if (LocalHead) {
5571 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s, node = %d\n",
5572 FuncName, i, j, (char *)cv, (int)TF->num_value[n]);
5573 }
5574
5575 /* look for a viewer that is showing this surface and
5576 has this surface in focus*/
5577 for (i=0; i<SUMAg_N_SVv; ++i) {
5578 SUMA_LHv("Checking viewer %d.\n", i);
5579 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
5580 /* is this viewer showing curSO ? */
5581 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv,
5582 curDO)) {
5583 if (SUMA_SV_Focus_ADO(&(SUMAg_SVv[i])) == curDO) {
5584 SUMA_JumpIndex((char *)cv, (void *)(&(SUMAg_SVv[i])));
5585 }
5586 }
5587 }
5588 }
5589 break;
5590 case 2:
5591 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
5592 if (LocalHead) {
5593 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s, node = %d\n",
5594 FuncName, i, j, (char *)cv, (int)TF->num_value[n]);
5595 }
5596 switch (ado->do_type) {
5597 case TRACT_type:
5598 for (i=0; i<SUMAg_N_SVv; ++i) {
5599 SUMA_LHv("Checking viewer %d.\n", i);
5600 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
5601 /* is this viewer showing curDO ? */
5602 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv,
5603 curDO)) {
5604 if (SUMA_SV_Focus_ADO(&(SUMAg_SVv[i])) == curDO) {
5605 SUMA_JumpIndex((char *)cv,
5606 (void *)(&(SUMAg_SVv[i])));
5607 }
5608 }
5609 }
5610 }
5611 break;
5612 default:
5613 SUMA_LH("Nothing to do here");
5614 break;
5615 }
5616 break;
5617 default:
5618 SUMA_SL_Err("Should not get this input");
5619 break;
5620 }
5621 SUMA_RETURNe;
5622 }
5623
5624
SUMA_IJKInput(void * data)5625 void SUMA_IJKInput(void *data) {
5626 SUMA_TpointInput (data);
5627 return;
5628 }
5629 /*!
5630 \brief Sends the node/datum flying when new value is entered
5631 */
SUMA_TpointInput(void * data)5632 void SUMA_TpointInput (void *data)
5633 {
5634 static char FuncName[]={"SUMA_TpointInput"};
5635 SUMA_ALL_DO *ado=(SUMA_ALL_DO *)data, *curDO = NULL;
5636 SUMA_TABLE_FIELD *TF=NULL;
5637 int i, n, j;
5638 void *cv=NULL;
5639 float fv3[3];
5640 char str[100];
5641 SUMA_X_SurfCont *SurfCont=NULL;
5642 SUMA_Boolean LocalHead = NOPE;
5643
5644 SUMA_ENTRY;
5645
5646 SUMA_LH("Called");
5647
5648 SurfCont = SUMA_ADO_Cont(ado);
5649
5650 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5651 SUMA_S_Err("Failed to get curDOp");
5652 SUMA_RETURNe;
5653 }
5654 TF = SurfCont->FaceTable;
5655 if (TF->cell_modified<0) SUMA_RETURNe;
5656 n = TF->cell_modified;
5657 i = n % TF->Ni;
5658 j = n / TF->Ni;
5659
5660 switch (j) {
5661 case 1:
5662 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
5663 if (LocalHead) {
5664 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s\n",
5665 FuncName, i, j, (char *)cv);
5666 }
5667
5668 /* look for a viewer that is showing this surface and
5669 has this surface in focus*/
5670 for (i=0; i<SUMAg_N_SVv; ++i) {
5671 SUMA_LHv("Checking viewer %d.\n", i);
5672 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
5673 /* is this viewer showing curSO ? */
5674 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv,
5675 curDO)) {
5676 if (SUMA_SV_Focus_ADO(&(SUMAg_SVv[i])) == curDO) {
5677 SUMA_JumpIndex((char *)cv, (void *)(&(SUMAg_SVv[i])));
5678 }
5679 }
5680 }
5681 }
5682 break;
5683 default:
5684 SUMA_SL_Err("Should not get this input");
5685 break;
5686 }
5687 SUMA_RETURNe;
5688 }
5689
5690 /* What happens when you select a graph's node?
5691 THis is parallel to SUMA_TriInput */
SUMA_GNodeInput(void * data)5692 void SUMA_GNodeInput (void *data)
5693 {
5694 static char FuncName[]={"SUMA_GNodeInput"};
5695 SUMA_ALL_DO *ado=(SUMA_ALL_DO *)data, *curDO = NULL;
5696 SUMA_TABLE_FIELD *TF=NULL;
5697 int i, n, j;
5698 void *cv=NULL;
5699 float fv3[3];
5700 char str[100];
5701 SUMA_X_SurfCont *SurfCont=NULL;
5702 SUMA_GRAPH_SAUX *GSaux=NULL;
5703 SUMA_DSET *dset = NULL;
5704
5705 SUMA_Boolean LocalHead = NOPE;
5706
5707 SUMA_ENTRY;
5708
5709 SUMA_LH("Called");
5710
5711 if (!ado || ado->do_type != GRAPH_LINK_type) {
5712 SUMA_S_Err("NULL/bad input");
5713 SUMA_RETURNe;
5714 }
5715 dset = SUMA_find_GLDO_Dset((SUMA_GraphLinkDO*)ado);
5716 GSaux = SDSET_GSAUX(dset);
5717
5718 SurfCont = SUMA_ADO_Cont(ado);
5719
5720 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5721 SUMA_S_Err("Failed to get curDOp");
5722 SUMA_RETURNe;
5723 }
5724 TF = SurfCont->FaceTable;
5725 if (TF->cell_modified<0) SUMA_RETURNe;
5726 n = TF->cell_modified;
5727 i = n % TF->Ni;
5728 j = n / TF->Ni;
5729
5730 if ((int)TF->num_value[n] < 0 ||
5731 (int)TF->num_value[n] < dset->Aux->range_node_index[0] ||
5732 (int)TF->num_value[n] > dset->Aux->range_node_index[1]) {
5733 SUMA_SLP_Err("Node index must be positive and \n"
5734 "less than the number of nodes \n"
5735 "forming the surface.\n");
5736 TF->num_value[n] = GSaux->PR->iAltSel[SUMA_ENODE_0];
5737 SUMA_TableF_SetString (TF);
5738 TF->cell_modified = -1;
5739 SUMA_RETURNe;
5740 }
5741
5742 switch (j) {
5743 case 1:
5744 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
5745 if (LocalHead) {
5746 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s, node = %d\n",
5747 FuncName, i, j, (char *)cv, (int)TF->num_value[n]);
5748 }
5749
5750 for (i=0; i<SUMAg_N_SVv; ++i) {
5751 SUMA_LHv("Checking viewer %d.\n", i);
5752 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
5753 /* is this viewer showing curSO ? */
5754 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv,
5755 curDO)) {
5756 if (SUMA_SV_Focus_ADO(&(SUMAg_SVv[i])) == curDO) {
5757 /* FocusFace works for this one too */
5758 SUMA_JumpFocusFace((char *)cv,
5759 (void *)(&(SUMAg_SVv[i])));
5760 }
5761 }
5762 }
5763 }
5764 break;
5765 default:
5766 SUMA_SL_Err("Should not get this input");
5767 break;
5768 }
5769 SUMA_RETURNe;
5770 }
5771 /*!
5772 \brief Sends the cross hair flying when new value is entered
5773 */
SUMA_XhairInput(void * data)5774 void SUMA_XhairInput (void* data)
5775 {
5776 static char FuncName[]={"SUMA_XhairInput"};
5777 SUMA_ALL_DO *ado=(SUMA_ALL_DO *)data, *curDO = NULL;
5778 SUMA_X_SurfCont *SurfCont=NULL;
5779 SUMA_SurfaceViewer *sv=NULL;
5780 SUMA_TABLE_FIELD *TF=NULL;
5781 int i, n, j;
5782 void *cv=NULL;
5783 float fv3[3];
5784 char str[100];
5785 SUMA_Boolean LocalHead = NOPE;
5786
5787 SUMA_ENTRY;
5788
5789 SUMA_LH("Called");
5790 SurfCont = SUMA_ADO_Cont(ado);
5791
5792 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
5793 SUMA_S_Err("Failed to get curDOp");
5794 SUMA_RETURNe;
5795 }
5796 TF = SurfCont->XhairTable;
5797 if (TF->cell_modified<0) SUMA_RETURNe;
5798 SUMA_LH("Cell modified, modifying ...");
5799 n = TF->cell_modified;
5800 i = n % TF->Ni;
5801 j = n / TF->Ni;
5802 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
5803 if (LocalHead) {
5804 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s\n",
5805 FuncName, i, j, (char *)cv);
5806 }
5807 /* Now parse that string into 3 numbers */
5808 if (SUMA_StringToNum ((char *)cv, (void *)fv3, 3,1) != 3) {
5809 SUMA_BEEP;
5810 str[0]='\0';
5811 } else {
5812 SUMA_XHAIR_STRING(fv3, str);
5813 }
5814 XtVaSetValues(TF->cells[n], XmNvalue, str, NULL);
5815
5816 /* look for a viewer that is showing this surface */
5817 for (i=0; i<SUMAg_N_SVv; ++i) {
5818 if (LocalHead)
5819 fprintf (SUMA_STDERR,"%s: Checking viewer %d.\n", FuncName, i);
5820 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
5821 /* is this viewer showing curDO ? */
5822 sv = &(SUMAg_SVv[i]);
5823 if (SUMA_isVisibleDO(sv, SUMAg_DOv, curDO)) {
5824 /* is this a new coordinate?
5825 Avoid calls due to cosmetic text changes */
5826 if (sv->Ch->c[0] != fv3[0] ||
5827 sv->Ch->c[1] != fv3[1] || sv->Ch->c[2] != fv3[2]) {
5828 if (LocalHead) fprintf(SUMA_STDERR,
5829 "%s: Calling for jump to %s\n",
5830 FuncName, str);
5831 SUMA_JumpXYZ(str, (void *)(&(SUMAg_SVv[i])));
5832 }
5833 }
5834 }
5835 }
5836 SUMA_RETURNe;
5837 }
5838
5839
5840 #define SETMEN (setmen > 1 || (setmen && isCur))
5841 #define REDISP (redisplay > 1 || (redisplay && NewDisp))
5842
SUMA_SetRangeValueNew_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int row,int col,float v1,float v2,int setmen,int redisplay,float * reset,SUMA_NUMERICAL_UNITS num_units)5843 int SUMA_SetRangeValueNew_one(SUMA_ALL_DO *ado,
5844 SUMA_OVERLAYS *colp,
5845 int row, int col,
5846 float v1, float v2,
5847 int setmen,
5848 int redisplay, float *reset,
5849 SUMA_NUMERICAL_UNITS num_units)
5850 {
5851 static char FuncName[]={"SUMA_SetRangeValueNew_one"};
5852 int NewDisp=0, isCur=0;
5853 SUMA_X_SurfCont *SurfCont=NULL;
5854 SUMA_OVERLAYS *curColPlane=NULL;
5855 SUMA_TABLE_FIELD *TF=NULL;
5856 SUMA_Boolean LocalHead = NOPE;
5857
5858 SUMA_ENTRY;
5859
5860 if (LocalHead) {
5861 SUMA_DUMP_TRACE("Who called SUMA_SetRangeValueNew_one?");
5862 }
5863
5864 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado)) ||
5865 !SurfCont->SetRangeTable || !reset) {
5866 SUMA_RETURN(0);
5867 }
5868 curColPlane = SUMA_ADO_CurColPlane(ado);
5869 if (!colp) colp = curColPlane;
5870
5871 if (colp && colp == curColPlane) {
5872 isCur=YUP;
5873 } else {
5874 isCur=NOPE;
5875 }
5876
5877 if (!colp) {
5878 SUMA_RETURN(0); /* not much to do */
5879 }
5880
5881 if (colp->SymIrange) { /* must set table fields in this case */
5882 if (!setmen) setmen = 1;
5883 }
5884
5885 TF = SurfCont->SetRangeTable;
5886 if (!TF) setmen = 0; /* can't set nothing */
5887
5888 if (num_units == SUMA_PERC_VALUE_UNITS) {
5889 float pr[2], prv[2], *Vsort=NULL;
5890
5891 /* Update, because for colorization (I) column, both colp->V
5892 and colp->Vperc get clamped by range */
5893 if (!SUMA_SetOverlay_Vecs(colp, 'V', colp->OptScl->find,
5894 "reset", 1)) {
5895 SUMA_S_Err("Failed to set overlay vecs");
5896 SUMA_RETURN(0);
5897 }
5898
5899 if (v2 < v1) v2 = v1;
5900 pr[0] = v1; pr[1] = v2;
5901 /* some safety checks */
5902 if (pr[1]<pr[0]) pr[1] = pr[0]+1;
5903 if (pr[1] > 100.0) pr[1] = 100.0;
5904 if (pr[0] < 0.0) pr[0] = 0.0;
5905
5906 #if 0 /* old but works */
5907 if (!colp->V) {
5908 SUMA_S_Err("Cannot do percentiles without colp->V");
5909 SUMA_RETURN(0);
5910 }
5911 if (!(Vsort = SUMA_PercRangeVol(colp->V, NULL, colp->N_V, pr, 2, prv,
5912 NULL, colp->OptScl->MaskZero, NULL))) {
5913 SUMA_S_Err("Failed to get perc. range");
5914 SUMA_RETURN(0);
5915 }
5916 SUMA_ifree(Vsort);
5917 #else
5918 prv[0] = SUMA_OverlayPercentile (colp, 'V', pr[0]);
5919 prv[1] = SUMA_OverlayPercentile (colp, 'V', pr[1]);
5920 #endif
5921
5922 SUMA_LH("Computed percentiles %f %f-->%f %f",
5923 pr[0], pr[1], prv[0], prv[1]);
5924 v1 = prv[0]; v2 = prv[1];
5925
5926 /* Need to update the value in the table struct */
5927 if (TF) ++setmen;
5928
5929 /* Remove percentile units */
5930 if (TF) TF->num_units = SUMA_NO_NUM_UNITS;
5931 }
5932
5933 NewDisp = NOPE;
5934 /* What are we dealing with ? */
5935 switch (row) {
5936 case 1: /* That's the Int. range */
5937 SUMA_LHv("Setting Int. Range, isCur=%d [%d %d] sym %d\n",
5938 isCur, row, col, colp->SymIrange);
5939 if (col == 1) { /* the min value */
5940 if (colp->SymIrange) {
5941 colp->OptScl->IntRange[0] = -fabs((double)v1);
5942 colp->OptScl->IntRange[1] = -colp->OptScl->IntRange[0];
5943 if (SETMEN) {
5944 SUMA_LHv("Inserting cell values %f and %f\n",
5945 colp->OptScl->IntRange[0], colp->OptScl->IntRange[1]);
5946 SUMA_INSERT_CELL_VALUE(TF, row, 1,
5947 colp->OptScl->IntRange[0]);
5948 SUMA_INSERT_CELL_VALUE(TF, row, 2,
5949 colp->OptScl->IntRange[1]);
5950 }
5951 } else {
5952 if (v1 > colp->OptScl->IntRange[1]) {
5953 *reset = colp->OptScl->IntRange[0];
5954 SUMA_RETURN(-1);
5955 } else {
5956 if (LocalHead)
5957 fprintf (SUMA_STDERR,"%s: IntRange[0] was %f, will be %f\n",
5958 FuncName, colp->OptScl->IntRange[0],
5959 v1);
5960 colp->OptScl->IntRange[0] = v1;
5961 if (SETMEN) {
5962 SUMA_INSERT_CELL_VALUE(TF, row, 1,
5963 colp->OptScl->IntRange[0]);
5964 }
5965 }
5966 }
5967 } else if (col==2) {
5968 if (colp->SymIrange) {
5969 colp->OptScl->IntRange[1] = fabs((double)v1);
5970 colp->OptScl->IntRange[0] = -colp->OptScl->IntRange[1];
5971 if (SETMEN) {
5972 SUMA_INSERT_CELL_VALUE(TF, row, 1,
5973 colp->OptScl->IntRange[0]);
5974 SUMA_INSERT_CELL_VALUE(TF, row, 2,
5975 colp->OptScl->IntRange[1]);
5976 }
5977 } else {
5978 if (v1 < colp->OptScl->IntRange[0]) {
5979 *reset = colp->OptScl->IntRange[1];
5980 SUMA_RETURN(-2);
5981 } else {
5982 colp->OptScl->IntRange[1] = v1;
5983 if (SETMEN) {
5984 SUMA_INSERT_CELL_VALUE(TF, row, 2,
5985 colp->OptScl->IntRange[1]);
5986 }
5987 }
5988 }
5989 } else if (col==-1) {
5990 if (v1 > v2) {
5991 SUMA_S_Errv("Bad range %f %f\n", v1, v2);
5992 SUMA_RETURN(-3);
5993 } else {
5994 colp->OptScl->IntRange[0] = v1;
5995 colp->OptScl->IntRange[1] = v2;
5996 if (SETMEN) {
5997 SUMA_INSERT_CELL_VALUE(TF, row, 1,
5998 colp->OptScl->IntRange[0]);
5999 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6000 colp->OptScl->IntRange[1]);
6001 }
6002 }
6003 } else { SUMA_SL_Err("What's going on John ?"); }
6004 if (isCur && colp->ShowMode > 0) NewDisp = YUP;
6005 break;
6006 case 2: /* That's the Brt.. range */
6007 SUMA_LH("Setting Brt. Range");
6008 if (col == 1) {
6009 if (v1 > colp->OptScl->BrightRange[1]) {
6010 *reset = colp->OptScl->BrightRange[0];
6011 SUMA_RETURN(-1);
6012 } else {
6013 colp->OptScl->BrightRange[0] = v1;
6014 if (SETMEN) {
6015 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6016 colp->OptScl->BrightRange[0]);
6017 }
6018 }
6019 } else if (col==2) {
6020 if (v1 < colp->OptScl->BrightRange[0]) {
6021 *reset = colp->OptScl->BrightRange[1];
6022 SUMA_RETURN(-2);
6023 } else {
6024 colp->OptScl->BrightRange[1] = v1;
6025 if (SETMEN) {
6026 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6027 colp->OptScl->BrightRange[1]);
6028 }
6029 }
6030 } else if (col == -1) {
6031 if (v1 > v2) {
6032 SUMA_S_Errv("Bad range %f %f\n", v1, v2);
6033 SUMA_RETURN(-3);
6034 } else {
6035 colp->OptScl->BrightRange[0] = v1;
6036 colp->OptScl->BrightRange[1] = v2;
6037 if (SETMEN) {
6038 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6039 colp->OptScl->BrightRange[0]);
6040 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6041 colp->OptScl->BrightRange[1]);
6042 }
6043 }
6044 } else { SUMA_SL_Err("What's going on Ron ?"); }
6045 if (isCur && colp->OptScl->UseBrt) NewDisp = YUP;
6046 break;
6047 case 3: /* That's the Brt. Map Range */
6048 SUMA_LH("Setting BrtMap. Range");
6049 if (col == 1) {
6050 if (v1 > colp->OptScl->BrightMap[1]) {
6051 *reset = colp->OptScl->BrightMap[0];
6052 SUMA_RETURN(-1);
6053 } else if (v1 < 0) {
6054 *reset = colp->OptScl->BrightMap[0];
6055 SUMA_RETURN(-1);
6056 } else {
6057 colp->OptScl->BrightMap[0] = v1;
6058 if (SETMEN) {
6059 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6060 colp->OptScl->BrightMap[0]);
6061 }
6062 }
6063 } else if (col==2) {
6064 if (v1 < colp->OptScl->BrightMap[0]) {
6065 *reset = colp->OptScl->BrightMap[1];
6066 SUMA_RETURN(-2);
6067 } else {
6068 colp->OptScl->BrightMap[1] = v1;
6069 if (SETMEN) {
6070 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6071 colp->OptScl->BrightMap[1]);
6072 }
6073 }
6074 } else if (col == -1) {
6075 if (v1 > v2 || v1 < 0) {
6076 SUMA_S_Errv("Bad range %f %f\n", v1, v2);
6077 SUMA_RETURN(-3);
6078 } else {
6079 colp->OptScl->BrightMap[0] = v1;
6080 colp->OptScl->BrightMap[1] = v2;
6081 if (SETMEN) {
6082 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6083 colp->OptScl->BrightMap[0]);
6084 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6085 colp->OptScl->BrightMap[1]);
6086 }
6087 }
6088 } else { SUMA_SL_Err("What's going on Mon ?"); }
6089 if (isCur && colp->OptScl->UseBrt) NewDisp = YUP;
6090 break;
6091 case 4: /* That's the coordinate bias Range */
6092 SUMA_LH("Setting CoordBias. Range");
6093 if (col == 1) {
6094 if (v1 > colp->OptScl->CoordBiasRange[1]) {
6095 *reset = colp->OptScl->CoordBiasRange[0];
6096 SUMA_RETURN(-1);
6097 } else { /* OK */
6098 colp->OptScl->CoordBiasRange[0] = v1;
6099 if (SETMEN) {
6100 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6101 colp->OptScl->CoordBiasRange[0]);
6102 }
6103 }
6104 } else if (col==2) {
6105 if (v1 < colp->OptScl->CoordBiasRange[0]) {
6106 *reset = colp->OptScl->CoordBiasRange[1];
6107 SUMA_RETURN(-2);
6108 } else { /* OK */
6109 colp->OptScl->CoordBiasRange[1] = v1;
6110 if (SETMEN) {
6111 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6112 colp->OptScl->CoordBiasRange[1]);
6113 }
6114 }
6115 } else if (col == -1) {
6116 if (v1 > v2) {
6117 SUMA_S_Errv("Bad range %f %f\n", v1, v2);
6118 SUMA_RETURN(-3);
6119 } else {
6120 colp->OptScl->CoordBiasRange[0] = v1;
6121 colp->OptScl->CoordBiasRange[1] = v2;
6122 if (SETMEN) {
6123 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6124 colp->OptScl->CoordBiasRange[0]);
6125 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6126 colp->OptScl->CoordBiasRange[1]);
6127 }
6128 }
6129 } else { SUMA_SL_Err("What's going on Hon ?"); }
6130 if (isCur) NewDisp = YUP;
6131 /* You might want to disable this feature if the colp
6132 is not shown */
6133 break;
6134 default:
6135 SUMA_SL_Err("You make me sick");
6136 break;
6137 }
6138
6139 /* Now, you need to redraw the deal */
6140 if (REDISP) {
6141 SUMA_ColorizePlane(curColPlane);
6142 SUMA_Remixedisplay(ado);
6143 }
6144
6145 /* update the Xhair Info block */
6146 if (curColPlane->OptScl->DoBias != SW_CoordBias_None) {
6147 SUMA_UpdateNodeNodeField(ado);
6148 }
6149 SUMA_UpdateNodeLblField(ado);
6150
6151 SUMA_RETURN(1);
6152 }
6153
SUMA_SetRangeValueNew(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int row,int col,float v1,float v2,int setmen,int redisplay,float * reset,SUMA_NUMERICAL_UNITS num_units)6154 int SUMA_SetRangeValueNew (SUMA_ALL_DO *ado,
6155 SUMA_OVERLAYS *colp,
6156 int row, int col,
6157 float v1, float v2,
6158 int setmen,
6159 int redisplay, float *reset,
6160 SUMA_NUMERICAL_UNITS num_units)
6161 {
6162 static char FuncName[]={"SUMA_SetRangeValueNew"};
6163 int NewDisp=0, an=0;
6164 SUMA_Boolean LocalHead = NOPE;
6165
6166 SUMA_ENTRY;
6167
6168 if (LocalHead) {
6169 fprintf(SUMA_STDERR,
6170 "%s:\n request to switch range \n", FuncName);
6171 }
6172
6173 an = SUMA_SetRangeValueNew_one(ado, colp, row, col,
6174 v1, v2, setmen,
6175 redisplay, reset, num_units);
6176 if (an <= 0) SUMA_RETURN(an);
6177
6178 if (ado->do_type == SO_type) {
6179 SUMA_SurfaceObject *SOC=NULL, *SO = (SUMA_SurfaceObject *)ado;
6180 SUMA_OVERLAYS *colpC=NULL;
6181 /* do we have a contralateral SO and overlay? */
6182 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
6183 if (colpC && SOC) {
6184 SUMA_LHv("Found contralateral equivalent to:\n"
6185 " %s and %s in\n"
6186 " %s and %s\n",
6187 SO->Label, CHECK_NULL_STR(colp->Label),
6188 SOC->Label, CHECK_NULL_STR(colpC->Label));
6189 an = SUMA_SetRangeValueNew_one((SUMA_ALL_DO *)SOC, colpC, row, col,
6190 v1, v2, 1,
6191 redisplay, reset, num_units);
6192 }
6193 }
6194
6195 SUMA_RETURN(an);
6196 }
6197
6198
SUMA_cb_SetRangeValue(void * data)6199 void SUMA_cb_SetRangeValue (void *data)
6200 {
6201 static char FuncName[]={"SUMA_cb_SetRangeValue"};
6202 SUMA_SRV_DATA srvdC, *srvd=NULL;
6203 SUMA_ALL_DO *ado=NULL;
6204 SUMA_OVERLAYS *colp=NULL;
6205 int n=-1,row=-1,col=-1, an=0;
6206 float reset = 0.0;
6207 void *cv=NULL;
6208 SUMA_TABLE_FIELD *TF=NULL;
6209 SUMA_X_SurfCont *SurfCont=NULL;
6210 SUMA_OVERLAYS *curColPlane=NULL;
6211 SUMA_Boolean LocalHead = NOPE;
6212
6213 SUMA_ENTRY;
6214
6215 if (LocalHead) {
6216 fprintf(SUMA_STDERR,
6217 "%s:\n request to switch range \n", FuncName);
6218 }
6219 if (!(srvd = (SUMA_SRV_DATA *)data)) SUMA_RETURNe;
6220 ado = srvd->ado; colp = srvd->colp;
6221 if (!ado) SUMA_RETURNe;
6222 SurfCont = SUMA_ADO_Cont(ado);
6223 curColPlane = SUMA_ADO_CurColPlane(ado);
6224
6225 if (!colp) colp = curColPlane;
6226
6227 TF = SurfCont->SetRangeTable;
6228 if (TF->cell_modified<0) SUMA_RETURNe;
6229 n = TF->cell_modified;
6230 row = n % TF->Ni;
6231 col = n / TF->Ni;
6232 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
6233 if (LocalHead) {
6234 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s\n",
6235 FuncName, row, col, (char *)cv);
6236 }
6237
6238 an = SUMA_SetRangeValueNew(ado, colp, row, col,
6239 TF->num_value[n], 0.0,
6240 0, 1, &reset, TF->num_units);
6241 if (an < 0) {
6242 if (an == -1 || an == -2) {
6243 SUMA_BEEP;
6244 TF->num_value[n] = reset;
6245 SUMA_TableF_SetString(TF);
6246 if (an == -1) { SUMA_SLP_Err("Lower bound > Upper bound!"); }
6247 else { SUMA_SLP_Err("Upper bound < Lower bound!"); }
6248 } else {
6249 SUMA_S_Err("Erriosity");
6250 }
6251 }
6252
6253 SUMA_RETURNe;
6254 }
6255
SUMA_SetClustValue_one(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int row,int col,float v1,float v2,int setmen,int redisplay,float * reset)6256 int SUMA_SetClustValue_one(SUMA_ALL_DO *ado,
6257 SUMA_OVERLAYS *colp,
6258 int row, int col,
6259 float v1, float v2,
6260 int setmen,
6261 int redisplay, float *reset)
6262 {
6263 static char FuncName[]={"SUMA_SetClustValue_one"};
6264 int NewDisp=0, isCur=0;
6265 SUMA_X_SurfCont *SurfCont=NULL;
6266 SUMA_OVERLAYS *curColPlane=NULL;
6267 SUMA_Boolean LocalHead = NOPE;
6268 SUMA_TABLE_FIELD *TF=NULL;
6269
6270 SUMA_ENTRY;
6271
6272 if (!ado || !(SurfCont=SUMA_ADO_Cont(ado)) ||
6273 !SurfCont->SetClustTable || !reset) {
6274 SUMA_RETURN(0);
6275 }
6276 curColPlane = SUMA_ADO_CurColPlane(ado);
6277 if (!colp) colp = curColPlane;
6278
6279 if (colp && colp == curColPlane) {
6280 isCur=YUP;
6281 } else {
6282 isCur=NOPE;
6283 }
6284
6285 if (!colp) {
6286 SUMA_RETURN(0); /* not much to do */
6287 }
6288
6289
6290 TF = SurfCont->SetClustTable;
6291 if (!TF) setmen = 0; /* can't set nothing */
6292
6293 NewDisp = NOPE;
6294 /* What are we dealing with ? */
6295 switch (row) {
6296 case 1: /* That's the Int. range */
6297 SUMA_LHv("Setting Clust params isCur=%d [%d %d]\n",
6298 isCur, row, col);
6299 if (col == 1) { /* the DistLim value */
6300 if (colp->OptScl->Clusterize &&
6301 colp->OptScl->ClustOpt->DistLim != v1) {
6302 colp->OptScl->RecomputeClust = 1;
6303 }
6304 colp->OptScl->ClustOpt->DistLim = v1;
6305 if (SETMEN) {
6306 SUMA_LHv("Inserting cell value %f \n",
6307 colp->OptScl->ClustOpt->DistLim);
6308 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6309 colp->OptScl->ClustOpt->DistLim);
6310 }
6311 } else if (col==2) {
6312 if (colp->OptScl->Clusterize &&
6313 colp->OptScl->ClustOpt->AreaLim != v1) {
6314 colp->OptScl->RecomputeClust = 1;
6315 }
6316 colp->OptScl->ClustOpt->AreaLim = v1;
6317 if (SETMEN) {
6318 SUMA_LHv("Inserting cell value %f \n",
6319 colp->OptScl->ClustOpt->AreaLim);
6320 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6321 colp->OptScl->ClustOpt->AreaLim);
6322 }
6323 } else if (col==-1) {
6324 if (colp->OptScl->Clusterize &&
6325 (colp->OptScl->ClustOpt->DistLim != v1 ||
6326 colp->OptScl->ClustOpt->AreaLim != v2)) {
6327 colp->OptScl->RecomputeClust = 1;
6328 }
6329 colp->OptScl->ClustOpt->DistLim = v1;
6330 colp->OptScl->ClustOpt->AreaLim = v2;
6331 if (SETMEN) {
6332 SUMA_LHv("Inserting cell values %f %f\n",
6333 colp->OptScl->ClustOpt->DistLim,
6334 colp->OptScl->ClustOpt->AreaLim);
6335 SUMA_INSERT_CELL_VALUE(TF, row, 1,
6336 colp->OptScl->ClustOpt->DistLim);
6337 SUMA_INSERT_CELL_VALUE(TF, row, 2,
6338 colp->OptScl->ClustOpt->AreaLim);
6339 }
6340 } else { SUMA_SL_Err("What's going on Jane ?"); }
6341 if (isCur &&
6342 colp->ShowMode > 0 && colp->ShowMode < SW_SurfCont_DsetViewXXX &&
6343 colp->OptScl->Clusterize)
6344 NewDisp = YUP;
6345 break;
6346 default:
6347 SUMA_SL_Err("You make me sick. What's that you're eating?");
6348 break;
6349 }
6350
6351 /* Now, you need to redraw the deal */
6352 if (REDISP) {
6353 SUMA_ColorizePlane(curColPlane);
6354 SUMA_Remixedisplay(ado);
6355 }
6356
6357 /* update the Xhair Info block */
6358 if (curColPlane->OptScl->DoBias != SW_CoordBias_None) {
6359 SUMA_UpdateNodeNodeField(ado);
6360 }
6361 SUMA_UpdateNodeLblField(ado);
6362
6363 SUMA_RETURN(1);
6364 }
6365
SUMA_SetClustValue(SUMA_ALL_DO * ado,SUMA_OVERLAYS * colp,int row,int col,float v1,float v2,int setmen,int redisplay,float * reset)6366 int SUMA_SetClustValue (SUMA_ALL_DO *ado,
6367 SUMA_OVERLAYS *colp,
6368 int row, int col,
6369 float v1, float v2,
6370 int setmen,
6371 int redisplay, float *reset)
6372 {
6373 static char FuncName[]={"SUMA_SetClustValue"};
6374 int NewDisp=0, an=0;
6375 SUMA_Boolean LocalHead = NOPE;
6376
6377 SUMA_ENTRY;
6378
6379 if (LocalHead) {
6380 fprintf(SUMA_STDERR,
6381 "%s:\n request to switch clust params \n", FuncName);
6382 }
6383
6384 an = SUMA_SetClustValue_one(ado, colp, row, col,
6385 v1, v2, setmen,
6386 redisplay, reset);
6387 if (an <= 0) SUMA_RETURN(an);
6388
6389 if (ado->do_type == SO_type) {
6390 SUMA_SurfaceObject *SOC=NULL, *SO = (SUMA_SurfaceObject *)ado;
6391 SUMA_OVERLAYS *colpC=NULL;
6392 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
6393 if (colpC && SOC) {
6394 SUMA_LHv("Found contralateral equivalent to:\n"
6395 " %s and %s in\n"
6396 " %s and %s\n",
6397 SO->Label, CHECK_NULL_STR(colp->Label),
6398 SOC->Label, CHECK_NULL_STR(colpC->Label));
6399 an = SUMA_SetClustValue_one((SUMA_ALL_DO *)SOC, colpC, row, col,
6400 v1, v2, 1,
6401 redisplay, reset);
6402 }
6403 }
6404 SUMA_RETURN(an);
6405 }
6406
6407
SUMA_cb_SetClustValue(void * data)6408 void SUMA_cb_SetClustValue (void *data)
6409 {
6410 static char FuncName[]={"SUMA_cb_SetClustValue"};
6411 SUMA_SRV_DATA srvdC, *srvd=NULL;
6412 SUMA_OVERLAYS *colp=NULL;
6413 SUMA_ALL_DO *ado=NULL;
6414 SUMA_X_SurfCont *SurfCont=NULL;
6415 SUMA_OVERLAYS *curColPlane=NULL;
6416 int n=-1,row=-1,col=-1, an=0;
6417 float reset = 0.0;
6418 void *cv=NULL;
6419 SUMA_TABLE_FIELD *TF=NULL;
6420 SUMA_Boolean LocalHead = NOPE;
6421
6422 SUMA_ENTRY;
6423
6424 if (LocalHead) {
6425 fprintf(SUMA_STDERR,
6426 "%s:\n request to switch range \n", FuncName);
6427 }
6428 if (!(srvd = (SUMA_SRV_DATA *)data)) SUMA_RETURNe;
6429 ado = srvd->ado; colp = srvd->colp;
6430 if (!ado) SUMA_RETURNe;
6431 SurfCont = SUMA_ADO_Cont(ado);
6432 curColPlane = SUMA_ADO_CurColPlane(ado);
6433 if (!colp) colp = curColPlane;
6434
6435 TF = SurfCont->SetClustTable;
6436 if (TF->cell_modified<0) SUMA_RETURNe;
6437 n = TF->cell_modified;
6438 row = n % TF->Ni;
6439 col = n / TF->Ni;
6440 XtVaGetValues(TF->cells[n], XmNvalue, &cv, NULL);
6441 if (LocalHead) {
6442 fprintf(SUMA_STDERR,"%s:\nTable cell[%d, %d]=%s\n",
6443 FuncName, row, col, (char *)cv);
6444 }
6445
6446 an = SUMA_SetClustValue(ado, colp, row, col,
6447 TF->num_value[n], 0.0,
6448 0, 1, &reset);
6449 if (an < 0) {
6450 SUMA_S_Warn("Error checking not handled yet.\n"
6451 "This upcoming code chunk is from\n"
6452 "sister function: SUMA_cb_SetRangeValueNew\n");
6453 if (an == -1 || an == -2) {
6454 SUMA_BEEP;
6455 TF->num_value[n] = reset;
6456 SUMA_TableF_SetString(TF);
6457 if (an == -1) { SUMA_SLP_Err("Doh"); }
6458 else { SUMA_SLP_Err("Duh"); }
6459 } else {
6460 SUMA_S_Err("Erriositation");
6461 }
6462 }
6463
6464 SUMA_RETURNe;
6465 }
6466
6467 /*!
6468 \brief updates string based on value entered in table field.
6469 Nothing is done unless field is numeric
6470 */
SUMA_TableF_SetString(SUMA_TABLE_FIELD * TF)6471 void SUMA_TableF_SetString (SUMA_TABLE_FIELD * TF)
6472 {
6473 static char FuncName[]={"SUMA_TableF_SetString"};
6474 char buf[36];
6475
6476 SUMA_ENTRY;
6477
6478 if (TF->cell_modified < 0) {
6479 /* nothing to do, user hit enter in field without modification */
6480 SUMA_RETURNe;
6481 }
6482 if (TF->type == SUMA_int) {
6483 sprintf (buf, "%-4d", (int)TF->num_value[TF->cell_modified]);
6484 }else if (TF->type == SUMA_float) {
6485 sprintf (buf, "%s",
6486 MV_format_fval2( TF->num_value[TF->cell_modified],
6487 TF->cwidth[TF->cell_modified / TF->Ni]));
6488 }else {
6489 /* fair enough, must be stringy */
6490 }
6491
6492 XtVaSetValues (TF->cells[TF->cell_modified], XmNvalue, buf, NULL);
6493 SUMA_RETURNe;
6494 }
6495
6496 /*!
6497 \brief This function is called when label field has been modified by user keyboard input.
6498 All it does is set TF->cell_modified to the 1D index of that cell
6499
6500 */
SUMA_TableF_cb_label_Modify(Widget w,XtPointer client_data,XtPointer call_data)6501 void SUMA_TableF_cb_label_Modify (Widget w, XtPointer client_data,
6502 XtPointer call_data)
6503 {
6504 static char FuncName[]={"SUMA_TableF_cb_label_Modify"};
6505 SUMA_TABLE_FIELD *TF=NULL;
6506 int ud=0;
6507 static int CurrentCell = -1;
6508 SUMA_Boolean LocalHead = NOPE;
6509
6510 SUMA_ENTRY;
6511
6512 SUMA_LH("Called");
6513
6514 TF = (SUMA_TABLE_FIELD *)client_data ;
6515
6516 if (!TF->editable) { /* this does not apply */
6517 SUMA_RETURNe;
6518 }
6519 if (TF->cell_modified != -1) {
6520 /* make sure it is the last one you'd been working on
6521 This check fails when I am dealing with mutliple tables
6522 If you need it, store a value for each cell and
6523 check them individually*/
6524 if (0 && CurrentCell >= 0 && TF->cell_modified != CurrentCell) {
6525 SUMA_SL_Err("cell_modified not reset.");
6526 SUMA_RETURNe;
6527 }
6528 }
6529 XtVaGetValues(w, XmNuserData, &ud, NULL);
6530 SUMA_LH("ud %d, cell modified %d", ud, TF->cell_modified);
6531 if (TF->cell_modified == -1) {
6532 /* fresh start, keep track */
6533 CurrentCell = ud;
6534 }
6535 TF->cell_modified = ud;
6536
6537 SUMA_RETURNe;
6538 }
6539
6540
6541 /*!
6542 \brief This function sets the color mapping options including the switch datasets and what have you
6543 It is called each time one loads a new data set and is meant to be called if the user adds a new
6544 colormap (not supported at the moment).
6545 \param NewMap --> New ColorMap was added.
6546 \param NewDset --> New Dataset was added.
6547 DO NOT CALL THIS FUNCTION if:
6548 You are switching color maps, you are switching Intensity/threshold and so on
6549 DO call this function if you load or switch between dsets
6550 Do call this function if you load a new color map
6551
6552 */
6553
SUMA_set_cmap_options(SUMA_ALL_DO * ado,SUMA_Boolean NewDset,SUMA_Boolean NewMap)6554 void SUMA_set_cmap_options(SUMA_ALL_DO *ado, SUMA_Boolean NewDset,
6555 SUMA_Boolean NewMap)
6556 {
6557 static char FuncName[]={"SUMA_set_cmap_options"};
6558 SUMA_Boolean LocalHead = NOPE;
6559
6560 SUMA_ENTRY;
6561
6562 if (!ado) SUMA_RETURNe;
6563 switch (ado->do_type) {
6564 case SO_type:
6565 SUMA_set_cmap_options_SO(ado, NewDset, NewMap);
6566 SUMA_RETURNe;
6567 break;
6568 case GDSET_type:
6569 SUMA_S_Err("No init for a DO that cannot be dispalyed\n"
6570 "without variant");
6571 SUMA_RETURNe;
6572 case CDOM_type:
6573 SUMA_set_cmap_options_CO(ado, NewDset, NewMap);
6574 SUMA_RETURNe;
6575 case GRAPH_LINK_type:
6576 SUMA_set_cmap_options_GLDO(ado, NewDset, NewMap);
6577 SUMA_RETURNe;
6578 break;
6579 case VO_type:
6580 SUMA_set_cmap_options_VO(ado, NewDset, NewMap);
6581 SUMA_RETURNe;
6582 break;
6583 default:
6584 SUMA_S_Errv("Nothing for type %s\n",
6585 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
6586 SUMA_RETURNe;
6587 break;
6588 }
6589
6590 SUMA_RETURNe;
6591 }
6592
SUMA_set_cmap_options_SO(SUMA_ALL_DO * ado,SUMA_Boolean NewDset,SUMA_Boolean NewMap)6593 void SUMA_set_cmap_options_SO(SUMA_ALL_DO *ado, SUMA_Boolean NewDset,
6594 SUMA_Boolean NewMap)
6595 {
6596 static char FuncName[]={"SUMA_set_cmap_options_SO"};
6597 SUMA_MenuItem *SwitchInt_Menu = NULL, *SwitchThr_Menu = NULL,
6598 *SwitchBrt_Menu = NULL;
6599 int N_items, FirstTime;
6600 SUMA_X_SurfCont *SurfCont=NULL;
6601 SUMA_OVERLAYS *curColPlane=NULL;
6602 SUMA_Boolean LocalHead = NOPE;
6603
6604 SUMA_ENTRY;
6605
6606 if (!ado) SUMA_RETURNe;
6607 if (ado->do_type != SO_type) {
6608 SUMA_S_Err("Should not be here");
6609 SUMA_RETURNe;
6610 }
6611 SurfCont = SUMA_ADO_Cont(ado);
6612 curColPlane = SUMA_ADO_CurColPlane(ado);
6613
6614 if (!SurfCont) SUMA_RETURNe;
6615 if (!SurfCont->opts_form || !SurfCont->opts_rc) SUMA_RETURNe;
6616 if (!curColPlane) SUMA_RETURNe;
6617 if (!NewDset && !NewMap && SurfCont->rcvo && SurfCont->rccm) {
6618 SUMA_SL_Err("Nothing to do");
6619 SUMA_RETURNe;
6620 }
6621 /* row column to contain all switching stuffs */
6622 if (!SurfCont->rcvo){
6623 SurfCont->rcvo = XtVaCreateWidget ("rowcolumn",
6624 xmRowColumnWidgetClass, SurfCont->opts_rc,
6625 XmNpacking, XmPACK_TIGHT,
6626 XmNorientation , XmVERTICAL ,
6627 XmNmarginHeight, 0 ,
6628 XmNmarginWidth , 0 ,
6629 NULL);
6630 NewDset = YUP; /* The first time around */
6631 } else {
6632 /* (no need ..) */
6633 /* XtUnmanageChild(SurfCont->rcvo); */
6634 }
6635
6636 if (NewDset) { /* The intensity / threshold / Brightness block*/
6637 /* link mode */
6638 if (!SurfCont->LinkModeMenu->mw[SW_LinkMode]) {
6639 Widget rc = NULL; /* one pass through this block ONLY */
6640 rc = XtVaCreateWidget ("rowcolumn",
6641 xmRowColumnWidgetClass, SurfCont->rcvo,
6642 XmNpacking, XmPACK_TIGHT,
6643 XmNorientation , XmHORIZONTAL ,
6644 XmNmarginHeight, 0 ,
6645 XmNmarginWidth , 0 ,
6646 NULL);
6647
6648 SUMA_LH("Forming map mode menu");
6649 SUMA_BuildMenuReset(0);
6650 SUMA_BuildMenu ( rc, XmMENU_OPTION,
6651 "IxT", '\0', YUP, LinkMode_Menu,
6652 (void *)ado,
6653 "SurfCont->Dset_Mapping->IxT",
6654 "Set I, T selection linking modes.",
6655 SUMA_SurfContHelp_Link,
6656 SurfCont->LinkModeMenu);
6657 XtManageChild (SurfCont->LinkModeMenu->mw[SW_LinkMode]);
6658
6659 XtManageChild(rc);
6660 }
6661
6662 if (!SurfCont->rcsw) {
6663 SurfCont->rcsw = XtVaCreateWidget ("rowcolumn",
6664 xmRowColumnWidgetClass, SurfCont->rcvo,
6665 XmNpacking, XmPACK_TIGHT,
6666 XmNorientation , XmHORIZONTAL ,
6667 XmNheight, 105, /* don't let that change dynamically, */
6668 XmNresizeHeight, False, /* it messes up the frame size, when you
6669 switch dsets*/
6670 XmNmarginHeight, 0 ,
6671 XmNmarginWidth , 0 ,
6672 NULL);
6673 } else {
6674 /* (no need ..) */
6675 /*XtUnmanageChild(SurfCont->rcsw); */
6676 }
6677 if (!SurfCont->rcsw_v1) {
6678 SurfCont->rcsw_v1 = XtVaCreateWidget ("rowcolumn",
6679 xmRowColumnWidgetClass, SurfCont->rcsw,
6680 XmNpacking, XmPACK_COLUMN,
6681 XmNorientation , XmVERTICAL ,
6682 XmNnumColumns, 1,
6683 XmNmarginHeight, 0 ,
6684 XmNmarginWidth , 0 ,
6685 NULL);
6686 }
6687 if (!SurfCont->rcsw_v2) {
6688 SurfCont->rcsw_v2 = XtVaCreateWidget ("rowcolumn",
6689 xmRowColumnWidgetClass, SurfCont->rcsw,
6690 XmNpacking, XmPACK_COLUMN,
6691 XmNorientation , XmVERTICAL ,
6692 XmNnumColumns, 1,
6693 XmNmarginHeight, 0 ,
6694 XmNmarginWidth , 0 ,
6695 NULL);
6696 }
6697
6698 /* Switching triplets */
6699 SwitchInt_Menu = SUMA_FormSwitchColMenuVector(ado, 0, &N_items);
6700 if (LocalHead) fprintf (SUMA_STDERR,"%s: %d items.\n", FuncName, N_items);
6701 if (SwitchInt_Menu || !N_items) {
6702 SurfCont->SwitchIntMenu =
6703 SUMA_Free_Menu_Widget(SurfCont->SwitchIntMenu);
6704 SurfCont->SwitchIntMenu =
6705 SUMA_Alloc_Menu_Widget(N_items+1);
6706 SUMA_BuildMenuReset(13);
6707 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
6708 "I", '\0', YUP, SwitchInt_Menu,
6709 (void *)ado,
6710 "SurfCont->Dset_Mapping->I",
6711 "Select Intensity (I) column, aka sub-brick. (BHelp for more)",
6712 SUMA_SurfContHelp_SelInt,
6713 SurfCont->SwitchIntMenu );
6714 XtInsertEventHandler( SurfCont->SwitchIntMenu->mw[0] ,
6715 /* handle events in optmenu */
6716 ButtonPressMask , /* button presses */
6717 FALSE , /* nonmaskable events? */
6718 SUMA_optmenu_EV , /* handler */
6719 (XtPointer) ado , /* client data */
6720 XtListTail ) ;
6721 if (LocalHead)
6722 SUMA_ShowMeTheChildren(SurfCont->SwitchIntMenu->mw[0]);
6723 XtManageChild (SurfCont->SwitchIntMenu->mw[0]);
6724 /* Now destroy the SwitchInt_Menu */
6725 SwitchInt_Menu = SUMA_FreeMenuVector(SwitchInt_Menu, N_items);
6726 /* setup the history to the proper widget */
6727 SUMA_Set_Menu_Widget(SurfCont->SwitchIntMenu,
6728 curColPlane->OptScl->find+1) ;
6729 } else {
6730 SUMA_SL_Err("NULL SwitchInt_Menu");
6731 }
6732
6733 SwitchThr_Menu = SUMA_FormSwitchColMenuVector(ado, 1, &N_items);
6734 if (SwitchThr_Menu || !N_items) {
6735 SurfCont->SwitchThrMenu =
6736 SUMA_Free_Menu_Widget(SurfCont->SwitchThrMenu);
6737 SurfCont->SwitchThrMenu =
6738 SUMA_Alloc_Menu_Widget(N_items+1);
6739 SUMA_BuildMenuReset(13);
6740 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
6741 "T", '\0', YUP, SwitchThr_Menu,
6742 (void *)ado,
6743 "SurfCont->Dset_Mapping->T",
6744 "Select Threshold (T) column, aka sub-brick. (BHelp for more)",
6745 SUMA_SurfContHelp_SelThr ,
6746 SurfCont->SwitchThrMenu );
6747 XtInsertEventHandler( SurfCont->SwitchThrMenu->mw[0] ,
6748 /* handle events in optmenu */
6749 ButtonPressMask , /* button presses */
6750 FALSE , /* nonmaskable events? */
6751 SUMA_optmenu_EV , /* handler */
6752 (XtPointer) ado , /* client data */
6753 XtListTail ) ;
6754 XtManageChild (SurfCont->SwitchThrMenu->mw[0]);
6755 /* Now destroy the SwitchThr_Menu */
6756 SwitchThr_Menu = SUMA_FreeMenuVector(SwitchThr_Menu, N_items);
6757 /* setup the history to the proper widget */
6758 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
6759 curColPlane->OptScl->tind+1);
6760 } else {
6761 SUMA_SL_Err("NULL SwitchThr_Menu");
6762 }
6763
6764 SwitchBrt_Menu = SUMA_FormSwitchColMenuVector(ado, 2, &N_items);
6765 if (SwitchBrt_Menu || !N_items) {
6766 SurfCont->SwitchBrtMenu =
6767 SUMA_Free_Menu_Widget(SurfCont->SwitchBrtMenu);
6768 SurfCont->SwitchBrtMenu =
6769 SUMA_Alloc_Menu_Widget(N_items+1);
6770 SUMA_BuildMenuReset(13);
6771 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
6772 "B", '\0', YUP, SwitchBrt_Menu,
6773 (void *)ado,
6774 "SurfCont->Dset_Mapping->B",
6775 "Select Brightness (B) column, aka sub-brick. (BHelp for more)",
6776 SUMA_SurfContHelp_SelBrt,
6777 SurfCont->SwitchBrtMenu );
6778 XtInsertEventHandler( SurfCont->SwitchBrtMenu->mw[0] ,
6779 /* handle events in optmenu */
6780 ButtonPressMask , /* button presses */
6781 FALSE , /* nonmaskable events? */
6782 SUMA_optmenu_EV , /* handler */
6783 (XtPointer) ado , /* client data */
6784 XtListTail ) ;
6785
6786 XtManageChild (SurfCont->SwitchBrtMenu->mw[0]);
6787 /* Now destroy the SwitchBrt_Menu */
6788 SwitchBrt_Menu = SUMA_FreeMenuVector(SwitchBrt_Menu, N_items);
6789 /* setup the history to the proper widget */
6790 SUMA_Set_Menu_Widget(SurfCont->SwitchBrtMenu,
6791 curColPlane->OptScl->bind+1);
6792 } else {
6793 SUMA_SL_Err("NULL SwitchBrt_Menu");
6794 }
6795
6796 if (1) {
6797 /* put the toggle buttons */
6798 if (!SurfCont->Int_tb) {
6799 SurfCont->Int_tb = XtVaCreateManagedWidget("v",
6800 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
6801 XtAddCallback (SurfCont->Int_tb,
6802 XmNvalueChangedCallback, SUMA_cb_SwitchInt_toggled, ado);
6803 SUMA_Register_Widget_Help(SurfCont->Int_tb, 1,
6804 "SurfCont->Dset_Mapping->I->v",
6805 "View (ON)/Hide Dset node colors",
6806 SUMA_SurfContHelp_SelIntTgl);
6807 SUMA_SET_SELECT_COLOR(SurfCont->Int_tb);
6808 }
6809 XmToggleButtonSetState (SurfCont->Int_tb,
6810 curColPlane->ShowMode > 0 ? 1:0 , NOPE);
6811
6812 if (!SurfCont->Thr_tb) {
6813 SurfCont->Thr_tb = XtVaCreateManagedWidget("v",
6814 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
6815 XtAddCallback (SurfCont->Thr_tb,
6816 XmNvalueChangedCallback, SUMA_cb_SwitchThr_toggled, ado);
6817 SUMA_SET_SELECT_COLOR(SurfCont->Thr_tb);
6818 SUMA_Register_Widget_Help(SurfCont->Thr_tb, 1,
6819 "SurfCont->Dset_Mapping->T->v",
6820 "Apply (ON)/Ignore thresholding",
6821 SUMA_SurfContHelp_SelThrTgl);
6822 }
6823 if (curColPlane->OptScl->tind >=0) {
6824 XmToggleButtonSetState (SurfCont->Thr_tb,
6825 curColPlane->OptScl->UseThr, NOPE);
6826 }else {
6827 XmToggleButtonSetState (SurfCont->Thr_tb, NOPE, NOPE);
6828 }
6829
6830 if (!SurfCont->Brt_tb) {
6831 SurfCont->Brt_tb = XtVaCreateManagedWidget("v",
6832 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
6833 XtAddCallback (SurfCont->Brt_tb,
6834 XmNvalueChangedCallback, SUMA_cb_SwitchBrt_toggled, ado);
6835 SUMA_SET_SELECT_COLOR(SurfCont->Brt_tb);
6836 SUMA_Register_Widget_Help(SurfCont->Brt_tb, 1,
6837 "SurfCont->Dset_Mapping->B->v",
6838 "View (ON)/Ignore brightness modulation",
6839 SUMA_SurfContHelp_SelBrtTgl);
6840 }
6841 if (curColPlane->OptScl->bind >=0) {
6842 XmToggleButtonSetState (SurfCont->Brt_tb,
6843 curColPlane->OptScl->UseBrt, NOPE);
6844 } else {
6845 XmToggleButtonSetState (SurfCont->Brt_tb, NOPE, NOPE);
6846 }
6847 }
6848 if (!XtIsManaged(SurfCont->rcsw_v1))
6849 XtManageChild (SurfCont->rcsw_v1);
6850 if (!XtIsManaged(SurfCont->rcsw_v2))
6851 XtManageChild (SurfCont->rcsw_v2);
6852 if (!XtIsManaged(SurfCont->rcsw)) XtManageChild (SurfCont->rcsw);
6853 } /* The intensity / threshold / Brightness block */
6854
6855
6856 {/* The Color map range and selector block */
6857 char *col_tit[]= { " ", "Min", "Max", NULL};
6858 char *col_hint[]= { "Clipping ranges",
6859 "Minimum clip value",
6860 "Maximum clip value" , NULL};
6861 char *col_help[]= { SUMA_SurfContHelp_SetRngTbl_r0,
6862 SUMA_SurfContHelp_SetRngTbl_c1,
6863 SUMA_SurfContHelp_SetRngTbl_c2 , NULL};
6864 char *row_tit[]= { " ", "I", "B", " " , "C", NULL};
6865 char *row_hint[]= {
6866 "Clipping ranges ",
6867 "Intensity clipping range (append '%' for percentiles, see BHelp)",
6868 "Brightness modulation clipping range (much more with BHelp)",
6869 "Brightness modulation factor range (much more with BHelp)" ,
6870 "Coordinate bias range (much more with BHelp)", NULL};
6871 char *row_help[]= { SUMA_SurfContHelp_SetRngTbl_r0,
6872 SUMA_SurfContHelp_SetRngTbl_r1,
6873 SUMA_SurfContHelp_SetRngTbl_r2,
6874 SUMA_SurfContHelp_SetRngTbl_r3,
6875 SUMA_SurfContHelp_SetRngTbl_r4, NULL};
6876 if (!SurfCont->rccm) {
6877 SurfCont->rccm = XtVaCreateWidget ("rowcolumn",
6878 xmRowColumnWidgetClass, SurfCont->rcvo,
6879 XmNpacking, XmPACK_TIGHT,
6880 XmNorientation , XmVERTICAL ,
6881 XmNmarginHeight, 0,
6882 XmNmarginWidth, 0,
6883 NULL);
6884 NewMap = YUP; /* the first time around */
6885 }
6886
6887 if (NewMap) {/* new colormaps */
6888 SUMA_Register_Widget_Help(SurfCont->rccm, 0,
6889 "SurfContCont->Dset_Mapping->SetRangeTable",
6890 "Node colorization parameters",
6891 "Set parameters for mapping node data onto color scale");
6892 SUMA_LH("NewMap set");
6893 if (!SurfCont->SetRangeTable->cells) {
6894 int colw[3] = { 1, 8, 8 };
6895 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)calloc(1,sizeof(SUMA_SRV_DATA));
6896 srvd->ado = ado; srvd->colp = NULL;
6897 /* create the widgets for the range table */
6898 SUMA_LH("Creating table");
6899 SUMA_CreateTable( SurfCont->rccm,
6900 5, 3,
6901 "SurfCont->Dset_Mapping->SetRangeTable",
6902 row_tit, col_tit,
6903 row_hint, col_hint,
6904 row_help, col_help,
6905 colw, YUP, SUMA_float,
6906 SUMA_cb_SetRangeValue, (void *)srvd,
6907 SUMA_SetRangeTableTit_EV, NULL,
6908 NULL, NULL,
6909 SurfCont->SetRangeTable);
6910 }
6911 if (!SurfCont->CoordBiasMenu->mw[SW_CoordBias]) {
6912 Widget rc = NULL; /* one pass through this block ONLY */
6913 rc = XtVaCreateWidget ("rowcolumn",
6914 xmRowColumnWidgetClass, SurfCont->rccm,
6915 XmNpacking, XmPACK_TIGHT,
6916 XmNorientation , XmHORIZONTAL ,
6917 XmNmarginHeight, 0 ,
6918 XmNmarginWidth , 0 ,
6919 NULL);
6920
6921 SUMA_LH("Forming map mode menu");
6922 SUMA_BuildMenuReset(0);
6923 SUMA_BuildMenu ( rc, XmMENU_OPTION,
6924 "Col", '\0', YUP, CmapMode_Menu,
6925 (void *)ado,
6926 "SurfCont->Dset_Mapping->Col",
6927 "Switch between color mapping modes.",
6928 SUMA_SurfContHelp_Col,
6929 SurfCont->CmapModeMenu);
6930 XtManageChild (SurfCont->CmapModeMenu->mw[SW_CmapMode]);
6931
6932 SUMA_LH("Forming new bias menu");
6933 SUMA_BuildMenuReset(0);
6934 SUMA_BuildMenu ( rc, XmMENU_OPTION,
6935 "Bias", '\0', YUP, CoordBias_Menu,
6936 (void *)ado,
6937 "SurfCont->Dset_Mapping->Bias",
6938 "Coordinate bias direction",
6939 SUMA_SurfContHelp_Bias,
6940 SurfCont->CoordBiasMenu);
6941 XtManageChild (SurfCont->CoordBiasMenu->mw[SW_CoordBias]);
6942
6943 XtManageChild(rc);
6944 }
6945
6946 if (!SurfCont->rccm_swcmap) {
6947 SUMA_LH("Creating rccm_swcmap");
6948 SurfCont->rccm_swcmap = XtVaCreateWidget ("rowcolumn",
6949 xmRowColumnWidgetClass, SurfCont->rccm,
6950 XmNpacking, XmPACK_TIGHT,
6951 XmNorientation , XmHORIZONTAL ,
6952 XmNmarginHeight, 0 ,
6953 XmNmarginWidth , 0 ,
6954 NULL);
6955 }
6956
6957 {
6958 SUMA_CreateUpdatableCmapMenu(ado);
6959
6960 #if 0
6961 /* Not any more, menu is now stuck in its own rc */
6962 /* the loader, needs to be recreated with colormap menu */
6963 if (SurfCont->CmapLoad_pb) {
6964 XtDestroyWidget(SurfCont->CmapLoad_pb);
6965 SurfCont->CmapLoad_pb = NULL;
6966 }
6967 #endif
6968 if (!SurfCont->CmapLoad_pb) {
6969 SUMA_LH("Forming CmapLoad button");
6970 SurfCont->CmapLoad_pb = XtVaCreateManagedWidget ("New",
6971 xmPushButtonWidgetClass,
6972 SurfCont->rccm_swcmap,
6973 NULL);
6974 XtAddCallback (SurfCont->CmapLoad_pb, XmNactivateCallback,
6975 SUMA_cb_Cmap_Load, (XtPointer) ado);
6976 SUMA_Register_Widget_Help(SurfCont->CmapLoad_pb , 1,
6977 "SurfCont->Dset_Mapping->Cmp->New",
6978 "Load new colormap",
6979 SUMA_SurfContHelp_CmpNew);
6980 }
6981 } /* new colormaps */
6982 if (!XtIsManaged(SurfCont->rccm_swcmap))
6983 XtManageChild (SurfCont->rccm_swcmap);
6984 }
6985
6986 /* Set the CoordBias's menu history to reflect current setting */
6987 SUMA_LH("Updating Link Mode History");
6988 SUMA_Set_Menu_Widget( SurfCont->LinkModeMenu,
6989 curColPlane->LinkMode);
6990
6991 SUMA_LH("Working the lock stuff ...");
6992 /* You'll need to fix the table's locking widget colors */
6993 if ( SurfCont->IntRangeLocked ==
6994 curColPlane->OptScl->AutoIntRange) {
6995 SUMA_LH(" Do the Int");
6996 /* need to put things in sync */
6997 SurfCont->IntRangeLocked = !SurfCont->IntRangeLocked;
6998 MCW_invert_widget_sync(SurfCont->SetRangeTable->cells[1],0);
6999 }
7000 if ( SurfCont->BrtRangeLocked ==
7001 curColPlane->OptScl->AutoBrtRange) {
7002 SUMA_LH(" Do the Brt");
7003 /* need to put things in sync */
7004 SurfCont->BrtRangeLocked = !SurfCont->BrtRangeLocked;
7005 MCW_invert_widget_sync(SurfCont->SetRangeTable->cells[2],0);
7006 }
7007
7008 /* Set the CoordBias's menu history to reflect current setting */
7009 SUMA_LH("Updating CoorBias chooser History");
7010 SUMA_Set_Menu_Widget( SurfCont->CoordBiasMenu,
7011 curColPlane->OptScl->DoBias);
7012
7013 /* Set the Col's menu history to reflect current setting */
7014 SUMA_LH("Updating Col chooser History");
7015 SUMA_Set_Menu_Widget( SurfCont->CmapModeMenu,
7016 curColPlane->OptScl->interpmode);
7017
7018 /* add the selectors for symmetric range and absolute threshold */
7019 if (!SurfCont->AbsThresh_tb) {
7020 Widget rc;
7021 rc = XtVaCreateWidget ("rowcolumn",
7022 xmRowColumnWidgetClass, SurfCont->rccm,
7023 XmNpacking, XmPACK_TIGHT,
7024 XmNorientation , XmHORIZONTAL ,
7025 XmNmarginHeight, 0 ,
7026 XmNmarginWidth , 0 ,
7027 NULL);
7028 /* create the absolute threshold toggle button */
7029 SurfCont->AbsThresh_tb = XtVaCreateManagedWidget("|T|",
7030 xmToggleButtonWidgetClass, rc,
7031 NULL);
7032 XtAddCallback (SurfCont->AbsThresh_tb,
7033 XmNvalueChangedCallback, SUMA_cb_AbsThresh_tb_toggled, ado);
7034 SUMA_Register_Widget_Help(SurfCont->AbsThresh_tb , 1,
7035 "SurfCont->Dset_Mapping->abs_T",
7036 "Absolute threshold ON/OFF",
7037 SUMA_SurfContHelp_AbsThr );
7038
7039 SUMA_SET_SELECT_COLOR(SurfCont->AbsThresh_tb);
7040
7041 /* create the symmetric range toggle button */
7042 SurfCont->SymIrange_tb = XtVaCreateManagedWidget("sym I",
7043 xmToggleButtonWidgetClass, rc, NULL);
7044 XtAddCallback (SurfCont->SymIrange_tb,
7045 XmNvalueChangedCallback, SUMA_cb_SymIrange_tb_toggled, ado);
7046 SUMA_Register_Widget_Help(SurfCont->SymIrange_tb, 1,
7047 "SurfCont->Dset_Mapping->sym_I",
7048 "Intensity range symmetry about 0 ",
7049 SUMA_SurfContHelp_Isym);
7050 SUMA_SET_SELECT_COLOR(SurfCont->SymIrange_tb);
7051
7052 /* add a button for zero masking */
7053 SurfCont->ShowZero_tb = XtVaCreateManagedWidget("shw 0",
7054 xmToggleButtonWidgetClass, rc, NULL);
7055 XtAddCallback (SurfCont->ShowZero_tb,
7056 XmNvalueChangedCallback, SUMA_cb_ShowZero_tb_toggled, ado);
7057 SUMA_Register_Widget_Help(SurfCont->ShowZero_tb, 1,
7058 "SurfCont->Dset_Mapping->shw_0",
7059 "Color masking of nodes with intensity = 0 ",
7060 SUMA_SurfContHelp_Shw0);
7061 SUMA_SET_SELECT_COLOR(SurfCont->ShowZero_tb);
7062 XtManageChild (rc);
7063 }
7064
7065 {/* The clustering options */
7066 char *col_tit[]= { " ", "Conn", "Area", NULL };
7067 char *col_hint[]={ "Clusterizing options",
7068 "Connectedness criterion",
7069 "Cluster Area Threshold", NULL };
7070 char *col_help[]={ SUMA_SurfContHelp_SetClustTbl_r0,
7071 SUMA_SurfContHelp_SetClustTbl_c1,
7072 SUMA_SurfContHelp_SetClustTbl_c2, NULL
7073 };
7074 char *row_tit[]={ " ", "Clst", NULL};
7075 char *row_hint[]={ "Clusterizing options", "Clust on/off", NULL};
7076 char *row_help[]={ SUMA_SurfContHelp_SetClustTbl_r0,
7077 SUMA_SurfContHelp_SetClustTbl_r1, NULL
7078 };
7079
7080 SUMA_LH("Receptacle");
7081 if (!SurfCont->rcclust) {
7082 SurfCont->rcclust = XtVaCreateWidget ("rowcolumn",
7083 xmRowColumnWidgetClass, SurfCont->opts_form,
7084 XmNpacking, XmPACK_TIGHT,
7085 XmNorientation , XmHORIZONTAL ,
7086 XmNmarginHeight, 0,
7087 XmNmarginWidth, 0,
7088 XmNrightAttachment, XmATTACH_FORM ,
7089 XmNleftAttachment, XmATTACH_NONE,
7090 XmNtopAttachment, XmATTACH_WIDGET ,
7091 XmNtopWidget, SurfCont->opts_rc,
7092 NULL);
7093 FirstTime = YUP; /* the first time around */
7094 } else {
7095 FirstTime = NOPE;
7096 }
7097
7098 if (FirstTime) {/* new clust */
7099 SUMA_LH("FirstTime set");
7100 if (!SurfCont->SetClustTable->cells) {
7101 int colw[3] = { 4, 6, 6 };
7102 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)
7103 calloc(1,sizeof(SUMA_SRV_DATA));
7104 srvd->ado = ado; srvd->colp = NULL;
7105 /* create the widgets for the range table */
7106 SUMA_LH("Creating table");
7107 SUMA_CreateTable( SurfCont->rcclust,
7108 2, 3,
7109 "SurfCont->Dset_Mapping->Clst",
7110 row_tit, col_tit,
7111 row_hint, col_hint,
7112 row_help, col_help,
7113 colw, YUP, SUMA_float,
7114 SUMA_cb_SetClustValue, (void *)srvd,
7115 SUMA_SetClustTableTit_EV, NULL,
7116 SUMA_SetClustTableCell_EV, NULL,
7117 SurfCont->SetClustTable);
7118 }
7119
7120 if (curColPlane->OptScl) {
7121 SUMA_SetTableTitleButton1(SurfCont->SetClustTable, 1,0, curColPlane->OptScl->Clusterize);
7122 }
7123 }
7124 SUMA_LH("Managerial");
7125
7126 if (!XtIsManaged(SurfCont->rcclust))
7127 XtManageChild (SurfCont->rcclust);
7128
7129 }/* The clustering options */
7130
7131 /* do the initialization */
7132 SUMA_InitClustTable(ado); /* init the clust table values*/
7133
7134 /* This button is NOT appropriate for anything other than
7135 SUMA_ABS_LESS_THAN and SUMA_LESS_THAN
7136 Probably need separate button ormenu system for other
7137 thresholding modes */
7138 if (curColPlane->OptScl->ThrMode == SUMA_ABS_LESS_THAN) {
7139 XmToggleButtonSetState( SurfCont->AbsThresh_tb, True, NOPE);
7140 } else if (curColPlane->OptScl->ThrMode == SUMA_LESS_THAN) {
7141 XmToggleButtonSetState( SurfCont->AbsThresh_tb, False, NOPE);
7142 } else {
7143 SUMA_S_Err("Not ready to handle ThrModeR of %d yet",
7144 curColPlane->OptScl->ThrMode);
7145 }
7146 if (!curColPlane->SymIrange) {
7147 XmToggleButtonSetState( SurfCont->SymIrange_tb, False, NOPE);
7148 } else {
7149 XmToggleButtonSetState( SurfCont->SymIrange_tb, True, NOPE);
7150 }
7151 if (!curColPlane->OptScl->MaskZero) {
7152 XmToggleButtonSetState( SurfCont->ShowZero_tb, True, NOPE);
7153 } else {
7154 XmToggleButtonSetState( SurfCont->ShowZero_tb, False, NOPE);
7155 }
7156
7157 if (!XtIsManaged(SurfCont->rccm)) XtManageChild (SurfCont->rccm);
7158
7159 }/* The Color map range and selector block */
7160
7161 if (1){ /* The Range values block*/
7162 char *col_tit[]= { " ", "Min", "Node", "Max", "Node", NULL};
7163 char *col_hint[]= { "Full range of values in Dset",
7164 "Minimum value in Dset column",
7165 "Node index at minimum",
7166 "Maximum value in Dset column",
7167 "Node index at maximum", NULL};
7168 char *col_help[]= { SUMA_SurfContHelp_RangeTbl_c0,
7169 SUMA_SurfContHelp_RangeTbl_c1,
7170 SUMA_SurfContHelp_RangeTbl_c2,
7171 SUMA_SurfContHelp_RangeTbl_c3,
7172 SUMA_SurfContHelp_RangeTbl_c4, NULL};
7173 char *row_tit[]= { " ", "I", "T", "B", NULL};
7174 char *row_hint[]= { "Full range of values in Dset",
7175 "Range of values in intensity (I) column",
7176 "Range of values in threshold (T) column",
7177 "Range of values in brightness (B) column", NULL};
7178 char *row_help[]= { SUMA_SurfContHelp_RangeTbl_c0,
7179 SUMA_SurfContHelp_RangeTbl_r1,
7180 SUMA_SurfContHelp_RangeTbl_r2,
7181 SUMA_SurfContHelp_RangeTbl_r3, NULL};
7182 if (!SurfCont->rcswr) {
7183 SurfCont->rcswr = XtVaCreateWidget ("rowcolumn",
7184 xmRowColumnWidgetClass, SurfCont->opts_form,
7185 XmNpacking, XmPACK_TIGHT,
7186 XmNorientation , XmVERTICAL ,
7187 XmNrightAttachment, XmATTACH_FORM ,
7188 XmNleftAttachment, XmATTACH_NONE,
7189 XmNtopAttachment, XmATTACH_WIDGET ,
7190 XmNtopWidget, SurfCont->rcclust,
7191 NULL);
7192 }
7193
7194 if (!SurfCont->RangeTable->cells) {
7195 int colw[5] = { 1, 6, 6, 6, 6 };
7196 /* create the widgets for the range table */
7197 SUMA_CreateTable( SurfCont->rcswr,
7198 4, 5,
7199 "SurfCont->Dset_Mapping->RangeTable",
7200 row_tit, col_tit,
7201 row_hint, col_hint,
7202 row_help, col_help,
7203 colw, NOPE, SUMA_string,
7204 NULL, NULL,
7205 NULL, NULL,
7206 SUMA_RangeTableCell_EV, (void *)ado,
7207 SurfCont->RangeTable);
7208 }
7209
7210 if (!XtIsManaged(SurfCont->rcswr)) XtManageChild (SurfCont->rcswr);
7211 } /* The Range values block */
7212
7213 if (NewDset) {
7214 /* initialize tables of range values */
7215 SUMA_InitRangeTable(ado, 2);
7216 }
7217
7218 if (!XtIsManaged(SurfCont->rcvo)) XtManageChild (SurfCont->rcvo);
7219 SUMA_FORCE_SCALE_HEIGHT(SUMA_ADO_Cont(ado));
7220
7221 SUMA_RETURNe;
7222 }
7223
SUMA_set_cmap_options_CO(SUMA_ALL_DO * ado,SUMA_Boolean NewDset,SUMA_Boolean NewMap)7224 void SUMA_set_cmap_options_CO(SUMA_ALL_DO *ado, SUMA_Boolean NewDset,
7225 SUMA_Boolean NewMap)
7226 {
7227 static char FuncName[]={"SUMA_set_cmap_options_CO"};
7228 SUMA_MenuItem *SwitchInt_Menu = NULL, *SwitchThr_Menu = NULL,
7229 *SwitchBrt_Menu = NULL;
7230 int N_items, FirstTime;
7231 SUMA_X_SurfCont *SurfCont=NULL;
7232 SUMA_OVERLAYS *curColPlane=NULL;
7233 SUMA_Boolean LocalHead = NOPE;
7234
7235 SUMA_ENTRY;
7236
7237 if (!ado) SUMA_RETURNe;
7238 if (ado->do_type != CDOM_type) {
7239 SUMA_S_Err("Should not be here");
7240 SUMA_RETURNe;
7241 }
7242 SurfCont = SUMA_ADO_Cont(ado);
7243 curColPlane = SUMA_ADO_CurColPlane(ado);
7244
7245 if (!SurfCont) SUMA_RETURNe;
7246
7247 SUMA_S_Err("Nothing here still");
7248
7249 SUMA_RETURNe;
7250 }
7251
SUMA_set_cmap_options_VO(SUMA_ALL_DO * ado,SUMA_Boolean NewDset,SUMA_Boolean NewMap)7252 void SUMA_set_cmap_options_VO(SUMA_ALL_DO *ado, SUMA_Boolean NewDset,
7253 SUMA_Boolean NewMap)
7254 {
7255 static char FuncName[]={"SUMA_set_cmap_options_VO"};
7256 SUMA_MenuItem *SwitchInt_Menu = NULL, *SwitchThr_Menu = NULL,
7257 *SwitchBrt_Menu = NULL;
7258 int N_items, FirstTime;
7259 SUMA_X_SurfCont *SurfCont=NULL;
7260 SUMA_OVERLAYS *curColPlane=NULL;
7261 SUMA_Boolean LocalHead = NOPE;
7262
7263 SUMA_ENTRY;
7264
7265 if (!ado) SUMA_RETURNe;
7266 if (ado->do_type != VO_type) {
7267 SUMA_S_Err("Should not be here");
7268 SUMA_RETURNe;
7269 }
7270 SurfCont = SUMA_ADO_Cont(ado);
7271 curColPlane = SUMA_ADO_CurColPlane(ado);
7272
7273 if (!SurfCont) SUMA_RETURNe;
7274 if (!SurfCont->opts_form || !SurfCont->opts_rc) SUMA_RETURNe;
7275 if (!curColPlane) SUMA_RETURNe;
7276 if (!NewDset && !NewMap && SurfCont->rcvo && SurfCont->rccm) {
7277 SUMA_SL_Err("Nothing to do");
7278 SUMA_RETURNe;
7279 }
7280 /* row column to contain all switching stuffs */
7281 if (!SurfCont->rcvo){
7282 SurfCont->rcvo = XtVaCreateWidget ("rowcolumn",
7283 xmRowColumnWidgetClass, SurfCont->opts_rc,
7284 XmNpacking, XmPACK_TIGHT,
7285 XmNorientation , XmVERTICAL ,
7286 XmNmarginHeight, 0 ,
7287 XmNmarginWidth , 0 ,
7288 NULL);
7289 NewDset = YUP; /* The first time around */
7290 } else {
7291 /* (no need ..) */
7292 /* XtUnmanageChild(SurfCont->rcvo); */
7293 }
7294
7295 if (NewDset) { /* The intensity / threshold / Brightness block*/
7296 /* link mode */
7297 if (!SurfCont->LinkModeMenu->mw[SW_LinkMode]) {
7298 Widget rc = NULL; /* one pass through this block ONLY */
7299 rc = XtVaCreateWidget ("rowcolumn",
7300 xmRowColumnWidgetClass, SurfCont->rcvo,
7301 XmNpacking, XmPACK_TIGHT,
7302 XmNorientation , XmHORIZONTAL ,
7303 XmNmarginHeight, 0 ,
7304 XmNmarginWidth , 0 ,
7305 NULL);
7306
7307 SUMA_LH("Forming map mode menu");
7308 SUMA_BuildMenuReset(0);
7309 SUMA_BuildMenu ( rc, XmMENU_OPTION,
7310 "IxT", '\0', YUP, LinkMode_Menu,
7311 (void *)ado,
7312 "VolCont->Dset_Mapping->IxT",
7313 "Set I, T selection linking modes.",
7314 SUMA_SurfContHelp_Link,
7315 SurfCont->LinkModeMenu);
7316 XtManageChild (SurfCont->LinkModeMenu->mw[SW_LinkMode]);
7317
7318 XtManageChild(rc);
7319 }
7320
7321 if (!SurfCont->rcsw) {
7322 SurfCont->rcsw = XtVaCreateWidget ("rowcolumn",
7323 xmRowColumnWidgetClass, SurfCont->rcvo,
7324 XmNpacking, XmPACK_TIGHT,
7325 XmNorientation , XmHORIZONTAL ,
7326 XmNheight, 105, /* don't let that change dynamically, */
7327 XmNresizeHeight, False, /* it messes up the frame size, when you
7328 switch dsets*/
7329 XmNmarginHeight, 0 ,
7330 XmNmarginWidth , 0 ,
7331 NULL);
7332 } else {
7333 /* (no need ..) */
7334 /*XtUnmanageChild(SurfCont->rcsw); */
7335 }
7336 if (!SurfCont->rcsw_v1) {
7337 SurfCont->rcsw_v1 = XtVaCreateWidget ("rowcolumn",
7338 xmRowColumnWidgetClass, SurfCont->rcsw,
7339 XmNpacking, XmPACK_COLUMN,
7340 XmNorientation , XmVERTICAL ,
7341 XmNnumColumns, 1,
7342 XmNmarginHeight, 0 ,
7343 XmNmarginWidth , 0 ,
7344 NULL);
7345 }
7346 if (!SurfCont->rcsw_v2) {
7347 SurfCont->rcsw_v2 = XtVaCreateWidget ("rowcolumn",
7348 xmRowColumnWidgetClass, SurfCont->rcsw,
7349 XmNpacking, XmPACK_COLUMN,
7350 XmNorientation , XmVERTICAL ,
7351 XmNnumColumns, 1,
7352 XmNmarginHeight, 0 ,
7353 XmNmarginWidth , 0 ,
7354 NULL);
7355 }
7356
7357 /* Switching triplets */
7358 SwitchInt_Menu = SUMA_FormSwitchColMenuVector(ado, 0, &N_items);
7359 if (LocalHead) fprintf (SUMA_STDERR,"%s: %d items.\n", FuncName, N_items);
7360 if (SwitchInt_Menu || !N_items) {
7361 SurfCont->SwitchIntMenu =
7362 SUMA_Free_Menu_Widget(SurfCont->SwitchIntMenu);
7363 SurfCont->SwitchIntMenu =
7364 SUMA_Alloc_Menu_Widget(N_items+1);
7365 SUMA_BuildMenuReset(13);
7366 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
7367 "I", '\0', YUP, SwitchInt_Menu,
7368 (void *)ado,
7369 "VolCont->Dset_Mapping->I",
7370 "Select Intensity (I) column, aka sub-brick. (BHelp for more)",
7371 SUMA_SurfContHelp_SelInt,
7372 SurfCont->SwitchIntMenu );
7373 XtInsertEventHandler( SurfCont->SwitchIntMenu->mw[0] ,
7374 /* handle events in optmenu */
7375 ButtonPressMask , /* button presses */
7376 FALSE , /* nonmaskable events? */
7377 SUMA_optmenu_EV , /* handler */
7378 (XtPointer) ado , /* client data */
7379 XtListTail ) ;
7380 if (LocalHead)
7381 SUMA_ShowMeTheChildren(SurfCont->SwitchIntMenu->mw[0]);
7382 XtManageChild (SurfCont->SwitchIntMenu->mw[0]);
7383 /* Now destroy the SwitchInt_Menu */
7384 SwitchInt_Menu = SUMA_FreeMenuVector(SwitchInt_Menu, N_items);
7385 /* setup the history to the proper widget */
7386 SUMA_Set_Menu_Widget(SurfCont->SwitchIntMenu,
7387 curColPlane->OptScl->find+1) ;
7388 } else {
7389 SUMA_SL_Err("NULL SwitchInt_Menu");
7390 }
7391
7392 SwitchThr_Menu = SUMA_FormSwitchColMenuVector(ado, 1, &N_items);
7393 if (SwitchThr_Menu || !N_items) {
7394 SurfCont->SwitchThrMenu =
7395 SUMA_Free_Menu_Widget(SurfCont->SwitchThrMenu);
7396 SurfCont->SwitchThrMenu =
7397 SUMA_Alloc_Menu_Widget(N_items+1);
7398 SUMA_BuildMenuReset(13);
7399 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
7400 "T", '\0', YUP, SwitchThr_Menu,
7401 (void *)ado,
7402 "VolCont->Dset_Mapping->T",
7403 "Select Threshold (T) column, aka sub-brick. (BHelp for more)",
7404 SUMA_SurfContHelp_SelThr ,
7405 SurfCont->SwitchThrMenu );
7406 XtInsertEventHandler( SurfCont->SwitchThrMenu->mw[0] ,
7407 /* handle events in optmenu */
7408 ButtonPressMask , /* button presses */
7409 FALSE , /* nonmaskable events? */
7410 SUMA_optmenu_EV , /* handler */
7411 (XtPointer) ado , /* client data */
7412 XtListTail ) ;
7413 XtManageChild (SurfCont->SwitchThrMenu->mw[0]);
7414 /* Now destroy the SwitchThr_Menu */
7415 SwitchThr_Menu = SUMA_FreeMenuVector(SwitchThr_Menu, N_items);
7416 /* setup the history to the proper widget */
7417 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
7418 curColPlane->OptScl->tind+1);
7419 } else {
7420 SUMA_SL_Err("NULL SwitchThr_Menu");
7421 }
7422
7423 SwitchBrt_Menu = SUMA_FormSwitchColMenuVector(ado, 2, &N_items);
7424 if (SwitchBrt_Menu || !N_items) {
7425 SurfCont->SwitchBrtMenu =
7426 SUMA_Free_Menu_Widget(SurfCont->SwitchBrtMenu);
7427 SurfCont->SwitchBrtMenu =
7428 SUMA_Alloc_Menu_Widget(N_items+1);
7429 SUMA_BuildMenuReset(13);
7430 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
7431 "B", '\0', YUP, SwitchBrt_Menu,
7432 (void *)ado,
7433 "VolCont->Dset_Mapping->B",
7434 "Select Brightness (B) column, aka sub-brick. (BHelp for more)",
7435 SUMA_SurfContHelp_SelBrt,
7436 SurfCont->SwitchBrtMenu );
7437 XtInsertEventHandler( SurfCont->SwitchBrtMenu->mw[0] ,
7438 /* handle events in optmenu */
7439 ButtonPressMask , /* button presses */
7440 FALSE , /* nonmaskable events? */
7441 SUMA_optmenu_EV , /* handler */
7442 (XtPointer) ado , /* client data */
7443 XtListTail ) ;
7444
7445 XtManageChild (SurfCont->SwitchBrtMenu->mw[0]);
7446 /* Now destroy the SwitchBrt_Menu */
7447 SwitchBrt_Menu = SUMA_FreeMenuVector(SwitchBrt_Menu, N_items);
7448 /* setup the history to the proper widget */
7449 SUMA_Set_Menu_Widget(SurfCont->SwitchBrtMenu,
7450 curColPlane->OptScl->bind+1);
7451 } else {
7452 SUMA_SL_Err("NULL SwitchBrt_Menu");
7453 }
7454
7455 if (1) {
7456 /* put the toggle buttons */
7457 if (!SurfCont->Int_tb) {
7458 SurfCont->Int_tb = XtVaCreateManagedWidget("v",
7459 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
7460 XtAddCallback (SurfCont->Int_tb,
7461 XmNvalueChangedCallback, SUMA_cb_SwitchInt_toggled, ado);
7462 SUMA_Register_Widget_Help(SurfCont->Int_tb, 1,
7463 "VolCont->Dset_Mapping->I->v",
7464 "View (ON)/Hide volume voxel colors",
7465 SUMA_VolContHelp_SelIntTgl);
7466
7467 SUMA_SET_SELECT_COLOR(SurfCont->Int_tb);
7468 }
7469 XmToggleButtonSetState (SurfCont->Int_tb,
7470 curColPlane->ShowMode > 0 ? 1:0 , NOPE);
7471
7472 if (!SurfCont->Thr_tb) {
7473 SurfCont->Thr_tb = XtVaCreateManagedWidget("v",
7474 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
7475 XtAddCallback (SurfCont->Thr_tb,
7476 XmNvalueChangedCallback, SUMA_cb_SwitchThr_toggled, ado);
7477 SUMA_SET_SELECT_COLOR(SurfCont->Thr_tb);
7478 SUMA_Register_Widget_Help(SurfCont->Thr_tb, 1,
7479 "VolCont->Dset_Mapping->T->v",
7480 "Apply (ON)/Ignore thresholding",
7481 SUMA_SurfContHelp_SelThrTgl);
7482 }
7483 if (curColPlane->OptScl->tind >=0) {
7484 XmToggleButtonSetState (SurfCont->Thr_tb,
7485 curColPlane->OptScl->UseThr, NOPE);
7486 }else {
7487 XmToggleButtonSetState (SurfCont->Thr_tb, NOPE, NOPE);
7488 }
7489
7490 if (!SurfCont->Brt_tb) {
7491 SurfCont->Brt_tb = XtVaCreateManagedWidget("v",
7492 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
7493 XtAddCallback (SurfCont->Brt_tb,
7494 XmNvalueChangedCallback, SUMA_cb_SwitchBrt_toggled, ado);
7495 SUMA_SET_SELECT_COLOR(SurfCont->Brt_tb);
7496 SUMA_Register_Widget_Help(SurfCont->Brt_tb, 1,
7497 "VolCont->Dset_Mapping->B->v",
7498 "View (ON)/Ignore brightness modulation",
7499 SUMA_SurfContHelp_SelBrtTgl);
7500 }
7501 if (curColPlane->OptScl->bind >=0) {
7502 XmToggleButtonSetState (SurfCont->Brt_tb,
7503 curColPlane->OptScl->UseBrt, NOPE);
7504 } else {
7505 XmToggleButtonSetState (SurfCont->Brt_tb, NOPE, NOPE);
7506 }
7507 }
7508 if (!XtIsManaged(SurfCont->rcsw_v1))
7509 XtManageChild (SurfCont->rcsw_v1);
7510 if (!XtIsManaged(SurfCont->rcsw_v2))
7511 XtManageChild (SurfCont->rcsw_v2);
7512 if (!XtIsManaged(SurfCont->rcsw)) XtManageChild (SurfCont->rcsw);
7513 } /* The intensity / threshold / Brightness block */
7514
7515
7516 {/* The Color map range and selector block */
7517 char *col_tit[]= { " ", "Min", "Max", NULL};
7518 char *col_hint[]= { "Clipping ranges",
7519 "Minimum clip value",
7520 "Maximum clip value" , NULL};
7521 char *col_help[]= { SUMA_SurfContHelp_SetRngTbl_r0,
7522 SUMA_SurfContHelp_SetRngTbl_c1,
7523 SUMA_SurfContHelp_SetRngTbl_c2 , NULL};
7524 char *row_tit[]= { " ", "I", "B", " " , "C", NULL};
7525 char *row_hint[]= {
7526 "Clipping ranges ",
7527 "Intensity clipping range (append '%' for percentiles, see BHelp)",
7528 "Brightness modulation clipping range (much more with BHelp)",
7529 "Brightness modulation factor range (much more with BHelp)" ,
7530 "Coordinate bias range (much more with BHelp)", NULL};
7531 char *row_help[]= { SUMA_SurfContHelp_SetRngTbl_r0,
7532 SUMA_SurfContHelp_SetRngTbl_r1,
7533 SUMA_SurfContHelp_SetRngTbl_r2,
7534 SUMA_SurfContHelp_SetRngTbl_r3,
7535 SUMA_SurfContHelp_SetRngTbl_r4, NULL};
7536 if (!SurfCont->rccm) {
7537 SurfCont->rccm = XtVaCreateWidget ("rowcolumn",
7538 xmRowColumnWidgetClass, SurfCont->rcvo,
7539 XmNpacking, XmPACK_TIGHT,
7540 XmNorientation , XmVERTICAL ,
7541 XmNmarginHeight, 0,
7542 XmNmarginWidth, 0,
7543 NULL);
7544 NewMap = YUP; /* the first time around */
7545 }
7546
7547 if (NewMap) {/* new colormaps */
7548 SUMA_LH("NewMap set");
7549 SUMA_Register_Widget_Help(SurfCont->rccm, 1,
7550 "VolCont->Dset_Mapping->SetRangeTable",
7551 "Voxel colorization parameters",
7552 "Set parameters for mapping data onto color scale");
7553 if (!SurfCont->SetRangeTable->cells) {
7554 int colw[3] = { 1, 8, 8 };
7555 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)calloc(1,sizeof(SUMA_SRV_DATA));
7556 srvd->ado = ado; srvd->colp = NULL;
7557 /* create the widgets for the range table */
7558 SUMA_LH("Creating table");
7559 SUMA_CreateTable( SurfCont->rccm,
7560 5, 3,
7561 "VolCont->Dset_Mapping->SetRangeTable",
7562 row_tit, col_tit,
7563 row_hint, col_hint,
7564 row_help, col_help,
7565 colw, YUP, SUMA_float,
7566 SUMA_cb_SetRangeValue, (void *)srvd,
7567 SUMA_SetRangeTableTit_EV, NULL,
7568 NULL, NULL,
7569 SurfCont->SetRangeTable);
7570 }
7571 if (!SurfCont->CoordBiasMenu->mw[SW_CoordBias]) {
7572 Widget rc = NULL; /* one pass through this block ONLY */
7573 rc = XtVaCreateWidget ("rowcolumn",
7574 xmRowColumnWidgetClass, SurfCont->rccm,
7575 XmNpacking, XmPACK_TIGHT,
7576 XmNorientation , XmHORIZONTAL ,
7577 XmNmarginHeight, 0 ,
7578 XmNmarginWidth , 0 ,
7579 NULL);
7580
7581 SUMA_LH("Forming map mode menu");
7582 SUMA_BuildMenuReset(0);
7583 SUMA_BuildMenu ( rc, XmMENU_OPTION,
7584 "Col", '\0', YUP, CmapMode_Menu,
7585 (void *)ado,
7586 "VolCont->Dset_Mapping->Col",
7587 "Switch between color mapping modes.",
7588 SUMA_SurfContHelp_Col,
7589 SurfCont->CmapModeMenu);
7590 XtManageChild (SurfCont->CmapModeMenu->mw[SW_CmapMode]);
7591
7592 #if 0
7593 SUMA_LH("Forming new bias menu");
7594 SUMA_BuildMenuReset(0);
7595 SUMA_BuildMenu ( rc, XmMENU_OPTION,
7596 "Bias", '\0', YUP, CoordBias_Menu,
7597 (void *)ado,
7598 "VolCont->Dset_Mapping->Bias",
7599 "Coordinate bias direction",
7600 SUMA_SurfContHelp_Bias,
7601 SurfCont->CoordBiasMenu);
7602 XtManageChild (SurfCont->CoordBiasMenu->mw[SW_CoordBias]);
7603 #endif
7604 XtManageChild(rc);
7605 }
7606
7607 if (!SurfCont->rccm_swcmap) {
7608 SUMA_LH("Creating rccm_swcmap");
7609 SurfCont->rccm_swcmap = XtVaCreateWidget ("rowcolumn",
7610 xmRowColumnWidgetClass, SurfCont->rccm,
7611 XmNpacking, XmPACK_TIGHT,
7612 XmNorientation , XmHORIZONTAL ,
7613 XmNmarginHeight, 0 ,
7614 XmNmarginWidth , 0 ,
7615 NULL);
7616 }
7617
7618 {
7619 SUMA_CreateUpdatableCmapMenu(ado);
7620
7621 #if 0
7622 /* Not any more, menu is now stuck in its own rc */
7623 /* the loader, needs to be recreated with colormap menu */
7624 if (SurfCont->CmapLoad_pb) {
7625 XtDestroyWidget(SurfCont->CmapLoad_pb);
7626 SurfCont->CmapLoad_pb = NULL;
7627 }
7628 #endif
7629 if (!SurfCont->CmapLoad_pb) {
7630 SUMA_LH("Forming CmapLoad button");
7631 SurfCont->CmapLoad_pb = XtVaCreateManagedWidget ("New",
7632 xmPushButtonWidgetClass,
7633 SurfCont->rccm_swcmap,
7634 NULL);
7635 XtAddCallback (SurfCont->CmapLoad_pb, XmNactivateCallback,
7636 SUMA_cb_Cmap_Load, (XtPointer) ado);
7637 SUMA_Register_Widget_Help(SurfCont->CmapLoad_pb , 1,
7638 "VolCont->Dset_Mapping->Cmp->New",
7639 "Load new colormap",
7640 SUMA_SurfContHelp_CmpNew);
7641 }
7642 } /* new colormaps */
7643 if (!XtIsManaged(SurfCont->rccm_swcmap))
7644 XtManageChild (SurfCont->rccm_swcmap);
7645 }
7646
7647 /* Set the CoordBias's menu history to reflect current setting */
7648 SUMA_LH("Updating Link Mode History");
7649 SUMA_Set_Menu_Widget( SurfCont->LinkModeMenu,
7650 curColPlane->LinkMode);
7651
7652 SUMA_LH("Working the lock stuff ...");
7653 /* You'll need to fix the table's locking widget colors */
7654 if ( SurfCont->IntRangeLocked ==
7655 curColPlane->OptScl->AutoIntRange) {
7656 SUMA_LH(" Do the Int");
7657 /* need to put things in sync */
7658 SurfCont->IntRangeLocked = !SurfCont->IntRangeLocked;
7659 MCW_invert_widget_sync(SurfCont->SetRangeTable->cells[1], 0);
7660 }
7661 if ( SurfCont->BrtRangeLocked ==
7662 curColPlane->OptScl->AutoBrtRange) {
7663 SUMA_LH(" Do the Brt");
7664 /* need to put things in sync */
7665 SurfCont->BrtRangeLocked = !SurfCont->BrtRangeLocked;
7666 MCW_invert_widget_sync(SurfCont->SetRangeTable->cells[2], 0);
7667 }
7668
7669 /* Set the CoordBias's menu history to reflect current setting */
7670 SUMA_LH("Updating CoorBias chooser History");
7671 SUMA_Set_Menu_Widget( SurfCont->CoordBiasMenu,
7672 curColPlane->OptScl->DoBias);
7673
7674 /* Set the Col's menu history to reflect current setting */
7675 SUMA_LH("Updating Col chooser History");
7676 SUMA_Set_Menu_Widget( SurfCont->CmapModeMenu,
7677 curColPlane->OptScl->interpmode);
7678
7679 /* add the selectors for symmetric range and absolute threshold */
7680 if (!SurfCont->AbsThresh_tb) {
7681 Widget rc;
7682 rc = XtVaCreateWidget ("rowcolumn",
7683 xmRowColumnWidgetClass, SurfCont->rccm,
7684 XmNpacking, XmPACK_TIGHT,
7685 XmNorientation , XmHORIZONTAL ,
7686 XmNmarginHeight, 0 ,
7687 XmNmarginWidth , 0 ,
7688 NULL);
7689 /* create the absolute threshold toggle button */
7690 SurfCont->AbsThresh_tb = XtVaCreateManagedWidget("|T|",
7691 xmToggleButtonWidgetClass, rc,
7692 NULL);
7693 XtAddCallback (SurfCont->AbsThresh_tb,
7694 XmNvalueChangedCallback, SUMA_cb_AbsThresh_tb_toggled, ado);
7695 SUMA_Register_Widget_Help(SurfCont->AbsThresh_tb , 1,
7696 "VolCont->Dset_Mapping->abs_T",
7697 "Absolute threshold ON/OFF",
7698 SUMA_SurfContHelp_AbsThr );
7699
7700 SUMA_SET_SELECT_COLOR(SurfCont->AbsThresh_tb);
7701
7702 /* create the symmetric range toggle button */
7703 SurfCont->SymIrange_tb = XtVaCreateManagedWidget("sym I",
7704 xmToggleButtonWidgetClass, rc, NULL);
7705 XtAddCallback (SurfCont->SymIrange_tb,
7706 XmNvalueChangedCallback, SUMA_cb_SymIrange_tb_toggled, ado);
7707 SUMA_Register_Widget_Help(SurfCont->SymIrange_tb, 1,
7708 "VolCont->Dset_Mapping->sym_I",
7709 "Intensity range symmetry about 0 ",
7710 SUMA_SurfContHelp_Isym);
7711 SUMA_SET_SELECT_COLOR(SurfCont->SymIrange_tb);
7712
7713 /* add a button for zero masking */
7714 SurfCont->ShowZero_tb = XtVaCreateManagedWidget("shw 0",
7715 xmToggleButtonWidgetClass, rc, NULL);
7716 XtAddCallback (SurfCont->ShowZero_tb,
7717 XmNvalueChangedCallback, SUMA_cb_ShowZero_tb_toggled, ado);
7718 SUMA_Register_Widget_Help(SurfCont->ShowZero_tb, 1,
7719 "VolCont->Dset_Mapping->shw_0",
7720 "Color masking of nodes with intensity = 0 ",
7721 SUMA_SurfContHelp_Shw0);
7722 SUMA_SET_SELECT_COLOR(SurfCont->ShowZero_tb);
7723 XtManageChild (rc);
7724 }
7725
7726 if (0) {/* The clustering options - NOT YET IMPLEMENTED FOR VOLUMES -
7727 Interface OK, but callbacks do not handle volumes yet */
7728 char *col_tit[]= { " ", "Conn", "Area", NULL };
7729 char *col_hint[]={ "Clusterizing options",
7730 "Connectedness criterion",
7731 "Cluster Area Threshold", NULL };
7732 char *col_help[]={ SUMA_SurfContHelp_SetClustTbl_r0,
7733 SUMA_SurfContHelp_SetClustTbl_c1,
7734 SUMA_SurfContHelp_SetClustTbl_c2, NULL
7735 };
7736 char *row_tit[]={ " ", "Clst", NULL};
7737 char *row_hint[]={ "Clusterizing options", "Clust on/off", NULL};
7738 char *row_help[]={ SUMA_SurfContHelp_SetClustTbl_r0,
7739 SUMA_SurfContHelp_SetClustTbl_r1, NULL
7740 };
7741
7742 SUMA_LH("Receptacle");
7743 if (!SurfCont->rcclust) {
7744 SurfCont->rcclust = XtVaCreateWidget ("rowcolumn",
7745 xmRowColumnWidgetClass, SurfCont->opts_form,
7746 XmNpacking, XmPACK_TIGHT,
7747 XmNorientation , XmHORIZONTAL ,
7748 XmNmarginHeight, 0,
7749 XmNmarginWidth, 0,
7750 XmNrightAttachment, XmATTACH_FORM ,
7751 XmNleftAttachment, XmATTACH_NONE,
7752 XmNtopAttachment, XmATTACH_WIDGET ,
7753 XmNtopWidget, SurfCont->opts_rc,
7754 NULL);
7755 FirstTime = YUP; /* the first time around */
7756 } else {
7757 FirstTime = NOPE;
7758 }
7759
7760 if (FirstTime) {/* new clust */
7761 SUMA_LH("FirstTime set");
7762 if (!SurfCont->SetClustTable->cells) {
7763 int colw[3] = { 4, 6, 6 };
7764 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)
7765 calloc(1,sizeof(SUMA_SRV_DATA));
7766 srvd->ado = ado; srvd->colp = NULL;
7767 /* create the widgets for the range table */
7768 SUMA_LH("Creating table");
7769 SUMA_CreateTable( SurfCont->rcclust,
7770 2, 3,
7771 "VolCont->Dset_Mapping->Clst",
7772 row_tit, col_tit,
7773 row_hint, col_hint,
7774 row_help, col_help,
7775 colw, YUP, SUMA_float,
7776 SUMA_cb_SetClustValue, (void *)srvd,
7777 SUMA_SetClustTableTit_EV, NULL,
7778 SUMA_SetClustTableCell_EV, NULL,
7779 SurfCont->SetClustTable);
7780 }
7781
7782 if (curColPlane->OptScl) {
7783 SUMA_SetTableTitleButton1(SurfCont->SetClustTable, 1,0, curColPlane->OptScl->Clusterize);
7784 }
7785 }
7786 SUMA_LH("Managerial");
7787
7788 if (!XtIsManaged(SurfCont->rcclust))
7789 XtManageChild (SurfCont->rcclust);
7790
7791 /* do the initialization */
7792 SUMA_InitClustTable(ado); /* init the clust table values*/
7793 }/* The clustering options */
7794
7795
7796 if (curColPlane->OptScl->ThrMode == SUMA_ABS_LESS_THAN) {
7797 XmToggleButtonSetState( SurfCont->AbsThresh_tb, True, NOPE);
7798 } else if (curColPlane->OptScl->ThrMode == SUMA_LESS_THAN){
7799 XmToggleButtonSetState( SurfCont->AbsThresh_tb, False, NOPE);
7800 } else {
7801 SUMA_S_Err("Not ready to handle ThrModeR of %d yet",
7802 curColPlane->OptScl->ThrMode);
7803 }
7804 if (!curColPlane->SymIrange) {
7805 XmToggleButtonSetState( SurfCont->SymIrange_tb, False, NOPE);
7806 } else {
7807 XmToggleButtonSetState( SurfCont->SymIrange_tb, True, NOPE);
7808 }
7809 if (!curColPlane->OptScl->MaskZero) {
7810 XmToggleButtonSetState( SurfCont->ShowZero_tb, True, NOPE);
7811 } else {
7812 XmToggleButtonSetState( SurfCont->ShowZero_tb, False, NOPE);
7813 }
7814
7815 if (!XtIsManaged(SurfCont->rccm)) XtManageChild (SurfCont->rccm);
7816
7817 }/* The Color map range and selector block */
7818
7819 { /* The Range values block*/
7820 char *col_tit[]= { " ", "Min", "Vox", "Max", "Vox", NULL};
7821 char *col_hint[]= { "Full range of values in Dset",
7822 "Minimum value in Dset column",
7823 "Node index at minimum",
7824 "Maximum value in Dset column",
7825 "Node index at maximum", NULL};
7826 char *col_help[]= { SUMA_SurfContHelp_RangeTbl_c0,
7827 SUMA_SurfContHelp_RangeTbl_c1,
7828 SUMA_SurfContHelp_RangeTbl_c2,
7829 SUMA_SurfContHelp_RangeTbl_c3,
7830 SUMA_SurfContHelp_RangeTbl_c4, NULL};
7831 char *row_tit[]= { " ", "I", "T", "B", NULL};
7832 char *row_hint[]= { "Full range of values in Dset",
7833 "Range of values in intensity (I) column",
7834 "Range of values in threshold (T) column",
7835 "Range of values in brightness (B) column", NULL};
7836 char *row_help[]= { SUMA_SurfContHelp_RangeTbl_c0,
7837 SUMA_SurfContHelp_RangeTbl_r1,
7838 SUMA_SurfContHelp_RangeTbl_r2,
7839 SUMA_SurfContHelp_RangeTbl_r3, NULL};
7840 if (!SurfCont->rcswr) {
7841 SurfCont->rcswr = XtVaCreateWidget ("rowcolumn",
7842 xmRowColumnWidgetClass, SurfCont->opts_form,
7843 XmNpacking, XmPACK_TIGHT,
7844 XmNorientation , XmVERTICAL ,
7845 XmNrightAttachment, XmATTACH_FORM ,
7846 XmNleftAttachment, XmATTACH_NONE,
7847 XmNtopAttachment, XmATTACH_WIDGET ,
7848 XmNtopWidget, SurfCont->rcclust?SurfCont->rcclust:SurfCont->opts_rc,
7849 NULL);
7850 }
7851
7852 if (!SurfCont->RangeTable->cells) {
7853 int colw[5] = { 1, 6, 6, 6, 6 };
7854 /* create the widgets for the range table */
7855 SUMA_CreateTable( SurfCont->rcswr,
7856 4, 5,
7857 "VolCont->Dset_Mapping->RangeTable",
7858 row_tit, col_tit,
7859 row_hint, col_hint,
7860 row_help, col_help,
7861 colw, NOPE, SUMA_string,
7862 NULL, NULL,
7863 NULL, NULL,
7864 SUMA_RangeTableCell_EV, (void *)ado,
7865 SurfCont->RangeTable);
7866 }
7867
7868 if (!XtIsManaged(SurfCont->rcswr)) XtManageChild (SurfCont->rcswr);
7869 } /* The Range values block */
7870
7871 if (NewDset) {
7872 /* initialize tables of range values */
7873 SUMA_InitRangeTable(ado, 2);
7874 }
7875
7876 if (!XtIsManaged(SurfCont->rcvo)) XtManageChild (SurfCont->rcvo);
7877 SUMA_FORCE_SCALE_HEIGHT(SUMA_ADO_Cont(ado));
7878
7879 SUMA_RETURNe;
7880 }
7881
SUMA_set_cmap_options_GLDO(SUMA_ALL_DO * ado,SUMA_Boolean NewDset,SUMA_Boolean NewMap)7882 void SUMA_set_cmap_options_GLDO(SUMA_ALL_DO *ado, SUMA_Boolean NewDset,
7883 SUMA_Boolean NewMap)
7884 {
7885 static char FuncName[]={"SUMA_set_cmap_options_GLDO"};
7886 SUMA_MenuItem *SwitchInt_Menu = NULL, *SwitchThr_Menu = NULL,
7887 *SwitchBrt_Menu = NULL;
7888 int N_items, FirstTime;
7889 SUMA_X_SurfCont *SurfCont=NULL;
7890 SUMA_OVERLAYS *curColPlane=NULL;
7891
7892 SUMA_Boolean LocalHead = NOPE;
7893
7894 SUMA_ENTRY;
7895
7896 if (!ado) SUMA_RETURNe;
7897
7898 SurfCont = SUMA_ADO_Cont(ado);
7899 curColPlane = SUMA_ADO_CurColPlane(ado);
7900
7901 if (!SurfCont) SUMA_RETURNe;
7902 if (!SurfCont->opts_form || !SurfCont->opts_rc) SUMA_RETURNe;
7903 if (!curColPlane) SUMA_RETURNe;
7904 if (!NewDset && !NewMap && SurfCont->rcvo && SurfCont->rccm) {
7905 SUMA_SL_Err("Nothing to do");
7906 SUMA_RETURNe;
7907 }
7908 /* row column to contain all switching stuffs */
7909 if (!SurfCont->rcvo){
7910 SurfCont->rcvo = XtVaCreateWidget ("rowcolumn",
7911 xmRowColumnWidgetClass, SurfCont->opts_rc,
7912 XmNpacking, XmPACK_TIGHT,
7913 XmNorientation , XmVERTICAL ,
7914 XmNmarginHeight, 0 ,
7915 XmNmarginWidth , 0 ,
7916 NULL);
7917 NewDset = YUP; /* The first time around */
7918 } else {
7919 /* (no need ..) */
7920 /* XtUnmanageChild(SurfCont->rcvo); */
7921 }
7922
7923 if (NewDset) { /* The intensity / threshold / Brightness block*/
7924 /* link mode */
7925 if (!SurfCont->LinkModeMenu->mw[SW_LinkMode]) {
7926 Widget rc = NULL; /* one pass through this block ONLY */
7927 rc = XtVaCreateWidget ("rowcolumn",
7928 xmRowColumnWidgetClass, SurfCont->rcvo,
7929 XmNpacking, XmPACK_TIGHT,
7930 XmNorientation , XmHORIZONTAL ,
7931 XmNmarginHeight, 0 ,
7932 XmNmarginWidth , 0 ,
7933 NULL);
7934
7935 SUMA_LH("Forming map mode menu");
7936 SUMA_BuildMenuReset(0);
7937 SUMA_BuildMenu ( rc, XmMENU_OPTION,
7938 "IxT", '\0', YUP, LinkMode_Menu,
7939 (void *)ado,
7940 "GraphCont->GDset_Mapping->IxT",
7941 "Set I, T selection linking modes.",
7942 SUMA_SurfContHelp_Link,
7943 SurfCont->LinkModeMenu);
7944 XtManageChild (SurfCont->LinkModeMenu->mw[SW_LinkMode]);
7945
7946 XtManageChild(rc);
7947 }
7948
7949 if (!SurfCont->rcsw) {
7950 SurfCont->rcsw = XtVaCreateWidget ("rowcolumn",
7951 xmRowColumnWidgetClass, SurfCont->rcvo,
7952 XmNpacking, XmPACK_TIGHT,
7953 XmNorientation , XmHORIZONTAL ,
7954 XmNheight, 105, /* don't let that change dynamically, */
7955 XmNresizeHeight, False, /* it messes up the frame size, when you
7956 switch dsets*/
7957 XmNmarginHeight, 0 ,
7958 XmNmarginWidth , 0 ,
7959 NULL);
7960 } else {
7961 /* (no need ..) */
7962 /*XtUnmanageChild(SurfCont->rcsw); */
7963 }
7964 if (!SurfCont->rcsw_v1) {
7965 SurfCont->rcsw_v1 = XtVaCreateWidget ("rowcolumn",
7966 xmRowColumnWidgetClass, SurfCont->rcsw,
7967 XmNpacking, XmPACK_COLUMN,
7968 XmNorientation , XmVERTICAL ,
7969 XmNnumColumns, 1,
7970 XmNmarginHeight, 0 ,
7971 XmNmarginWidth , 0 ,
7972 NULL);
7973 }
7974 if (!SurfCont->rcsw_v2) {
7975 SurfCont->rcsw_v2 = XtVaCreateWidget ("rowcolumn",
7976 xmRowColumnWidgetClass, SurfCont->rcsw,
7977 XmNpacking, XmPACK_COLUMN,
7978 XmNorientation , XmVERTICAL ,
7979 XmNnumColumns, 1,
7980 XmNmarginHeight, 0 ,
7981 XmNmarginWidth , 0 ,
7982 NULL);
7983 }
7984
7985 /* Switching triplets */
7986 SwitchInt_Menu =
7987 SUMA_FormSwitchColMenuVector(ado, 0, &N_items);
7988 if (LocalHead) fprintf (SUMA_STDERR,"%s: %d items.\n", FuncName, N_items);
7989 if (SwitchInt_Menu || !N_items) {
7990 SurfCont->SwitchIntMenu =
7991 SUMA_Free_Menu_Widget(SurfCont->SwitchIntMenu);
7992 SurfCont->SwitchIntMenu =
7993 SUMA_Alloc_Menu_Widget(N_items+1);
7994 SUMA_BuildMenuReset(13);
7995 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
7996 "I", '\0', YUP, SwitchInt_Menu,
7997 (void *)ado,
7998 "GraphCont->GDset_Mapping->I",
7999 "Select Intensity (I) column, aka sub-brick. (BHelp for more)",
8000 SUMA_SurfContHelp_SelInt,
8001 SurfCont->SwitchIntMenu );
8002 XtInsertEventHandler( SurfCont->SwitchIntMenu->mw[0] ,
8003 /* handle events in optmenu */
8004 ButtonPressMask , /* button presses */
8005 FALSE , /* nonmaskable events? */
8006 SUMA_optmenu_EV , /* handler */
8007 (XtPointer) ado , /* client data */
8008 XtListTail ) ;
8009 if (LocalHead)
8010 SUMA_ShowMeTheChildren(SurfCont->SwitchIntMenu->mw[0]);
8011 XtManageChild (SurfCont->SwitchIntMenu->mw[0]);
8012 /* Now destroy the SwitchInt_Menu */
8013 SwitchInt_Menu = SUMA_FreeMenuVector(SwitchInt_Menu, N_items);
8014 /* setup the history to the proper widget */
8015 SUMA_Set_Menu_Widget(SurfCont->SwitchIntMenu,
8016 curColPlane->OptScl->find+1) ;
8017 } else {
8018 SUMA_SL_Err("NULL SwitchInt_Menu");
8019 }
8020
8021 SwitchThr_Menu =
8022 SUMA_FormSwitchColMenuVector(ado, 1, &N_items);
8023 if (SwitchThr_Menu || !N_items) {
8024 SurfCont->SwitchThrMenu =
8025 SUMA_Free_Menu_Widget(SurfCont->SwitchThrMenu);
8026 SurfCont->SwitchThrMenu =
8027 SUMA_Alloc_Menu_Widget(N_items+1);
8028 SUMA_BuildMenuReset(13);
8029 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
8030 "T", '\0', YUP, SwitchThr_Menu,
8031 (void *)ado,
8032 "GraphCont->GDset_Mapping->T",
8033 "Select Threshold (T) column, aka sub-brick. (BHelp for more)",
8034 SUMA_SurfContHelp_SelThr ,
8035 SurfCont->SwitchThrMenu );
8036 XtInsertEventHandler( SurfCont->SwitchThrMenu->mw[0] ,
8037 /* handle events in optmenu */
8038 ButtonPressMask , /* button presses */
8039 FALSE , /* nonmaskable events? */
8040 SUMA_optmenu_EV , /* handler */
8041 (XtPointer) ado , /* client data */
8042 XtListTail ) ;
8043 XtManageChild (SurfCont->SwitchThrMenu->mw[0]);
8044 /* Now destroy the SwitchThr_Menu */
8045 SwitchThr_Menu = SUMA_FreeMenuVector(SwitchThr_Menu, N_items);
8046 /* setup the history to the proper widget */
8047 SUMA_Set_Menu_Widget(SurfCont->SwitchThrMenu,
8048 curColPlane->OptScl->tind+1);
8049 } else {
8050 SUMA_SL_Err("NULL SwitchThr_Menu");
8051 }
8052
8053 SwitchBrt_Menu =
8054 SUMA_FormSwitchColMenuVector(ado, 2, &N_items);
8055 if (SwitchBrt_Menu || !N_items) {
8056 SurfCont->SwitchBrtMenu =
8057 SUMA_Free_Menu_Widget(SurfCont->SwitchBrtMenu);
8058 SurfCont->SwitchBrtMenu =
8059 SUMA_Alloc_Menu_Widget(N_items+1);
8060 SUMA_BuildMenuReset(13);
8061 SUMA_BuildMenu (SurfCont->rcsw_v1, XmMENU_OPTION, /* populate it */
8062 "B", '\0', YUP, SwitchBrt_Menu,
8063 (void *)ado,
8064 "GraphCont->GDset_Mapping->B",
8065 "Select Brightness (B) column, aka sub-brick. (BHelp for more)",
8066 SUMA_SurfContHelp_SelBrt,
8067 SurfCont->SwitchBrtMenu );
8068 XtInsertEventHandler( SurfCont->SwitchBrtMenu->mw[0] ,
8069 /* handle events in optmenu */
8070 ButtonPressMask , /* button presses */
8071 FALSE , /* nonmaskable events? */
8072 SUMA_optmenu_EV , /* handler */
8073 (XtPointer) ado , /* client data */
8074 XtListTail ) ;
8075
8076 XtManageChild (SurfCont->SwitchBrtMenu->mw[0]);
8077 /* Now destroy the SwitchBrt_Menu */
8078 SwitchBrt_Menu = SUMA_FreeMenuVector(SwitchBrt_Menu, N_items);
8079 /* setup the history to the proper widget */
8080 SUMA_Set_Menu_Widget(SurfCont->SwitchBrtMenu,
8081 curColPlane->OptScl->bind+1);
8082 } else {
8083 SUMA_SL_Err("NULL SwitchBrt_Menu");
8084 }
8085
8086 if (1) {
8087 /* put the toggle buttons */
8088 if (!SurfCont->Int_tb) {
8089 SurfCont->Int_tb = XtVaCreateManagedWidget("v",
8090 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
8091 XtAddCallback (SurfCont->Int_tb,
8092 XmNvalueChangedCallback, SUMA_cb_SwitchInt_toggled, ado);
8093 SUMA_Register_Widget_Help(SurfCont->Int_tb, 1,
8094 "GraphCont->GDset_Mapping->I->v",
8095 "View (ON)/Hide graph edge colors",
8096 SUMA_GraphContHelp_SelIntTgl);
8097 SUMA_SET_SELECT_COLOR(SurfCont->Int_tb);
8098 }
8099 XmToggleButtonSetState (SurfCont->Int_tb,
8100 curColPlane->ShowMode > 0 ? 1:0 , NOPE);
8101
8102 if (!SurfCont->Thr_tb) {
8103 SurfCont->Thr_tb = XtVaCreateManagedWidget("v",
8104 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
8105 XtAddCallback (SurfCont->Thr_tb,
8106 XmNvalueChangedCallback, SUMA_cb_SwitchThr_toggled, ado);
8107 SUMA_SET_SELECT_COLOR(SurfCont->Thr_tb);
8108 SUMA_Register_Widget_Help(SurfCont->Thr_tb, 1,
8109 "GraphCont->GDset_Mapping->T->v",
8110 "Apply (ON)/Ignore thresholding",
8111 SUMA_SurfContHelp_SelThrTgl);
8112 }
8113 if (curColPlane->OptScl->tind >=0) {
8114 XmToggleButtonSetState (SurfCont->Thr_tb,
8115 curColPlane->OptScl->UseThr, NOPE);
8116 }else {
8117 XmToggleButtonSetState (SurfCont->Thr_tb, NOPE, NOPE);
8118 }
8119
8120 if (!SurfCont->Brt_tb) {
8121 SurfCont->Brt_tb = XtVaCreateManagedWidget("v",
8122 xmToggleButtonWidgetClass, SurfCont->rcsw_v2, NULL);
8123 XtAddCallback (SurfCont->Brt_tb,
8124 XmNvalueChangedCallback, SUMA_cb_SwitchBrt_toggled, ado);
8125 SUMA_SET_SELECT_COLOR(SurfCont->Brt_tb);
8126 SUMA_Register_Widget_Help(SurfCont->Brt_tb, 1,
8127 "GraphCont->GDset_Mapping->B->v",
8128 "View (ON)/Ignore brightness modulation",
8129 SUMA_SurfContHelp_SelBrtTgl);
8130 }
8131 if (curColPlane->OptScl->bind >=0) {
8132 XmToggleButtonSetState (SurfCont->Brt_tb,
8133 curColPlane->OptScl->UseBrt, NOPE);
8134 } else {
8135 XmToggleButtonSetState (SurfCont->Brt_tb, NOPE, NOPE);
8136 }
8137 }
8138 if (!XtIsManaged(SurfCont->rcsw_v1))
8139 XtManageChild (SurfCont->rcsw_v1);
8140 if (!XtIsManaged(SurfCont->rcsw_v2))
8141 XtManageChild (SurfCont->rcsw_v2);
8142 if (!XtIsManaged(SurfCont->rcsw)) XtManageChild (SurfCont->rcsw);
8143 } /* The intensity / threshold / Brightness block */
8144
8145
8146 {/* The Color map range and selector block */
8147 char *col_tit[]= { " ", "Min", "Max", NULL};
8148 char *col_hint[]= { "Clipping ranges",
8149 "Minimum clip value",
8150 "Maximum clip value" , NULL};
8151 char *col_help[]= { SUMA_SurfContHelp_SetRngTbl_r0,
8152 SUMA_SurfContHelp_SetRngTbl_c1,
8153 SUMA_SurfContHelp_SetRngTbl_c2 , NULL};
8154 char *row_tit[]= { " ", "I", "B", " " , "C", NULL};
8155 char *row_hint[]= {
8156 "Clipping ranges ",
8157 "Intensity clipping range (append '%' for percentiles, see BHelp)",
8158 "Brightness modulation clipping range (much more with BHelp)",
8159 "Brightness modulation factor range (much more with BHelp)" ,
8160 "Coordinate bias range (much more with BHelp)", NULL};
8161 char *row_help[]= { SUMA_SurfContHelp_SetRngTbl_r0,
8162 SUMA_SurfContHelp_SetRngTbl_r1,
8163 SUMA_SurfContHelp_SetRngTbl_r2,
8164 SUMA_SurfContHelp_SetRngTbl_r3,
8165 SUMA_SurfContHelp_SetRngTbl_r4, NULL};
8166 if (!SurfCont->rccm) {
8167 SurfCont->rccm = XtVaCreateWidget ("rowcolumn",
8168 xmRowColumnWidgetClass, SurfCont->rcvo,
8169 XmNpacking, XmPACK_TIGHT,
8170 XmNorientation , XmVERTICAL ,
8171 XmNmarginHeight, 0,
8172 XmNmarginWidth, 0,
8173 NULL);
8174 NewMap = YUP; /* the first time around */
8175 }
8176
8177 if (NewMap) {/* new colormaps */
8178 SUMA_LH("NewMap set");
8179 SUMA_Register_Widget_Help(SurfCont->rccm, 0,
8180 "GraphCont->GDset_Mapping->SetRangeTable",
8181 "Edge colorization parameters",
8182 "Set parameters for mapping edge data onto color scale");
8183 if (!SurfCont->SetRangeTable->cells) {
8184 int colw[3] = { 1, 8, 8 };
8185 SUMA_SRV_DATA *srvd=(SUMA_SRV_DATA *)calloc(1,sizeof(SUMA_SRV_DATA));
8186 srvd->ado = ado; srvd->colp = NULL;
8187 /* create the widgets for the range table */
8188 SUMA_LH("Creating table");
8189 SUMA_CreateTable( SurfCont->rccm,
8190 5, 3,
8191 "GraphCont->GDset_Mapping->SetRangeTable",
8192 row_tit, col_tit,
8193 row_hint, col_hint,
8194 row_help, col_help,
8195 colw, YUP, SUMA_float,
8196 SUMA_cb_SetRangeValue, (void *)srvd,
8197 SUMA_SetRangeTableTit_EV, NULL,
8198 NULL, NULL,
8199 SurfCont->SetRangeTable);
8200 }
8201 if (!SurfCont->CoordBiasMenu->mw[SW_CoordBias]) {
8202 Widget rc = NULL; /* one pass through this block ONLY */
8203 rc = XtVaCreateWidget ("rowcolumn",
8204 xmRowColumnWidgetClass, SurfCont->rccm,
8205 XmNpacking, XmPACK_TIGHT,
8206 XmNorientation , XmHORIZONTAL ,
8207 XmNmarginHeight, 0 ,
8208 XmNmarginWidth , 0 ,
8209 NULL);
8210
8211 SUMA_LH("Forming map mode menu");
8212 SUMA_BuildMenuReset(0);
8213 SUMA_BuildMenu ( rc, XmMENU_OPTION,
8214 "Col", '\0', YUP, CmapMode_Menu,
8215 (void *)ado,
8216 "GraphCont->GDset_Mapping->Col",
8217 "Switch between color mapping modes.",
8218 SUMA_SurfContHelp_Col,
8219 SurfCont->CmapModeMenu);
8220 XtManageChild (SurfCont->CmapModeMenu->mw[SW_CmapMode]);
8221
8222 #if 0
8223 SUMA_LH("Forming new bias menu");
8224 SUMA_BuildMenuReset(0);
8225 SUMA_BuildMenu ( rc, XmMENU_OPTION,
8226 "Bias", '\0', YUP, CoordBias_Menu,
8227 (void *)ado,
8228 "GraphCont->GDset_Mapping->Bias",
8229 "Coordinate bias direction",
8230 SUMA_SurfContHelp_Bias,
8231 SurfCont->CoordBiasMenu);
8232 XtManageChild (SurfCont->CoordBiasMenu->mw[SW_CoordBias]);
8233 #endif
8234
8235 XtManageChild(rc);
8236 }
8237
8238 if (!SurfCont->rccm_swcmap) {
8239 SUMA_LH("Creating rccm_swcmap");
8240 SurfCont->rccm_swcmap = XtVaCreateWidget ("rowcolumn",
8241 xmRowColumnWidgetClass, SurfCont->rccm,
8242 XmNpacking, XmPACK_TIGHT,
8243 XmNorientation , XmHORIZONTAL ,
8244 XmNmarginHeight, 0 ,
8245 XmNmarginWidth , 0 ,
8246 NULL);
8247 }
8248
8249 {
8250 SUMA_CreateUpdatableCmapMenu((SUMA_ALL_DO *)ado);
8251
8252 #if 0
8253 /* Not any more, menu is now stuck in its own rc */
8254 /* the loader, needs to be recreated with colormap menu */
8255 if (SurfCont->CmapLoad_pb) {
8256 XtDestroyWidget(SurfCont->CmapLoad_pb);
8257 SurfCont->CmapLoad_pb = NULL;
8258 }
8259 #endif
8260 if (!SurfCont->CmapLoad_pb) {
8261 SUMA_LH("Forming CmapLoad button");
8262 SurfCont->CmapLoad_pb = XtVaCreateManagedWidget ("New",
8263 xmPushButtonWidgetClass,
8264 SurfCont->rccm_swcmap,
8265 NULL);
8266 XtAddCallback (SurfCont->CmapLoad_pb, XmNactivateCallback,
8267 SUMA_cb_Cmap_Load, (XtPointer) ado);
8268 SUMA_Register_Widget_Help(SurfCont->CmapLoad_pb , 1,
8269 "GraphCont->GDset_Mapping->Cmp->New",
8270 "Load new colormap",
8271 SUMA_SurfContHelp_CmpNew);
8272 }
8273 } /* new colormaps */
8274 if (!XtIsManaged(SurfCont->rccm_swcmap))
8275 XtManageChild (SurfCont->rccm_swcmap);
8276 }
8277
8278 /* Set the CoordBias's menu history to reflect current setting */
8279 SUMA_LH("Updating Link Mode History");
8280 SUMA_Set_Menu_Widget( SurfCont->LinkModeMenu,
8281 curColPlane->LinkMode);
8282
8283 SUMA_LH("Working the lock stuff ...");
8284 /* You'll need to fix the table's locking widget colors */
8285 if ( SurfCont->IntRangeLocked ==
8286 curColPlane->OptScl->AutoIntRange) {
8287 SUMA_LH(" Do the Int");
8288 /* need to put things in sync */
8289 SurfCont->IntRangeLocked = !SurfCont->IntRangeLocked;
8290 MCW_invert_widget_sync(SurfCont->SetRangeTable->cells[1], 0);
8291 }
8292 if ( SurfCont->BrtRangeLocked ==
8293 curColPlane->OptScl->AutoBrtRange) {
8294 SUMA_LH(" Do the Brt");
8295 /* need to put things in sync */
8296 SurfCont->BrtRangeLocked = !SurfCont->BrtRangeLocked;
8297 MCW_invert_widget_sync(SurfCont->SetRangeTable->cells[2], 0);
8298 }
8299
8300 /* Set the CoordBias's menu history to reflect current setting */
8301 SUMA_LH("Updating CoorBias chooser History");
8302 SUMA_Set_Menu_Widget( SurfCont->CoordBiasMenu,
8303 curColPlane->OptScl->DoBias);
8304
8305 /* Set the Col's menu history to reflect current setting */
8306 SUMA_LH("Updating Col chooser History");
8307 SUMA_Set_Menu_Widget( SurfCont->CmapModeMenu,
8308 curColPlane->OptScl->interpmode);
8309
8310 /* add the selectors for symmetric range and absolute threshold */
8311 if (!SurfCont->AbsThresh_tb) {
8312 Widget rc;
8313 rc = XtVaCreateWidget ("rowcolumn",
8314 xmRowColumnWidgetClass, SurfCont->rccm,
8315 XmNpacking, XmPACK_TIGHT,
8316 XmNorientation , XmHORIZONTAL ,
8317 XmNmarginHeight, 0 ,
8318 XmNmarginWidth , 0 ,
8319 NULL);
8320 /* create the absolute threshold toggle button */
8321 SurfCont->AbsThresh_tb = XtVaCreateManagedWidget("|T|",
8322 xmToggleButtonWidgetClass, rc,
8323 NULL);
8324 XtAddCallback (SurfCont->AbsThresh_tb,
8325 XmNvalueChangedCallback, SUMA_cb_AbsThresh_tb_toggled, ado);
8326 SUMA_Register_Widget_Help(SurfCont->AbsThresh_tb , 1,
8327 "GraphCont->GDset_Mapping->abs_T",
8328 "Absolute threshold ON/OFF",
8329 SUMA_SurfContHelp_AbsThr );
8330
8331 SUMA_SET_SELECT_COLOR(SurfCont->AbsThresh_tb);
8332
8333 /* create the symmetric range toggle button */
8334 SurfCont->SymIrange_tb = XtVaCreateManagedWidget("sym I",
8335 xmToggleButtonWidgetClass, rc, NULL);
8336 XtAddCallback (SurfCont->SymIrange_tb,
8337 XmNvalueChangedCallback, SUMA_cb_SymIrange_tb_toggled, ado);
8338 SUMA_Register_Widget_Help(SurfCont->SymIrange_tb, 1,
8339 "GraphCont->GDset_Mapping->sym_I",
8340 "Intensity range symmetry about 0 ",
8341 SUMA_SurfContHelp_Isym );
8342 SUMA_SET_SELECT_COLOR(SurfCont->SymIrange_tb);
8343
8344 /* add a button for zero masking */
8345 SurfCont->ShowZero_tb = XtVaCreateManagedWidget("shw 0",
8346 xmToggleButtonWidgetClass, rc, NULL);
8347 XtAddCallback (SurfCont->ShowZero_tb,
8348 XmNvalueChangedCallback, SUMA_cb_ShowZero_tb_toggled, ado);
8349 SUMA_Register_Widget_Help(SurfCont->ShowZero_tb, 1,
8350 "GraphCont->GDset_Mapping->shw_0",
8351 "Color masking of nodes with intensity = 0 ",
8352 SUMA_SurfContHelp_Shw0);
8353 SUMA_SET_SELECT_COLOR(SurfCont->ShowZero_tb);
8354 XtManageChild (rc);
8355 }
8356
8357 if (curColPlane->OptScl->ThrMode == SUMA_ABS_LESS_THAN) {
8358 XmToggleButtonSetState( SurfCont->AbsThresh_tb, True, NOPE);
8359 } else if (curColPlane->OptScl->ThrMode == SUMA_LESS_THAN) {
8360 XmToggleButtonSetState( SurfCont->AbsThresh_tb, False, NOPE);
8361 } else {
8362 SUMA_S_Err("Not ready to handle ThrModeR of %d yet",
8363 curColPlane->OptScl->ThrMode);
8364 }
8365 if (!curColPlane->SymIrange) {
8366 XmToggleButtonSetState( SurfCont->SymIrange_tb, False, NOPE);
8367 } else {
8368 XmToggleButtonSetState( SurfCont->SymIrange_tb, True, NOPE);
8369 }
8370 if (!curColPlane->OptScl->MaskZero) {
8371 XmToggleButtonSetState( SurfCont->ShowZero_tb, True, NOPE);
8372 } else {
8373 XmToggleButtonSetState( SurfCont->ShowZero_tb, False, NOPE);
8374 }
8375
8376 if (!XtIsManaged(SurfCont->rccm)) XtManageChild (SurfCont->rccm);
8377
8378 }/* The Color map range and selector block */
8379
8380 if (1){ /* The Range values block*/
8381 char *col_tit[]= { " ", "Min", "Edge", "Max", "Edge", NULL};
8382 char *col_hint[]= { "Full range of values in Dset",
8383 "Minimum value in Dset column",
8384 "Edge index at minimum",
8385 "Maximum value in Dset column",
8386 "Edge index at maximum", NULL};
8387 char *col_help[]= { SUMA_SurfContHelp_RangeTbl_c0,
8388 SUMA_SurfContHelp_RangeTbl_c1,
8389 SUMA_GraphContHelp_RangeTbl_c2,
8390 SUMA_SurfContHelp_RangeTbl_c3,
8391 SUMA_GraphContHelp_RangeTbl_c4, NULL};
8392 char *row_tit[]= { " ", "I", "T", "B", NULL};
8393 char *row_hint[]= { "Full range of values in Dset",
8394 "Range of values in intensity (I) column",
8395 "Range of values in threshold (T) column",
8396 "Range of values in brightness (B) column", NULL};
8397 char *row_help[]= { SUMA_SurfContHelp_RangeTbl_c0,
8398 SUMA_SurfContHelp_RangeTbl_r1,
8399 SUMA_SurfContHelp_RangeTbl_r2,
8400 SUMA_SurfContHelp_RangeTbl_r3, NULL};
8401 if (!SurfCont->rcswr) {
8402 SurfCont->rcswr = XtVaCreateWidget ("rowcolumn",
8403 xmRowColumnWidgetClass, SurfCont->opts_form,
8404 XmNpacking, XmPACK_TIGHT,
8405 XmNorientation , XmVERTICAL ,
8406 XmNrightAttachment, XmATTACH_FORM ,
8407 XmNleftAttachment, XmATTACH_NONE,
8408 XmNtopAttachment, XmATTACH_WIDGET ,
8409 XmNtopWidget, SurfCont->opts_rc,
8410 NULL);
8411 }
8412
8413 if (!SurfCont->RangeTable->cells) {
8414 int colw[5] = { 1, 6, 6, 6, 6 };
8415 /* create the widgets for the range table */
8416 SUMA_CreateTable( SurfCont->rcswr,
8417 4, 5,
8418 "GraphCont->GDset_Mapping->RangeTable",
8419 row_tit, col_tit,
8420 row_hint, col_hint,
8421 row_help, col_help,
8422 colw, NOPE, SUMA_string,
8423 NULL, NULL,
8424 NULL, NULL,
8425 SUMA_RangeTableCell_EV, (void *)ado,
8426 SurfCont->RangeTable);
8427 }
8428
8429 if (!XtIsManaged(SurfCont->rcswr)) XtManageChild (SurfCont->rcswr);
8430 } /* The Range values block */
8431
8432 if (NewDset) {
8433 /* initialize tables of range values */
8434 SUMA_InitRangeTable(ado, 2);
8435 }
8436
8437 if (!XtIsManaged(SurfCont->rcvo)) XtManageChild (SurfCont->rcvo);
8438 SUMA_FORCE_SCALE_HEIGHT(SUMA_ADO_Cont(ado));
8439
8440 SUMA_RETURNe;
8441 }
8442
8443 /*!
8444 A function to create the cmap selection menu
8445 in a manner that can be recreated if the menu
8446 contents change. You can call this function
8447 repeatedly whenever menu contents change
8448 */
SUMA_CreateUpdatableCmapMenu(SUMA_ALL_DO * ado)8449 void SUMA_CreateUpdatableCmapMenu(SUMA_ALL_DO *ado)
8450 {
8451 static char FuncName[]={"SUMA_CreateUpdatableCmapMenu"};
8452 SUMA_MenuItem *SwitchCmap_Menu = NULL;
8453 SUMA_X_SurfCont *SurfCont=NULL;
8454 char *wname;
8455 SUMA_Boolean LocalHead = NOPE;
8456
8457 SUMA_ENTRY;
8458
8459 if (!SUMAg_CF->scm) {
8460 SUMAg_CF->scm = SUMA_Build_Color_maps();
8461 if (!SUMAg_CF->scm) {
8462 SUMA_SL_Err("Failed to build color maps.\n");
8463 SUMA_RETURNe;
8464 }
8465 }
8466
8467 SurfCont = SUMA_ADO_Cont(ado);
8468 if (!SurfCont->rc_CmapCont) { /* first pass, create placement container */
8469 SurfCont->rc_CmapCont = XtVaCreateWidget ("rowcolumn",
8470 xmRowColumnWidgetClass, SurfCont->rccm_swcmap,
8471 XmNpacking, XmPACK_TIGHT,
8472 XmNorientation , XmHORIZONTAL ,
8473 XmNmarginHeight, 0 ,
8474 XmNmarginWidth , 0 ,
8475 NULL);
8476 }
8477
8478 SUMA_LH("Forming CmapMenu");
8479 SwitchCmap_Menu = SUMA_FormSwitchCmapMenuVector(SUMAg_CF->scm->CMv,
8480 SUMAg_CF->scm->N_maps);
8481 switch(ado->do_type) {
8482 case SO_type:
8483 wname = "SurfCont->Dset_Mapping->Cmp";
8484 break;
8485 case VO_type:
8486 wname = "VolCont->Dset_Mapping->Cmp";
8487 break;
8488 case GRAPH_LINK_type:
8489 wname = "GraphCont->GDset_Mapping->Cmp";
8490 break;
8491 default:
8492 wname = "WhatIsThisFor->Cmp";
8493 break;
8494 }
8495
8496 if (SwitchCmap_Menu) {
8497 SurfCont->SwitchCmapMenu =
8498 SUMA_Free_Menu_Widget(SurfCont->SwitchCmapMenu);
8499 SurfCont->SwitchCmapMenu =
8500 SUMA_Alloc_Menu_Widget(SUMAg_CF->scm->N_maps+1);
8501 SUMA_BuildMenuReset(10);
8502 SUMA_BuildMenu ( SurfCont->rc_CmapCont,
8503 XmMENU_OPTION, /* populate it */
8504 "Cmp", '\0', YUP, SwitchCmap_Menu,
8505 (void *)ado,
8506 wname,
8507 "Switch between available color maps."
8508 " (BHelp for more)",
8509 SUMA_SurfContHelp_Cmp,
8510 SurfCont->SwitchCmapMenu );
8511 XtInsertEventHandler( SurfCont->SwitchCmapMenu->mw[0] ,
8512 /* handle events in optmenu */
8513 ButtonPressMask , /* button presses */
8514 FALSE , /* nonmaskable events? */
8515 SUMA_optmenu_EV , /* handler */
8516 (XtPointer)ado , /* client data */
8517 XtListTail ) ;
8518 XtManageChild (SurfCont->SwitchCmapMenu->mw[0]);
8519 /* Now destroy the SwitchCmap_Menu */
8520 SwitchCmap_Menu = SUMA_FreeMenuVector(SwitchCmap_Menu,
8521 SUMAg_CF->scm->N_maps);
8522 }
8523
8524 XtManageChild(SurfCont->rc_CmapCont);
8525
8526 SUMA_RETURNe;
8527 }
8528
SUMA_InitClustTable(SUMA_ALL_DO * ado)8529 SUMA_Boolean SUMA_InitClustTable(SUMA_ALL_DO *ado)
8530 {
8531 static char FuncName[]={"SUMA_InitClustTable"};
8532 SUMA_TABLE_FIELD *TFs;
8533 SUMA_Boolean ColorizeBaby;
8534 SUMA_X_SurfCont *SurfCont=NULL;
8535 SUMA_OVERLAYS *curColPlane=NULL;
8536 SUMA_SCALE_TO_MAP_OPT *OptScl;
8537 SUMA_Boolean LocalHead = NOPE;
8538
8539 SUMA_ENTRY;
8540
8541 SurfCont = SUMA_ADO_Cont(ado);
8542 curColPlane = SUMA_ADO_CurColPlane(ado);
8543
8544 if (!SurfCont) SUMA_RETURN(NOPE);
8545 if (ado->do_type == VO_type) {
8546 /* At the moment GUI is for interactive clustering is turned off, but
8547 to be safe, return without complaints */
8548 SUMA_LH("Nothing to do here until you implement clustering for volumes");
8549 SUMA_RETURN(YUP);
8550 }
8551 TFs = SurfCont->SetClustTable;
8552 if (!TFs) SUMA_RETURN(NOPE);
8553 OptScl = curColPlane->OptScl;
8554
8555 ColorizeBaby = NOPE; /* Not sure if I'll need this one here */
8556
8557 SUMA_INSERT_CELL_VALUE(TFs, 1, 1, OptScl->ClustOpt->DistLim);
8558 SUMA_INSERT_CELL_VALUE(TFs, 1, 2, OptScl->ClustOpt->AreaLim);
8559 SUMA_SetTableTitleButton1(TFs, 1,0, OptScl->Clusterize);
8560
8561 if (ColorizeBaby) {
8562 if (!SUMA_ColorizePlane (curColPlane)) {
8563 SUMA_SLP_Err("Failed to colorize plane.\n");
8564 SUMA_RETURN(NOPE);
8565 }
8566 }
8567
8568 SUMA_RETURN(YUP);
8569 }
8570 /*!
8571 \brief updates table with data value range
8572 and the table where user sets mapping
8573 range (that last one depends on what)
8574 SO: You know what
8575 what: (int) -1: Do NOTHING with user accessible mapping ranges
8576 0: intensity only
8577 1: brightness modulation only
8578 2: Set all user accessible mapping ranges
8579 */
SUMA_InitRangeTable(SUMA_ALL_DO * ado,int what)8580 SUMA_Boolean SUMA_InitRangeTable(SUMA_ALL_DO *ado, int what)
8581 {
8582 static char FuncName[]={"SUMA_InitRangeTable"};
8583 char srange_min[50], srange_max[50], srange_minloc[50], srange_maxloc[50];
8584 SUMA_TABLE_FIELD *TF, *TFs;
8585 int i, j, i1D, fi, bi, ti;
8586 double range[2];
8587 NI_element *nel;
8588 SUMA_SCALE_TO_MAP_OPT *OptScl;
8589 SUMA_Boolean DoIs = NOPE, DoBs = NOPE, ColorizeBaby;
8590 SUMA_X_SurfCont *SurfCont=NULL;
8591 SUMA_OVERLAYS *curColPlane=NULL;
8592 SUMA_Boolean LocalHead = NOPE;
8593
8594 SUMA_ENTRY;
8595
8596 if (LocalHead) {
8597 SUMA_DUMP_TRACE("Who just called SUMA_InitRangeTable?");
8598 }
8599 if (!ado) {
8600 SUMA_SL_Err("NULL ado");
8601 SUMA_RETURN(NOPE);
8602 }
8603 SurfCont = SUMA_ADO_Cont(ado);
8604 curColPlane = SUMA_ADO_CurColPlane(ado);
8605
8606 if (!SurfCont || !curColPlane) SUMA_RETURN(NOPE);
8607 TF = SurfCont->RangeTable;
8608 TFs = SurfCont->SetRangeTable;
8609 if (!TF || !TFs || !TF->cells || !TFs->cells) SUMA_RETURN(NOPE);
8610 OptScl = curColPlane->OptScl;
8611 fi = OptScl->find;
8612 ti = OptScl->tind;
8613 bi = OptScl->bind;
8614 ColorizeBaby = NOPE;
8615
8616 switch (what) {
8617 case -1:
8618 DoIs = NOPE;
8619 DoBs = NOPE;
8620 break;
8621 case 2:
8622 DoIs = YUP;
8623 DoBs = YUP;
8624 break;
8625 case 0:
8626 DoIs = YUP;
8627 break;
8628 case 1:
8629 DoBs = YUP;
8630 break;
8631 default:
8632 SUMA_SL_Err("That's stupid Joe!");
8633 SUMA_RETURN(NOPE);
8634 break;
8635 }
8636
8637 /* TF Range table Int*/
8638 SUMA_LHv("Setting Int. fi=%d\n", fi);
8639 SUMA_RANGE_STRING(curColPlane->dset_link,
8640 fi, srange_min, srange_max,
8641 srange_minloc, srange_maxloc, range);
8642 SUMA_INSERT_CELL_STRING(TF, 1, 1, srange_min);/* min */
8643 SUMA_INSERT_CELL_STRING(TF, 1, 2, srange_minloc);/* minloc */
8644 SUMA_INSERT_CELL_STRING(TF, 1, 3, srange_max);/* max */
8645 SUMA_INSERT_CELL_STRING(TF, 1, 4, srange_maxloc);/* maxloc */
8646
8647 /* TFs Range table Int*/
8648 if (DoIs) {
8649 if (curColPlane->OptScl->AutoIntRange) {
8650 if (!curColPlane->ForceIntRange[0] &&
8651 !curColPlane->ForceIntRange[1]) {
8652 if ( OptScl->IntRange[0] != range[0] ||
8653 OptScl->IntRange[1] != range[1] ) {
8654 ColorizeBaby = YUP;
8655 OptScl->IntRange[0] = range[0]; OptScl->IntRange[1] = range[1];
8656 }
8657 } else {
8658 SUMA_LH("Using ForceIntRange");
8659 if ( OptScl->IntRange[0] !=
8660 curColPlane->ForceIntRange[0] ||
8661 OptScl->IntRange[1] !=
8662 curColPlane->ForceIntRange[1] ) {
8663 ColorizeBaby = YUP;
8664 OptScl->IntRange[0] = curColPlane->ForceIntRange[0];
8665 OptScl->IntRange[1] = curColPlane->ForceIntRange[1];
8666 }
8667 }
8668
8669 /* enforce the SymIrange option */
8670 if (curColPlane->SymIrange) {
8671 if ( OptScl->IntRange[1] !=
8672 SUMA_LARG_ABS(OptScl->IntRange[0], OptScl->IntRange[1]) ||
8673 OptScl->IntRange[0] != -OptScl->IntRange[1]) {
8674 ColorizeBaby = YUP;
8675 OptScl->IntRange[1] =
8676 SUMA_LARG_ABS(OptScl->IntRange[0], OptScl->IntRange[1]);
8677 OptScl->IntRange[0] = -OptScl->IntRange[1];
8678 }
8679 }
8680
8681 SUMA_INSERT_CELL_VALUE(TFs, 1, 1, OptScl->IntRange[0]);/* min */
8682 SUMA_INSERT_CELL_VALUE(TFs, 1, 2, OptScl->IntRange[1]);/* max */
8683 if (curColPlane->OptScl->AutoIntRange < 0) {
8684 /* snap out of the initialization and go to user's default */
8685 curColPlane->OptScl->AutoIntRange =
8686 SUMA_isEnv("SUMA_Auto_I_Range","YES") ? 1:0;
8687 SUMA_LHv("AutoIntRange now %d\n",
8688 curColPlane->OptScl->AutoIntRange);
8689 }
8690 }else {
8691 /* Make sure viewer is showing same values as in OptScl */
8692 /* enforce the SymIrange option */
8693 if (curColPlane->SymIrange) {
8694 if ( OptScl->IntRange[1] !=
8695 SUMA_LARG_ABS(OptScl->IntRange[0], OptScl->IntRange[1]) ||
8696 OptScl->IntRange[0] != -OptScl->IntRange[1]) {
8697 ColorizeBaby = YUP;
8698 OptScl->IntRange[1] =
8699 SUMA_LARG_ABS(OptScl->IntRange[0], OptScl->IntRange[1]);
8700 OptScl->IntRange[0] = -OptScl->IntRange[1];
8701 }
8702 }
8703 SUMA_LH("Imposing...");
8704 if ( OptScl->IntRange[0] != TFs->num_value[1*TFs->Ni+1] ||
8705 OptScl->IntRange[1] != TFs->num_value[2*TFs->Ni+1] ) {
8706 SUMA_INSERT_CELL_VALUE(TFs, 1, 1, OptScl->IntRange[0]);/* min */
8707 SUMA_INSERT_CELL_VALUE(TFs, 1, 2, OptScl->IntRange[1]);/* max */
8708 }
8709 }
8710 }
8711 /* TF Range table Thr*/
8712 SUMA_LH("Setting Thr.");
8713 SUMA_RANGE_STRING(curColPlane->dset_link, ti,
8714 srange_min, srange_max,
8715 srange_minloc, srange_maxloc, range);
8716 SUMA_INSERT_CELL_STRING(TF, 2, 1, srange_min);/* min */
8717 SUMA_INSERT_CELL_STRING(TF, 2, 2, srange_minloc);/* minloc */
8718 SUMA_INSERT_CELL_STRING(TF, 2, 3, srange_max);/* max */
8719 SUMA_INSERT_CELL_STRING(TF, 2, 4, srange_maxloc);/* maxloc */
8720
8721 /* TF Range table Brt*/
8722 SUMA_LH("Setting Brt.");
8723 SUMA_RANGE_STRING(curColPlane->dset_link, bi,
8724 srange_min, srange_max,
8725 srange_minloc, srange_maxloc, range);
8726 SUMA_INSERT_CELL_STRING(TF, 3, 1, srange_min);/* min */
8727 SUMA_INSERT_CELL_STRING(TF, 3, 2, srange_minloc);/* minloc */
8728 SUMA_INSERT_CELL_STRING(TF, 3, 3, srange_max);/* max */
8729 SUMA_INSERT_CELL_STRING(TF, 3, 4, srange_maxloc);/* maxloc */
8730 /* TFs Range table Brt*/
8731 if (DoBs) {
8732 if (curColPlane->OptScl->AutoBrtRange) {
8733 if ( OptScl->BrightRange[0] != range[0] ||
8734 OptScl->BrightRange[1] != range[1] ) {
8735 ColorizeBaby = YUP;
8736 OptScl->BrightRange[0] = range[0]; OptScl->BrightRange[1] = range[1];
8737 }
8738 SUMA_INSERT_CELL_VALUE(TFs, 2, 1, OptScl->BrightRange[0]);/* min */
8739 SUMA_INSERT_CELL_VALUE(TFs, 2, 2, OptScl->BrightRange[1]);/* max */
8740 /* TFs Range table BrtMap*/
8741 SUMA_INSERT_CELL_VALUE(TFs, 3, 1, OptScl->BrightMap[0]);/* min */
8742 SUMA_INSERT_CELL_VALUE(TFs, 3, 2, OptScl->BrightMap[1]);/* max */
8743 if (curColPlane->OptScl->AutoBrtRange < 0) {
8744 /* snap out of the initialization and go to user's default */
8745 curColPlane->OptScl->AutoBrtRange =
8746 SUMA_isEnv("SUMA_Auto_B_Range","YES") ? 1:0;
8747 SUMA_LHv("AutoBrtRange now %d\n",
8748 curColPlane->OptScl->AutoBrtRange);
8749 }
8750 } else {
8751 /* Make sure viewer is showing same values as in OptScl */
8752 if ( OptScl->BrightRange[0] != TFs->num_value[1*TFs->Ni+2] ||
8753 OptScl->BrightRange[1] != TFs->num_value[2*TFs->Ni+2] ||
8754 OptScl->BrightMap[0] != TFs->num_value[1*TFs->Ni+3] ||
8755 OptScl->BrightMap[1] != TFs->num_value[2*TFs->Ni+3] ) {
8756 SUMA_INSERT_CELL_VALUE(TFs, 2, 1, OptScl->BrightRange[0]);/* min */
8757 SUMA_INSERT_CELL_VALUE(TFs, 2, 2, OptScl->BrightRange[1]);/* max */
8758 /* TFs Range table BrtMap*/
8759 SUMA_INSERT_CELL_VALUE(TFs, 3, 1, OptScl->BrightMap[0]);/* min */
8760 SUMA_INSERT_CELL_VALUE(TFs, 3, 2, OptScl->BrightMap[1]);/* max */
8761 }
8762 }
8763 }
8764
8765 /* TFs Range table CoordBias*/
8766 SUMA_INSERT_CELL_VALUE(TFs, 4, 1, OptScl->CoordBiasRange[0]);/* min */
8767 SUMA_INSERT_CELL_VALUE(TFs, 4, 2, OptScl->CoordBiasRange[1]);/* max */
8768
8769 if (ColorizeBaby) {
8770 if (!SUMA_ColorizePlane (curColPlane)) {
8771 SUMA_SLP_Err("Failed to colorize plane.\n");
8772 SUMA_RETURN(NOPE);
8773 }
8774 }
8775 SUMA_RETURN(YUP);
8776 }
8777
SUMA_AssembleCmapList(SUMA_COLOR_MAP ** CMv,int N_maps)8778 SUMA_ASSEMBLE_LIST_STRUCT * SUMA_AssembleCmapList(SUMA_COLOR_MAP **CMv,
8779 int N_maps)
8780 {
8781 static char FuncName[]={"SUMA_AssembleCmapList"};
8782 SUMA_ASSEMBLE_LIST_STRUCT *clist_str = NULL;
8783 int i;
8784 SUMA_Boolean LocalHead = NOPE;
8785
8786 SUMA_ENTRY;
8787
8788 clist_str = SUMA_CreateAssembleListStruct();
8789 clist_str->clist = (char **)SUMA_calloc(N_maps, sizeof(char *));
8790 clist_str->oplist = (void **)SUMA_calloc(N_maps, sizeof(void *));
8791 clist_str->N_clist = N_maps;
8792
8793 for (i=0; i<N_maps; ++i) {
8794 clist_str->clist[i] = SUMA_copy_string(CMv[i]->Name);
8795 clist_str->oplist[i] = (void*)CMv[i];
8796 }
8797
8798 SUMA_RETURN(clist_str);
8799 }
8800
SUMA_AssembleDsetColList(SUMA_DSET * dset)8801 SUMA_ASSEMBLE_LIST_STRUCT * SUMA_AssembleDsetColList(SUMA_DSET *dset)
8802 {
8803 static char FuncName[]={"SUMA_AssembleDsetColList"};
8804 SUMA_ASSEMBLE_LIST_STRUCT *clist_str = NULL;
8805 int i;
8806 SUMA_Boolean LocalHead = NOPE;
8807
8808 SUMA_ENTRY;
8809
8810 if (SDSET_VECNUM(dset) < 1) SUMA_RETURN(clist_str);
8811
8812 clist_str = SUMA_CreateAssembleListStruct();
8813 clist_str->clist = (char **)SUMA_calloc(SDSET_VECNUM(dset), sizeof(char *));
8814 clist_str->oplist = (void **)SUMA_calloc(SDSET_VECNUM(dset), sizeof(void *));
8815 clist_str->N_clist = SDSET_VECNUM(dset);
8816 clist_str->content_id = SUMA_copy_string(SDSET_ID(dset));
8817
8818 for (i=0; i<SDSET_VECNUM(dset); ++i) {
8819 clist_str->clist[SDSET_VECNUM(dset)-1-i] =
8820 SUMA_DsetColLabelCopy(dset,i, 1);
8821 clist_str->oplist[SDSET_VECNUM(dset)-1-i] = (XTP_CAST)i;
8822 }
8823
8824 SUMA_RETURN(clist_str);
8825 }
8826
8827 /*!
8828 \brief opens a list selection for choosing a Dset column
8829 */
SUMA_DsetColSelectList(SUMA_ALL_DO * ado,int type,int refresh,int bringup)8830 SUMA_Boolean SUMA_DsetColSelectList(
8831 SUMA_ALL_DO *ado, int type,
8832 int refresh, int bringup)
8833 {
8834 static char FuncName[]={"SUMA_DsetColSelectList"};
8835 SUMA_LIST_WIDGET *LW = NULL;
8836 SUMA_X_SurfCont *SurfCont=NULL;
8837 SUMA_OVERLAYS *curColPlane=NULL;
8838 SUMA_Boolean LocalHead = NOPE;
8839
8840 SUMA_ENTRY;
8841
8842 SUMA_LH("Called");
8843
8844 SurfCont = SUMA_ADO_Cont(ado);
8845 curColPlane = SUMA_ADO_CurColPlane(ado);
8846 if (!ado || !SurfCont) SUMA_RETURN(NOPE);
8847
8848 /* Widget is common to a surface controller. */
8849 switch (type) {
8850 case 0:
8851 LW = SurfCont->SwitchIntMenu->lw;
8852 if (!LW) {
8853 SUMA_LH("Allocating widget");
8854 /* need to create widget */
8855 LW = SUMA_AllocateScrolledList (
8856 "Switch Intensity", SUMA_LSP_BROWSE,
8857 NOPE, NOPE,
8858 SurfCont->TLS, SWP_POINTER_OFF,
8859 150,
8860 SUMA_cb_SelectSwitchInt, (void *)ado,
8861 SUMA_cb_SelectSwitchInt, (void *)ado,
8862 SUMA_cb_CloseSwitchLst, NULL);
8863
8864 SurfCont->SwitchIntMenu->lw = LW;
8865 refresh = 1; /* no doubt aboot it */
8866 } else {
8867 if ( (void *)ado != LW->Default_Data ||
8868 (void *)ado != LW->Select_Data) {
8869 /* just update the callback data info in LW */
8870 SUMA_UpdateScrolledListData(LW, (void *)ado, (void *)ado, NULL);
8871 }
8872
8873 }
8874 break;
8875 case 1:
8876 LW = SurfCont->SwitchThrMenu->lw;
8877 if (!LW) {
8878 SUMA_LH("Allocating widget");
8879 /* need to create widget */
8880 LW = SUMA_AllocateScrolledList (
8881 "Switch Threshold", SUMA_LSP_BROWSE,
8882 NOPE, NOPE,
8883 SurfCont->TLS, SWP_POINTER_OFF,
8884 150,
8885 SUMA_cb_SelectSwitchThr, (void *)ado,
8886 SUMA_cb_SelectSwitchThr, (void *)ado,
8887 SUMA_cb_CloseSwitchLst, NULL);
8888
8889 SurfCont->SwitchThrMenu->lw = LW;
8890 refresh = 1; /* no doubt aboot it */
8891 } else {
8892 if ( (void *)ado != LW->Default_Data ||
8893 (void *)ado != LW->Select_Data) {
8894 /* just update the callback data info in LW */
8895 SUMA_UpdateScrolledListData(LW, (void *)ado, (void *)ado, NULL);
8896 }
8897
8898 }
8899 break;
8900 case 2:
8901 LW = SurfCont->SwitchBrtMenu->lw;
8902 if (!LW) {
8903 SUMA_LH("Allocating widget");
8904 /* need to create widget */
8905 LW = SUMA_AllocateScrolledList (
8906 "Switch Brightness", SUMA_LSP_BROWSE,
8907 NOPE, NOPE,
8908 SurfCont->TLS, SWP_POINTER_OFF,
8909 150,
8910 SUMA_cb_SelectSwitchBrt, (void *)ado,
8911 SUMA_cb_SelectSwitchBrt, (void *)ado,
8912 SUMA_cb_CloseSwitchLst, NULL);
8913
8914 SurfCont->SwitchBrtMenu->lw = LW;
8915 refresh = 1; /* no doubt aboot it */
8916 } else {
8917 if ( (void *)ado != LW->Default_Data ||
8918 (void *)ado != LW->Select_Data) {
8919 /* just update the callback data info in LW */
8920 SUMA_UpdateScrolledListData(LW, (void *)ado, (void *)ado, NULL);
8921 }
8922
8923 }
8924 break;
8925 default:
8926 SUMA_SL_Err("Unexpected type");
8927 SUMA_RETURN(NOPE);
8928 }
8929
8930 /* Refresh if LW exists, but request is for a new data set */
8931 if (!refresh &&
8932 strcmp(LW->ALS->content_id,
8933 SDSET_ID(curColPlane->dset_link))) {
8934 refresh=1;
8935 }
8936
8937 if (refresh) {
8938 /* Now creating list*/
8939 if (LW->ALS) {
8940 if (LocalHead) SUMA_S_Err("Freeing the hag.");
8941 LW->ALS = SUMA_FreeAssembleListStruct(LW->ALS);
8942 }
8943 SUMA_LH("Assembling");
8944 LW->ALS = SUMA_AssembleDsetColList(curColPlane->dset_link);
8945 if (!LW->ALS) {
8946 SUMA_SL_Err("Failed to assemble list");
8947 SUMA_RETURN(NOPE);
8948 }
8949 if (LW->ALS->N_clist < 0) {
8950 SUMA_SL_Err("Failed in SUMA_AssembleDsetColList");
8951 SUMA_RETURN(NOPE);
8952 }
8953 if (!LW->ALS->N_clist) {
8954 SUMA_SLP_Note ("No Dset Cols to choose from.");
8955 SUMA_RETURN(NOPE);
8956 }
8957 }
8958
8959 if (bringup)
8960 SUMA_CreateScrolledList ( LW->ALS->clist, LW->ALS->N_clist, NOPE, LW);
8961
8962 SUMA_RETURN(YUP);
8963 }
8964
8965
SUMA_GetListIchoice(XmListCallbackStruct * cbs,SUMA_LIST_WIDGET * LW,SUMA_Boolean * CloseShop)8966 int SUMA_GetListIchoice(XmListCallbackStruct *cbs,
8967 SUMA_LIST_WIDGET *LW,
8968 SUMA_Boolean *CloseShop)
8969 {
8970 static char FuncName[]={"SUMA_GetListIchoice"};
8971 int ichoice;
8972 char *choice=NULL;
8973 SUMA_Boolean Found = NOPE;
8974 SUMA_Boolean LocalHead = NOPE;
8975
8976 SUMA_ENTRY;
8977
8978 *CloseShop = NOPE;
8979 ichoice = -1;
8980 if (!LW) {
8981 SUMA_S_Err("NULL LW!");
8982 SUMA_RETURN(ichoice);
8983 }
8984
8985
8986 if ( cbs->reason == XmCR_SINGLE_SELECT ||
8987 cbs->reason == XmCR_BROWSE_SELECT) {
8988 if (LocalHead)
8989 fprintf (SUMA_STDERR,
8990 "%s: Single selection (reason %d, (%d, %d)),\n"
8991 "list widget %s... \n",
8992 FuncName, cbs->reason,
8993 XmCR_SINGLE_SELECT, XmCR_BROWSE_SELECT , LW->Label);
8994 } else {
8995 if (LocalHead)
8996 fprintf (SUMA_STDERR,
8997 "%s: Default selection (reason %d, (%d, %d)),\n"
8998 "list widget %s... \n",
8999 FuncName, cbs->reason,
9000 XmCR_SINGLE_SELECT, XmCR_BROWSE_SELECT, LW->Label);
9001 /*double click or enter on that one, close shop after selection */
9002 *CloseShop = YUP;
9003 }
9004
9005 XmStringGetLtoR (cbs->item, XmFONTLIST_DEFAULT_TAG, &choice);
9006
9007 if (LocalHead)
9008 fprintf (SUMA_STDERR,
9009 "%s: Selected item: %s {%s} (%d)\n",
9010 FuncName, choice, choice, cbs->item_position);
9011 LW->lastitempos = cbs->item_position; /* store for next opening */
9012 /* because of sorting, choice cannot be used
9013 as an index into clist and oplist in ALS */
9014 Found = NOPE;
9015 ichoice = 0;
9016 do {
9017 if (LocalHead)
9018 fprintf (SUMA_STDERR,"%s: Comparing:\t>%s<\t>%s<\n",
9019 FuncName, LW->ALS->clist[ichoice], choice);
9020 if (strcmp(LW->ALS->clist[ichoice],
9021 choice) == 0) Found = YUP;
9022 else ++ichoice;
9023 } while (ichoice < LW->ALS->N_clist && !Found);
9024
9025 if (!Found) { /* do older search, with strncmp dunno why it
9026 was like that
9027 but I worry about backward compatibility */
9028 ichoice = 0;
9029 do {
9030 if (LocalHead)
9031 fprintf (SUMA_STDERR,"%s: Comparing:\t>%s<\t>%s<\n",
9032 FuncName, LW->ALS->clist[ichoice], choice);
9033 if (strncmp(LW->ALS->clist[ichoice],
9034 choice, strlen(choice)) == 0) Found = YUP;
9035 else ++ichoice;
9036 } while (ichoice < LW->ALS->N_clist && !Found);
9037 }
9038
9039 if (!Found) {
9040 SUMA_SLP_Err("Choice not found.");
9041 SUMA_RETURN(-1);
9042 }
9043
9044 XtFree (choice);
9045 SUMA_RETURN(ichoice);
9046 }
9047 /*!
9048 \brief function that handles switching intensity from the list widget
9049 \sa SUMA_cb_SwitchIntensity
9050 */
SUMA_cb_SelectSwitchInt(Widget w,XtPointer client_data,XtPointer call_data)9051 void SUMA_cb_SelectSwitchInt (
9052 Widget w, XtPointer client_data,
9053 XtPointer call_data)
9054 {
9055 static char FuncName[]={"SUMA_cb_SelectSwitchInt"};
9056 SUMA_ALL_DO *ado = NULL;
9057 SUMA_LIST_WIDGET *LW = NULL;
9058 XmListCallbackStruct *cbs = (XmListCallbackStruct *) call_data;
9059 int ichoice;
9060 SUMA_X_SurfCont *SurfCont=NULL;
9061 SUMA_Boolean CloseShop = NOPE;
9062 SUMA_Boolean LocalHead = NOPE;
9063
9064 SUMA_ENTRY;
9065
9066 SUMA_LH("Called");
9067 ado = (SUMA_ALL_DO *)client_data;
9068 SurfCont = SUMA_ADO_Cont(ado);
9069 LW = SurfCont->SwitchIntMenu->lw;
9070
9071 if ((ichoice = SUMA_GetListIchoice(cbs, LW, &CloseShop))==-1) {
9072 SUMA_RETURNe;
9073 }
9074
9075
9076 if (!SUMA_SelectSwitchDsetCol(ado, LW, 0, ichoice)) {
9077 SUMA_S_Err("Failed to SelectSwitchDsetCol");
9078 SUMA_RETURNe;
9079 }
9080
9081 if (CloseShop) {
9082 SUMA_cb_CloseSwitchLst( w, (XtPointer)LW, call_data);
9083 }
9084
9085 /* update Lbl fields */
9086 SUMA_UpdateNodeLblField(ado);
9087
9088 SUMA_RETURNe;
9089 }
9090
SUMA_cb_SelectSwitchThr(Widget w,XtPointer client_data,XtPointer call_data)9091 void SUMA_cb_SelectSwitchThr (
9092 Widget w, XtPointer client_data,
9093 XtPointer call_data)
9094 {
9095 static char FuncName[]={"SUMA_cb_SelectSwitchThr"};
9096 SUMA_ALL_DO *ado = NULL;
9097 XmListCallbackStruct *cbs = (XmListCallbackStruct *) call_data;
9098 SUMA_Boolean CloseShop = NOPE;
9099 SUMA_LIST_WIDGET *LW = NULL;
9100 int ichoice;
9101 SUMA_X_SurfCont *SurfCont=NULL;
9102 SUMA_Boolean LocalHead = NOPE;
9103
9104 SUMA_ENTRY;
9105
9106 SUMA_LH("Called");
9107 ado = (SUMA_ALL_DO *)client_data;
9108 SurfCont = SUMA_ADO_Cont(ado);
9109 LW = SurfCont->SwitchThrMenu->lw;
9110
9111 if ((ichoice = SUMA_GetListIchoice(cbs, LW, &CloseShop))==-1) {
9112 SUMA_RETURNe;
9113 }
9114
9115 if (!SUMA_SelectSwitchDsetCol(ado, LW, 1, ichoice)) {
9116 SUMA_S_Err("Failed to SelectSwitchDsetCol");
9117 SUMA_RETURNe;
9118 }
9119
9120 if (CloseShop) {
9121 SUMA_cb_CloseSwitchLst( w, (XtPointer)LW, call_data);
9122 }
9123
9124 /* update Lbl fields */
9125 SUMA_UpdateNodeLblField(ado);
9126
9127 SUMA_RETURNe;
9128 }
9129
SUMA_cb_SelectSwitchBrt(Widget w,XtPointer client_data,XtPointer call_data)9130 void SUMA_cb_SelectSwitchBrt (
9131 Widget w, XtPointer client_data,
9132 XtPointer call_data)
9133 {
9134 static char FuncName[]={"SUMA_cb_SelectSwitchBrt"};
9135 SUMA_ALL_DO *ado = NULL;
9136 XmListCallbackStruct *cbs = (XmListCallbackStruct *) call_data;
9137 SUMA_Boolean CloseShop = NOPE;
9138 SUMA_LIST_WIDGET *LW = NULL;
9139 int ichoice;
9140 SUMA_X_SurfCont *SurfCont=NULL;
9141 SUMA_Boolean LocalHead = NOPE;
9142
9143 SUMA_ENTRY;
9144
9145 SUMA_LH("Called");
9146 ado = (SUMA_ALL_DO *)client_data;
9147 SurfCont = SUMA_ADO_Cont(ado);
9148 LW = SurfCont->SwitchBrtMenu->lw;
9149
9150 if ((ichoice = SUMA_GetListIchoice(cbs, LW, &CloseShop))==-1) {
9151 SUMA_RETURNe;
9152 }
9153
9154 if (!SUMA_SelectSwitchDsetCol(ado, LW, 2, ichoice)) {
9155 SUMA_S_Err("Failed to SelectSwitchDsetCol");
9156 SUMA_RETURNe;
9157 }
9158
9159 if (CloseShop) {
9160 SUMA_cb_CloseSwitchLst( w, (XtPointer)LW, call_data);
9161 }
9162
9163 /* update Lbl fields */
9164 SUMA_UpdateNodeLblField(ado);
9165
9166 SUMA_RETURNe;
9167 }
9168
9169
SUMA_SelectSwitchDsetCol(SUMA_ALL_DO * ado,SUMA_LIST_WIDGET * LW,int block,int ichoice)9170 int SUMA_SelectSwitchDsetCol(
9171 SUMA_ALL_DO *ado,
9172 SUMA_LIST_WIDGET *LW,
9173 int block,
9174 int ichoice)
9175 {
9176 static char FuncName[]={"SUMA_SelectSwitchDsetCol"};
9177 SUMA_MenuCallBackData data;
9178 SUMA_X_SurfCont *SurfCont=NULL;
9179 SUMA_OVERLAYS *curColPlane=NULL;
9180 SUMA_Boolean LocalHead = NOPE;
9181
9182 SUMA_ENTRY;
9183
9184 SUMA_LH("Called");
9185 if (!ado || !LW || block < 0 || block > 2 || ichoice < 0) SUMA_RETURN(0);
9186 SurfCont = SUMA_ADO_Cont(ado);
9187 curColPlane = SUMA_ADO_CurColPlane(ado);
9188
9189
9190 /* now retrieve that choice from the
9191 SUMA_ASSEMBLE_LIST_STRUCT structure and initialize */
9192 if (LW->ALS) {
9193 if (LocalHead)
9194 fprintf (SUMA_STDERR,
9195 "%s: N_clist = %d\n",
9196 FuncName, LW->ALS->N_clist);
9197 if (LW->ALS->N_clist > ichoice) {
9198 if (LocalHead)
9199 fprintf (SUMA_STDERR,
9200 "%s: Retrieved Column indexed %d\n",
9201 FuncName, (INT_CAST)LW->ALS->oplist[ichoice]);
9202
9203 switch (block){
9204 case 0:
9205 if (!SUMA_SwitchColPlaneIntensity
9206 (ado, curColPlane,
9207 (INT_CAST)LW->ALS->oplist[ichoice], 1)) {
9208 SUMA_SL_Err("Failed in SUMA_SwitchColPlaneIntensity");
9209 }
9210 break;
9211 case 1:
9212 if (!SUMA_SwitchColPlaneThreshold
9213 (ado, curColPlane,
9214 (INT_CAST)LW->ALS->oplist[ichoice], 1)) {
9215 SUMA_SL_Err("Failed in SUMA_SwitchColPlaneThreshold");
9216 }
9217 break;
9218 case 2:
9219 if (!SUMA_SwitchColPlaneBrightness
9220 (ado, curColPlane,
9221 (INT_CAST)LW->ALS->oplist[ichoice], 1)) {
9222 SUMA_SL_Err("Failed in SUMA_SwitchColPlaneBrightness");
9223 }
9224 break;
9225 default:
9226 SUMA_S_Err("Ah NON!");
9227 SUMA_RETURN(0);
9228 break;
9229 }
9230 }
9231 } else {
9232 if (LocalHead) fprintf (SUMA_STDERR,"%s: NULL ALS\n", FuncName);
9233 }
9234
9235 SUMA_RETURN(1);
9236 }
9237
9238 /*!
9239 \brief function that handles closing switch * list widget
9240 expects LW in client_data
9241 */
SUMA_cb_CloseSwitchLst(Widget w,XtPointer client_data,XtPointer call)9242 void SUMA_cb_CloseSwitchLst (Widget w, XtPointer client_data, XtPointer call)
9243 {
9244 static char FuncName[]={"SUMA_cb_CloseSwitchLst"};
9245 SUMA_LIST_WIDGET *LW = NULL;
9246 SUMA_Boolean LocalHead = NOPE;
9247
9248 SUMA_ENTRY;
9249
9250 SUMA_LH("Called");
9251
9252 LW = (SUMA_LIST_WIDGET *)client_data;
9253
9254 switch (SUMA_CLOSE_MODE) {/* No open GL drawables in this widget*/
9255 case SUMA_WITHDRAW:
9256 if (LocalHead)
9257 fprintf (SUMA_STDERR,
9258 "%s: Withdrawing list widget %s...\n",
9259 FuncName, LW->Label);
9260
9261 XWithdrawWindow(SUMAg_CF->X->DPY_controller1,
9262 XtWindow(LW->toplevel),
9263 XScreenNumberOfScreen(XtScreen(LW->toplevel)));
9264 break;
9265 case SUMA_DESTROY:
9266 if (LocalHead)
9267 fprintf (SUMA_STDERR,
9268 "%s: Destroying list widget %s...\n",
9269 FuncName, LW->Label);
9270 XtDestroyWidget(LW->toplevel);
9271 LW->toplevel = NULL;
9272 break;
9273 default:
9274 SUMA_S_Err("Not ready for this type of closing");
9275 SUMA_RETURNe;
9276 break;
9277 }
9278
9279 LW->isShaded = YUP;
9280
9281
9282
9283 SUMA_RETURNe;
9284 }
9285
9286
9287 /*!
9288 \brief opens a list selection for choosing a color map
9289 */
SUMA_CmapSelectList(SUMA_ALL_DO * ado,int refresh,int bringup)9290 SUMA_Boolean SUMA_CmapSelectList(SUMA_ALL_DO *ado, int refresh,
9291 int bringup)
9292 {
9293 static char FuncName[]={"SUMA_CmapSelectList"};
9294 SUMA_LIST_WIDGET *LW = NULL;
9295 SUMA_X_SurfCont *SurfCont=NULL;
9296 SUMA_Boolean LocalHead = NOPE;
9297
9298 SUMA_ENTRY;
9299
9300 if (!SUMAg_CF->scm) {
9301 SUMAg_CF->scm = SUMA_Build_Color_maps();
9302 if (!SUMAg_CF->scm) {
9303 SUMA_SL_Err("Failed to build color maps.\n");
9304 SUMA_RETURN(NOPE);
9305 }
9306 }
9307
9308 /* Widget is common to all SUMA */
9309 LW = SUMAg_CF->X->SwitchCmapLst;
9310 SurfCont = SUMA_ADO_Cont(ado);
9311
9312 if (!LW) {
9313 SUMA_LH("Allocating widget");
9314 /* need to create widget */
9315 LW = SUMA_AllocateScrolledList (
9316 "Switch Cmap", SUMA_LSP_BROWSE,
9317 NOPE, NOPE,
9318 SurfCont->TLS, SWP_POINTER_OFF,
9319 125,
9320 SUMA_cb_SelectSwitchCmap, (void *)ado,
9321 SUMA_cb_SelectSwitchCmap, (void *)ado,
9322 SUMA_cb_CloseSwitchCmap, NULL);
9323
9324 SUMAg_CF->X->SwitchCmapLst = LW;
9325 refresh = 1; /* no doubt aboot it */
9326 } else {
9327 if ((void *)ado != LW->Default_Data || (void *)ado != LW->Select_Data) {
9328 /* just update the callback data info in LW */
9329 SUMA_UpdateScrolledListData(LW, (void *)ado, (void *)ado, NULL);
9330 }
9331 }
9332
9333 if (refresh) {
9334 /* Now creating list*/
9335 if (LW->ALS) {
9336 if (LocalHead) SUMA_S_Err("Freeing the hag.");
9337 LW->ALS = SUMA_FreeAssembleListStruct(LW->ALS);
9338 }
9339 SUMA_LH("Assembling");
9340 LW->ALS = SUMA_AssembleCmapList(SUMAg_CF->scm->CMv, SUMAg_CF->scm->N_maps);
9341 if (!LW->ALS) {
9342 SUMA_SL_Err("Failed to assemble list");
9343 SUMA_RETURN(NOPE);
9344 }
9345 if (LW->ALS->N_clist < 0) {
9346 SUMA_SL_Err("Failed in SUMA_AssembleCmapList");
9347 SUMA_RETURN(NOPE);
9348 }
9349 if (!LW->ALS->N_clist) {
9350 SUMA_SLP_Note ("No cmaps to choose from.");
9351 SUMA_RETURN(NOPE);
9352 }
9353 }
9354
9355 if (bringup)
9356 SUMA_CreateScrolledList ( LW->ALS->clist, LW->ALS->N_clist, NOPE, LW);
9357
9358 SUMA_RETURN(YUP);
9359 }
9360
SUMA_SetCmodeMenuChoice(SUMA_ALL_DO * ado,char * str)9361 SUMA_Boolean SUMA_SetCmodeMenuChoice(SUMA_ALL_DO *ado, char *str)
9362 {
9363 static char FuncName[]={"SUMA_SetCmodeMenuChoice"};
9364 int i, Nbutt = 0, nstr=0, nf=0;
9365 Widget whist = NULL, *w = NULL;
9366 SUMA_X_SurfCont *SurfCont=NULL;
9367 SUMA_Boolean LocalHead = NOPE;
9368
9369 SUMA_ENTRY;
9370
9371 SurfCont = SUMA_ADO_Cont(ado);
9372 SUMA_LHv("So(%p), SurfCont(%p), CmapModeMenu(%p)\n",
9373 ado, SurfCont, SurfCont->CmapModeMenu);
9374 w = SurfCont->CmapModeMenu->mw;
9375 if (!w) {
9376 SUMA_LH("NULL w");
9377 SUMA_RETURN(NOPE);
9378 }
9379 if (!str) {
9380 SUMA_S_Err("NULL str");
9381 SUMA_RETURN(NOPE);
9382 }
9383 /* what's your history joe ? */
9384 XtVaGetValues( w[0], XmNmenuHistory , &whist , NULL ) ;
9385 if (!whist) {
9386 SUMA_SL_Err("NULL whist!");
9387 SUMA_RETURN(NOPE);
9388 }
9389
9390 if (LocalHead) {
9391 fprintf (SUMA_STDERR,"%s: The history is NAMED: %s (%d buttons total)\n",
9392 FuncName, XtName(whist), Nbutt);
9393 }
9394 if (!strcasecmp(XtName(whist), str)) {
9395 SUMA_LHv("Current setting of %s same as %s, nothing to do.\n",
9396 XtName(whist),str);
9397 SUMA_RETURN(YUP);
9398 }
9399 nstr = strlen(str);
9400
9401 /* Now search the widgets in w for a widget labeled str */
9402 for (i=0; i< SW_N_CmapMode; ++i) {
9403 if (LocalHead)
9404 fprintf (SUMA_STDERR,"I have %s, want %s\n", XtName(w[i]), str);
9405 nf = strcasecmp(str, XtName(w[i]));
9406 if (nf == 0) {
9407 SUMA_LH("Match!");
9408 XtVaSetValues( w[0], XmNmenuHistory , w[i] , NULL ) ;
9409 SUMA_SetCmapMode(ado, i);
9410 SUMA_RETURN(YUP);
9411 }
9412 }
9413
9414 SUMA_RETURN(NOPE);
9415 }
9416
9417 /*!
9418 This function will fail if the strings have been trunctated
9419 Consider writing SetMenuChoiceUserData
9420 */
SUMA_SetCmapMenuChoice(SUMA_ALL_DO * ado,char * str)9421 SUMA_Boolean SUMA_SetCmapMenuChoice(SUMA_ALL_DO *ado, char *str)
9422 {
9423 static char FuncName[]={"SUMA_SetCmapMenuChoice"};
9424 int i, Nbutt = 0, nstr=0, nf=0;
9425 Widget whist = NULL, *w = NULL;
9426 SUMA_X_SurfCont *SurfCont=NULL;
9427 SUMA_OVERLAYS *curColPlane=NULL;
9428 SUMA_Boolean LocalHead = NOPE;
9429
9430 SUMA_ENTRY;
9431
9432 SurfCont = SUMA_ADO_Cont(ado);
9433 curColPlane = SUMA_ADO_CurColPlane(ado);
9434 SUMA_LHv("DO(%p), SurfCont(%p), SwitchCmapMenu(%p)\n",
9435 ado, SurfCont, SurfCont?SurfCont->SwitchCmapMenu:NULL);
9436
9437 if (!ado || !SurfCont || !SurfCont->SwitchCmapMenu) {
9438 SUMA_S_Err("NULL input");
9439 SUMA_RETURN(NOPE);
9440 }
9441
9442 w = SurfCont->SwitchCmapMenu->mw;
9443 if (!w) {
9444 SUMA_LH("NULL w");
9445 SUMA_RETURN(NOPE);
9446 }
9447 if (!str) {
9448 SUMA_S_Err("NULL str");
9449 SUMA_RETURN(NOPE);
9450 }
9451 /* what's your history joe ? */
9452 XtVaGetValues( w[0], XmNmenuHistory , &whist , NULL ) ;
9453 if (!whist) {
9454 SUMA_SL_Err("NULL whist!");
9455 SUMA_S_Notev("ado(%p), SurfCont(%p), SwitchCmapMenu(%p), %s\n",
9456 ado, SurfCont, SurfCont->SwitchCmapMenu, str);
9457 SUMA_RETURN(NOPE);
9458 }
9459
9460 if (LocalHead) {
9461 fprintf (SUMA_STDERR,"%s: The history is NAMED: %s (%d buttons total)\n",
9462 FuncName, XtName(whist), Nbutt);
9463 }
9464
9465 nstr = strlen(str);
9466 /* Now search the widgets in w for a widget labeled str */
9467 for (i=0; i< SurfCont->SwitchCmapMenu->N_mw; ++i) {
9468 if (LocalHead)
9469 fprintf (SUMA_STDERR,"I have %s, want %s\n", XtName(w[i]), str);
9470 if (nstr > strlen(XtName(w[i]))) { /* name in list got trunctated ...*/
9471 nf = strncmp(str, XtName(w[i]), strlen(XtName(w[i])));
9472 } else {
9473 nf = strcmp(str, XtName(w[i]));
9474 }
9475 if (nf == 0) {
9476 SUMA_LH("Match!");
9477 XtVaSetValues( w[0], XmNmenuHistory , w[i] , NULL ) ;
9478 SUMA_RETURN(YUP);
9479 }
9480 }
9481
9482 SUMA_RETURN(NOPE);
9483 }
9484
SUMA_SelectSwitchCmap_one(SUMA_ALL_DO * ado,SUMA_LIST_WIDGET * LW,int ichoice,SUMA_Boolean CloseShop,int setmen)9485 int SUMA_SelectSwitchCmap_one( SUMA_ALL_DO *ado, SUMA_LIST_WIDGET *LW,
9486 int ichoice, SUMA_Boolean CloseShop, int setmen)
9487 {
9488 static char FuncName[]={"SUMA_SelectSwitchCmap_one"};
9489 SUMA_COLOR_MAP *CM = NULL;
9490 char *choice=NULL;
9491
9492 SUMA_Boolean LocalHead = NOPE;
9493
9494 SUMA_ENTRY;
9495
9496 if (!ado || !LW) SUMA_RETURN(0);
9497
9498 /* retrieve that choice from the SUMA_ASSEMBLE_LIST_STRUCT structure
9499 and initialize the drawing window */
9500 if (LW->ALS) {
9501 if (LocalHead)
9502 fprintf (SUMA_STDERR,"%s: N_clist = %d\n",
9503 FuncName, LW->ALS->N_clist);
9504 if (LW->ALS->N_clist > ichoice) {
9505 CM = (SUMA_COLOR_MAP *)LW->ALS->oplist[ichoice];
9506 if (LocalHead)
9507 fprintf (SUMA_STDERR,"%s: Retrieved Colmap named %s\n",
9508 FuncName, CM->Name);
9509 /* Now you need to set the button menu to reflect the choice made */
9510 if (!SUMA_SetCmapMenuChoice (ado, LW->ALS->clist[ichoice])) {
9511 SUMA_SL_Err("Failed in SUMA_SetCmapMenuChoice");
9512 }
9513 if (!SUMA_SwitchColPlaneCmap(ado, CM)) {
9514 SUMA_SL_Err("Failed in SUMA_SwitchColPlaneCmap");
9515 }
9516 }
9517 } else {
9518 if (LocalHead) fprintf (SUMA_STDERR,"%s: NULL ALS\n", FuncName);
9519 }
9520
9521 if (CloseShop) {
9522 SUMA_cb_CloseSwitchCmap( NULL, (XtPointer)LW, NULL);
9523 }
9524
9525 /* update Lbl fields */
9526 SUMA_UpdateNodeLblField(ado);
9527
9528
9529 SUMA_RETURN(1);
9530 }
9531
SUMA_SelectSwitchCmap(SUMA_ALL_DO * ado,SUMA_LIST_WIDGET * LW,int ichoice,SUMA_Boolean CloseShop,int setmen)9532 int SUMA_SelectSwitchCmap( SUMA_ALL_DO *ado, SUMA_LIST_WIDGET *LW,
9533 int ichoice, SUMA_Boolean CloseShop, int setmen)
9534 {
9535 static char FuncName[]={"SUMA_SelectSwitchCmap"};
9536 SUMA_SurfaceObject *SO=NULL, *SOC=NULL;
9537 SUMA_OVERLAYS *colpC=NULL, *colp = NULL;
9538 SUMA_Boolean LocalHead = NOPE;
9539
9540 SUMA_ENTRY;
9541
9542 if (!ado || !LW) SUMA_RETURN(0);
9543
9544 if (!SUMA_SelectSwitchCmap_one(ado, LW, ichoice, CloseShop, setmen)) {
9545 SUMA_RETURN(0);
9546 }
9547
9548 if (ado->do_type == SO_type) {
9549 SO = (SUMA_SurfaceObject *)ado;
9550 colp = SUMA_ADO_CurColPlane(ado);
9551 colpC = SUMA_Contralateral_overlay(colp, SO, &SOC);
9552 if (colpC && SOC) {
9553 SUMA_LHv("Found contralateral equivalent to:\n"
9554 " %s and %s in\n"
9555 " %s and %s\n",
9556 SO->Label, CHECK_NULL_STR(colp->Label),
9557 SOC->Label, CHECK_NULL_STR(colpC->Label));
9558 if (!SUMA_SelectSwitchCmap_one((SUMA_ALL_DO *)SOC, LW, ichoice, 0, 1)) {
9559 SUMA_S_Warn("Failed in contralaterality");
9560 SUMA_RETURN(0);
9561 }
9562 }
9563 }
9564
9565 SUMA_RETURN(1);
9566 }
9567
9568
9569 /*!
9570 \brief function that handles switching colormap from the list widget
9571 \sa SUMA_cb_SwitchCmap
9572 */
SUMA_cb_SelectSwitchCmap(Widget w,XtPointer client_data,XtPointer call_data)9573 void SUMA_cb_SelectSwitchCmap (Widget w, XtPointer client_data,
9574 XtPointer call_data)
9575 {
9576 static char FuncName[]={"SUMA_cb_SelectSwitchCmap"};
9577 SUMA_ALL_DO *ado = NULL;
9578 SUMA_LIST_WIDGET *LW = NULL;
9579 SUMA_Boolean CloseShop = NOPE;
9580 XmListCallbackStruct *cbs = (XmListCallbackStruct *) call_data;
9581 int ichoice = -1;
9582 SUMA_Boolean LocalHead = NOPE;
9583
9584 SUMA_ENTRY;
9585
9586 SUMA_LH("Called");
9587 ado = (SUMA_ALL_DO *)client_data;
9588 LW = SUMAg_CF->X->SwitchCmapLst;
9589
9590 ichoice = SUMA_GetListIchoice(cbs, LW, &CloseShop);
9591
9592 if (!SUMA_SelectSwitchCmap(ado, LW, ichoice, CloseShop, 1)) {
9593 SUMA_S_Err("glitch");
9594 SUMA_RETURNe;
9595 }
9596
9597 SUMA_RETURNe;
9598 }
9599
SUMA_SwitchColPlaneCmap(SUMA_ALL_DO * ado,SUMA_COLOR_MAP * CM)9600 SUMA_Boolean SUMA_SwitchColPlaneCmap(SUMA_ALL_DO *ado, SUMA_COLOR_MAP *CM)
9601 {
9602 static char FuncName[]={"SUMA_SwitchColPlaneCmap"};
9603 SUMA_OVERLAYS *over = NULL;
9604 SUMA_X_SurfCont *SurfCont=NULL;
9605 SUMA_Boolean LocalHead = NOPE;
9606 static int nwarn=0;
9607
9608 SUMA_ENTRY;
9609
9610 SUMA_LH("Called");
9611 if (!ado || !CM) { SUMA_RETURN(NOPE); }
9612
9613 SurfCont = SUMA_ADO_Cont(ado);
9614
9615 if (!SurfCont) { SUMA_RETURN(NOPE); }
9616
9617 over = SUMA_ADO_CurColPlane(ado);
9618 if (!over) { SUMA_RETURN(NOPE); }
9619
9620 if (over->ShowMode == SW_SurfCont_DsetViewCon ||
9621 over->ShowMode == SW_SurfCont_DsetViewCaC ) { /* wants contours */
9622 if (SUMA_NeedsLinearizing(CM)) {
9623 if (!nwarn) {
9624 SUMA_SLP_Note("Cannot do contouring with colormaps\n"
9625 "that panes of unequal sizes.\n"
9626 "Contouring turned off.\n"
9627 "Notice shown once per session.");
9628 ++nwarn;
9629 }
9630 over->ShowMode = SW_SurfCont_DsetViewCol;
9631 SUMA_Set_Menu_Widget( SurfCont->DsetViewModeMenu,
9632 SUMA_ShowMode2ShowModeMenuItem(over->ShowMode));
9633 /* kill current contours */
9634 SUMA_KillOverlayContours(over);
9635 }
9636 }
9637
9638 SUMA_STRING_REPLACE(over->cmapname, CM->Name);
9639 if (!SUMA_ColorizePlane (over)) {
9640 SUMA_SLP_Err("Failed to colorize plane.\n");
9641 SUMA_RETURN(NOPE);
9642 }
9643
9644 /* reset zoom and translation vectors */
9645 SurfCont->cmp_ren->FOV = SUMA_CMAP_FOV_INITIAL;
9646 SurfCont->cmp_ren->translateVec[0] =
9647 SurfCont->cmp_ren->translateVec[1] =
9648 SurfCont->cmp_ren->translateVec[2] = 0.0;
9649
9650 /* update the color map display NOW, no workprocess crap. ZSS Mar. 7 08*/
9651 #if 0
9652 /* With this, the next call to SUMA_Remixedisplay,
9653 causes an error: glXSwapBuffers: no context for this drawable
9654 because SUMA_cmap_wid_handleRedisplay is still to be processed
9655 as SUMA_cmap_wid_postRedisplay puts it in as a workprocess.
9656 You need to force the immediate execution of
9657 SUMA_cmap_wid_handleRedisplay which resets the context before
9658 returning */
9659 SUMA_LH("Calling SUMA_cmap_wid_postRedisplay");
9660 SUMA_cmap_wid_postRedisplay(NULL, (XtPointer)ado, NULL);
9661 #else
9662 SUMA_cmap_wid_handleRedisplay((XtPointer)ado);
9663 #endif
9664
9665 SUMA_LH("Calling SUMA_Remixedisplay on %s", ADO_LABEL(ado));
9666 SUMA_Remixedisplay(ado);
9667
9668 SUMA_LH("Returning");
9669 SUMA_RETURN(YUP);
9670 }
9671 /*!
9672 \brief function that handles closing switch colormap list widget
9673 expects LW in client_data
9674 */
SUMA_cb_CloseSwitchCmap(Widget w,XtPointer client_data,XtPointer call)9675 void SUMA_cb_CloseSwitchCmap (Widget w, XtPointer client_data, XtPointer call)
9676 {
9677 static char FuncName[]={"SUMA_cb_CloseSwitchCmap"};
9678 SUMA_LIST_WIDGET *LW = NULL;
9679 SUMA_Boolean LocalHead = NOPE;
9680
9681 SUMA_ENTRY;
9682
9683 SUMA_LH("Called");
9684
9685 SUMA_cb_CloseSwitchLst(w, client_data, call);
9686 /* Now calling standard lst closing function May 2009*/
9687 SUMA_RETURNe; /* get out */
9688
9689 /* Pre May 2009 */
9690 LW = (SUMA_LIST_WIDGET *)client_data;
9691
9692 switch (SUMA_CLOSE_MODE) {/* No open GL drawables in this widget*/
9693 case SUMA_WITHDRAW:
9694 if (LocalHead)
9695 fprintf (SUMA_STDERR,
9696 "%s: Withdrawing list widget %s...\n",
9697 FuncName, LW->Label);
9698
9699 XWithdrawWindow(SUMAg_CF->X->DPY_controller1,
9700 XtWindow(LW->toplevel),
9701 XScreenNumberOfScreen(XtScreen(LW->toplevel)));
9702 break;
9703 case SUMA_DESTROY:
9704 if (LocalHead)
9705 fprintf (SUMA_STDERR,
9706 "%s: Destroying list widget %s...\n", FuncName, LW->Label);
9707 XtDestroyWidget(LW->toplevel);
9708 LW->toplevel = NULL;
9709 break;
9710 default:
9711 SUMA_S_Err("Not setup to deal with this closing type");
9712 SUMA_RETURNe;
9713 break;
9714 }
9715
9716 LW->isShaded = YUP;
9717
9718
9719
9720 SUMA_RETURNe;
9721 }
9722
9723 /* based on bbox.c's optmenu_EV */
SUMA_optmenu_EV(Widget w,XtPointer cd,XEvent * ev,Boolean * continue_to_dispatch)9724 void SUMA_optmenu_EV( Widget w , XtPointer cd ,
9725 XEvent *ev , Boolean *continue_to_dispatch )
9726 {
9727 static char FuncName[]={"SUMA_optmenu_EV"};
9728 Dimension lw=0 ;
9729 Widget * children , wl = NULL;
9730 XButtonEvent * bev = (XButtonEvent *) ev ;
9731 int num_children , ic ;
9732 SUMA_ALL_DO *ado = (SUMA_ALL_DO *)cd;
9733 SUMA_Boolean LocalHead = NOPE;
9734
9735 SUMA_ENTRY;
9736
9737 SUMA_LH("Called");
9738
9739 /* see note in bbox.c optmenu_EV for the condition below*/
9740 if( bev->button == Button2 ){
9741 XUngrabPointer( bev->display , CurrentTime ) ;
9742 SUMA_RETURNe ;
9743 }
9744
9745 if( w == NULL || ado == NULL ) SUMA_RETURNe ;
9746
9747 if( bev->button != Button3 ) SUMA_RETURNe ;
9748
9749 if (LocalHead) {
9750 SUMA_LH("Les enfants de w");
9751 SUMA_ShowMeTheChildren(w);
9752 }
9753
9754 /* get the widget named "OptionLabel" */
9755 wl = XtNameToWidget(w, "OptionLabel");
9756 if (!wl) {
9757 SUMA_SL_Err("Failed to find la widget"); /* do continue */
9758 } else { /* confine yourself to the label, young man */
9759 XtVaGetValues( wl , XmNwidth, &lw , NULL ) ;
9760 if( bev->x > lw ) SUMA_RETURNe ;
9761 }
9762
9763 /* Need to create a list */
9764 SUMA_LHv("Now creating list XtName(w)=%s \n", XtName(w));
9765 if (strcmp(XtName(w), "I") == 0) {
9766 if (!SUMA_DsetColSelectList(ado, 0, 0, 1)) {
9767 SUMA_SLP_Err("Failed to create DsetList");
9768 SUMA_RETURNe;
9769 }
9770 } else if (strcmp(XtName(w), "T") == 0){
9771 if (!SUMA_DsetColSelectList(ado, 1, 0, 1)) {
9772 SUMA_SLP_Err("Failed to create DsetList");
9773 SUMA_RETURNe;
9774 }
9775 } else if (strcmp(XtName(w), "B") == 0){
9776 if (!SUMA_DsetColSelectList(ado, 2, 0, 1)) {
9777 SUMA_SLP_Err("Failed to create DsetList");
9778 SUMA_RETURNe;
9779 }
9780 } else if (strcmp(XtName(w), "Cmp") == 0){
9781 if (!SUMA_CmapSelectList(ado, 0, 1)) {
9782 SUMA_SLP_Err("Failed to create DsetList");
9783 SUMA_RETURNe;
9784 }
9785 } else {
9786 SUMA_SLP_Err("wahtchyoutalkinaboutwillis?");
9787 SUMA_RETURNe;
9788 }
9789 SUMA_RETURNe;
9790
9791 }
9792
SUMA_CreateXhairWidgets(Widget parent,SUMA_ALL_DO * ado)9793 void SUMA_CreateXhairWidgets(Widget parent, SUMA_ALL_DO *ado)
9794 {
9795 static char FuncName[]={"SUMA_CreateXhairWidgets"};
9796 SUMA_ENTRY;
9797
9798 if (!ado) {
9799 SUMA_RETURNe;
9800 }
9801 switch (ado->do_type) {
9802 case SO_type:
9803 SUMA_CreateXhairWidgets_SO(parent, ado);
9804 break;
9805 case GDSET_type:
9806 SUMA_S_Err("Should not create widgets for a DO that "
9807 "can't be displayed without variant");
9808 SUMA_RETURNe;
9809 case CDOM_type:
9810 SUMA_CreateXhairWidgets_CO(parent, ado);
9811 SUMA_RETURNe;
9812 break;
9813 case GRAPH_LINK_type:
9814 SUMA_CreateXhairWidgets_GLDO(parent, ado);
9815 break;
9816 case TRACT_type:
9817 SUMA_CreateXhairWidgets_TDO(parent, ado);
9818 break;
9819 case MASK_type:
9820 SUMA_CreateXhairWidgets_MDO(parent, ado);
9821 break;
9822 case VO_type:
9823 SUMA_CreateXhairWidgets_VO(parent, ado);
9824 break;
9825 default:
9826 SUMA_S_Errv("Not ready for this beast %d (%s)\n",
9827 ado->do_type, SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
9828 break;
9829 }
9830 SUMA_RETURNe;
9831 }
9832
SUMA_CreateXhairWidgets_SO(Widget parent,SUMA_ALL_DO * ado)9833 void SUMA_CreateXhairWidgets_SO(Widget parent, SUMA_ALL_DO *ado)
9834 {
9835 static char FuncName[]={"SUMA_CreateXhairWidgets_SO"};
9836 char *Xhair_tit[]= { "Xhr ", NULL};
9837 char *Xhair_hint[]= { "Crosshair coordinates.", NULL};
9838 char *Xhair_help[]= { SUMA_SurfContHelp_Xhr , NULL};
9839 char *Node_tit[]= { "Node" , NULL};
9840 char *Node_hint[]= { "Node index", NULL};
9841 char *Node_help[]= { SUMA_SurfContHelp_Node , NULL};
9842 char *Face_tit[]= { "Tri ", NULL};
9843 char *Face_hint[]= { "1- Triangle index, 2- Nodes forming tiangle", NULL};
9844 char *Face_help[]= { SUMA_SurfContHelp_Tri , NULL};
9845 char *Data_tit[]= { " ", "Intens", "Thresh", "Bright" , NULL};
9846 char *Data_colhint[]= { "Data Values at node in focus",
9847 "Intensity (I) value",
9848 "Threshold (T) value",
9849 "Brightness modulation (B) value" , NULL};
9850 char *Data_colhelp[]= { SUMA_SurfContHelp_NodeValTblc0,
9851 SUMA_SurfContHelp_NodeValTblc1,
9852 SUMA_SurfContHelp_NodeValTblc2,
9853 SUMA_SurfContHelp_NodeValTblc3 , NULL};
9854
9855 char *Data_rtit[]= { " ", "Val " , NULL};
9856 char *Data_rowhint[]= { "Data Values at node in focus",
9857 "Data Values at node in focus" , NULL};
9858 char *Data_rowhelp[]= { SUMA_SurfContHelp_NodeValTblr0,
9859 SUMA_SurfContHelp_NodeValTblr0 , NULL};
9860
9861 char *Label_tit[]= { "Lbl ", NULL};
9862 char *Label_hint[]= { "Color at node in focus", NULL};
9863 char *Label_help[]= { SUMA_SurfContHelp_NodeLabelTblr0 , NULL};
9864 SUMA_X_SurfCont *SurfCont=NULL;
9865 Widget rcc;
9866
9867 SUMA_Boolean LocalHead = NOPE;
9868
9869 SUMA_ENTRY;
9870
9871 if (!ado || ado->do_type != SO_type || !(SurfCont = SUMA_ADO_Cont(ado))) {
9872 SUMA_RETURNe;
9873 }
9874 /* a row column to contain them all */
9875 rcc = XtVaCreateWidget ("rowcolumn",
9876 xmRowColumnWidgetClass, parent,
9877 XmNpacking, XmPACK_TIGHT,
9878 XmNleftAttachment,XmATTACH_FORM ,
9879 XmNorientation , XmVERTICAL ,
9880 XmNmarginHeight , 0 ,
9881 XmNmarginWidth , 0 ,
9882 NULL);
9883
9884 /* a simple table with the xhair coordinate */
9885 SUMA_LH("Creating Xhair coordinates table");
9886 {
9887 int colw[] = { 4, 27 };
9888 SUMA_CreateTable(rcc,
9889 1, 2,
9890 "SurfCont->Xhair_Info->Xhr",
9891 Xhair_tit, NULL,
9892 Xhair_hint, NULL,
9893 Xhair_help, NULL,
9894 colw, YUP, SUMA_string,
9895 SUMA_XhairInput, (void*)ado,
9896 NULL, NULL,
9897 NULL, NULL,
9898 SurfCont->XhairTable);
9899 }
9900 /* a table for a node's index */
9901 SUMA_LH("Creating node table");
9902 {
9903 int colw[]={4, 6, 19};
9904 SUMA_CreateTable(rcc,
9905 1, 3,
9906 "SurfCont->Xhair_Info->Node",
9907 Node_tit, NULL,
9908 Node_hint, NULL,
9909 Node_help, NULL,
9910 colw, YUP, SUMA_int,
9911 SUMA_NodeInput, (void*)ado,
9912 NULL, NULL,
9913 NULL, NULL,
9914 SurfCont->NodeTable);
9915 /* disable the 3rd entry cell */
9916 SUMA_SetCellEditMode(SurfCont->NodeTable, 0, 2, 0);
9917 }
9918 /* a table for the triangle in focus */
9919 SUMA_LH("Creating Face table");
9920 {
9921 int colw[]={4, 6, 19} ;
9922 SUMA_CreateTable(rcc,
9923 1, 3,
9924 "SurfCont->Xhair_Info->Tri",
9925 Face_tit, NULL,
9926 Face_hint, NULL,
9927 Face_help, NULL,
9928 colw, YUP, SUMA_int,
9929 SUMA_TriInput, (void*)ado,
9930 NULL, NULL,
9931 NULL, NULL,
9932 SurfCont->FaceTable);
9933 /* disable the 3rd entry cell */
9934 SUMA_SetCellEditMode(SurfCont->FaceTable, 0, 2, 0);
9935 }
9936 /* a table for the Dset values at node in focus */
9937 SUMA_LH("Creating Dset Val table");
9938 {
9939 int colw[]={ 4, 7, 7, 7};
9940 SUMA_CreateTable(rcc,
9941 2, 4,
9942 "SurfCont->Xhair_Info->Val",
9943 Data_rtit, Data_tit,
9944 Data_rowhint, Data_colhint,
9945 Data_rowhelp, Data_colhelp,
9946 colw, NOPE, SUMA_float,
9947 NULL, NULL,
9948 NULL, NULL,
9949 NULL, NULL,
9950 SurfCont->DataTable);
9951 }
9952 /* a table for a node's label*/
9953 SUMA_LH("Creating label table");
9954 {
9955 int colw[]={4, 26};
9956 SUMA_CreateTable(rcc,
9957 1, 2,
9958 "SurfCont->Xhair_Info->Lbl",
9959 Label_tit, NULL,
9960 Label_hint, NULL,
9961 Label_help, NULL,
9962 colw, NOPE, SUMA_string,
9963 NULL, NULL,
9964 NULL, NULL,
9965 NULL, NULL,
9966 SurfCont->LabelTable);
9967 }
9968 XtManageChild(rcc);
9969 SUMA_RETURNe;
9970
9971 }
9972
SUMA_CreateXhairWidgets_GLDO(Widget parent,SUMA_ALL_DO * ado)9973 void SUMA_CreateXhairWidgets_GLDO(Widget parent, SUMA_ALL_DO *ado)
9974 {
9975 static char FuncName[]={"SUMA_CreateXhairWidgets_GLDO"};
9976 char *Xhair_tit[]= { "Xhr ", NULL};
9977 char *Xhair_hint[]= { "Crosshair coordinates.", NULL};
9978 char *Xhair_help[]= { SUMA_SurfContHelp_Xhr , NULL};
9979 char *Node_tit[]= { "Node" , NULL};
9980 char *Node_hint[]= { "Closest Node index", NULL};
9981 char *Node_help[]= { SUMA_SurfContHelp_GNode , NULL};
9982 char *Edge_tit[]= { "Edge", NULL};
9983 char *Edge_hint[]= { "1- Edge index, 2- Nodes forming (directed) edge",
9984 NULL};
9985 char *Edge_help[]= { SUMA_SurfContHelp_GEdge , NULL};
9986 char *Data_tit[]= { " ", "Intens", "Thresh", "Bright" , NULL};
9987 char *Data_colhint[]= { "Data Values at Edge in Focus",
9988 "Intensity (I) value",
9989 "Threshold (T) value",
9990 "Brightness modulation (B) value" , NULL};
9991 char *Data_colhelp[]= { SUMA_SurfContHelp_GEdgeValTblc0,
9992 SUMA_SurfContHelp_GEdgeValTblc1,
9993 SUMA_SurfContHelp_GEdgeValTblc2,
9994 SUMA_SurfContHelp_GEdgeValTblc3 , NULL};
9995
9996 char *Data_rtit[]= { " ", "Val " , NULL};
9997 char *Data_rowhint[]= { "Data Values at Edge in Focus",
9998 "Data Values at Edge in Focus" , NULL};
9999 char *Data_rowhelp[]= { SUMA_SurfContHelp_GEdgeValTblr0,
10000 SUMA_SurfContHelp_GEdgeValTblr0 , NULL};
10001
10002 char *Label_tit[]= { "Lbl ", NULL};
10003 char *Label_hint[]= { "Label of edge in focus", NULL};
10004 char *Label_help[]= { SUMA_SurfContHelp_GEdgeLabelTblr0 , NULL};
10005 SUMA_X_SurfCont *SurfCont=NULL;
10006 Widget rcc;
10007 SUMA_Boolean LocalHead = NOPE;
10008
10009 SUMA_ENTRY;
10010
10011 if (!ado || ado->do_type != GRAPH_LINK_type ||
10012 !(SurfCont = SUMA_ADO_Cont(ado))) {
10013 SUMA_S_Errv("Something's amiss %p, type %d (%s) (must be GRAPH_LINK)\n",
10014 ado, ado?ado->do_type:0, ADO_TNAME(ado));
10015 SUMA_RETURNe;
10016 }
10017
10018 /* a row column to contain them all */
10019 rcc = XtVaCreateWidget ("rowcolumn",
10020 xmRowColumnWidgetClass, parent,
10021 XmNpacking, XmPACK_TIGHT,
10022 XmNleftAttachment,XmATTACH_FORM ,
10023 XmNorientation , XmVERTICAL ,
10024 XmNmarginHeight , 0 ,
10025 XmNmarginWidth , 0 ,
10026 NULL);
10027
10028 /* a simple table with the xhair coordinate */
10029 SUMA_LH("Creating Xhair coordinates table");
10030 {
10031 int colw[] = { 4, 27 };
10032 SUMA_CreateTable(rcc,
10033 1, 2,
10034 "GraphCont->Xhair_Info->Xhr",
10035 Xhair_tit, NULL,
10036 Xhair_hint, NULL,
10037 Xhair_help, NULL,
10038 colw, YUP, SUMA_string,
10039 SUMA_XhairInput, (void*)ado,
10040 NULL, NULL,
10041 NULL, NULL,
10042 SurfCont->XhairTable);
10043 }
10044 /* a table for the edge in focus */
10045 SUMA_LH("Creating Edge table");
10046 {
10047 int colw[]={4, 6, 19} ;
10048 SUMA_CreateTable(rcc,
10049 1, 3,
10050 "GraphCont->Xhair_Info->Edge",
10051 Edge_tit, NULL,
10052 Edge_hint, NULL,
10053 Edge_help, NULL,
10054 colw, YUP, SUMA_int,
10055 SUMA_NodeInput, (void*)ado,
10056 NULL, NULL,
10057 NULL, NULL,
10058 SurfCont->NodeTable);
10059 /* disable the 3rd entry cell */
10060 SUMA_SetCellEditMode(SurfCont->NodeTable, 0, 2, 0);
10061 }
10062 /* a table for a node's index */
10063 SUMA_LH("Creating graph node table");
10064 {
10065 int colw[]={4, 6, 19};
10066 SUMA_CreateTable(rcc,
10067 1, 3,
10068 "GraphCont->Xhair_Info->Node",
10069 Node_tit, NULL,
10070 Node_hint, NULL,
10071 Node_help, NULL,
10072 colw, YUP, SUMA_int,
10073 SUMA_GNodeInput, (void*)ado,
10074 NULL, NULL,
10075 NULL, NULL,
10076 SurfCont->FaceTable);
10077 /* disable the 3rd entry cell */
10078 SUMA_SetCellEditMode(SurfCont->FaceTable, 0, 2, 0);
10079 }
10080 /* a table for the Dset values at node in focus */
10081 SUMA_LH("Creating Dset Val table");
10082 {
10083 int colw[]={ 4, 7, 7, 7};
10084 SUMA_CreateTable(rcc,
10085 2, 4,
10086 "GraphCont->Xhair_Info->Val",
10087 Data_rtit, Data_tit,
10088 Data_rowhint, Data_colhint,
10089 Data_rowhelp, Data_colhelp,
10090 colw, NOPE, SUMA_float,
10091 NULL, NULL,
10092 NULL, NULL,
10093 NULL, NULL,
10094 SurfCont->DataTable);
10095 }
10096 /* a table for a node's label*/
10097 SUMA_LH("Creating label table");
10098 {
10099 int colw[]={4, 26};
10100 SUMA_CreateTable(rcc,
10101 1, 2,
10102 "GraphCont->Xhair_Info->Lbl",
10103 Label_tit, NULL,
10104 Label_hint, NULL,
10105 Label_help, NULL,
10106 colw, NOPE, SUMA_string,
10107 NULL, NULL,
10108 NULL, NULL,
10109 NULL, NULL,
10110 SurfCont->LabelTable);
10111 }
10112 XtManageChild(rcc);
10113 SUMA_RETURNe;
10114
10115 }
10116
SUMA_CreateXhairWidgets_TDO(Widget parent,SUMA_ALL_DO * ado)10117 void SUMA_CreateXhairWidgets_TDO(Widget parent, SUMA_ALL_DO *ado)
10118 {
10119 static char FuncName[]={"SUMA_CreateXhairWidgets_TDO"};
10120 char *Xhair_tit[]= { "Xhr ", NULL};
10121 char *Xhair_hint[]= { "Crosshair coordinates.", NULL};
10122 char *Xhair_help[]= { SUMA_SurfContHelp_Xhr , NULL};
10123 char *I_tit[]= { "Ind ", NULL };
10124 char *I_hint[] = { "Point index in whole network", NULL };
10125 char *I_help[] = { SUMA_TractContHelp_I, NULL };
10126 char *BTP_tit[]= { "BTP" , NULL};
10127 char *BTP_hint[]= { "Bundle index in network, Tract index in bundle, "
10128 "Point index in tract",
10129 NULL};
10130 char *BTP_help[]= { SUMA_SurfContHelp_BTP , NULL};
10131 char *Data_tit[]= { " ", "Intens", "Thresh", "Bright" , NULL};
10132 char *Data_colhint[]= { "Data values at tract point in focus",
10133 "Intensity (I) value",
10134 "Threshold (T) value",
10135 "Brightness modulation (B) value" , NULL};
10136 char *Data_colhelp[]= { SUMA_TractContHelp_NodeValTblc0,
10137 SUMA_SurfContHelp_NodeValTblc1,
10138 SUMA_SurfContHelp_NodeValTblc2,
10139 SUMA_SurfContHelp_NodeValTblc3 , NULL};
10140
10141 char *Data_rtit[]= { " ", "Val " , NULL};
10142 char *Data_rowhint[]= { "Data Values at point in focus",
10143 "Data Values at point in focus" , NULL};
10144 char *Data_rowhelp[]= { SUMA_SurfContHelp_NodeValTblr0,
10145 SUMA_SurfContHelp_NodeValTblr0 , NULL};
10146
10147 char *Label_tit[]= { "Lbl ", NULL};
10148 char *Label_hint[]= { "Label at selected point", NULL};
10149 char *Label_help[]= { SUMA_TractContHelp_NodeLabelTblr0 , NULL};
10150 SUMA_X_SurfCont *SurfCont=NULL;
10151 Widget rcc, rcch;
10152
10153 SUMA_Boolean LocalHead = NOPE;
10154
10155 SUMA_ENTRY;
10156
10157 if (!ado || ado->do_type != TRACT_type || !(SurfCont = SUMA_ADO_Cont(ado))) {
10158 SUMA_RETURNe;
10159 }
10160 /* a row column to contain them all */
10161 rcc = XtVaCreateWidget ("rowcolumn",
10162 xmRowColumnWidgetClass, parent,
10163 XmNpacking, XmPACK_TIGHT,
10164 XmNleftAttachment,XmATTACH_FORM ,
10165 XmNorientation , XmVERTICAL ,
10166 XmNmarginHeight , 0 ,
10167 XmNmarginWidth , 0 ,
10168 NULL);
10169
10170 /* a simple table with the xhair coordinate */
10171 SUMA_LH("Creating Xhair coordinates table");
10172 {
10173 int colw[] = { 4, 27 };
10174 SUMA_CreateTable(rcc,
10175 1, 2,
10176 "TractCont->Xhair_Info->Xhr",
10177 Xhair_tit, NULL,
10178 Xhair_hint, NULL,
10179 Xhair_help, NULL,
10180 colw, YUP, SUMA_string,
10181 SUMA_XhairInput, (void*)ado,
10182 NULL, NULL,
10183 NULL, NULL,
10184 SurfCont->XhairTable);
10185 }
10186 rcch = XtVaCreateWidget ("rowcolumn",
10187 xmRowColumnWidgetClass, rcc,
10188 XmNpacking, XmPACK_TIGHT,
10189 XmNleftAttachment,XmATTACH_FORM ,
10190 XmNorientation , XmHORIZONTAL ,
10191 XmNmarginHeight , 0 ,
10192 XmNmarginWidth , 0 ,
10193 NULL);
10194 /* a table for a point's index */
10195 SUMA_LH("Creating point table");
10196 {
10197 int colw[]={3, 5};
10198 SUMA_CreateTable(rcch,
10199 1, 2,
10200 "TractCont->Xhair_Info->Ind",
10201 I_tit, NULL,
10202 I_hint, NULL,
10203 I_help, NULL,
10204 colw, YUP, SUMA_int,
10205 SUMA_NodeInput, (void*)ado,
10206 NULL, NULL,
10207 NULL, NULL,
10208 SurfCont->NodeTable);
10209 }
10210 /* a table for a point's BTP index */
10211 SUMA_LH("Creating BTP table");
10212 {
10213 int colw[]={4, 15};
10214 SUMA_CreateTable(rcch,
10215 1, 2,
10216 "TractCont->Xhair_Info->BTP",
10217 BTP_tit, NULL,
10218 BTP_hint, NULL,
10219 BTP_help, NULL,
10220 colw, YUP, SUMA_string,
10221 SUMA_TpointInput, (void*)ado,
10222 NULL, NULL,
10223 NULL, NULL,
10224 SurfCont->FaceTable);
10225 }
10226 XtManageChild(rcch);
10227
10228
10229 /* a table for the Dset values at node in focus */
10230 SUMA_LH("Creating Dset Val table");
10231 {
10232 int colw[]={ 4, 7, 7, 7};
10233 SUMA_CreateTable(rcc,
10234 2, 4,
10235 "TractCont->Xhair_Info->Val",
10236 Data_rtit, Data_tit,
10237 Data_rowhint, Data_colhint,
10238 Data_rowhelp, Data_colhelp,
10239 colw, NOPE, SUMA_float,
10240 NULL, NULL,
10241 NULL, NULL,
10242 NULL, NULL,
10243 SurfCont->DataTable);
10244 }
10245 /* a table for a node's label*/
10246 SUMA_LH("Creating label table");
10247 {
10248 int colw[]={4, 26};
10249 SUMA_CreateTable(rcc,
10250 1, 2,
10251 "TractCont->Xhair_Info->Lbl",
10252 Label_tit, NULL,
10253 Label_hint, NULL,
10254 Label_help, NULL,
10255 colw, NOPE, SUMA_string,
10256 NULL, NULL,
10257 NULL, NULL,
10258 NULL, NULL,
10259 SurfCont->LabelTable);
10260 }
10261 XtManageChild(rcc);
10262 SUMA_RETURNe;
10263 }
10264
SUMA_CreateXhairWidgets_MDO(Widget parent,SUMA_ALL_DO * ado)10265 void SUMA_CreateXhairWidgets_MDO(Widget parent, SUMA_ALL_DO *ado)
10266 {
10267 static char FuncName[]={"SUMA_CreateXhairWidgets_MDO"};
10268 char *Xhair_tit[]= { "Xhr ", NULL};
10269 char *Xhair_hint[]= { "Crosshair coordinates.", NULL};
10270 char *Xhair_help[]= { SUMA_SurfContHelp_Xhr , NULL};
10271 char *I_tit[]= { "Ind ", NULL };
10272 char *I_hint[] = { "Point index in whole network", NULL };
10273 char *I_help[] = { SUMA_TractContHelp_I, NULL };
10274 char *BTP_tit[]= { "BTP" , NULL};
10275 char *BTP_hint[]= { "Bundle index in network, Tract index in bundle, "
10276 "Point index in tract",
10277 NULL};
10278 char *BTP_help[]= { SUMA_SurfContHelp_BTP , NULL};
10279 char *Data_tit[]= { " ", "Intens", "Thresh", "Bright" , NULL};
10280 char *Data_colhint[]= { "Data Values at tract point in focus",
10281 "Intensity (I) value",
10282 "Threshold (T) value",
10283 "Brightness modulation (B) value" , NULL};
10284 char *Data_colhelp[]= { SUMA_SurfContHelp_NodeValTblc0,
10285 SUMA_SurfContHelp_NodeValTblc1,
10286 SUMA_SurfContHelp_NodeValTblc2,
10287 SUMA_SurfContHelp_NodeValTblc3 , NULL};
10288
10289 char *Data_rtit[]= { " ", "Val " , NULL};
10290 char *Data_rowhint[]= { "Data Values at point in focus",
10291 "Data Values at point in focus" , NULL};
10292 char *Data_rowhelp[]= { SUMA_SurfContHelp_NodeValTblr0,
10293 SUMA_SurfContHelp_NodeValTblr0 , NULL};
10294
10295 char *Label_tit[]= { "Lbl ", NULL};
10296 char *Label_hint[]= { "Label at node in focus", NULL};
10297 char *Label_help[]= { SUMA_SurfContHelp_NodeLabelTblr0 , NULL};
10298 SUMA_X_SurfCont *SurfCont=NULL;
10299 Widget rcc, rcch;
10300
10301 SUMA_Boolean LocalHead = NOPE;
10302
10303 SUMA_ENTRY;
10304
10305 if (!ado || ado->do_type != MASK_type || !(SurfCont = SUMA_ADO_Cont(ado))) {
10306 SUMA_RETURNe;
10307 }
10308
10309 SUMA_S_Warn("Nothing done below");
10310 SUMA_RETURNe;
10311
10312 /* a row column to contain them all */
10313 rcc = XtVaCreateWidget ("rowcolumn",
10314 xmRowColumnWidgetClass, parent,
10315 XmNpacking, XmPACK_TIGHT,
10316 XmNleftAttachment,XmATTACH_FORM ,
10317 XmNorientation , XmVERTICAL ,
10318 XmNmarginHeight , 0 ,
10319 XmNmarginWidth , 0 ,
10320 NULL);
10321
10322 /* a simple table with the xhair coordinate */
10323 SUMA_LH("Creating Xhair coordinates table");
10324 {
10325 int colw[] = { 4, 27 };
10326 SUMA_CreateTable(rcc,
10327 1, 2,
10328 "MaskCont->NOT_DONE->Xhr",
10329 Xhair_tit, NULL,
10330 Xhair_hint, NULL,
10331 Xhair_help, NULL,
10332 colw, YUP, SUMA_string,
10333 SUMA_XhairInput, (void*)ado,
10334 NULL, NULL,
10335 NULL, NULL,
10336 SurfCont->XhairTable);
10337 }
10338 rcch = XtVaCreateWidget ("rowcolumn",
10339 xmRowColumnWidgetClass, rcc,
10340 XmNpacking, XmPACK_TIGHT,
10341 XmNleftAttachment,XmATTACH_FORM ,
10342 XmNorientation , XmHORIZONTAL ,
10343 XmNmarginHeight , 0 ,
10344 XmNmarginWidth , 0 ,
10345 NULL);
10346 /* a table for a point's index */
10347 SUMA_LH("Creating point table");
10348 {
10349 int colw[]={3, 5};
10350 SUMA_CreateTable(rcch,
10351 1, 2,
10352 "MaskCont->NOT_DONE->I",
10353 I_tit, NULL,
10354 I_hint, NULL,
10355 I_help, NULL,
10356 colw, YUP, SUMA_int,
10357 SUMA_NodeInput, (void*)ado,
10358 NULL, NULL,
10359 NULL, NULL,
10360 SurfCont->NodeTable);
10361 }
10362 /* a table for a point's BTP index */
10363 SUMA_LH("Creating BTP table");
10364 {
10365 int colw[]={4, 15};
10366 SUMA_CreateTable(rcch,
10367 1, 2,
10368 "MaskCont->NOT_DONE->BTP",
10369 BTP_tit, NULL,
10370 BTP_hint, NULL,
10371 BTP_help, NULL,
10372 colw, YUP, SUMA_string,
10373 SUMA_TpointInput, (void*)ado,
10374 NULL, NULL,
10375 NULL, NULL,
10376 SurfCont->FaceTable);
10377 }
10378 XtManageChild(rcch);
10379
10380
10381 /* a table for the Dset values at node in focus */
10382 SUMA_LH("Creating Dset Val table");
10383 {
10384 int colw[]={ 4, 7, 7, 7};
10385 SUMA_CreateTable(rcc,
10386 2, 4,
10387 "MaskCont->NOT_DONE->Val",
10388 Data_rtit, Data_tit,
10389 Data_rowhint, Data_colhint,
10390 Data_rowhelp, Data_colhelp,
10391 colw, NOPE, SUMA_float,
10392 NULL, NULL,
10393 NULL, NULL,
10394 NULL, NULL,
10395 SurfCont->DataTable);
10396 }
10397 /* a table for a node's label*/
10398 SUMA_LH("Creating label table");
10399 {
10400 int colw[]={4, 26};
10401 SUMA_CreateTable(rcc,
10402 1, 2,
10403 "MaskCont->NOT_DONE->Lbl",
10404 Label_tit, NULL,
10405 Label_hint, NULL,
10406 Label_help, NULL,
10407 colw, NOPE, SUMA_string,
10408 NULL, NULL,
10409 NULL, NULL,
10410 NULL, NULL,
10411 SurfCont->LabelTable);
10412 }
10413 XtManageChild(rcc);
10414 SUMA_RETURNe;
10415
10416 }
10417
SUMA_CreateXhairWidgets_VO(Widget parent,SUMA_ALL_DO * ado)10418 void SUMA_CreateXhairWidgets_VO(Widget parent, SUMA_ALL_DO *ado)
10419 {
10420 static char FuncName[]={"SUMA_CreateXhairWidgets_VO"};
10421 char *Xhair_tit[]= { "Xhr ", NULL};
10422 char *Xhair_hint[]= { "Crosshair coordinates.", NULL};
10423 char *Xhair_help[]= { SUMA_SurfContHelp_Xhr , NULL};
10424 char *I_tit[]= { "Ind ", NULL };
10425 char *I_hint[] = { "Voxel 1D index in volume", NULL };
10426 char *I_help[] = { SUMA_VolContHelp_I, NULL };
10427 char *BTP_tit[]= { "IJK" , NULL};
10428 char *BTP_hint[]= { "Voxel 3D indices in volume",
10429 NULL};
10430 char *BTP_help[]= { SUMA_SurfContHelp_IJK , NULL};
10431 char *Data_tit[]= { " ", "Intens", "Thresh", "Bright" , NULL};
10432 char *Data_colhint[]= { "Data Values at voxel in focus",
10433 "Intensity (I) value",
10434 "Threshold (T) value",
10435 "Brightness modulation (B) value" , NULL};
10436 char *Data_colhelp[]= { SUMA_VolContHelp_NodeValTblc0,
10437 SUMA_SurfContHelp_NodeValTblc1,
10438 SUMA_SurfContHelp_NodeValTblc2,
10439 SUMA_SurfContHelp_NodeValTblc3 , NULL};
10440
10441 char *Data_rtit[]= { " ", "Val " , NULL};
10442 char *Data_rowhint[]= { "Data values at voxel in focus",
10443 "Data values at voxel in focus" , NULL};
10444 char *Data_rowhelp[]= { SUMA_SurfContHelp_NodeValTblr0,
10445 SUMA_SurfContHelp_NodeValTblr0 , NULL};
10446
10447 char *Label_tit[]= { "Lbl ", NULL};
10448 char *Label_hint[]= { "Label at voxel in focus", NULL};
10449 char *Label_help[]= { SUMA_SurfContHelp_NodeLabelTblr0 , NULL};
10450 SUMA_X_SurfCont *SurfCont=NULL;
10451 Widget rcc, rcch;
10452
10453 SUMA_Boolean LocalHead = NOPE;
10454
10455 SUMA_ENTRY;
10456
10457 if (!ado || ado->do_type != VO_type || !(SurfCont = SUMA_ADO_Cont(ado))) {
10458 SUMA_RETURNe;
10459 }
10460
10461 /* a row column to contain them all */
10462 rcc = XtVaCreateWidget ("rowcolumn",
10463 xmRowColumnWidgetClass, parent,
10464 XmNpacking, XmPACK_TIGHT,
10465 XmNleftAttachment,XmATTACH_FORM ,
10466 XmNorientation , XmVERTICAL ,
10467 XmNmarginHeight , 0 ,
10468 XmNmarginWidth , 0 ,
10469 NULL);
10470
10471 /* a simple table with the xhair coordinate */
10472 SUMA_LH("Creating Xhair coordinates table");
10473 {
10474 int colw[] = { 4, 27 };
10475 SUMA_CreateTable(rcc,
10476 1, 2,
10477 "VolCont->Xhair_Info->Xhr",
10478 Xhair_tit, NULL,
10479 Xhair_hint, NULL,
10480 Xhair_help, NULL,
10481 colw, YUP, SUMA_string,
10482 SUMA_XhairInput, (void*)ado,
10483 NULL, NULL,
10484 NULL, NULL,
10485 SurfCont->XhairTable);
10486 }
10487 rcch = XtVaCreateWidget ("rowcolumn",
10488 xmRowColumnWidgetClass, rcc,
10489 XmNpacking, XmPACK_TIGHT,
10490 XmNleftAttachment,XmATTACH_FORM ,
10491 XmNorientation , XmHORIZONTAL ,
10492 XmNmarginHeight , 0 ,
10493 XmNmarginWidth , 0 ,
10494 NULL);
10495 /* a table for a point's index */
10496 SUMA_LH("Creating point table");
10497 {
10498 int colw[]={3, 6};
10499 SUMA_CreateTable(rcch,
10500 1, 2,
10501 "VolCont->Xhair_Info->Ind",
10502 I_tit, NULL,
10503 I_hint, NULL,
10504 I_help, NULL,
10505 colw, YUP, SUMA_int,
10506 SUMA_NodeInput, (void*)ado,
10507 NULL, NULL,
10508 NULL, NULL,
10509 SurfCont->NodeTable);
10510 }
10511 /* a table for a point's BTP index */
10512 SUMA_LH("Creating IJK table");
10513 {
10514 int colw[]={4, 15};
10515 SUMA_CreateTable(rcch,
10516 1, 2,
10517 "VolCont->Xhair_Info->IJK",
10518 BTP_tit, NULL,
10519 BTP_hint, NULL,
10520 BTP_help, NULL,
10521 colw, YUP, SUMA_string,
10522 SUMA_IJKInput, (void*)ado,
10523 NULL, NULL,
10524 NULL, NULL,
10525 SurfCont->FaceTable);
10526 }
10527 XtManageChild(rcch);
10528
10529
10530 /* a table for the Dset values at node in focus */
10531 SUMA_LH("Creating Dset Val table");
10532 {
10533 int colw[]={ 4, 7, 7, 7};
10534 SUMA_CreateTable(rcc,
10535 2, 4,
10536 "VolCont->Xhair_Info->Val",
10537 Data_rtit, Data_tit,
10538 Data_rowhint, Data_colhint,
10539 Data_rowhelp, Data_colhelp,
10540 colw, NOPE, SUMA_float,
10541 NULL, NULL,
10542 NULL, NULL,
10543 NULL, NULL,
10544 SurfCont->DataTable);
10545 }
10546 /* a table for a voxel's label*/
10547 SUMA_LH("Creating label table");
10548 {
10549 int colw[]={4, 26};
10550 SUMA_CreateTable(rcc,
10551 1, 2,
10552 "VolCont->Xhair_Info->Lbl",
10553 Label_tit, NULL,
10554 Label_hint, NULL,
10555 Label_help, NULL,
10556 colw, NOPE, SUMA_string,
10557 NULL, NULL,
10558 NULL, NULL,
10559 NULL, NULL,
10560 SurfCont->LabelTable);
10561 }
10562 XtManageChild(rcc);
10563 SUMA_RETURNe;
10564
10565 }
10566
10567 /* I suspect this will be a mixture of _VO and _SO */
SUMA_CreateXhairWidgets_CO(Widget parent,SUMA_ALL_DO * ado)10568 void SUMA_CreateXhairWidgets_CO(Widget parent, SUMA_ALL_DO *ado)
10569 {
10570 static char FuncName[]={"SUMA_CreateXhairWidgets_CO"};
10571 char *Xhair_tit[]= { "Xhr ", NULL};
10572 char *Xhair_hint[]= { "Crosshair coordinates.", NULL};
10573 char *Xhair_help[]= { SUMA_SurfContHelp_Xhr , NULL};
10574 char *I_tit[]= { "Ind ", NULL };
10575 char *I_hint[] = { "Voxel 1D index in volume", NULL };
10576 char *I_help[] = { SUMA_VolContHelp_I, NULL };
10577 char *BTP_tit[]= { "IJK" , NULL};
10578 char *BTP_hint[]= { "Voxel 3D indices in volume",
10579 NULL};
10580 char *BTP_help[]= { SUMA_SurfContHelp_IJK , NULL};
10581 char *Data_tit[]= { " ", "Intens", "Thresh", "Bright" , NULL};
10582 char *Data_colhint[]= { "Data Values at voxel in focus",
10583 "Intensity (I) value",
10584 "Threshold (T) value",
10585 "Brightness modulation (B) value" , NULL};
10586 char *Data_colhelp[]= { SUMA_VolContHelp_NodeValTblc0,
10587 SUMA_SurfContHelp_NodeValTblc1,
10588 SUMA_SurfContHelp_NodeValTblc2,
10589 SUMA_SurfContHelp_NodeValTblc3 , NULL};
10590
10591 char *Data_rtit[]= { " ", "Val " , NULL};
10592 char *Data_rowhint[]= { "Data values at voxel in focus",
10593 "Data values at voxel in focus" , NULL};
10594 char *Data_rowhelp[]= { SUMA_SurfContHelp_NodeValTblr0,
10595 SUMA_SurfContHelp_NodeValTblr0 , NULL};
10596
10597 char *Label_tit[]= { "Lbl ", NULL};
10598 char *Label_hint[]= { "Label at voxel in focus", NULL};
10599 char *Label_help[]= { SUMA_SurfContHelp_NodeLabelTblr0 , NULL};
10600 SUMA_X_SurfCont *SurfCont=NULL;
10601 Widget rcc, rcch;
10602
10603 SUMA_Boolean LocalHead = NOPE;
10604
10605 SUMA_ENTRY;
10606
10607 if (!ado || ado->do_type != CDOM_type || !(SurfCont = SUMA_ADO_Cont(ado))) {
10608 SUMA_RETURNe;
10609 }
10610
10611 SUMA_S_Err("Fill me up scotty, premium dude, premium");
10612
10613 SUMA_RETURNe;
10614 }
10615
SUMA_CreateCmapWidgets(Widget parent,SUMA_ALL_DO * ado)10616 void SUMA_CreateCmapWidgets(Widget parent, SUMA_ALL_DO *ado)
10617 {
10618 static char FuncName[]={"SUMA_CreateCmapWidgets"};
10619 char slabel[100], wname[64]={"NoTsEt"}, *blk=NULL;
10620 Widget rct, rcc, rco;
10621 XtVarArgsList arglist=NULL;
10622 SUMA_X_SurfCont *SurfCont=NULL;
10623 SUMA_Boolean LocalHead = NOPE;
10624
10625 SUMA_ENTRY;
10626
10627 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) {
10628 SUMA_S_Err("NULL input");
10629 SUMA_RETURNe;
10630 }
10631
10632 if (SurfCont->opts_rc) {
10633 SUMA_SL_Err("Non null opts_rc\nThis should not be.");
10634 SUMA_RETURNe;
10635 }
10636
10637 if (ado->do_type == GRAPH_LINK_type) {
10638 blk = "GDset_Mapping";
10639 } else {
10640 blk = "Dset_Mapping";
10641 }
10642
10643 SurfCont->opts_form = XtVaCreateWidget ("form",
10644 xmFormWidgetClass, parent,
10645 NULL);
10646
10647 SurfCont->opts_rc = XtVaCreateWidget ("rowcolumn",
10648 xmRowColumnWidgetClass, SurfCont->opts_form,
10649 XmNpacking, XmPACK_TIGHT,
10650 XmNleftAttachment,XmATTACH_FORM ,
10651 XmNorientation , XmHORIZONTAL ,
10652 XmNmarginHeight , 0 ,
10653 XmNmarginWidth , 0 ,
10654 NULL);
10655
10656 SUMA_LH("Creating the threshold bar widgets");
10657 { /* the threshold bar */
10658 rct = XtVaCreateWidget ("rowcolumn",
10659 xmRowColumnWidgetClass, SurfCont->opts_rc,
10660 XmNpacking, XmPACK_TIGHT,
10661 XmNresizeHeight, False, /* important that this rc is not to be resized
10662 automatically,
10663 otherwise, the fix SUMA_FORCE_SCALE_HEIGHT
10664 will fail
10665 */
10666 XmNresizeWidth, False,
10667 XmNwidth, SUMA_SCALE_WIDTH,
10668 XmNheight, SUMA_SCALE_HEIGHT,
10669 XmNorientation , XmVERTICAL ,
10670 XmNmarginHeight , 0 ,
10671 XmNmarginWidth , 0 ,
10672 NULL);
10673 /* convenient common arguments for scales */
10674 arglist = XtVaCreateArgsList( NULL,
10675 XmNshowValue, True,
10676 XmNmaximum, 255,
10677 XmNscaleMultiple, 5,
10678 XmNheight, SUMA_SCALE_HEIGHT,
10679 XmNuserData, (XtPointer)0,
10680 NULL);
10681
10682 /* put a string on top of the scale
10683 Can use XmNtitleString but it is placed on the side.
10684 Too much waisted space */
10685 #if 0
10686 sprintf(slabel,"Thr.");
10687 SurfCont->thr_lb = XtVaCreateManagedWidget (slabel,
10688 xmLabelWidgetClass, rct,
10689 XmNwidth, SUMA_SCALE_WIDTH,
10690 XmNrecomputeSize, False,
10691 /* don't let it change size,
10692 it messes up the slider */
10693 NULL);
10694 #else
10695 {
10696 int colw[]={6};
10697 char *lhint[]={ "Threshold Value (append 'p' to set by p value, "
10698 "'%' to set by percentile)", NULL};
10699 char *lhelp[]={ SUMA_SurfContHelp_SetThreshTblr0, NULL};
10700 if (!SurfCont->SetThrScaleTable->cells) {
10701 snprintf(wname, 63, "%s->%s->ThrVal",
10702 SUMA_do_type_2_contwname(SurfCont->do_type), blk);
10703 SUMA_CreateTable( rct,
10704 1, 1,
10705 wname,
10706 NULL, NULL,
10707 lhint, NULL,
10708 lhelp, NULL,
10709 colw, YUP, SUMA_float,
10710 SUMA_cb_SetScaleThr, (void *)ado,
10711 NULL, NULL,
10712 NULL, NULL,
10713 SurfCont->SetThrScaleTable);
10714 }
10715 }
10716 #endif
10717 /* add a vertical scale for the intensity */
10718 SurfCont->thr_sc = XtVaCreateManagedWidget("Thr.",
10719 xmScaleWidgetClass, rct,
10720 XtVaNestedList, arglist,
10721 NULL);
10722 #ifdef USING_LESSTIF
10723 if (LocalHead) fprintf(stderr,"\n========= setting width to %d\n",
10724 SUMA_SCALE_SLIDER_WIDTH);
10725 XtVaSetValues( SurfCont->thr_sc,
10726 XmNscaleWidth, SUMA_SCALE_SLIDER_WIDTH , NULL ) ;
10727 #endif
10728
10729
10730 XtAddCallback (SurfCont->thr_sc,
10731 XmNvalueChangedCallback,
10732 SUMA_cb_set_threshold,
10733 (XtPointer) ado);
10734
10735 XtAddCallback (SurfCont->thr_sc,
10736 XmNdragCallback,
10737 SUMA_cb_set_threshold_label,
10738 (XtPointer) ado);
10739 snprintf(wname, 63, "%s->%s->Cmap->scale",
10740 SUMA_do_type_2_contwname(SurfCont->do_type), blk);
10741 SUMA_Register_Widget_Help(SurfCont->thr_sc , 1,
10742 wname,
10743 "Set the threshold for 'T' values",
10744 SUMA_SurfContHelp_ThrScale);
10745
10746 /* put a string for the pvalue */
10747 sprintf(slabel,"p [N/A]\nq [N/A]");
10748 SurfCont->thrstat_lb = XtVaCreateManagedWidget ("font8",
10749 xmLabelWidgetClass, rct,
10750 XmNwidth, SUMA_SCALE_WIDTH,
10751 XmNrecomputeSize, False,
10752 LABEL_ARG(slabel),
10753 XmNinitialResourcesPersistent, False ,
10754 NULL);
10755
10756 snprintf(wname, 63, "%s->%s->Cmap->pval",
10757 SUMA_do_type_2_contwname(SurfCont->do_type), blk);
10758 SUMA_Register_Widget_Help(SurfCont->thrstat_lb , 1,
10759 wname,
10760 "Nominal p-value per node; FDR q-value",
10761 SUMA_SurfContHelp_ThreshStats);
10762 XtManageChild (rct);
10763 }/* the threshold bar */
10764
10765 if (arglist) XtFree(arglist); arglist = NULL;
10766
10767 SUMA_LH("The colorbar");
10768 {/* the color bar */
10769 Widget rcc2;
10770 rcc = XtVaCreateWidget ("rowcolumn",
10771 xmRowColumnWidgetClass, SurfCont->opts_rc,
10772 XmNpacking, XmPACK_TIGHT,
10773 XmNorientation , XmVERTICAL ,
10774 XmNmarginHeight , 0 ,
10775 XmNmarginWidth , 0 ,
10776 NULL);
10777
10778 sprintf(slabel," ");
10779 SurfCont->cmaptit_lb = XtVaCreateManagedWidget (slabel,
10780 xmLabelWidgetClass, rcc,
10781 NULL);
10782 /* need another rc for the cmap to avoid having
10783 the glxarea resized by cmaptit_lb
10784 and SwitchCmapMenu */
10785 rcc2 = XtVaCreateWidget ("rowcolumn",
10786 xmRowColumnWidgetClass, rcc,
10787 XmNpacking, XmPACK_TIGHT,
10788 XmNorientation , XmHORIZONTAL ,
10789 XmNmarginHeight , 0 ,
10790 XmNmarginWidth , 0 ,
10791 NULL);
10792
10793 /* open me a glxarea */
10794 SUMA_LH("Forming glxarea");
10795 {
10796 #ifdef SUMA_MOTIF_GLXAREA
10797 SurfCont->cmp_ren->cmap_wid = XtVaCreateManagedWidget("glxarea",
10798 glwMDrawingAreaWidgetClass, rcc2,
10799 GLwNvisualInfo, SUMAg_SVv[0].X->VISINFO,
10800 XtNcolormap, SUMAg_SVv[0].X->CMAP,
10801 XmNwidth, SUMA_CMAP_WIDTH,
10802 XmNheight, SUMA_CMAP_HEIGHT,
10803 NULL);
10804 #else
10805 SurfCont->cmp_ren->cmap_wid =
10806 XtVaCreateManagedWidget("glxarea",
10807 glwDrawingAreaWidgetClass, rcc2,
10808 GLwNvisualInfo, SUMAg_SVv[0].X->VISINFO,
10809 XtNcolormap, SUMAg_SVv[0].X->CMAP,
10810 XmNwidth, SUMA_CMAP_WIDTH,
10811 XmNheight, SUMA_CMAP_HEIGHT,
10812 NULL);
10813 #endif
10814 snprintf(wname, 63, "%s->%s->Cmap->bar",
10815 SUMA_do_type_2_contwname(SurfCont->do_type), blk);
10816 SUMA_Register_Widget_Help(SurfCont->cmp_ren->cmap_wid ,1,
10817 wname,
10818 "Colorbar for 'I' values",
10819 SUMA_SurfContHelp_ColorBar);
10820 XtManageChild (rcc2);
10821
10822 SUMA_LH("Callbacks on glxarea");
10823 /* add me some callbacks */
10824 XtAddCallback( SurfCont->cmp_ren->cmap_wid,
10825 GLwNginitCallback, SUMA_cmap_wid_graphicsInit,
10826 (XtPointer )ado);
10827 XtAddCallback( SurfCont->cmp_ren->cmap_wid,
10828 GLwNexposeCallback, SUMA_cmap_wid_expose,
10829 (XtPointer )ado);
10830 XtAddCallback( SurfCont->cmp_ren->cmap_wid,
10831 GLwNresizeCallback, SUMA_cmap_wid_resize,
10832 (XtPointer )ado);
10833 XtAddCallback( SurfCont->cmp_ren->cmap_wid,
10834 GLwNinputCallback, SUMA_cmap_wid_input,
10835 (XtPointer )ado);
10836 }
10837
10838 if (SUMAg_CF->Fake_Cmap) {
10839 #define NPANE_MIN 2
10840 #define NPANE_MAX 20
10841 #define PANE_WIDTH 15
10842 #define PANE_MIN_HEIGHT 5
10843 #define PANE_LOFF 6
10844 #define PANE_SPACING 2
10845
10846 #define PANE_MAXMODE 2
10847 #define SASH_HNO 1
10848 Widget frm, pw;
10849 SUMA_S_Warn("Creating X11 cmap for snapshot taking only!");
10850
10851 /*
10852 frm = XtVaCreateManagedWidget( "pbar" , xmFrameWidgetClass , rcc2 ,
10853 XmNshadowType , XmSHADOW_ETCHED_IN ,
10854 NULL ) ;
10855
10856 pw = XtVaCreateManagedWidget( "pbar" , xmPanedWindowWidgetClass , frm ,
10857 XmNsashWidth , PANE_WIDTH-2*PANE_SPACING,
10858 XmNsashIndent , PANE_SPACING ,
10859 XmNsashHeight , SASH_HNO ,
10860 XmNmarginHeight , 0 ,
10861 XmNmarginWidth , 0 ,
10862 XmNspacing , PANE_SPACING ,
10863 XmNx , 0 , XmNy , 0 ,
10864 XmNtraversalOn, True ,
10865 XmNinitialResourcesPersistent , False ,
10866 NULL ) ;
10867 SurfCont->Fake_pbar = XtVaCreateWidget(
10868 "pbar" , xmDrawnButtonWidgetClass , pw ,
10869 XmNpaneMinimum , PANE_MIN_HEIGHT ,
10870 XmNallowResize , True ,
10871 XmNheight , SUMA_CMAP_HEIGHT ,
10872 XmNwidth , PANE_WIDTH,
10873 XmNborderWidth , 0 ,
10874 XmNmarginWidth , 0 ,
10875 XmNmarginHeight , 0 ,
10876 XmNhighlightThickness , 0 ,
10877 XmNpushButtonEnabled , True ,
10878 XmNuserData , (XtPointer)ado ,
10879 XmNtraversalOn , True ,
10880 XmNinitialResourcesPersistent , False ,
10881 NULL ) ;
10882 */
10883 SurfCont->Fake_pbar = XmCreateDrawingArea(rcc2, "pbar", NULL, 0);
10884 XtVaSetValues(SurfCont->Fake_pbar, XmNheight , SUMA_CMAP_HEIGHT ,
10885 XmNwidth , SUMA_CMAP_WIDTH,
10886 XmNallowResize , False ,
10887 NULL);
10888 XtManageChild (SurfCont->Fake_pbar);
10889 XtManageChild (rcc2);
10890 XtAddCallback( SurfCont->Fake_pbar, XmNexposeCallback,
10891 SUMA_PBAR_bigexpose_CB, (XtPointer )ado ) ;
10892 /* The following commands were part of a failed attempt
10893 at getting the rest of the widgets - sub-brick selectors
10894 etc. to appear when the glxarea drawing widget was not
10895 created. For some reason, little other than the X11 colormap
10896 would show if I did not create SurfCont->cmp_ren->cmap_wid
10897 above. Interestingly, commenting out the SurfCont->cmp_ren->cmap_wid
10898 callbacks above also had the same effect.
10899 So the solution is to render both and make one super thin. It is
10900 rendered in black anyway when the picture is snapped so it makes
10901 little difference in the end. ZSS Nov 2014 */
10902 XtAddCallback( SurfCont->Fake_pbar,
10903 XmNresizeCallback, SUMA_PBAR_bigresize_CB,
10904 (XtPointer )ado);
10905 XtAddCallback( SurfCont->Fake_pbar,
10906 XmNinputCallback, SUMA_PBAR_biginput_CB,
10907 (XtPointer )ado);
10908 XtVaSetValues( SurfCont->cmp_ren->cmap_wid,
10909 XmNheight , 1,
10910 XmNwidth , 1,
10911 NULL);
10912 }
10913
10914 XtManageChild (rcc);
10915 } /* the colorbar */
10916
10917 /* The options will be created as needed, when colorplanes are switched.
10918 see SUMA_InitializeColPlaneShell */
10919
10920 XtManageChild (SurfCont->opts_rc);
10921 XtManageChild (SurfCont->opts_form);
10922
10923 SUMA_RETURNe;
10924 }
10925
SUMA_FreeMenuVector(SUMA_MenuItem * menu,int Nels)10926 SUMA_MenuItem *SUMA_FreeMenuVector(SUMA_MenuItem *menu, int Nels)
10927 {
10928 static char FuncName[]={"SUMA_FreeMenuVector"};
10929 int i;
10930
10931 SUMA_ENTRY;
10932
10933 if (!menu) {SUMA_RETURN(NULL);}
10934 if (Nels <= 0) {SUMA_RETURN(NULL);}
10935
10936 for (i=0; i<Nels; ++i) {
10937 if (menu[i].label) SUMA_free(menu[i].label);
10938 if (menu[i].accelerator) SUMA_free(menu[i].accelerator);
10939 if (menu[i].accel_text) SUMA_free(menu[i].accel_text);
10940 if (menu[i].subitems) {
10941 SUMA_SL_Err("Don't know how to free subitems yet."); }
10942 }
10943 SUMA_free(menu);
10944
10945 SUMA_RETURN(NULL);
10946 }
10947
SUMA_FormSwitchColMenuVector(SUMA_ALL_DO * ado,int what,int * N_items)10948 SUMA_MenuItem *SUMA_FormSwitchColMenuVector(SUMA_ALL_DO *ado,
10949 int what, int *N_items)
10950 {
10951 static char FuncName[]={"SUMA_FormSwitchColMenuVector"};
10952 SUMA_MenuItem *menu = NULL;
10953 int i, isarrow;
10954 void (*callback)();
10955 NI_element *nel = NULL;
10956 SUMA_X_SurfCont *SurfCont=NULL;
10957 SUMA_OVERLAYS *curColPlane=NULL;
10958 SUMA_Boolean LocalHead = NOPE;
10959
10960 SUMA_ENTRY;
10961
10962 if (!ado) { SUMA_SL_Err("NULL ado"); SUMA_RETURN (menu);}
10963
10964 SurfCont = SUMA_ADO_Cont(ado);
10965 curColPlane = SUMA_ADO_CurColPlane(ado);
10966
10967
10968 if (!SurfCont) { SUMA_SL_Err("NULL SurfCont"); SUMA_RETURN (menu);}
10969 if (!curColPlane) {
10970 SUMA_SL_Err("NULL curColPlane"); SUMA_RETURN (menu);}
10971 if (!curColPlane->dset_link) {
10972 SUMA_SL_Err("NULL curColPlane->dset_link");
10973 SUMA_RETURN (menu);}
10974
10975 nel = curColPlane->dset_link->dnel;
10976 if (!nel) { SUMA_SL_Err("NULL nel"); SUMA_RETURN (menu);}
10977 if (!nel->vec_num) { SUMA_SL_Err("no vecs"); SUMA_RETURN (menu);}
10978
10979 /* decide on callback */
10980 switch (what) {
10981 case 0:
10982 callback = SUMA_cb_SwitchIntensity;
10983 break;
10984 case 1:
10985 callback = SUMA_cb_SwitchThreshold;
10986 break;
10987 case 2:
10988 callback = SUMA_cb_SwitchBrightness;
10989 break;
10990 default:
10991 SUMA_SL_Err("No such what");
10992 SUMA_RETURN(menu);
10993 }
10994
10995 /* Allocate for menu */
10996 menu = (SUMA_MenuItem *)SUMA_calloc((nel->vec_num+1), sizeof(SUMA_MenuItem));
10997 isarrow = SUMA_AllowArrowFieldMenus((nel->vec_num+1), "I");
10998 /* "I", or "B", or "T" OK */
10999
11000 /* fillup menu */
11001 for (i=0; i < nel->vec_num; ++i) {
11002 if (!isarrow) {
11003 menu[i].label =
11004 SUMA_DsetColLabelCopy(curColPlane->dset_link, i, 1);
11005 } else {
11006 /* SUMA_DsetColLabelCopy is slow as a dog for very large numbers
11007 of sub-bricks. In any case, sub-brick labels are not that
11008 important here, this should be improved someday*/
11009 menu[i].label = (char*)malloc(13*sizeof(char));
11010 snprintf(menu[i].label,11*sizeof(char), "sb%d", i-1);
11011 }
11012 menu[i].class = &xmPushButtonWidgetClass;
11013 menu[i].mnemonic = '\0';
11014 menu[i].accelerator = NULL;
11015 menu[i].accel_text = NULL;
11016 menu[i].callback = callback;
11017 menu[i].callback_data = (XTP_CAST)(i+1); /* DO NOT USE THE zeroth item */
11018 menu[i].subitems = NULL;
11019 }
11020
11021 /* add the stop sign. That's what SUMA_BuildMenu uses to figure out the
11022 number of elements */
11023 menu[nel->vec_num].label = NULL;
11024
11025 *N_items = nel->vec_num;
11026
11027 SUMA_RETURN (menu);
11028 }
11029
SUMA_ShowMeTheChildren(Widget w)11030 void SUMA_ShowMeTheChildren(Widget w) {
11031 SUMA_DoForTheChildren(w,0, 0, 0);
11032 }
11033
SUMA_UnmanageTheChildren(Widget w)11034 void SUMA_UnmanageTheChildren(Widget w) {
11035 SUMA_DoForTheChildren(w, -1, 0, 0);
11036 }
SUMA_ManageTheChildren(Widget w)11037 void SUMA_ManageTheChildren(Widget w) {
11038 SUMA_DoForTheChildren(w, 1, 0, 0);
11039 }
11040
11041 /*!
11042 Perform operation on the children of a widget
11043 i = 0: Write out the names of the widgets
11044 1: Manage widgets
11045 -1: Unmanage widgets
11046 */
SUMA_DoForTheChildren(Widget w,int i,int lvl,int rec)11047 void SUMA_DoForTheChildren(Widget w, int i, int lvl, int rec)
11048 {
11049 static char FuncName[]={"SUMA_DoForTheChildren"};
11050 Widget * children = NULL;
11051 int num_children=0, num_children2=0, ic , Nbutt=0, kk=0;
11052 SUMA_Boolean LocalHead = NOPE;
11053
11054 SUMA_ENTRY;
11055
11056 XtVaGetValues( w , XmNchildren , &children ,
11057 XmNnumChildren , &num_children ,
11058 XmNbuttonCount, &Nbutt,
11059 NULL ) ;
11060 for( ic=0 ; ic < num_children ; ic++ ){
11061 if (rec) { /* recursive, but ugly output */
11062 XtVaGetValues( children[ic] , XmNnumChildren , &num_children2, NULL);
11063 if (num_children2) SUMA_DoForTheChildren(children[ic],i, lvl+1, rec);
11064 }
11065 if (LocalHead) {
11066 /* what's the name jane ? */
11067 XtVaGetValues (children[ic], XmNbuttonCount, &Nbutt, NULL);
11068 for (kk=0; kk<lvl; ++kk) fprintf (SUMA_STDERR," ");
11069 fprintf (SUMA_STDERR, "%d.%d: %s (%d N_butts)\n",
11070 lvl, ic, XtName(children[ic]), Nbutt);
11071 }
11072 switch (i) {
11073 case 1:
11074 XtManageChild(children[ic]);
11075 break;
11076 case -1:
11077 XtUnmanageChild(children[ic]);
11078 break;
11079 case 0:
11080 /* what's the name jane ? */
11081 XtVaGetValues (children[ic], XmNbuttonCount, &Nbutt, NULL);
11082 for (kk=0; kk<lvl; ++kk) fprintf (SUMA_STDERR," ");
11083 fprintf (SUMA_STDERR, "%d.%d: %s (%d N_butts)\n",
11084 lvl, ic, XtName(children[ic]), Nbutt);
11085 break;
11086 default:
11087 SUMA_S_Err("Action %d unknown", i);
11088 SUMA_RETURNe;
11089 }
11090 }
11091
11092 if (i==0 || LocalHead) {
11093 for (kk=0; kk<lvl; ++kk) fprintf (SUMA_STDERR," ");
11094 fprintf (SUMA_STDERR,
11095 "%s: Widget '%s' (lvl %d) has (%d) children (%d N_butts):\n",
11096 FuncName, XtName(w), lvl, num_children, Nbutt);
11097 }
11098 SUMA_RETURNe;
11099 }
11100
SUMA_FindChildWidgetNamed(Widget w,char * name)11101 Widget SUMA_FindChildWidgetNamed(Widget w, char *name)
11102 {
11103 static char FuncName[]={"SUMA_FindChildWidgetNamed"};
11104 Widget * children = NULL;
11105 int num_children=0, num_children2=0, ic , Nbutt=0, kk=0;
11106 char *wn;
11107 SUMA_Boolean LocalHead = NOPE;
11108
11109 SUMA_ENTRY;
11110 if (!w || !name) SUMA_RETURN(NULL);
11111 XtVaGetValues( w , XmNchildren , &children ,
11112 XmNnumChildren , &num_children ,
11113 XmNbuttonCount, &Nbutt,
11114 NULL ) ;
11115 for( ic=0 ; ic < num_children ; ic++ ){
11116 if ((wn = XtName(children[ic]))) {
11117 if (!strcmp(wn,name)) SUMA_RETURN(children[ic]);
11118 }
11119 }
11120 SUMA_RETURN(NULL);
11121 }
11122
SUMA_FormSwitchCmapMenuVector(SUMA_COLOR_MAP ** CMv,int N_maps)11123 SUMA_MenuItem *SUMA_FormSwitchCmapMenuVector(SUMA_COLOR_MAP **CMv, int N_maps)
11124 {
11125 static char FuncName[]={"SUMA_FormSwitchCmapMenuVector"};
11126 SUMA_MenuItem *menu = NULL;
11127 int i;
11128 void (*callback)();
11129 NI_element *nel = NULL;
11130 SUMA_Boolean LocalHead = NOPE;
11131
11132 SUMA_ENTRY;
11133
11134 if (!CMv) { SUMA_SL_Err("NULL CMv"); SUMA_RETURN (menu);}
11135 if (N_maps <=0) { SUMA_SL_Err("N_maps <=0"); SUMA_RETURN (menu);}
11136
11137 callback = SUMA_cb_SwitchCmap;
11138
11139 /* Allocate for menu */
11140 menu = (SUMA_MenuItem *)SUMA_calloc((N_maps+1),sizeof(SUMA_MenuItem));
11141
11142 /* fillup menu */
11143 for (i=0; i < N_maps; ++i) {
11144 menu[i].label = SUMA_copy_string(CMv[i]->Name);
11145 menu[i].class = &xmPushButtonWidgetClass;
11146 menu[i].mnemonic = '\0';
11147 menu[i].accelerator = NULL;
11148 menu[i].accel_text = NULL;
11149 menu[i].callback = callback;
11150 menu[i].callback_data = (XtPointer)CMv[i];
11151 /* (used to be i+1)DO NOT USE THE 0 for the first button. 0th index is reserved for the rc widget */
11152 menu[i].subitems = NULL;
11153 }
11154
11155 /* add the stop sign. That's what SUMA_BuildMenu uses to figure out \
11156 the number of elements */
11157 menu[N_maps].label = NULL;
11158
11159 SUMA_RETURN (menu);
11160 }
11161
11162 /* This one here, recalculates the p and q value for a new threshold
11163 and displays the results on the widget
11164 */
SUMA_UpdatePvalueField(SUMA_ALL_DO * ado,float thresh)11165 void SUMA_UpdatePvalueField (SUMA_ALL_DO *ado, float thresh)
11166 {/* set the pvalue */
11167 static char FuncName[]={"SUMA_UpdatePvalueField"};
11168 float p[3], zval = -1.0;
11169 int statcode;
11170 SUMA_X_SurfCont *SurfCont=NULL;
11171 SUMA_OVERLAYS *curColPlane=NULL;
11172 SUMA_Boolean LocalHead = NOPE;
11173
11174 SUMA_ENTRY;
11175
11176 if (!ado) {
11177 SUMA_SL_Err("NULL ado");
11178 SUMA_RETURNe;
11179 }
11180 SurfCont = SUMA_ADO_Cont(ado);
11181 curColPlane = SUMA_ADO_CurColPlane(ado);
11182
11183 if (!SurfCont ||
11184 !SurfCont->thr_sc ||
11185 !curColPlane ||
11186 !curColPlane->dset_link) {
11187 SUMA_SL_Err("NULL SurfCont");
11188 SUMA_RETURNe;
11189 }
11190
11191 /* see if you can get the stat codes */
11192 if (!SUMA_GetDsetColStatAttr(
11193 curColPlane->dset_link,
11194 curColPlane->OptScl->tind,
11195 &statcode,
11196 p, (p+1), (p+2))) {
11197 SUMA_LH("Error");
11198 }else if (statcode) {
11199 SUMA_LHv("Have stats at sb %d\n"
11200 "statcode %d: %f %f %f\n",
11201 curColPlane->OptScl->tind,
11202 statcode, p[0], p[1], p[2]);
11203 curColPlane->OptScl->ThreshStats[0] =
11204 THD_stat_to_pval( thresh , statcode , p ) ;
11205
11206 SUMA_LHv("Have pval of %f\n",
11207 curColPlane->OptScl->ThreshStats[0]);
11208 if( curColPlane->OptScl->ThreshStats[0] >= 0.0 ){
11209 SUMA_LH("zvaling ...\n")
11210 zval = SUMA_fdrcurve_zval(
11211 curColPlane->dset_link,
11212 curColPlane->OptScl->tind,
11213 thresh) ;
11214 if( zval > 0.0f ){
11215 curColPlane->OptScl->ThreshStats[1] =
11216 2.0*qg(zval) ; /* convert z back to FDR q */
11217 }
11218 }
11219 } else {
11220 /* no stats */
11221 curColPlane->OptScl->ThreshStats[0] = -1.0;
11222 curColPlane->OptScl->ThreshStats[1] = -1.0;
11223 }
11224 SUMA_LHv("statcode %d: %f %f %f\n"
11225 "Thresh %f, p %f, q %f\n",
11226 statcode, p[0], p[1], p[2],
11227 thresh,
11228 curColPlane->OptScl->ThreshStats[0],
11229 curColPlane->OptScl->ThreshStats[1]);
11230
11231
11232 { /* form the text, a la afni */
11233 char buf[100]={"Rien"};
11234 float pval = curColPlane->OptScl->ThreshStats[0];
11235 float qval = curColPlane->OptScl->ThreshStats[1];
11236 if( pval < 0.0 ){
11237 strcpy( buf , "p=N/A") ;
11238 } else {
11239 if( pval == 0.0 ){
11240 strcpy( buf , "p=0" ) ;
11241 } else if( pval >= 0.9999 ){
11242 strcpy( buf , "p=1" ) ;
11243 } else if( pval >= 0.0010 ){
11244 char qbuf[16] ;
11245 sprintf( qbuf , "%5.4f" , pval ) ;
11246 strcpy(buf,"p=");
11247 SUMA_strncat(buf,qbuf+1,99);/*qbuf+1 skips leading 0*/
11248 } else {
11249 int dec = (int)(0.999 - log10(pval)) ;
11250 zval = pval * pow( 10.0 , (double) dec ) ; /* between 1 and 10 */
11251 if( dec < 10 ) sprintf( buf , "p=%3.1f-%1d" , zval , dec ) ;
11252 else sprintf( buf , "p=%1d.-%2d" , (int)rint(zval), dec ) ;
11253 }
11254 }
11255 if( qval > 0.0f && qval < 0.9999 ){
11256 char qbuf[16] ;
11257 if( qval >= 0.0010 ) sprintf(qbuf,"%5.4f",qval) ;
11258 else {
11259 int dec = (int)(0.999 - log10(qval)) ;
11260 zval = qval * pow( 10.0 , (double)dec ) ; /* between 1 and 10 */
11261 if( dec < 10 ) sprintf( qbuf, " %3.1f-%1d", zval, dec );
11262 else sprintf( qbuf, " %1d.-%2d" , (int)rint(zval), dec );
11263 }
11264 strcat(buf,"\nq=") ; SUMA_strncat(buf,qbuf+1,99) ;
11265 } else {
11266 SUMA_strncat(buf,"\nq=N/A",99) ;
11267 }
11268
11269 MCW_set_widget_label( SurfCont->thrstat_lb, buf );
11270 }
11271
11272 SUMA_RETURNe;
11273 }
11274
11275
SUMA_SetScaleRange(SUMA_ALL_DO * ado,double range[2])11276 void SUMA_SetScaleRange(SUMA_ALL_DO *ado, double range[2])
11277 {
11278 static char FuncName[]={"SUMA_SetScaleRange"};
11279 int min_v, max_v, scl, dec, cv=0;
11280 Widget w ;
11281 double dtmp, rmult;
11282 char slabel[100];
11283 static int nwarn = 0;
11284 SUMA_X_SurfCont *SurfCont=NULL;
11285 SUMA_OVERLAYS *curColPlane=NULL;
11286 SUMA_Boolean LocalHead = NOPE;
11287
11288 SUMA_ENTRY;
11289
11290 if (!ado) {
11291 SUMA_SL_Err("NULL ado");
11292 SUMA_RETURNe;
11293 }
11294 SurfCont = SUMA_ADO_Cont(ado);
11295 curColPlane = SUMA_ADO_CurColPlane(ado);
11296
11297 rmult = (double)SUMA_floatEnv("SUMA_Range_Multiplier", 0.0) ;
11298 if (rmult > 0.0f && rmult != 1.0f) {
11299 SUMA_LHv("Applying range multipler of %f\n", rmult);
11300 range[0] = range[0]*rmult;
11301 range[1] = range[1]*rmult;
11302 }
11303
11304 if (!SurfCont->thr_sc) {
11305 SUMA_SL_Err("NULL widget");
11306 SUMA_RETURNe;
11307 }
11308
11309 w = SurfCont->thr_sc;
11310
11311 if (range[1] <= range[0]) range[1] = range[0] + 1;
11312
11313 if (curColPlane->OptScl->ThrMode == SUMA_ABS_LESS_THAN) {
11314 SUMA_LH("Absolutizing Threshold Range");
11315 if (fabs((double)range[0]) > fabs((double)range[1])) {
11316 range[1] = fabs((double)range[0]); range[0] = 0.0;
11317 } else {
11318 range[1] = fabs((double)range[1]); range[0] = 0.0;
11319 }
11320 } else if (curColPlane->OptScl->ThrMode == SUMA_LESS_THAN) {
11321
11322 } else {
11323 SUMA_S_Err("Not ready for ThrModeR == %d", curColPlane->OptScl->ThrMode);
11324 }
11325 if (range[1] - range[0] > pow(10.0,SUMAg_CF->SUMA_ThrScalePowerBias)) {
11326 /* no need for power */
11327 dec = 0;
11328 if (range[0] > MRI_maxint) min_v=MRI_maxint;
11329 else if (range[0] < -MRI_maxint) min_v=-MRI_maxint;
11330 else min_v = (int)(range[0] );
11331 if (range[1] > MRI_maxint) max_v=MRI_maxint;
11332 else if (range[1] < -MRI_maxint) max_v=-MRI_maxint;
11333 else max_v = (int)(range[1] );
11334 dtmp = 2.0*(max_v-min_v)/MRI_maxint;
11335 if (dtmp >= 0.499) {
11336 /* See comment for similar block below */
11337 if (!nwarn)
11338 SUMA_S_Warn( "Data range too big for threshold scale.\n"
11339 "Range will be trimmed.\n"
11340 "Similar messages will be muted");
11341 ++nwarn;
11342 /* Range cannot be too big.
11343 X11 Warning 1:
11344 Name: Thr.
11345 Class: XmScale
11346 (Maximum - minimum) cannot be greater than INT_MAX / 2;
11347 minimum has been set to zero,
11348 maximum may have been set to (INT_MAX/2).
11349 */
11350 max_v /= (dtmp+0.01);
11351 min_v /= (dtmp+0.01);
11352 }
11353 scl = (max_v -min_v) / 10;
11354 } else {
11355 /* what power of 10 is needed (based on Bob's settings in afni_wid.c)? */
11356 dec = (int)ceil( log((double)(range[1] - range[0] + 0.001)) / log (10) );
11357 /* Add the scale bias, so that dec is at least = bias*/
11358 if (dec < SUMAg_CF->SUMA_ThrScalePowerBias)
11359 dec = SUMAg_CF->SUMA_ThrScalePowerBias;
11360 dtmp = (range[0] * pow(10.0, dec));
11361 if (dtmp > MRI_maxint) min_v=MRI_maxint;
11362 else if (dtmp < -MRI_maxint) min_v=-MRI_maxint;
11363 else min_v = (int)(dtmp);
11364 dtmp = range[1] * pow(10.0, dec);
11365 if (dtmp > MRI_maxint) max_v=MRI_maxint;
11366 else if (dtmp < -MRI_maxint) max_v=-MRI_maxint;
11367 else max_v = (int)(dtmp + 0.001);
11368 dtmp = 2.0*(max_v-min_v)/MRI_maxint;
11369 if (dtmp >= 0.499) {
11370 /* Perhaps I should include a scale value multiplier = 1/dtmp
11371 so that users can still get the full range.
11372 Problem is that users will not see the proper value
11373 on the silder bar, unless I start setting it explicitly
11374 in the widget. Best to wait and see who'd need it. */
11375 if (!nwarn)
11376 SUMA_S_Warn( "Data range too big for threshold scale.\n"
11377 "Range will be trimmed\n"
11378 "Similar messages will be muted");
11379 ++nwarn;
11380 /* Range cannot be too big.
11381 X11 Warning 1:
11382 Name: Thr.
11383 Class: XmScale
11384 (Maximum - minimum) cannot be greater than INT_MAX / 2;
11385 minimum has been set to zero,
11386 maximum may have been set to (INT_MAX/2).
11387 */
11388 max_v /= (dtmp+0.01);
11389 min_v /= (dtmp+0.01);
11390 }
11391
11392 scl = (max_v -min_v) / 10;
11393 }
11394
11395 if (max_v <= min_v || scl < 0) {
11396 /* happens when max_v is so large that you get trash when typecast to int.
11397 That's the case when you're using the number of nodes in a surface
11398 for example and you set dec to something demented like 6 !
11399 Need a clever function here */
11400 SUMA_SLP_Note("Bad auto scaling \nparameters for threshold bar.\n"
11401 "Using defaults");
11402 min_v = (int)(range[0]);
11403 max_v = (int)(range[1])+1;
11404 scl = (max_v - min_v) / 10;
11405 dec = 1;
11406 }
11407
11408 #if 0
11409 /* make sure the current value is not less than the min or greater
11410 than the max */
11411 XtVaGetValues(w, XmNvalue, &cv, NULL);
11412 #else
11413 /* what was the slider's previous value in this dset ?*/
11414 dtmp = curColPlane->OptScl->ThreshRange[0] * pow(10.0, dec);
11415 if (dtmp > 0) cv = (int) (dtmp+0.5);
11416 else cv = (int) (dtmp-0.5);
11417 #endif
11418
11419 if (LocalHead)
11420 fprintf (SUMA_STDERR,
11421 "%s:\n"
11422 " min %d max %d scalemult %d decimals %d\n"
11423 "Current scale value %d\n",
11424 FuncName, min_v, max_v, scl, dec, cv);
11425 if (cv < min_v) {
11426 cv = min_v;
11427 /* must update threshold value in options structure*/
11428 curColPlane->OptScl->ThreshRange[0] =
11429 (float)cv / pow(10.0, dec);
11430 } else if (cv > max_v) {
11431 cv = max_v;
11432 curColPlane->OptScl->ThreshRange[0] =
11433 (float)cv / pow(10.0, dec);
11434 }
11435 /* set the slider bar */
11436 XtVaSetValues(w,
11437 XmNmaximum, max_v,
11438 XmNminimum, min_v,
11439 XmNvalue, cv,
11440 XmNscaleMultiple, scl,
11441 XmNdecimalPoints , dec,
11442 XmNuserData, (XTP_CAST)dec,
11443 NULL);
11444
11445 /* set the label on top */
11446 if (curColPlane->OptScl->ThrMode != SUMA_ABS_LESS_THAN) {
11447 sprintf(slabel, "%5s", MV_format_fval((float)cv / pow(10.0, dec)));
11448 } else if (curColPlane->OptScl->ThrMode != SUMA_LESS_THAN){
11449 /* used to use this:
11450 sprintf(slabel, "|%5s|", ....
11451 but that does not work in the editable field ... */
11452 sprintf(slabel, "%5s", MV_format_fval((float)cv / pow(10.0, dec)));
11453 } else {
11454 SUMA_S_Err("Not ready to handle ThrModeR of %d yet",
11455 curColPlane->OptScl->ThrMode);
11456 }
11457 /* SUMA_SET_LABEL(SurfCont->thr_lb, slabel);*/
11458 SUMA_INSERT_CELL_STRING(SurfCont->SetThrScaleTable, 0,0,slabel);
11459
11460 SUMA_UpdatePvalueField (ado,
11461 curColPlane->OptScl->ThreshRange[0]);
11462
11463 SUMA_RETURNe;
11464 }
11465
11466
11467 /*!
11468 \brief A function to update the field showing
11469 Xhair coordinates.
11470 Xhair is a property of the viewer rather than
11471 the surface but it makes more sense to display
11472 the coordinates, in certain cases, in the
11473 surface controllers
11474 */
SUMA_UpdateXhairField(SUMA_SurfaceViewer * sv)11475 SUMA_Boolean SUMA_UpdateXhairField(SUMA_SurfaceViewer *sv)
11476 {
11477 static char FuncName[]={"SUMA_UpdateXhairField"};
11478 int i=0, N_SOlist=0, SOlist[SUMA_MAX_DISPLAYABLE_OBJECTS];
11479 SUMA_DO *dov = SUMAg_DOv;
11480 SUMA_ALL_DO *ado=NULL, *curDO=NULL;
11481 SUMA_X_SurfCont *SurfCont=NULL;
11482 SUMA_OVERLAYS *curColPlane=NULL;
11483 char str[100]={""};
11484 SUMA_Boolean LocalHead = NOPE;
11485
11486 SUMA_ENTRY;
11487
11488 if (!sv) SUMA_RETURN(NOPE);
11489
11490 /* Which abjects are visible in this SV ? */
11491 N_SOlist = SUMA_Selectable_ADOs(sv, dov, SOlist);
11492 for (i=0; i<N_SOlist; ++i) {
11493 SUMA_LHv("working %d/%d shown surfaces/DOs ...\n", i, N_SOlist);
11494 ado = (SUMA_ALL_DO *)dov[SOlist[i]].OP;
11495 SurfCont = SUMA_ADO_Cont(ado);
11496 curColPlane = SUMA_ADO_CurColPlane(ado);
11497 if (ado->do_type == MASK_type) {/* No cross hair tricks */
11498 SUMA_RETURN(YUP);
11499 }
11500 if (SurfCont) { /* does this surface have surface controller ? */
11501 /* is this controller, displaying information for that surface ? */
11502 SUMA_LHv("Working controller for %s\n", SUMA_ADO_Label(ado));
11503 if (!(curDO = SUMA_SurfCont_GetcurDOp(SurfCont))) {
11504 SUMA_LH("No curDOp"); /* that's OK, happens when controller not
11505 yet created for this DO */
11506 continue;
11507 }
11508 if (curDO == ado) {
11509 /* OK, show the coordinate */
11510 SUMA_LHv("Setting cross hair at %f %f %f\n",
11511 sv->Ch->c[0],sv->Ch->c[1],sv->Ch->c[2]);
11512 SUMA_XHAIR_STRING(sv->Ch->c, str);
11513 SUMA_LH("%s",str);
11514 XtVaSetValues(SurfCont->XhairTable->cells[1],
11515 XmNvalue, str, NULL);
11516 SUMA_UpdateCrossHairNodeLabelField(sv);
11517 }
11518 }
11519
11520 }
11521
11522 SUMA_RETURN(YUP);
11523
11524 }
11525
SUMA_UpdateNodeField(SUMA_ALL_DO * ado)11526 SUMA_Boolean SUMA_UpdateNodeField(SUMA_ALL_DO *ado)
11527 {
11528 static char FuncName[]={"SUMA_UpdateNodeField"};
11529 int i=0;
11530 SUMA_OVERLAYS *Sover=NULL, *targetSover=NULL;
11531 NI_group *ngr=NULL;
11532 DListElmt *el=NULL;
11533 SUMA_CALLBACK *cb=NULL;
11534 char *targetSO_idcode=NULL, *targetSover_name=NULL, *lbls=NULL;
11535 SUMA_X_SurfCont *SurfCont=NULL;
11536 SUMA_Boolean LocalHead = NOPE;
11537
11538 SUMA_ENTRY;
11539
11540 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) SUMA_RETURN(NOPE);
11541 SUMA_LHv("Entry, SurfCont=%p, ado %p\n",
11542 ado, SurfCont);
11543 if (LocalHead) SUMA_DUMP_TRACE("Who Called Me?");
11544 if (!SUMA_isSurfContWidgetCreated(SurfCont)) {
11545 /* No controller created yet, return quietly */
11546 SUMA_RETURN(YUP);
11547 }
11548 Sover = SUMA_ADO_CurColPlane(ado);
11549 SUMA_LHv("Sover %p, ado type %d %s, callbacks %p, HoldClickCallbacks %d\n",
11550 Sover, ado->do_type, SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type),
11551 SUMAg_CF->callbacks, SUMAg_CF->HoldClickCallbacks);
11552 switch (ado->do_type) {
11553 case SO_type: {
11554 SUMA_SurfaceObject *curSO=NULL, *targetSO=NULL, *SO=NULL;
11555 SO = (SUMA_SurfaceObject *)ado;
11556 if (!(curSO =(SUMA_SurfaceObject *)SUMA_SurfCont_GetcurDOp(SurfCont))) {
11557 SUMA_S_Err("Failed to get curDOp");
11558 SUMA_RETURN(NOPE);
11559 }
11560
11561 /* Do we have click callbacks pending? */
11562 if (SUMAg_CF->callbacks && !SUMAg_CF->HoldClickCallbacks) {
11563 el = dlist_head(SUMAg_CF->callbacks);
11564 while (el) {
11565 cb = (SUMA_CALLBACK *)el->data;
11566 if ( cb->event == SUMA_NEW_NODE_ACTIVATE_EVENT &&
11567 cb->active > 0 &&
11568 cb->pending) {
11569 SUMA_LHv("Calling active pending click callback %s\n",
11570 cb->FunctionName);
11571 if (!SUMA_ExecuteCallback(cb, 1, ado, 0)) {
11572 SUMA_S_Err("Failed to execute callback");
11573 break;
11574 }
11575 } else {
11576 if (cb->active == -1) {
11577 SUMA_LH("Callback inactive");
11578 }
11579 }
11580 el = dlist_next(el);
11581 }
11582 }
11583
11584 if (SUMA_isRelated_SO(SO, curSO, 1)) {
11585 SUMA_LH( "Updating GUI Node Fields, "
11586 "whereami is handled in SUMA_UpdateNodeLblField");
11587 SUMA_UPDATE_ALL_NODE_GUI_FIELDS(ado);
11588 } else {
11589 SUMA_LH("No GUI Node Field Updates, but may use a whereami update");
11590 if (SUMAg_CF->X->Whereami_TextShell) {
11591 lbls = SUMA_GetLabelsAtSelection(ado, SO->SelectedNode, -1);
11592 if (lbls) SUMA_free(lbls); lbls = NULL;
11593 }
11594 }
11595
11596 if ( !SO->SurfCont->ShowCurForeOnly ||
11597 SO->SurfCont->GraphHidden) { /* graph updating can be done
11598 for all planes */
11599 for (i=0; i<SO->N_Overlays; ++i) {
11600 Sover = SO->Overlays[i];
11601 if ( Sover
11602 && Sover->dset_link
11603 && Sover->rowgraph_mtd ) {
11604 SUMA_OverlayGraphAtNode(Sover,
11605 (SUMA_ALL_DO *)SO,
11606 SO->SelectedNode);
11607 }
11608 }
11609 } else {
11610 Sover = SO->SurfCont->curColPlane;
11611 if ( Sover
11612 && Sover->dset_link
11613 && Sover->rowgraph_mtd ) {
11614 SUMA_OverlayGraphAtNode(Sover,
11615 (SUMA_ALL_DO *)SO,
11616 SO->SelectedNode);
11617 }
11618 }
11619 break; }
11620 case GDSET_type: {
11621 SUMA_S_Err("Should not call with this type DO because without\n"
11622 "a variant it cannot be displayed");
11623 SUMA_RETURN(NOPE);
11624 break; }
11625 case CDOM_type:
11626 case VO_type:
11627 case TRACT_type:
11628 case GRAPH_LINK_type:
11629 {
11630 SUMA_ALL_DO *curado=NULL;
11631 if (LocalHead && ado->do_type == GRAPH_LINK_type) {
11632 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
11633 SUMA_DSET *dset=NULL;
11634 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
11635 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
11636 SUMA_ADO_Label(ado));
11637 SUMA_RETURN(NOPE);
11638 }
11639 }
11640
11641 if (!(curado = SUMA_SurfCont_GetcurDOp(SurfCont))) {
11642 SUMA_S_Err("Failed to get curDOp");
11643 break;
11644 }
11645 SUMA_LHv("Working %s, curado %s on label %s\n",
11646 ADO_TNAME(ado), ADO_TNAME(curado), ADO_LABEL(ado));
11647
11648 /* Do we have click callbacks pending? */
11649 if (SUMAg_CF->callbacks && !SUMAg_CF->HoldClickCallbacks) {
11650 el = dlist_head(SUMAg_CF->callbacks);
11651 while (el) {
11652 cb = (SUMA_CALLBACK *)el->data;
11653 if ( cb->event == SUMA_NEW_NODE_ACTIVATE_EVENT &&
11654 cb->active > 0 &&
11655 cb->pending) {
11656 SUMA_S_Warnv("Click callback %s disabled on graphs\n",
11657 cb->FunctionName);
11658 #if 0 /* will need to deal with this when the need arises */
11659 if (!SUMA_ExecuteCallback(cb, 1, ado, 0)) {
11660 SUMA_S_Err("Failed to execute callback");
11661 break;
11662 }
11663 #endif
11664 } else {
11665 if (cb->active == -1) {
11666 SUMA_LH("Callback inactive");
11667 }
11668 }
11669 el = dlist_next(el);
11670 }
11671 }
11672
11673 if (SUMA_isRelated(ado, curado, 1)) {
11674 SUMA_LH( "Updating GUI Node Fields, "
11675 "whereami is handled in SUMA_UpdateNodeLblField");
11676 SUMA_UPDATE_ALL_NODE_GUI_FIELDS(ado);
11677 } else {
11678 SUMA_LH("No GUI Node Field Updates, but may use a whereami update");
11679 if (SUMAg_CF->X->Whereami_TextShell) {
11680 lbls = SUMA_GetLabelsAtSelection(ado,
11681 SUMA_ADO_SelectedDatum(ado, NULL, NULL),
11682 SUMA_ADO_SelectedSecondary(ado));
11683 if (lbls) SUMA_free(lbls); lbls = NULL;
11684 }
11685 }
11686
11687 SUMA_LH("On to graphing");
11688 if ( !SurfCont->ShowCurForeOnly ||
11689 SurfCont->GraphHidden) { /* graph updating can be done
11690 for all planes */
11691 for (i=0; i<SUMA_ADO_N_Overlays(ado); ++i) {
11692 Sover = SUMA_ADO_Overlay(ado,i);
11693 if ( Sover
11694 && Sover->dset_link
11695 && Sover->rowgraph_mtd ) {
11696 SUMA_OverlayGraphAtNode(Sover,
11697 ado,
11698 SUMA_ADO_SelectedDatum(ado, NULL, NULL));
11699 }
11700 }
11701 } else {
11702 Sover = SurfCont->curColPlane;
11703 if ( Sover
11704 && Sover->dset_link
11705 && Sover->rowgraph_mtd ) {
11706 SUMA_OverlayGraphAtNode(Sover,
11707 ado,
11708 SUMA_ADO_SelectedDatum(ado, NULL, NULL));
11709 }
11710 }
11711 SUMA_RETURN(YUP);
11712 break; }
11713 case MASK_type:
11714 SUMA_S_Warn("Anything to be done here for masks?");
11715 SUMA_RETURN(YUP);
11716 default:
11717 SUMA_S_Errv("Nothing to do with %s\n",
11718 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
11719 SUMA_RETURN(NOPE);
11720 }
11721 SUMA_RETURN(YUP);
11722
11723 }
11724
SUMA_UpdatePointField(SUMA_ALL_DO * ado)11725 SUMA_Boolean SUMA_UpdatePointField(SUMA_ALL_DO*ado)
11726 {
11727 static char FuncName[]={"SUMA_UpdatePointField"};
11728 int i=0;
11729 SUMA_OVERLAYS *Sover=NULL;
11730 char str[100];
11731 float *fv=NULL;
11732 SUMA_X_SurfCont *SurfCont=NULL;
11733 SUMA_Boolean LocalHead = NOPE;
11734
11735 SUMA_ENTRY;
11736
11737 if (!ado || !(SurfCont = SUMA_ADO_Cont(ado))) SUMA_RETURN(NOPE);
11738 SUMA_LHv("Entry, SurfCont=%p, ado %p\n",
11739 ado, SurfCont);
11740 if (!SUMA_isSurfContWidgetCreated(SurfCont)) {
11741 /* No controller created yet, return quietly */
11742 SUMA_RETURN(YUP);
11743 }
11744 Sover = SUMA_ADO_CurColPlane(ado);
11745 SUMA_LHv("Sover %p, ado type %d %s\n",
11746 Sover, ado->do_type, SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
11747 switch (ado->do_type) {
11748 case SO_type: {
11749 SUMA_S_Err("Not for SOs this!");
11750 break; }
11751
11752 case GDSET_type: {
11753 SUMA_S_Err("Should not call with this type DO because without\n"
11754 "a variant it cannot be displayed");
11755 SUMA_RETURN(NOPE);
11756 break; }
11757 case GRAPH_LINK_type:
11758 {
11759 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
11760 SUMA_DSET *dset=NULL;
11761 SUMA_GRAPH_SAUX *GSaux=NULL;
11762 SUMA_ALL_DO *curado=NULL;
11763 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
11764 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
11765 SUMA_ADO_Label(ado));
11766 SUMA_RETURN(NOPE);
11767 }
11768 if (!(curado = SUMA_SurfCont_GetcurDOp(SurfCont))) {
11769 SUMA_S_Err("Failed to get curDOp");
11770 break;
11771 }
11772 GSaux = SDSET_GSAUX(dset);
11773 SUMA_LHv("Working %s (%s), curado %s (%s) on dset %s\n",
11774 ADO_TNAME(ado), SUMA_ADO_Label(ado),
11775 ADO_TNAME(curado), SUMA_ADO_Label(curado),
11776 SDSET_LABEL(dset));
11777
11778 if (!SurfCont->FaceTable||
11779 !SurfCont->FaceTable->num_value) { /* table widgets not set yet ?*/
11780 SUMA_RETURN(NOPE);
11781 }
11782
11783 if (SUMA_isRelated(ado, curado, 1)) {
11784 SUMA_LH( "Updating GUI Point Fields, ");
11785 if (curado == ado) {
11786 if (GSaux->PR->iAltSel[SUMA_ENODE_0] >= 0) {
11787 sprintf(str, "%ld", GSaux->PR->iAltSel[SUMA_ENODE_0]);
11788 SurfCont->FaceTable->num_value[1] =
11789 GSaux->PR->iAltSel[SUMA_ENODE_0];
11790 XtVaSetValues(SurfCont->FaceTable->cells[1],
11791 XmNvalue, str, NULL);
11792 fv = SUMA_GDSET_NodeXYZ(dset, GSaux->PR->iAltSel[SUMA_ENODE_0],
11793 SUMA_ADO_variant(ado),NULL);
11794 sprintf(str, "%f, %f, %f", fv[0], fv[1], fv[2]);
11795
11796 XtVaSetValues(SurfCont->FaceTable->cells[2],
11797 XmNvalue, str, NULL);
11798 } else {
11799 XtVaSetValues(SurfCont->FaceTable->cells[1],
11800 XmNvalue, "-1", NULL);
11801 SurfCont->FaceTable->num_value[1] = -1;
11802 XtVaSetValues(SurfCont->FaceTable->cells[2],
11803 XmNvalue, "x, x, x", NULL);
11804 }
11805 }
11806 }
11807
11808 SUMA_RETURN(YUP);
11809 break; }
11810
11811 default:
11812 SUMA_S_Errv("Nothing to do with %s\n",
11813 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
11814 SUMA_RETURN(NOPE);
11815 }
11816 SUMA_RETURN(YUP);
11817 }
11818
SUMA_UpdateNodeNodeField(SUMA_ALL_DO * ado)11819 SUMA_Boolean SUMA_UpdateNodeNodeField(SUMA_ALL_DO *ado)
11820 {
11821 static char FuncName[]={"SUMA_UpdateNodeNodeField"};
11822 char str[101];
11823 SUMA_X_SurfCont *SurfCont=NULL;
11824 int SelectedNode, ivsel[SUMA_N_IALTSEL_TYPES];
11825 float *fv;
11826 SUMA_Boolean LocalHead = NOPE;
11827
11828 SUMA_ENTRY;
11829
11830 if (!ado) {
11831 SUMA_SL_Err("NULL ado");
11832 SUMA_RETURN(NOPE);
11833 }
11834 SurfCont = SUMA_ADO_Cont(ado);
11835 SelectedNode = SUMA_ADO_SelectedDatum(ado, NULL, NULL);
11836 SUMA_LH("Working %d on %s\n", SelectedNode, ADO_LABEL(ado));
11837 if (!SurfCont || !SurfCont->NodeTable) SUMA_RETURN(NOPE);
11838 if (SelectedNode < 0 || SelectedNode > SUMA_ADO_Max_Datum_Index(ado))
11839 SUMA_RETURN(NOPE);
11840 if (!SurfCont->NodeTable->num_value) { /* Table widgets not created yet? */
11841 SUMA_RETURN(NOPE);
11842 }
11843 sprintf(str, "%d", SelectedNode);
11844 SurfCont->NodeTable->num_value[1] = SelectedNode;
11845 XtVaSetValues(SurfCont->NodeTable->cells[1], XmNvalue, str, NULL);
11846 switch (ado->do_type) {
11847 case SO_type:
11848 fv = SUMA_ADO_DatumXYZ(ado,SelectedNode, NULL);
11849 sprintf(str, "%s, ",
11850 MV_format_fval2(fv[0], 7));
11851 SUMA_strncat(str, MV_format_fval2(fv[1], 7), 100);
11852 SUMA_strncat(str, ", ", 100);
11853 SUMA_strncat(str, MV_format_fval2(fv[2], 7), 100 );
11854 XtVaSetValues(SurfCont->NodeTable->cells[2], XmNvalue, str, NULL);
11855 break;
11856 case GRAPH_LINK_type: {
11857 int i0, i1;
11858 SUMA_DSET *dset=SUMA_find_GLDO_Dset((SUMA_GraphLinkDO*)ado);
11859 SUMA_GRAPH_SAUX *GSaux=SDSET_GSAUX(dset);
11860 if (SUMA_GDSET_SegIndexToPoints(dset, SelectedNode,
11861 &i0, &i1, NULL)) {
11862 sprintf(str, "%d, %d", i0, i1);
11863 } else {
11864 sprintf(str, "-,-");
11865 }
11866 XtVaSetValues(SurfCont->NodeTable->cells[2], XmNvalue, str, NULL);
11867 break; }
11868 case TRACT_type: {
11869 if (!SurfCont->FaceTable) SUMA_RETURN(NOPE);
11870 SUMA_ADO_SelectedDatum(ado, (void *)ivsel, NULL);
11871 sprintf(str, "%d, %d, %d",
11872 ivsel[SUMA_NET_BUN], ivsel[SUMA_BUN_TRC], ivsel[SUMA_TRC_PNT]);
11873 XtVaSetValues(SurfCont->FaceTable->cells[1], XmNvalue, str, NULL);
11874 break; }
11875 case MASK_type: {
11876 SUMA_S_Warn("Anything for this?");
11877 break; }
11878 case VO_type: {
11879 if (!SurfCont->FaceTable) SUMA_RETURN(NOPE);
11880 SUMA_ADO_SelectedDatum(ado, (void *)ivsel, NULL);
11881 sprintf(str, "%d, %d, %d",
11882 ivsel[SUMA_VOL_I], ivsel[SUMA_VOL_J], ivsel[SUMA_VOL_K]);
11883 XtVaSetValues(SurfCont->FaceTable->cells[1], XmNvalue, str, NULL);
11884 break; }
11885 default:
11886 SUMA_S_Errv("No love for %s\n", ADO_TNAME(ado));
11887 break;
11888 }
11889
11890 SUMA_RETURN(YUP);
11891 }
11892
11893 /* A lazy wrapper for SUMA_FormNodeValFieldStrings to return
11894 values but not the strings.
11895 This function is not very efficient, since all the strings
11896 are formed and then discarded.
11897 */
SUMA_GetNodeValsAtSelection(SUMA_ALL_DO * ado,SUMA_DSET * dset,int Node,int find,int tind,int bind,double * I,double * T,double * B)11898 SUMA_Boolean SUMA_GetNodeValsAtSelection(SUMA_ALL_DO *ado,
11899 SUMA_DSET *dset, int Node,
11900 int find, int tind, int bind,
11901 double *I, double *T, double *B)
11902 {
11903 static char FuncName[] = {"SUMA_GetNodeValsAtSelection"};
11904 char **sar=NULL;
11905 int i;
11906
11907 SUMA_ENTRY;
11908
11909 sar = SUMA_FormNodeValFieldStrings(ado, dset, Node, find, tind, bind,
11910 1, I, T, B);
11911 if (!sar) SUMA_RETURN(NOPE);
11912 for (i=0; i<3; ++i) SUMA_ifree(sar[i]);
11913 SUMA_ifree(sar);
11914
11915 SUMA_RETURN(YUP);
11916 }
11917
SUMA_FormNodeValFieldStrings(SUMA_ALL_DO * ado,SUMA_DSET * dset,int Node,int find,int tind,int bind,int dec,double * I,double * T,double * B)11918 char **SUMA_FormNodeValFieldStrings(SUMA_ALL_DO *ado,
11919 SUMA_DSET *dset, int Node,
11920 int find, int tind, int bind,
11921 int dec, double *I, double *T, double *B)
11922 {
11923 static char FuncName[]={"SUMA_FormNodeValFieldStrings"};
11924 char **sar=NULL;
11925 double dval;
11926 int Found = -1;
11927 SUMA_DATUM_LEVEL lev = 0;
11928 int Max_Node_Index = -1;
11929 SUMA_Boolean LocalHead = NOPE;
11930
11931 SUMA_ENTRY;
11932
11933 if (!ado || !dset) SUMA_RETURN(sar);
11934 if (I) *I=-1.0;
11935 if (T) *T=-1.0;
11936 if (B) *B=-1.0;
11937 Max_Node_Index = SUMA_ADO_Max_Datum_Index(ado);
11938
11939 /* What datum level do we have here ? */
11940 switch ((lev = SUMA_sdset_datum_level(dset))) {
11941 case SUMA_ELEM_DAT:
11942 SUMA_LH("Datum %d is expected to refer to an elementary datum level",
11943 Node);
11944 break;
11945 case SUMA_LEV1_DAT:
11946 SUMA_LH("Datum %d is expected to refer to a level1 datum", Node);
11947 break;
11948 case SUMA_LEV2_DAT:
11949 SUMA_LH("Datum %d is expected to refer to a level2 datum", Node);
11950 break;
11951 default:
11952 SUMA_S_Err("You're not on the level %d", lev);
11953 break;
11954 }
11955
11956 /* 1- Where is this node in the data set ? */
11957 if (Node > -1) {
11958 Found = SUMA_GetNodeRow_FromNodeIndex_s( dset, Node, Max_Node_Index );
11959 } else {
11960 Found = -1;
11961 }
11962 if (LocalHead) {
11963 fprintf( SUMA_STDERR,
11964 "%s: Node index %d is at row %d in dset %p "
11965 "(label %s, filename %s).\n",
11966 FuncName, Node, Found,
11967 dset,
11968 SDSET_LABEL(dset),
11969 SDSET_FILENAME(dset));
11970 }
11971
11972 if (Found >= 0) {
11973 sar = (char **)SUMA_calloc(3, sizeof(char *));
11974 /* 2- What is the value of the intensity */
11975 if ((sar[0] = SUMA_GetDsetValInCol(dset, find, Found, &dval))) {
11976 if (dec > 0) {
11977 SUMA_free(sar[0]);
11978 sar[0] = SUMA_copy_string(MV_format_fval2(dval, dec));
11979 }
11980 SUMA_LHv("str_int=%s, dval = %f\n",sar[0], dval);
11981 if (I) *I = dval;
11982 } else {
11983 sar[0] = SUMA_copy_string("X");
11984 SUMA_SL_Err("Failed to get str_int");
11985 }
11986 if ((sar[1] = SUMA_GetDsetValInCol(dset, tind, Found, &dval))) {
11987 if (dec > 0) {
11988 SUMA_free(sar[1]);
11989 sar[1] = SUMA_copy_string(MV_format_fval2(dval, dec));
11990 }
11991 SUMA_LHv("str_thr=%s, dval = %f\n",sar[1], dval);
11992 if (T) *T = dval;
11993 } else {
11994 sar[1] = SUMA_copy_string("X");
11995 SUMA_SL_Err("Failed to get str_thr");
11996 }
11997 if ((sar[2] = SUMA_GetDsetValInCol(dset, bind, Found, &dval))) {
11998 if (dec > 0) {
11999 SUMA_free(sar[2]);
12000 sar[2] = SUMA_copy_string(MV_format_fval2(dval, dec));
12001 }
12002 SUMA_LHv("str_brt=%s, dval = %f\n",sar[2], dval);
12003 if (B) *B = dval;
12004 } else {
12005 SUMA_SL_Err("Failed to get str_brt");
12006 sar[2] = SUMA_copy_string("X");
12007 }
12008 }
12009
12010 SUMA_RETURN(sar);
12011 }
12012
12013 /*!
12014 Like SUMA_ADO_SelectedDatum, except that
12015 if the overlay plane is for a non-elementary
12016 datum, the datum selection is adjusted properly
12017 Set Sover to NULL if you want to use
12018 the current overlay
12019 */
SUMA_ADO_ColPlane_SelectedDatum(SUMA_ALL_DO * ado,SUMA_OVERLAYS * Sover)12020 int SUMA_ADO_ColPlane_SelectedDatum(SUMA_ALL_DO *ado, SUMA_OVERLAYS *Sover)
12021 {
12022 static char FuncName[]={"SUMA_ADO_ColPlane_SelectedDatum"};
12023 int SelectedNode = -1, ivsel[SUMA_N_IALTSEL_TYPES];
12024 SUMA_Boolean LocalHead = NOPE;
12025
12026 SUMA_ENTRY;
12027
12028 if (!ado) {
12029 SUMA_LH("Null ado");
12030 SUMA_RETURN(-1);
12031 }
12032
12033 if (!Sover) Sover = SUMA_ADO_CurColPlane(ado);
12034 if (!Sover) {
12035 SUMA_LH("Null Sover and no current overlay plane");
12036 SUMA_RETURN(-1);
12037 }
12038
12039 SelectedNode = SUMA_ADO_SelectedDatum(ado, (void *)ivsel, NULL);
12040 SUMA_LH("Selection: %d -- %d %d %d %d",
12041 SelectedNode, ivsel[0], ivsel[1], ivsel[2], ivsel[3]);
12042 if (Sover->dtlvl != SUMA_ELEM_DAT) {
12043 switch (ado->do_type) {
12044 case TRACT_type:
12045 if (Sover->dtlvl == SUMA_LEV1_DAT)
12046 SelectedNode = ivsel[SUMA_NET_TRC];
12047 else if (Sover->dtlvl == SUMA_LEV2_DAT)
12048 SelectedNode = ivsel[SUMA_NET_BUN];
12049 break;
12050 default:
12051 SUMA_S_Err("Not ready for non-elementary datum for type %s\n",
12052 ADO_TNAME(ado));
12053 break;
12054 }
12055 }
12056
12057 SUMA_RETURN(SelectedNode);
12058 }
12059
SUMA_UpdateNodeValField(SUMA_ALL_DO * ado)12060 SUMA_Boolean SUMA_UpdateNodeValField(SUMA_ALL_DO *ado)
12061 {
12062 static char FuncName[]={"SUMA_UpdateNodeValField"};
12063 char **sar=NULL;
12064 double I, T, B;
12065 SUMA_OVERLAYS *Sover=NULL;
12066 SUMA_X_SurfCont *SurfCont=NULL;
12067 int SelectedNode = -1;
12068 SUMA_Boolean LocalHead = NOPE;
12069
12070 SUMA_ENTRY;
12071
12072 if (!ado) {
12073 SUMA_LH("Null ado");
12074 SUMA_RETURN(NOPE);
12075 }
12076
12077 Sover = SUMA_ADO_CurColPlane(ado);
12078 if (!Sover) {
12079 SUMA_LH("Null Sover");
12080 SUMA_RETURN(NOPE);
12081 }
12082 SurfCont = SUMA_ADO_Cont(ado);
12083 if (!SurfCont || !SurfCont->DataTable ||
12084 !SurfCont->DataTable->cells) SUMA_RETURN(NOPE);
12085
12086 SelectedNode = SUMA_ADO_ColPlane_SelectedDatum(ado, Sover);
12087 if (!(sar = SUMA_FormNodeValFieldStrings(ado, Sover->dset_link,
12088 SelectedNode,
12089 Sover->OptScl->find,
12090 Sover->OptScl->tind,
12091 Sover->OptScl->bind, 0, &I, &T, &B))) {
12092 SUMA_LH("Failed to get strings");
12093 } else {
12094 SUMA_LH("Got strings");
12095 }
12096 if (sar && sar[0]) {
12097 SUMA_INSERT_CELL_STRING(SurfCont->DataTable, 1, 1, sar[0]);
12098 SUMA_free(sar[0]);
12099 } else {
12100 SUMA_INSERT_CELL_STRING(SurfCont->DataTable, 1, 1, "Err");
12101 }
12102 /* Set the table num values too, otherwise you can't read out
12103 the numerical values if you wish and that's just a shame
12104 for numerical tables such as this one. */
12105 SUMA_SET_CELL_VALUE(SurfCont->DataTable, 1, 1, I);
12106 if (sar && sar[1]) {
12107 SUMA_INSERT_CELL_STRING(SurfCont->DataTable, 1, 2, sar[1]);
12108 SUMA_free(sar[1]);
12109 } else {
12110 SUMA_INSERT_CELL_STRING(SurfCont->DataTable, 1, 2, "Err");
12111 }
12112 SUMA_SET_CELL_VALUE(SurfCont->DataTable, 1, 1, T);
12113 if (sar && sar[2]) {
12114 SUMA_INSERT_CELL_STRING(SurfCont->DataTable, 1, 3, sar[2]);
12115 SUMA_free(sar[2]);
12116 } else {
12117 SUMA_INSERT_CELL_STRING(SurfCont->DataTable, 1, 3, "Err");
12118 }
12119 SUMA_SET_CELL_VALUE(SurfCont->DataTable, 1, 1, B);
12120 if (sar) SUMA_free(sar); sar = NULL;
12121
12122 SUMA_RETURN(YUP);
12123 }
12124
12125 /*!< Get values at current selection on current plane
12126 if (fromtable) then read the values from the
12127 displayed table structure.
12128 */
SUMA_GetValuesAtSelection(SUMA_ALL_DO * ado,int fromtable,float * I,float * T,float * B)12129 SUMA_Boolean SUMA_GetValuesAtSelection(SUMA_ALL_DO *ado, int fromtable,
12130 float *I, float *T, float *B)
12131 {
12132 static char FuncName[]={"SUMA_GetValuesAtSelection"};
12133 SUMA_OVERLAYS *Sover=NULL;
12134 SUMA_X_SurfCont *SurfCont=NULL;
12135 int SelectedNode = -1;
12136 double II=0.0, TT=0.0, BB=0.0;
12137 SUMA_Boolean LocalHead = NOPE;
12138
12139 SUMA_ENTRY;
12140
12141 if (!ado) {
12142 SUMA_LH("Null ado");
12143 SUMA_RETURN(NOPE);
12144 }
12145
12146 Sover = SUMA_ADO_CurColPlane(ado);
12147 if (!Sover) {
12148 SUMA_LH("Null Sover");
12149 SUMA_RETURN(NOPE);
12150 }
12151 SurfCont = SUMA_ADO_Cont(ado);
12152 if (!SurfCont) SUMA_RETURN(NOPE);
12153
12154 SelectedNode = SUMA_ADO_ColPlane_SelectedDatum(ado, Sover);
12155
12156 if (fromtable && (!SurfCont->DataTable ||
12157 !SurfCont->DataTable->cells)) {
12158 SUMA_LH("Controller not initialized, "
12159 "cannot retrieve values from table, trying without");
12160 fromtable = 0;
12161 }
12162 if (fromtable) {
12163 if (!SurfCont->DataTable ||
12164 !SurfCont->DataTable->cells) {
12165 SUMA_S_Err("Controller not initialized, "
12166 "cannot retrieve values from table");
12167 SUMA_RETURN(NOPE);
12168 }
12169 /* Check that SelectedNode matches that in the node index table too */
12170 if (SelectedNode != SurfCont->NodeTable->num_value[1]) {
12171 /* table not updated yet perhaps */
12172 SUMA_S_Note("Forced update of value fields (%d) (%f)to be safe",
12173 SelectedNode, SurfCont->NodeTable->num_value[1]);
12174 SUMA_UpdateNodeValField(ado);
12175 }
12176 SUMA_LH("Fetching from table");
12177 if (I) SUMA_GET_CELL_VALUE(SurfCont->DataTable, 1, 1, *I);
12178 if (T) SUMA_GET_CELL_VALUE(SurfCont->DataTable, 1, 2, *T);
12179 if (B) SUMA_GET_CELL_VALUE(SurfCont->DataTable, 1, 3, *B);
12180 } else {
12181 if (!SUMA_GetNodeValsAtSelection(ado, Sover->dset_link,
12182 SelectedNode,
12183 Sover->OptScl->find,
12184 Sover->OptScl->tind,
12185 Sover->OptScl->bind,
12186 &II, &TT, &BB)) {
12187
12188 SUMA_S_Err("Failed to get sel values");
12189 SUMA_RETURN(NOPE);
12190 }
12191 if (I) *I = II;
12192 if (T) *T = TT;
12193 if (B) *B = BB;
12194 }
12195 SUMA_RETURN(YUP);
12196 }
12197
SUMA_GetLabelsAtSelection(SUMA_ALL_DO * ado,int node,int sec)12198 char *SUMA_GetLabelsAtSelection(SUMA_ALL_DO *ado, int node, int sec)
12199 {
12200 static char FuncName[]={"SUMA_GetLabelsAtSelection"};
12201 SUMA_Boolean LocalHead = NOPE;
12202
12203 SUMA_ENTRY;
12204
12205 if (!ado) SUMA_RETURN(NULL);
12206
12207 switch (ado->do_type) {
12208 case SO_type:
12209 SUMA_RETURN(SUMA_GetLabelsAtSelection_ADO(ado,node, sec));
12210 break;
12211 case GDSET_type:
12212 SUMA_S_Warn("Not ready to return labels for dsets, and should I be?");
12213 break;
12214 case CDOM_type:
12215 case VO_type:
12216 case MASK_type:
12217 case TRACT_type:
12218 case GRAPH_LINK_type:
12219 SUMA_RETURN(SUMA_GetLabelsAtSelection_ADO(ado,node, sec));
12220 break;
12221 default:
12222 SUMA_LHv("No labels ready for type %s\n",
12223 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
12224 break;
12225 }
12226
12227 SUMA_RETURN(NULL);
12228 }
12229
12230 /* Do we have labels at this location ?
12231 node is the 'datum' index, primary selection - think node on surface,
12232 or edge on graph
12233 sec is the secondary selection index - think FaceSet on surface,
12234 or node on graph*/
SUMA_GetLabelsAtSelection_ADO(SUMA_ALL_DO * ado,int node,int sec)12235 char *SUMA_GetLabelsAtSelection_ADO(SUMA_ALL_DO *ado, int node, int sec)
12236 {
12237 static char FuncName[]={"SUMA_GetLabelsAtSelection_ADO"};
12238 char *lbls=NULL;
12239 int key = -1, OverInd=-1, i0, i, sp;
12240 SUMA_DSET *cdset=NULL, *dd=NULL;
12241 SUMA_OVERLAYS *colplane=NULL, *Sover=NULL;
12242 SUMA_COLOR_MAP *CM=NULL;
12243 DListElmt *el=NULL, *NextElm=NULL;
12244 DList *list=NULL;
12245 SUMA_EngineData *ED=NULL;
12246 char **sar=NULL, stmp[64]={""};
12247 char *seps[3]={"I=", " T=", " B="};
12248 SUMA_Boolean LocalHead = NOPE;
12249 SUMA_ENTRY;
12250
12251 if (!ado) SUMA_RETURN(NULL);
12252
12253 /* Any clusters? */
12254 SUMA_LHv("on ADO %s, looking for labels for selection %d and secondary %d\n",
12255 SUMA_ADO_Label(ado), node, sec);
12256
12257 if (ado->do_type == SO_type) {
12258 SUMA_SurfaceObject *SO = (SUMA_SurfaceObject *)ado;
12259 el = dlist_head(SUMAg_CF->DsetList);
12260 while (el) {
12261 dd = (SUMA_DSET*)el->data;
12262 if (SUMA_isDsetRelated(dd, SO) &&
12263 (colplane = SUMA_Fetch_OverlayPointerByDset (
12264 (SUMA_ALL_DO*)SO, dd, &OverInd)) &&
12265 colplane->OptScl) {
12266 SUMA_LHv("Have Dset %s related to SO\n", SDSET_LABEL(dd));
12267 /* is dd a LabelDset ? */
12268 if ( (SUMA_is_Label_dset(dd, NULL) ||
12269 SUMA_is_Label_dset_col(dd,colplane->OptScl->find))
12270 && node >= 0 ) {
12271 SUMA_LHv("dset %s will work with SO", SDSET_LABEL(dd));
12272 key = SUMA_GetDsetNodeValInCol2( dd, colplane->OptScl->find,
12273 node, -1);
12274 /* get the overlay for that dset */
12275 if (key >= 0) {
12276 /* get the colormap for that colplane */
12277 if ((CM = SUMA_FindNamedColMap (colplane->cmapname)) &&
12278 CM->cname) {
12279 if ((i0 = SUMA_ColMapKeyIndex(key, CM)) >= 0) {
12280 if (!lbls) {
12281 lbls = SUMA_copy_string(CM->cname[i0]);
12282 } else {
12283 lbls = SUMA_append_replace_string(lbls,CM->cname[i0],
12284 "|", 1);
12285 }
12286 }
12287 }
12288 }
12289 }
12290 }
12291 el = dlist_next(el);
12292 }
12293 }
12294
12295
12296 if ((Sover = SUMA_ADO_CurColPlane(ado))) {
12297 if (SDSET_TYPE(Sover->dset_link) != SUMA_NODE_RGB ) {/* Have labels */
12298 if (!(sar = SUMA_FormNodeValFieldStrings(ado,
12299 Sover->dset_link,
12300 node,
12301 Sover->OptScl->find,
12302 Sover->OptScl->tind,
12303 Sover->OptScl->bind, 5,
12304 NULL, NULL, NULL))) {
12305 SUMA_LH("No Sar");
12306 } else if (1) { /* include sub-brick labels */
12307 SUMA_LH("Sar: %s %s %s",
12308 SUMA_CHECK_NULL_STR(sar[0]),SUMA_CHECK_NULL_STR(sar[1]),
12309 SUMA_CHECK_NULL_STR(sar[2]));
12310 if (lbls) lbls = SUMA_append_replace_string(lbls,"\n","",1);
12311 if (sar[0] && sar[1] && sar[2]) {
12312 if (!strcmp(sar[0],sar[1]) && !strcmp(sar[2],sar[1])) {
12313 lbls = SUMA_append_replace_string(lbls, "(I,T,B)", "",1);
12314 lbls = SUMA_append_replace_string(lbls,
12315 SUMA_DsetColLabel(Sover->dset_link,
12316 Sover->OptScl->find),
12317 "",1);
12318 lbls = SUMA_append_replace_string(lbls, sar[0], "=",1);
12319 } else if (!strcmp(sar[0],sar[1])) {
12320 lbls = SUMA_append_replace_string(lbls, "(I,T)", "",1);
12321 lbls = SUMA_append_replace_string(lbls,
12322 SUMA_DsetColLabel(Sover->dset_link,
12323 Sover->OptScl->find),
12324 "",1);
12325 lbls = SUMA_append_replace_string(lbls, sar[0], "=",1);
12326
12327 lbls = SUMA_append_replace_string(lbls, " (B)", "",1);
12328 lbls = SUMA_append_replace_string(lbls,
12329 SUMA_DsetColLabel(Sover->dset_link,
12330 Sover->OptScl->bind),
12331 "",1);
12332 lbls = SUMA_append_replace_string(lbls, sar[2], "=", 1);
12333 } else if (!strcmp(sar[1],sar[2])) {
12334 lbls = SUMA_append_replace_string(lbls, "(I)", "",1);
12335 lbls = SUMA_append_replace_string(lbls,
12336 SUMA_DsetColLabel(Sover->dset_link,
12337 Sover->OptScl->find),
12338 "",1);
12339 lbls = SUMA_append_replace_string(lbls, sar[0], "=",1);
12340
12341 lbls = SUMA_append_replace_string(lbls, " (B,T)", "",1);
12342 lbls = SUMA_append_replace_string(lbls,
12343 SUMA_DsetColLabel(Sover->dset_link,
12344 Sover->OptScl->bind),
12345 "",1);
12346 lbls = SUMA_append_replace_string(lbls, sar[2], "=", 1);
12347 } else if (!strcmp(sar[0],sar[2])) {
12348 lbls = SUMA_append_replace_string(lbls, "(I,B)", "",1);
12349 lbls = SUMA_append_replace_string(lbls,
12350 SUMA_DsetColLabel(Sover->dset_link,
12351 Sover->OptScl->find),
12352 "",1);
12353 lbls = SUMA_append_replace_string(lbls, sar[0], "=",1);
12354
12355 lbls = SUMA_append_replace_string(lbls, " (T)", "",1);
12356 lbls = SUMA_append_replace_string(lbls,
12357 SUMA_DsetColLabel(Sover->dset_link,
12358 Sover->OptScl->tind),
12359 "",1);
12360 lbls = SUMA_append_replace_string(lbls, sar[1], "=", 1);
12361 } else {
12362 for (sp=0,i=0;i<3;++i) {
12363 if (sar[i]) {
12364 if (sp)
12365 lbls = SUMA_append_replace_string(lbls," ","", 1);
12366 lbls = SUMA_append_replace_string(lbls,
12367 SUMA_DsetColLabel(Sover->dset_link,
12368 i==0 ? Sover->OptScl->find :
12369 ( i == 1 ? Sover->OptScl->tind:
12370 Sover->OptScl->bind)),
12371 "",1);
12372 lbls = SUMA_append_replace_string(lbls,sar[i],"=", 1);
12373 sp=1;
12374 SUMA_free(sar[i]); sar[i]=NULL;
12375 }
12376 }
12377 }
12378 } else {
12379 for (sp=0,i=0;i<3;++i) {
12380 if (sar[i]) {
12381 if (sp)
12382 lbls = SUMA_append_replace_string(lbls," ","", 1);
12383 lbls = SUMA_append_replace_string(lbls,
12384 SUMA_DsetColLabel(Sover->dset_link,
12385 i==0 ? Sover->OptScl->find :
12386 ( i == 1 ? Sover->OptScl->tind:
12387 Sover->OptScl->bind)),
12388 "",1);
12389 lbls = SUMA_append_replace_string(lbls,sar[i],"=", 1);
12390 sp=1;
12391 SUMA_free(sar[i]); sar[i]=NULL;
12392 }
12393 }
12394
12395 }
12396 SUMA_free(sar); sar=NULL;
12397 if (ado->do_type == SO_type) {
12398 if ((sp=SUMA_NodeClustNumber(Sover, node,
12399 (SUMA_SurfaceObject *)ado, NULL))) {
12400 sprintf(stmp,"\nIn cluster %d", sp);
12401 if (lbls) lbls = SUMA_append_replace_string(lbls,stmp,"",1);
12402 }
12403 }
12404 } else { /* old approach to labeling, I,T, business only */
12405 SUMA_LH("Old");
12406 if (lbls) lbls = SUMA_append_replace_string(lbls,"\n","",1);
12407 if (sar[0] && sar[1] && sar[2]) {
12408 if (!strcmp(sar[0],sar[1]) && !strcmp(sar[2],sar[1])) {
12409 lbls = SUMA_append_replace_string(lbls, sar[0], "I,T,B=",1);
12410 } else if (!strcmp(sar[0],sar[1])) {
12411 lbls = SUMA_append_replace_string(lbls, sar[0], "I,T=",1);
12412 lbls = SUMA_append_replace_string(lbls, sar[2], " B=", 1);
12413 } else if (!strcmp(sar[1],sar[2])) {
12414 lbls = SUMA_append_replace_string(lbls, sar[0], "I=",1);
12415 lbls = SUMA_append_replace_string(lbls, sar[1], " B,T=", 1);
12416 } else {
12417 for (i=0;i<3;++i) {
12418 if (sar[i]) {
12419 lbls = SUMA_append_replace_string(lbls,sar[i],
12420 seps[i], 1);
12421 SUMA_free(sar[i]); sar[i]=NULL;
12422 }
12423 }
12424 }
12425 } else {
12426 for (i=0;i<3;++i) {
12427 if (sar[i]) {
12428 lbls = SUMA_append_replace_string(lbls,sar[i],
12429 seps[i], 1);
12430 SUMA_free(sar[i]); sar[i]=NULL;
12431 }
12432 }
12433 }
12434 SUMA_free(sar); sar=NULL;
12435 }
12436 }/* Have labels */
12437
12438 /* Some coord info for select few ? */
12439
12440 if (ado->do_type == GRAPH_LINK_type) {
12441 SUMA_DSET *gset=NULL;
12442 char *stmp=NULL, *pref=NULL;
12443 gset = SUMA_find_GLDO_Dset((SUMA_GraphLinkDO*)ado);
12444 if (node >= 0) { /* an edge */
12445 pref = "\nGpair "; /* I was using "Cell" and "Edge"
12446 depending on the variant, but
12447 the label is shared across viewers
12448 so that does not work well */
12449 if ((stmp=SUMA_GDSET_Edge_Label(gset, node, pref, NULL))) {
12450 SUMA_LHv("Adding edge label %s\n", stmp);
12451 lbls = SUMA_append_replace_string(lbls,stmp,"", 1);
12452 SUMA_ifree(stmp);
12453 }
12454 } else {
12455 if (sec >= 0) { /* all from some node */
12456 if ((stmp=SUMA_GDSET_Node_Label(gset, sec))) {
12457 SUMA_LHv("Got graph node label %s\n", stmp);
12458 stmp = SUMA_append_replace_string("\nGnode ", stmp, "", 0);
12459 lbls = SUMA_append_replace_string(lbls,stmp,"", 1);
12460 SUMA_ifree(stmp);
12461 }
12462 }
12463 }
12464 }
12465
12466 /* Bundles, tracts? */
12467 if (ado->do_type == TRACT_type) {
12468 SUMA_TractDO *tdo=(SUMA_TractDO *)ado;
12469 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
12470 TAYLOR_BUNDLE *tb=NULL;
12471 char stmp[256], *be=NULL;
12472 if (node >= 0) { /* spell out where you are */
12473 if (TSaux->PR->iAltSel[SUMA_NET_BUN] >= 0 &&
12474 TSaux->PR->iAltSel[SUMA_BUN_TRC] >= 0 &&
12475 TSaux->PR->iAltSel[SUMA_TRC_PNT] >= 0 ) {
12476 if ( (tb = TDO_BUNDLE(tdo, TSaux->PR->iAltSel[SUMA_NET_BUN])) &&
12477 tb->bundle_ends ) {
12478 be = tb->bundle_ends;
12479 }
12480 snprintf(stmp, 256,
12481 "%s%s%cPnt %ld, trct %ld, bnd %ld",
12482 lbls?"\n":"", be ? be:"", be ? '\n':'\0',
12483 TSaux->PR->iAltSel[SUMA_TRC_PNT],
12484 TSaux->PR->iAltSel[SUMA_BUN_TRC],
12485 TSaux->PR->iAltSel[SUMA_NET_BUN]);
12486 lbls = SUMA_append_replace_string(lbls,stmp,"", 0);
12487 }
12488 }
12489 }
12490
12491 /* Volume object */
12492 if (ado->do_type == VO_type) {
12493 SUMA_VolumeObject *vo=(SUMA_VolumeObject *)ado;
12494 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
12495 char stmp[256];
12496 SUMA_LH("Vol consideration with %s and node %d",
12497 lbls, node);
12498 if (node >= 0) { /* spell out where you are */
12499 if (VSaux->PR->iAltSel[SUMA_VOL_I] >= 0 &&
12500 VSaux->PR->iAltSel[SUMA_VOL_J] >= 0 &&
12501 VSaux->PR->iAltSel[SUMA_VOL_K] >= 0 ) {
12502 snprintf(stmp, 256,
12503 "%sVoxel [%ld,%ld,%ld] at [%.2f,%.2f,%.2f]",
12504 lbls?"\n":"",
12505 VSaux->PR->iAltSel[SUMA_VOL_I],
12506 VSaux->PR->iAltSel[SUMA_VOL_J],
12507 VSaux->PR->iAltSel[SUMA_VOL_K],
12508 VSaux->PR->PickXYZ[0],
12509 VSaux->PR->PickXYZ[1],
12510 VSaux->PR->PickXYZ[2]);
12511 lbls = SUMA_append_replace_string(lbls,stmp,"", 0);
12512 if (LocalHead) { /* Just for fun */
12513 char variant[8];
12514 SUMA_dset_gui_slice_from_tex_slice_d(vo->VE, 0,
12515 VSaux->PR->dAltSel+SUMA_VOL_SLC_EQ0,
12516 0, variant,NULL);
12517 SUMA_LH("%s, slice %.2f,%.2f,%.2f, %.2f: %s\n", stmp,
12518 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ0],
12519 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ1],
12520 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ2],
12521 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ3],
12522 variant);
12523 }
12524 }
12525 }
12526 }
12527
12528 /* Mask object */
12529 if (ado->do_type == MASK_type) {
12530 char stmp[256];
12531 snprintf(stmp, 256,
12532 "%sMask selected",
12533 lbls?"\n":"");
12534 lbls = SUMA_append_replace_string(lbls,stmp,"", 0);
12535 }
12536 }
12537
12538 /* Do we need to tell Santa? */
12539 if (ado->do_type == SO_type &&
12540 lbls && SUMAg_CF->X->Whereami_TextShell) {
12541 if (!list) list = SUMA_CreateList();
12542 ED = SUMA_InitializeEngineListData (SE_Whereami);
12543 if (!(NextElm = SUMA_RegisterEngineListCommand ( list, ED,
12544 SEF_vp, (void *)ado,
12545 SES_Suma, NULL, NOPE,
12546 SEI_Head, NULL))) {
12547 fprintf (SUMA_STDERR,
12548 "Error %s: Failed to register command.\n",
12549 FuncName);
12550 }
12551 if (!(NextElm = SUMA_RegisterEngineListCommand ( list, ED,
12552 SEF_s, (void *)lbls, /* Copy by value */
12553 SES_Suma, NULL, NOPE,
12554 SEI_In, NextElm))) {
12555 fprintf (SUMA_STDERR,
12556 "Error %s: Failed to add data.\n",
12557 FuncName);
12558 }
12559
12560 if (!SUMA_Engine (&list)) {
12561 fprintf(stderr,
12562 "Error %s: SUMA_Engine call failed.\n", FuncName);
12563 }
12564 }
12565 SUMA_LH("Returning %s", lbls);
12566 SUMA_RETURN(lbls);
12567 }
12568
12569 /* transform string to a TextNIDO,
12570 If sv is not NULL,
12571 then NIDO is added to SUMAg_DOv and registered with sv
12572 Do not free what it returned because it is added to SUMA's DOv
12573 else
12574 the returned nido is all yours to manage
12575
12576 */
SUMA_NodeLabelToTextNIDO(char * lbls,SUMA_ALL_DO * ado,SUMA_SurfaceViewer * sv)12577 SUMA_NIDO *SUMA_NodeLabelToTextNIDO (char *lbls, SUMA_ALL_DO *ado,
12578 SUMA_SurfaceViewer *sv)
12579 {
12580 static char FuncName[]={"SUMA_NodeLabelToTextNIDO"};
12581 static void * default_font=GLUT_BITMAP_9_BY_15;
12582 int i=0;
12583 float txcol[4] = {0.2, 0.5, 1, 1.0};
12584 float default_color[4] = {0.2, 0.5, 1, 1.0}, *v;
12585 float topscr[3]={ 0.5, 1.0, 0.0 };
12586 SUMA_DO_CoordType coord_type = SUMA_WORLD;
12587 SUMA_DO_CoordUnits default_coord_units = SUMA_WORLD_UNIT;
12588 SUMA_NIDO *nido=NULL;
12589 NI_element *nini = NULL;
12590
12591 SUMA_ENTRY;
12592
12593
12594 if (0) { /* on crosshair, does not look so nice. Keep it for the record*/
12595 nido = SUMA_BlankNIDO(NULL, "AHorseWithNoName",
12596 SUMA_ADO_LDP(ado), NULL, NULL);
12597 nini = NI_new_data_element("T", 0);
12598
12599 v = SUMA_ADO_DatumXYZ(ado, SUMA_ADO_SelectedDatum(ado, NULL, NULL), NULL);
12600 coord_type = SUMA_WORLD;
12601 } else {/* fixed on screen */
12602 nido = SUMA_BlankNIDO(NULL, "AHorseWithNoName",
12603 NULL, "fixed", NULL);
12604 nini = NI_new_data_element("T", 0);
12605 coord_type = SUMA_SCREEN;
12606 NI_set_attribute(nini,"v_align", "top");
12607 NI_set_attribute(nini,"h_align", "center");
12608 NI_set_attribute(nini,"shadow","yes"); /* Not ready for prime time */
12609 v = topscr;
12610 }
12611 NI_SET_FLOATv( nini, "coord", v, 3);
12612 NI_set_attribute(nini,"text", lbls);
12613 NI_set_attribute(nini, "font", SUMA_EnvVal("SUMA_CrossHairLabelFont"));
12614 for (i=0;i<3;++i) default_color[i] = 1.0 - sv->clear_color[i];
12615 NI_SET_FLOATv( nini, "col", default_color,3);
12616
12617 NI_add_to_group(nido->ngr, nini);
12618
12619 if (sv) {
12620 /* addDO (repeated nidos will get replaced)
12621 As long as its ID remains the same, then
12622 SUMA_AddDO, will free its precursor and
12623 replace with the new one*/
12624 if (!SUMA_AddDO(SUMAg_DOv, &SUMAg_N_DOv, (void *)nido,
12625 NIDO_type, coord_type)) {
12626 fprintf( SUMA_STDERR,"Error %s: Failed in SUMA_AddDO. (leak)\n",
12627 FuncName);
12628 SUMA_RETURN(NULL);
12629 }
12630
12631 /* register DO with viewer */
12632 if (!SUMA_RegisterDO(SUMAg_N_DOv-1, sv)) {
12633 fprintf(SUMA_STDERR,"Error %s: Failed in SUMA_RegisterDO. (leak)\n",
12634 FuncName);
12635 SUMA_RETURN(NULL);
12636 }
12637 }
12638
12639 SUMA_RETURN(nido);
12640 }
12641
SUMA_UpdateNodeLblField(SUMA_ALL_DO * ado)12642 SUMA_Boolean SUMA_UpdateNodeLblField(SUMA_ALL_DO *ado)
12643 {
12644 static char FuncName[]={"SUMA_UpdateNodeLblField"};
12645
12646 if (!ado) return(NOPE);
12647 switch(ado->do_type) {
12648 case SO_type: {
12649 return(SUMA_UpdateNodeLblField_ADO(ado));
12650 break; }
12651 case GDSET_type: {
12652 SUMA_S_Warn("Should I be updating this guy and not it GLDO?");
12653 return(YUP);
12654 break; }
12655 case CDOM_type:
12656 case VO_type:
12657 case TRACT_type:
12658 case MASK_type:
12659 case GRAPH_LINK_type: {
12660 return(SUMA_UpdateNodeLblField_ADO(ado));
12661 break; }
12662 default:
12663 SUMA_S_Errv("Bad type %s for this function\n",
12664 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
12665 return(NOPE);
12666 }
12667 return(NOPE);
12668 }
12669
12670 /*!
12671 Updates places where a node's value is shown
12672 */
SUMA_UpdateNodeLblField_ADO(SUMA_ALL_DO * ado)12673 SUMA_Boolean SUMA_UpdateNodeLblField_ADO(SUMA_ALL_DO *ado)
12674 {
12675 static char FuncName[]={"SUMA_UpdateNodeLblField_ADO"};
12676 int Found = -1;
12677 char *lbls=NULL, *ltmp=NULL;
12678 char str_col[101];
12679 SUMA_OVERLAYS *Sover=NULL;
12680 SUMA_X_SurfCont *SurfCont=NULL;
12681 SUMA_Boolean LocalHead = NOPE;
12682
12683 SUMA_ENTRY;
12684
12685 if (!ado || (!(SurfCont=SUMA_ADO_Cont(ado))
12686 && !SUMAg_CF->X->Whereami_TextShell)) {
12687 /* absolutely nothing to do */
12688 SUMA_RETURN(NOPE);
12689 }
12690
12691 switch(ado->do_type) {
12692 case CDOM_type:
12693 case VO_type:
12694 case GRAPH_LINK_type:
12695 case MASK_type:
12696 case TRACT_type:
12697 case SO_type:
12698 /* get labels from Label Datasets, and update whereami
12699 window if needed*/
12700 lbls = SUMA_GetLabelsAtSelection_ADO(ado,
12701 SUMA_ADO_SelectedDatum(ado, NULL, NULL),
12702 SUMA_ADO_SelectedSecondary(ado));
12703 SUMA_LHv("Label Dsets: %s\n", lbls);
12704 break;
12705 case GDSET_type:
12706 SUMA_S_Warn("Should be using GRAPH_LINK_type instead");
12707 break;
12708 default:
12709 break;
12710 }
12711
12712
12713 if (SurfCont && SurfCont->LabelTable && SurfCont->LabelTable->cells) {
12714 Sover = SUMA_ADO_CurColPlane(ado);
12715 if (!Sover) {
12716 SUMA_RETURN(NOPE);
12717 }
12718 /* seems the '!' were remnants - */
12719 /* revert to original logic, but avoid warnings
12720 * (to later evaluate changes) todo: apply ShowMode
12721 * original : if (!Sover->ShowMode > 0)
12722 * fix?? : if ( Sover->ShowMode > 0)
12723 * - seems like we want to actually show here
12724 * temp.as.orig : if ( !Sover->ShowMode )
12725 *
12726 * comment : orig/temp would only show on 0,
12727 * which does not make sense
12728 * : since block adds, prob a show>0 condition
12729 * 19 Feb 2021 [rickr] */
12730 if ( ! Sover->ShowMode ) {
12731 SUMA_LH("Col plane hidden");
12732 sprintf(str_col,"hidden color overlay");
12733 if (lbls) lbls = SUMA_append_replace_string(lbls, str_col, "; col=", 1);
12734 else lbls = SUMA_copy_string(str_col);
12735 SUMA_INSERT_CELL_STRING(SurfCont->LabelTable, 0, 1, lbls);
12736 if (lbls) SUMA_free(lbls); lbls = NULL;
12737 SUMA_RETURN(YUP);
12738 }
12739
12740 Found = SUMA_GetNodeOverInd(Sover,
12741 SUMA_ADO_ColPlane_SelectedDatum(ado, Sover));
12742
12743 if (Found < 0) {
12744 SUMA_Boolean Reasoned = NOPE;
12745 SUMA_LH("Node not found.\nLikely masked by threshold");
12746 sprintf(str_col,"masked");
12747 /* try to find out why it is masked */
12748 if (!Reasoned && SurfCont->DataTable) {
12749 SUMA_LH("Checking if there is no data for this node");
12750 {
12751 void *n=NULL;
12752 XtVaGetValues(
12753 SurfCont->DataTable->cells[1*SurfCont->DataTable->Ni+1],
12754 XmNvalue, &n, NULL);
12755 if (strcmp((char *)n, "NoData") == 0) {
12756 /* no data at all */
12757 sprintf(str_col,"no data for this node");
12758 Reasoned = YUP;
12759 }
12760 }
12761 }
12762 if (!Reasoned && SurfCont->DataTable) { /* is the value 0 ? */
12763 SUMA_LH("Checking if node value is zero & zero is not being shown");
12764 if (Sover->OptScl->MaskZero &&
12765 SurfCont->DataTable->num_value[1*SurfCont->DataTable->Ni+1]) {
12766 sprintf(str_col,"masked by zero value");
12767 }
12768 }
12769 } else {
12770 {
12771 /* Now we know what the index of this node
12772 is in the overlay plane (and the data) */
12773 sprintf(str_col,"%s",
12774 MV_format_fval2(Sover->ColVec[3*Found],5));
12775 SUMA_strncat( str_col,", ", 100);
12776 SUMA_strncat( str_col,
12777 MV_format_fval2(Sover->ColVec[3*Found+1],5), 100);
12778 SUMA_strncat( str_col,", ", 100);
12779 SUMA_strncat( str_col,
12780 MV_format_fval2(Sover->ColVec[3*Found+2],5), 100);
12781 SUMA_LH("%s", str_col);
12782 }
12783 }
12784 if (lbls) ltmp = SUMA_append_replace_string(lbls, str_col, "; col=", 0);
12785 else ltmp = SUMA_copy_string(str_col);
12786 SUMA_INSERT_CELL_STRING(SurfCont->LabelTable, 0, 1, ltmp);
12787 SUMA_free(ltmp); ltmp=NULL;
12788 }
12789
12790 if (lbls) SUMA_free(lbls); lbls = NULL;
12791
12792 SUMA_RETURN(YUP);
12793 }
12794
12795
SUMA_UpdateCrossHairNodeLabelField(SUMA_SurfaceViewer * sv)12796 SUMA_Boolean SUMA_UpdateCrossHairNodeLabelField(SUMA_SurfaceViewer *sv)
12797 {
12798 static char FuncName[]={"SUMA_UpdateCrossHairNodeLabelField"};
12799 char *lbls=NULL;
12800 SUMA_ALL_DO *ado=NULL;
12801 SUMA_Boolean LocalHead = NOPE;
12802
12803 SUMA_ENTRY;
12804
12805 if (!sv || !sv->Ch || sv->Ch->adoID < 0) {
12806 /* nothing to do */
12807 SUMA_RETURN(NOPE);
12808 }
12809
12810 if (!(ado = (SUMA_ALL_DO *)(SUMAg_DOv[sv->Ch->adoID].OP))) {
12811 SUMA_RETURN(NOPE);
12812 }
12813 if ( sv->ShowLabelAtXhair &&
12814 (lbls = SUMA_GetLabelsAtSelection(ado, sv->Ch->datumID, sv->Ch->secID))) {
12815 SUMA_LH("Got %s (%d)",lbls, sv->ShowLabelAtXhair);
12816 SUMA_NodeLabelToTextNIDO (lbls, ado, sv);
12817 SUMA_free(lbls); lbls = NULL;
12818 } else {
12819 SUMA_LH("Got NOTHING or %d", sv->ShowLabelAtXhair);
12820 SUMA_NodeLabelToTextNIDO ("", ado, sv);
12821 }
12822
12823 SUMA_RETURN(YUP);
12824 }
12825
SUMA_UpdateCrossHairNodeLabelFieldForDO(SUMA_ALL_DO * curDO)12826 int SUMA_UpdateCrossHairNodeLabelFieldForDO(SUMA_ALL_DO *curDO)
12827 {
12828 static char FuncName[]={"SUMA_UpdateCrossHairNodeLabelFieldForDO"};
12829 int i=0, iup=0;
12830 SUMA_SurfaceViewer *sv=NULL;
12831
12832 SUMA_ENTRY;
12833
12834 if (!curDO) SUMA_RETURN(0);
12835
12836 /* update any viewer that is showing this
12837 surface */
12838 for (i=0; i<SUMAg_N_SVv; ++i) {
12839 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
12840 /* is this viewer showing curDO ? */
12841 if (SUMA_isRegisteredDO(&(SUMAg_SVv[i]), SUMAg_DOv, curDO)) {
12842 sv = &(SUMAg_SVv[i]);
12843 SUMA_UpdateCrossHairNodeLabelField(sv);
12844 ++iup;
12845 }
12846 }
12847 }
12848
12849 SUMA_RETURN(iup);
12850 }
12851
12852
SUMA_UpdateTriField(SUMA_SurfaceObject * SO)12853 SUMA_Boolean SUMA_UpdateTriField(SUMA_SurfaceObject *SO)
12854 {
12855 static char FuncName[]={"SUMA_UpdateTriField"};
12856 SUMA_SurfaceObject *curSO=NULL;
12857 char str[100];
12858 SUMA_Boolean LocalHead = NOPE;
12859
12860 SUMA_ENTRY;
12861
12862 if (!SO) SUMA_RETURN(NOPE);
12863
12864 if (SO->SurfCont) {
12865 if (!SO->SurfCont->FaceTable||
12866 !SO->SurfCont->FaceTable->num_value) { /* table widgets not set yet ?*/
12867 SUMA_RETURN(NOPE);
12868 }
12869
12870 if (!(curSO=(SUMA_SurfaceObject *)SUMA_SurfCont_GetcurDOp(SO->SurfCont))) {
12871 SUMA_S_Err("Failed to get curDOp");
12872 SUMA_RETURN(NOPE);
12873 }
12874 if (curSO == SO) {
12875 if (SO->SelectedFaceSet >= 0) {
12876 sprintf(str, "%d", SO->SelectedFaceSet);
12877 SO->SurfCont->FaceTable->num_value[1] = SO->SelectedFaceSet;
12878 XtVaSetValues(SO->SurfCont->FaceTable->cells[1],
12879 XmNvalue, str, NULL);
12880 sprintf(str, "%d, %d, %d",
12881 SO->FaceSetList[3*SO->SelectedFaceSet],
12882 SO->FaceSetList[3*SO->SelectedFaceSet+1],
12883 SO->FaceSetList[3*SO->SelectedFaceSet+2]);
12884 XtVaSetValues(SO->SurfCont->FaceTable->cells[2],
12885 XmNvalue, str, NULL);
12886 } else {
12887 XtVaSetValues(SO->SurfCont->FaceTable->cells[1],
12888 XmNvalue, "-1", NULL);
12889 SO->SurfCont->FaceTable->num_value[1] = -1;
12890 XtVaSetValues(SO->SurfCont->FaceTable->cells[2],
12891 XmNvalue, "x, x, x", NULL);
12892 }
12893 }
12894 }
12895
12896 SUMA_RETURN(YUP);
12897
12898 }
12899
12900 /*!
12901 \brief set the values of the cross-hair group in the surface controller
12902
12903 \sa SUMA_Init_SurfCont_SurfParam
12904 \sa SUMA_InitializeColPlaneShell
12905 \sa the set of SUMA_UpdateNode*Field functions
12906 */
SUMA_Init_SurfCont_CrossHair(SUMA_ALL_DO * ado)12907 SUMA_Boolean SUMA_Init_SurfCont_CrossHair(SUMA_ALL_DO *ado)
12908 {
12909 static char FuncName[]={"SUMA_Init_SurfCont_CrossHair"};
12910 int i;
12911 SUMA_Boolean LocalHead = NOPE;
12912
12913 SUMA_ENTRY;
12914
12915 if (!ado) SUMA_RETURN(YUP);
12916
12917 /* set the cross hair and related fields */
12918 switch (ado->do_type) {
12919 case SO_type:
12920 SUMA_UpdateTriField((SUMA_SurfaceObject *)ado);
12921 SUMA_UpdateNodeField(ado);
12922 break;
12923 case GDSET_type:
12924 SUMA_S_Err("No init for a DO that cannot be dispalyed\n"
12925 "without variant");
12926 SUMA_RETURN(NOPE);
12927 break;
12928 case CDOM_type:
12929 SUMA_S_Err("So much to do, so little time"
12930 "Probably something like SUMA_UpdateNodeField");
12931 SUMA_RETURN(NOPE);
12932 break;
12933 case GRAPH_LINK_type: {
12934 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
12935 SUMA_DSET *dset=NULL;
12936 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
12937 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
12938 SUMA_ADO_Label(ado));
12939 SUMA_RETURN(NOPE);
12940 }
12941 SUMA_UpdatePointField(ado);
12942 SUMA_UpdateNodeField(ado);
12943 break; }
12944 case TRACT_type: {
12945 SUMA_UpdateNodeField(ado);
12946 break; }
12947 case MASK_type: {
12948 static int ncnt;
12949 if (!ncnt) {
12950 ++ncnt;
12951 SUMA_LH("Nothing to be done for masks here");
12952 }
12953 break; }
12954 case VO_type: {
12955 SUMA_UpdateNodeField(ado);
12956 break; }
12957 default:
12958 SUMA_S_Errv("Nothing to do with %s\n",
12959 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
12960 SUMA_RETURN(NOPE);
12961 }
12962
12963 /* look for a viewer that is showing this surface and has
12964 this surface in focus*/
12965 for (i=0; i<SUMAg_N_SVv; ++i) {
12966 if (LocalHead) fprintf (SUMA_STDERR,
12967 "%s: Checking viewer %d.\n", FuncName, i);
12968 if (!SUMAg_SVv[i].isShaded && SUMAg_SVv[i].X->TOPLEVEL) {
12969 /* is this viewer showing DO ? */
12970 if (SUMA_isVisibleDO(&(SUMAg_SVv[i]), SUMAg_DOv, ado)) {
12971 if (SUMA_SV_Focus_ADO(&(SUMAg_SVv[i])) == ado) {
12972 SUMA_UpdateXhairField(&(SUMAg_SVv[i]));
12973 }
12974 }
12975 }
12976 }
12977
12978 SUMA_RETURN(YUP);
12979 }
12980
12981 /*!
12982 Load Cmap callback
12983 Expect SO in data
12984 */
SUMA_cb_Cmap_Load(Widget w,XtPointer data,XtPointer client_data)12985 void SUMA_cb_Cmap_Load(Widget w, XtPointer data, XtPointer client_data)
12986 {
12987 static char FuncName[]={"SUMA_cb_Cmap_Load"};
12988 SUMA_LIST_WIDGET *LW=NULL;
12989 SUMA_ALL_DO *ado=NULL;
12990 SUMA_X_SurfCont *SurfCont=NULL;
12991 DList *list = NULL;
12992 SUMA_EngineData *ED = NULL;
12993 DListElmt *NextElm = NULL;
12994 SUMA_Boolean LocalHead = NOPE;
12995
12996 SUMA_ENTRY;
12997
12998 SUMA_LH("Called");
12999
13000 if (!(ado = (SUMA_ALL_DO *)data) || !(SurfCont = SUMA_ADO_Cont(ado))) {
13001 SUMA_S_Err("NULL input");
13002 SUMA_RETURNe;
13003 }
13004 if (!list) list = SUMA_CreateList();
13005 ED = SUMA_InitializeEngineListData (SE_OpenCmapFileSelection);
13006 if (!(NextElm = SUMA_RegisterEngineListCommand ( list, ED,
13007 SEF_vp, (void *)ado,
13008 SES_Suma, NULL, NOPE,
13009 SEI_Head, NULL))) {
13010 fprintf (SUMA_STDERR, "Error %s: Failed to register command.\n", FuncName);
13011 }
13012 SUMA_RegisterEngineListCommand ( list, ED,
13013 SEF_ip, (void *)SurfCont->TLS,
13014 SES_Suma, NULL, NOPE,
13015 SEI_In, NextElm);
13016 if (!SUMA_Engine (&list)) {
13017 fprintf(SUMA_STDERR, "Error %s: SUMA_Engine call failed.\n", FuncName);
13018 }
13019
13020 SUMA_RETURNe;
13021 }
13022
SUMA_LoadCmapFile_eng(char * filename)13023 SUMA_COLOR_MAP *SUMA_LoadCmapFile_eng(char *filename)
13024 {
13025 static char FuncName[]={"SUMA_LoadCmapFile_eng"};
13026 SUMA_COLOR_MAP *Cmap=NULL;
13027 SUMA_DSET_FORMAT form;
13028 SUMA_Boolean LocalHead = NOPE;
13029
13030 SUMA_ENTRY;
13031
13032 /* find out if file exists and how many values it contains */
13033 if (!SUMA_filexists(filename)) {
13034 SUMA_S_Err("File not found");
13035 SUMA_RETURN(NULL);
13036 }
13037
13038 /* take a stab at the format */
13039 form = SUMA_GuessFormatFromExtension(filename, NULL);
13040
13041 /* load the baby */
13042 Cmap = NULL;
13043 switch (form) {
13044 case SUMA_1D:
13045 Cmap = SUMA_Read_Color_Map_1D (filename);
13046 if (Cmap == NULL) {
13047 SUMA_S_Err("Could not load colormap.");
13048 SUMA_RETURN(NULL);
13049 }
13050 break;
13051 case SUMA_ASCII_NIML:
13052 case SUMA_BINARY_NIML:
13053 case SUMA_NIML:
13054 Cmap = SUMA_Read_Color_Map_NIML(filename);
13055 break;
13056 default:
13057 SUMA_S_Err( "Format not recognized.\n"
13058 "I won't try to guess.\n"
13059 "Do use the proper extension.");
13060 break;
13061 }
13062
13063 SUMA_RETURN(Cmap);
13064 }
13065
13066 /*! Loads a colormap file and adds it to the list of colormaps */
SUMA_LoadCmapFile(char * filename,void * data)13067 void SUMA_LoadCmapFile (char *filename, void *data)
13068 {
13069 static char FuncName[]={"SUMA_LoadCmapFile"};
13070 SUMA_ALL_DO *ado = NULL;
13071 SUMA_IRGB *irgb=NULL;
13072 int OverInd = -1, lnp=-1, loc[2];
13073 char *np=NULL;
13074 int bringup = 0;
13075 SUMA_DSET_FORMAT form;
13076 DList *list=NULL;
13077 SUMA_LIST_WIDGET *LW=NULL;
13078 SUMA_COLOR_MAP *Cmap=NULL;
13079 SUMA_PARSED_NAME * pn=NULL;
13080 SUMA_Boolean LocalHead = NOPE;
13081
13082 SUMA_ENTRY;
13083
13084 if (!SUMAg_CF->scm) {
13085 SUMAg_CF->scm = SUMA_Build_Color_maps();
13086 if (!SUMAg_CF->scm) {
13087 SUMA_SL_Err("Failed to build color maps.\n");
13088 SUMA_RETURNe;
13089 }
13090 }
13091
13092 if (LocalHead) {
13093 fprintf (SUMA_STDERR,
13094 "%s: Received request to load %s \n",
13095 FuncName, filename);
13096 }
13097
13098 if (!SUMA_filexists(filename)) {
13099 SUMA_SLP_Err("File not found");
13100 SUMA_RETURNe;
13101 }
13102
13103 if (!(Cmap=SUMA_LoadCmapFile_eng(filename))) {
13104 SUMA_SLP_Err("Failed to load cmap. File format may not have been\n"
13105 "recognized from filename extension.\n"
13106 "Use either .1D.cmap or .niml.cmap for name extension.\n");
13107 SUMA_RETURNe;
13108 }
13109 /* have Cmap, add to dbase */
13110
13111 /* remove path from name for pretty purposes */
13112 pn = SUMA_ParseFname(Cmap->Name, NULL);
13113 SUMA_STRING_REPLACE(Cmap->Name, pn->FileName_NoExt);
13114 SUMA_Free_Parsed_Name(pn); pn = NULL;
13115 SUMAg_CF->scm->CMv = SUMA_Add_ColorMap (Cmap, SUMAg_CF->scm->CMv,
13116 &(SUMAg_CF->scm->N_maps));
13117
13118 /* Now you need to close any pre-existing switch Cmap window */
13119 bringup = 0;
13120 if (SUMAg_CF->X->SwitchCmapLst) {
13121 if (SUMAg_CF->X->SwitchCmapLst->toplevel &&
13122 !SUMAg_CF->X->SwitchCmapLst->isShaded) {
13123 /* close that baby */
13124 SUMA_cb_CloseSwitchCmap( NULL, (XtPointer)SUMAg_CF->X->SwitchCmapLst,
13125 NULL);
13126 bringup = 1;
13127 }
13128 }
13129
13130 if (data) {
13131 ado = (SUMA_ALL_DO *)data;
13132
13133 if (LocalHead) {
13134 fprintf (SUMA_STDERR,
13135 "%s: bonding colormap %s to surface %s.\n",
13136 FuncName, filename, SUMA_ADO_Label(ado));
13137 }
13138
13139 /* refresh the list */
13140 SUMA_CmapSelectList(ado, 1, bringup);
13141
13142 /* update the menu buttons */
13143 SUMA_CreateUpdatableCmapMenu(ado);
13144
13145 /* Set the menu button to the current choice */
13146 if (!SUMA_SetCmapMenuChoice (ado, Cmap->Name)) {
13147 SUMA_SL_Err("Failed in SUMA_SetCmapMenuChoice");
13148 }
13149
13150 /* switch to the recently loaded cmap */
13151 if (!SUMA_SwitchColPlaneCmap(ado, Cmap)) {
13152 SUMA_SL_Err("Failed in SUMA_SwitchColPlaneCmap");
13153 }
13154
13155 /* update Lbl fields */
13156 SUMA_UpdateNodeLblField(ado);
13157 }
13158
13159
13160 SUMA_RETURNe;
13161 }
13162
13163 /* Insert a color map from a dataset into the database.
13164 See function LoadCmapFile for details */
SUMA_Insert_Cmap_of_Dset(SUMA_DSET * dset)13165 SUMA_Boolean SUMA_Insert_Cmap_of_Dset(SUMA_DSET *dset)
13166 {
13167 static char FuncName[]={"SUMA_Insert_Cmap_of_Dset"};
13168 NI_group *ngr=NULL;
13169 SUMA_COLOR_MAP *Cmap=NULL;
13170 SUMA_PARSED_NAME * pn=NULL;
13171
13172 SUMA_ENTRY;
13173
13174 if (!dset) SUMA_RETURN(NOPE);
13175 if (!SUMAg_CF->scm) {
13176 SUMAg_CF->scm = SUMA_Build_Color_maps();
13177 if (!SUMAg_CF->scm) {
13178 SUMA_SL_Err("Failed to build color maps.\n");
13179 SUMA_RETURN(NOPE);
13180 }
13181 }
13182
13183 if (!(ngr = SUMA_NI_Cmap_of_Dset(dset))) {
13184 SUMA_RETURN(YUP); /* OK, nothing to do */
13185 }
13186
13187 /* turn cmap into SUMA's structure */
13188 if (!(Cmap = SUMA_NICmapToCmap(ngr))) {
13189 SUMA_S_Err("Failed in translation");
13190 SUMA_RETURN(NOPE);
13191 }
13192
13193 /* remove path from name for pretty purposes */
13194 pn = SUMA_ParseFname(Cmap->Name, NULL);
13195 SUMA_STRING_REPLACE(Cmap->Name, pn->FileName_NoExt);
13196 SUMA_Free_Parsed_Name(pn); pn = NULL;
13197 SUMAg_CF->scm->CMv = SUMA_Add_ColorMap (Cmap, SUMAg_CF->scm->CMv,
13198 &(SUMAg_CF->scm->N_maps));
13199
13200 /* Set cmap name to go with dset SRT stands for SUMA_RUN_TIME attribute
13201 This might be a way to kill attributes before writing out dataset */
13202 NI_set_attribute(dset->ngr, "SRT_use_this_cmap", Cmap->Name);
13203
13204 SUMA_RETURN(YUP);
13205 }
13206
13207
13208 /*!
13209 SUMA_ADO_CurColPlane: Return the current col plane for any DO
13210 This is meant to replace all of the old SO->SurfCont->curColPlane
13211
13212 For some DO with a DOCont, such as DSET_type, the answer
13213 will be GSaux->Overlay
13214 For the rest the answer is NULL
13215 */
SUMA_ADO_CurColPlane(SUMA_ALL_DO * ado)13216 SUMA_OVERLAYS * SUMA_ADO_CurColPlane(SUMA_ALL_DO *ado)
13217 {
13218 static char FuncName[]={"SUMA_ADO_CurColPlane"};
13219 SUMA_Boolean LocalHead = NOPE;
13220
13221 if (!ado) return(NULL);
13222 SUMA_LHv("Have %d\n", ado->do_type);
13223 switch(ado->do_type) {
13224 case SO_type: {
13225 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13226 if (!SO->SurfCont) return(NULL);
13227 return(SO->SurfCont->curColPlane);
13228 break; }
13229 case CDOM_type: {
13230 SUMA_CIFTI_SAUX *CSaux = SUMA_ADO_CSaux(ado);
13231 if (!CSaux || !CSaux->DOCont) return(NULL);
13232 return(CSaux->DOCont->curColPlane);
13233 break; }
13234 case GDSET_type: {
13235 SUMA_DSET *dset=(SUMA_DSET *)ado;
13236 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13237 if (!GSaux) return(NULL);
13238 return(GSaux->Overlay);
13239 break; }
13240 case GRAPH_LINK_type: {
13241 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13242 SUMA_DSET *dset=NULL;
13243 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13244 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13245 SUMA_ADO_Label(ado));
13246 return(NULL);
13247 }
13248 return(SUMA_ADO_CurColPlane((SUMA_ALL_DO *)dset));
13249 break; }
13250 case MASK_type: {
13251 SUMA_MASK_SAUX *MSaux = SUMA_ADO_MSaux(ado);
13252 if (!MSaux || !MSaux->DOCont) return(NULL);
13253 return(MSaux->DOCont->curColPlane);
13254 break; }
13255 case TRACT_type: {
13256 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
13257 if (!TSaux || !TSaux->DOCont) return(NULL);
13258 return(TSaux->DOCont->curColPlane);
13259 break; }
13260 case VO_type: {
13261 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
13262 if (!VSaux || !VSaux->DOCont) return(NULL);
13263 return(VSaux->DOCont->curColPlane);
13264 break; }
13265 default:
13266 return(NULL);
13267 }
13268 return(NULL);
13269 }
13270
SUMA_ADO_Overlay0(SUMA_ALL_DO * ado)13271 SUMA_OVERLAYS * SUMA_ADO_Overlay0(SUMA_ALL_DO *ado)
13272 {
13273 static char FuncName[]={"SUMA_ADO_Overlay0"};
13274 return(SUMA_ADO_Overlay(ado, 0));
13275 }
13276
SUMA_ADO_Overlay(SUMA_ALL_DO * ado,int i)13277 SUMA_OVERLAYS * SUMA_ADO_Overlay(SUMA_ALL_DO *ado, int i)
13278 {
13279 static char FuncName[]={"SUMA_ADO_Overlay"};
13280 SUMA_OVERLAYS **overlays=NULL;
13281 int N_over=0;
13282
13283 if (!ado || i<0) return(NULL);
13284 if ((overlays = SUMA_ADO_Overlays(ado, &N_over))) {
13285 if (i < N_over) return(overlays[i]);
13286 }
13287 return(NULL);
13288 }
13289
SUMA_ADO_Append_Overlay(SUMA_ALL_DO * ado,SUMA_OVERLAYS ** over)13290 SUMA_Boolean SUMA_ADO_Append_Overlay(SUMA_ALL_DO *ado, SUMA_OVERLAYS **over)
13291 {
13292 static char FuncName[]={"SUMA_ADO_Append_Overlay"};
13293 SUMA_OVERLAYS ** overlays = NULL;
13294 int N_over = -1;
13295
13296 SUMA_ENTRY;
13297
13298 if (!over || !*over) {
13299 SUMA_S_Err("No overlay to add !");
13300 SUMA_RETURN (NOPE);
13301 }
13302 overlays = SUMA_ADO_Overlays(ado, &N_over);
13303 if (!overlays || N_over < 0) {
13304 SUMA_S_Err("No overlays (%p) or N_over (%d)", overlays, N_over);
13305 SUMA_RETURN (NOPE);
13306 }
13307
13308 if (N_over+1 >= SUMA_MAX_OVERLAYS) {
13309 SUMA_SL_Crit("Too many color overlays.");
13310 SUMA_RETURN (NOPE);
13311 }
13312
13313 switch (ado->do_type) {
13314 case SO_type: {
13315 SUMA_SurfaceObject *SO = (SUMA_SurfaceObject *)ado;
13316 SUMA_S_Warn("Case not tested yet");
13317 overlays[N_over] = *over;
13318 *over = NULL;
13319 ++SO->N_Overlays;
13320 break; }
13321 case TRACT_type: {
13322 SUMA_TractDO *tdo = (SUMA_TractDO *)ado;
13323 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
13324 overlays[N_over] = *over;
13325 *over = NULL;
13326 ++TSaux->N_Overlays;
13327 break; }
13328 case MASK_type: {
13329 SUMA_MaskDO *mdo = (SUMA_MaskDO *)ado;
13330 SUMA_MASK_SAUX *MSaux = SUMA_ADO_MSaux(ado);
13331 overlays[N_over] = *over;
13332 *over = NULL;
13333 ++MSaux->N_Overlays;
13334 break; }
13335 case VO_type: {
13336 SUMA_VolumeObject *vo = (SUMA_VolumeObject *)ado;
13337 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
13338 overlays[N_over] = *over;
13339 *over = NULL;
13340 ++VSaux->N_Overlays;
13341 break; }
13342 case CDOM_type: {
13343 SUMA_CIFTI_SAUX *CSaux = SUMA_ADO_CSaux(ado);
13344 overlays[N_over] = *over;
13345 *over = NULL;
13346 ++CSaux->N_Overlays;
13347 break; }
13348 case GDSET_type: {
13349 SUMA_DSET *dset=(SUMA_DSET *)ado;
13350 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13351 SUMA_S_Warn("Case not tested yet");
13352 if (!GSaux) {
13353 SUMA_S_Err("NULL GSaux");
13354 SUMA_RETURN(NOPE);
13355 }
13356 if (N_over > 0) {
13357 SUMA_S_Err("Not ready or shouldn't add more than one overlay \n"
13358 "for dsets");
13359 SUMA_RETURN(NOPE);
13360 }
13361 GSaux->Overlay = *over;
13362 *over = NULL;
13363 break; }
13364 case GRAPH_LINK_type: {
13365 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13366 SUMA_DSET *dset=NULL;
13367 SUMA_Boolean ans = NOPE;
13368 SUMA_S_Warn("Case not tested yet");
13369 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13370 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13371 SUMA_ADO_Label(ado));
13372 SUMA_RETURN(NOPE);
13373 }
13374 ans = SUMA_ADO_Append_Overlay((SUMA_ALL_DO *)dset, over);
13375 if (!ans) SUMA_RETURN(NOPE);
13376 *over = NULL;
13377 break; }
13378 default:
13379 SUMA_S_Err("Not ready for %d\n", ado->do_type);
13380 SUMA_RETURN(NOPE);
13381 break;
13382 }
13383
13384 SUMA_RETURN(YUP);
13385 }
13386
SUMA_ADO_Overlays(SUMA_ALL_DO * ado,int * N_over)13387 SUMA_OVERLAYS ** SUMA_ADO_Overlays(SUMA_ALL_DO *ado, int *N_over)
13388 {
13389 static char FuncName[]={"SUMA_ADO_Overlays"};
13390
13391 if (!ado) return(NULL);
13392
13393 if (N_over) *N_over = -1;
13394
13395 switch(ado->do_type) {
13396 case SO_type: {
13397 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13398 if (N_over) *N_over = SO->N_Overlays;
13399 return(SO->Overlays);
13400 break; }
13401 case CDOM_type: {
13402 SUMA_CIFTI_SAUX *CSaux = SUMA_ADO_CSaux(ado);
13403 if (!CSaux) return(NULL);
13404 if (N_over) *N_over = CSaux->N_Overlays;
13405 return(CSaux->Overlays);
13406 break; }
13407 case GDSET_type: {
13408 SUMA_DSET *dset=(SUMA_DSET *)ado;
13409 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13410 if (!GSaux || !GSaux->Overlay) return(NULL);
13411 if (N_over) *N_over = 1;
13412 return(&(GSaux->Overlay));
13413 break; }
13414 case GRAPH_LINK_type: {
13415 int N_n;
13416 SUMA_OVERLAYS **oo=NULL;
13417 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13418 SUMA_DSET *dset=NULL;
13419 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13420 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13421 SUMA_ADO_Label(ado));
13422 return(NULL);
13423 }
13424 if ((oo = SUMA_ADO_Overlays((SUMA_ALL_DO *)dset, &N_n))){
13425 if (N_over) *N_over = N_n;
13426 return(oo);
13427 }
13428 break; }
13429 case TRACT_type: {
13430 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
13431 if (!TSaux) return(NULL);
13432 if (N_over) *N_over = TSaux->N_Overlays;
13433 return(TSaux->Overlays);
13434 break; }
13435 case MASK_type: {
13436 SUMA_MASK_SAUX *MSaux = SUMA_ADO_MSaux(ado);
13437 if (!MSaux) return(NULL);
13438 if (N_over) *N_over = MSaux->N_Overlays;
13439 return(MSaux->Overlays);
13440 break; }
13441 case VO_type: {
13442 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
13443 if (!VSaux) return(NULL);
13444 if (N_over) *N_over = VSaux->N_Overlays;
13445 return(VSaux->Overlays);
13446 break; }
13447 default:
13448 return(NULL);
13449 }
13450 return(NULL);
13451 }
13452
13453
SUMA_ADO_N_Overlays(SUMA_ALL_DO * ado)13454 int SUMA_ADO_N_Overlays(SUMA_ALL_DO *ado)
13455 {
13456 static char FuncName[]={"SUMA_ADO_N_Overlays"};
13457 if (!ado) return(-1);
13458 switch(ado->do_type) {
13459 case SO_type: {
13460 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13461 return(SO->N_Overlays);
13462 break; }
13463 case CDOM_type: {
13464 SUMA_CIFTI_SAUX *CSaux = SUMA_ADO_CSaux(ado);
13465 if (!CSaux) return(-1);
13466 return(CSaux->N_Overlays);
13467 break; }
13468 case GDSET_type: {
13469 SUMA_DSET *dset=(SUMA_DSET *)ado;
13470 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13471 if (!GSaux) return(-1);
13472 return(1);
13473 break; }
13474 case GRAPH_LINK_type: {
13475 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13476 SUMA_DSET *dset=NULL;
13477 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13478 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13479 SUMA_ADO_Label(ado));
13480 return(-1);
13481 }
13482 return(SUMA_ADO_N_Overlays((SUMA_ALL_DO *)dset));
13483 break; }
13484 case TRACT_type: {
13485 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
13486 if (!TSaux) return(-1);
13487 return(TSaux->N_Overlays);
13488 break; }
13489 case MASK_type: {
13490 SUMA_MASK_SAUX *MSaux = SUMA_ADO_MSaux(ado);
13491 if (!MSaux) return(-1);
13492 return(MSaux->N_Overlays);
13493 break; }
13494 case VO_type: {
13495 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
13496 if (!VSaux) return(-1);
13497 return(VSaux->N_Overlays);
13498 break; }
13499
13500 default:
13501 return(-1);
13502 }
13503 return(-1);
13504 }
13505
13506 /*!
13507 This function returns a selected datum for a DO
13508 For surfaces, this is always SurfCont->SelectedNode
13509 For SDSETs, it is GSaux->PR->datum_index
13510 */
SUMA_ADO_SelectedDatum(SUMA_ALL_DO * ado,void * extra,void * extra2)13511 int SUMA_ADO_SelectedDatum(SUMA_ALL_DO *ado, void *extra, void *extra2)
13512 {
13513 static char FuncName[]={"SUMA_ADO_SelectedDatum"};
13514 SUMA_Boolean LocalHead = NOPE;
13515
13516 if (!ado) return(-1);
13517 SUMA_LHv("Here with %d (%s), %s\n",
13518 ado->do_type, ADO_TNAME(ado), SUMA_ADO_Label(ado));
13519 switch(ado->do_type) {
13520 case SO_type: {
13521 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13522 return(SO->SelectedNode);
13523 break; }
13524 case CDOM_type: {
13525 SUMA_CIFTI_SAUX *CSaux = SUMA_ADO_CSaux(ado);
13526 if (!CSaux) return(-1);
13527 /* Plenty of room to return extras, once we figure those out.
13528 Selections could be on surfaces or volumes so what needs
13529 to be filled out in the extras will depend on the type of
13530 domain over which the selection was made. */
13531 return(CSaux->PR->datum_index);
13532 break; }
13533 case GDSET_type: {
13534 SUMA_DSET *dset=(SUMA_DSET *)ado;
13535 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13536 if (!GSaux) return(-1);
13537 return(GSaux->PR->datum_index);
13538 break; }
13539 case GRAPH_LINK_type: {
13540 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13541 SUMA_DSET *dset=NULL;
13542 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13543 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13544 SUMA_ADO_Label(ado));
13545 return(-1);
13546 }
13547 return(SUMA_ADO_SelectedDatum((SUMA_ALL_DO *)dset, extra, extra2));
13548 break; }
13549 case TRACT_type: {
13550 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
13551 if (!TSaux) return(-1);
13552 if (extra) {
13553 int *ivsel = (int *)extra;
13554 ivsel[SUMA_NET_BUN] = TSaux->PR->iAltSel[SUMA_NET_BUN];
13555 ivsel[SUMA_BUN_TRC] = TSaux->PR->iAltSel[SUMA_BUN_TRC];
13556 ivsel[SUMA_TRC_PNT] = TSaux->PR->iAltSel[SUMA_TRC_PNT];
13557 ivsel[SUMA_NET_TRC] = TSaux->PR->iAltSel[SUMA_NET_TRC];
13558 }
13559 return(TSaux->PR->datum_index);
13560 break; }
13561 case VO_type: {
13562 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
13563 if (!VSaux) return(-1);
13564 if (extra) {
13565 int *ivsel = (int *)extra;
13566 ivsel[SUMA_VOL_I] = VSaux->PR->iAltSel[SUMA_VOL_I];
13567 ivsel[SUMA_VOL_J] = VSaux->PR->iAltSel[SUMA_VOL_J];
13568 ivsel[SUMA_VOL_K] = VSaux->PR->iAltSel[SUMA_VOL_K];
13569 ivsel[SUMA_VOL_IJK] = VSaux->PR->iAltSel[SUMA_VOL_IJK];
13570 }
13571 if (extra2) {
13572 float *fvsel = (float *)extra2;
13573 fvsel[SUMA_VOL_SLC_EQ0] = VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ0];
13574 fvsel[SUMA_VOL_SLC_EQ1] = VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ1];
13575 fvsel[SUMA_VOL_SLC_EQ2] = VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ2];
13576 fvsel[SUMA_VOL_SLC_EQ3] = VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ3];
13577 }
13578
13579 return(VSaux->PR->datum_index);
13580 break; }
13581 case MASK_type: {
13582 static int ncnt=0;
13583 if (!ncnt) {
13584 SUMA_S_Warn("Not ready for mask objects, returning 0"); ++ncnt;
13585 }
13586 return(0);
13587 break; }
13588 default:
13589 return(-1);
13590 }
13591 return(-1);
13592 }
13593
13594 /*!
13595 This function returns secondary selections a DO
13596 For surfaces, this is always SurfCont->SelectedFaceSet
13597 For SDSETs, it is GSaux->PR->iAltSel[SUMA_ENODE_0]
13598 */
SUMA_ADO_SelectedSecondary(SUMA_ALL_DO * ado)13599 int SUMA_ADO_SelectedSecondary(SUMA_ALL_DO *ado)
13600 {
13601 static char FuncName[]={"SUMA_ADO_SelectedSecondary"};
13602 SUMA_Boolean LocalHead = NOPE;
13603
13604 if (!ado) return(-1);
13605 SUMA_LHv("Here with %d (%s), %s\n",
13606 ado->do_type, ADO_TNAME(ado), SUMA_ADO_Label(ado));
13607 switch(ado->do_type) {
13608 case SO_type: {
13609 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13610 return(SO->SelectedFaceSet);
13611 break; }
13612 case CDOM_type: {
13613 SUMA_S_Err("What gets set will depend on PR->primitive. \n"
13614 "Consider SUMA_ADO_SelectedSecondary() and ponder away.");
13615 return(-1);
13616 break; }
13617 case GDSET_type: {
13618 SUMA_DSET *dset=(SUMA_DSET *)ado;
13619 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13620 if (!GSaux) return(-1);
13621 return(GSaux->PR->iAltSel[SUMA_ENODE_0]);
13622 break; }
13623 case GRAPH_LINK_type: {
13624 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13625 SUMA_DSET *dset=NULL;
13626 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13627 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13628 SUMA_ADO_Label(ado));
13629 return(-1);
13630 }
13631 return(SUMA_ADO_SelectedSecondary((SUMA_ALL_DO *)dset));
13632 break; }
13633 case TRACT_type: {
13634 SUMA_LH("No secondary selections on tracts.");
13635 return(-1);
13636 break; }
13637 case MASK_type: {
13638 SUMA_LH("No secondary selections on masks.");
13639 return(-1);
13640 break; }
13641 case VO_type: {
13642 SUMA_LH("No secondary selections on volumes.");
13643 return(-1);
13644 break; }
13645 default:
13646 return(-1);
13647 }
13648 return(-1);
13649 }
13650
13651 /* Was what was selected a primitive of the DO that carries
13652 data ?
13653 A selected edge on a graph would return YES
13654 A selected node on a graph would return NOPE
13655 */
SUMA_is_ADO_Datum_Primitive(SUMA_ALL_DO * ado,SUMA_COLID_OFFSET_DATUM * codf)13656 SUMA_Boolean SUMA_is_ADO_Datum_Primitive(SUMA_ALL_DO *ado,
13657 SUMA_COLID_OFFSET_DATUM *codf)
13658 {
13659 static char FuncName[]={"SUMA_is_ADO_Datum_Primitive"};
13660
13661 if (!ado || !codf) return(NOPE);
13662
13663 switch (ado->do_type) {
13664 case VO_type:
13665 case CDOM_type:
13666 case SO_type:
13667 SUMA_S_Err("Function not ready to handle colid selection modes"
13668 "on surfaces or volumes");
13669 break;
13670 case GDSET_type:
13671 case GRAPH_LINK_type:
13672 if (codf->primitive && !strcmp(codf->primitive,"segments"))
13673 return(YUP);
13674 break;
13675 default:
13676 SUMA_S_Errv("Not ready to deal with type %s\n",
13677 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
13678 break;
13679 }
13680
13681 return(NOPE);
13682 }
13683
SUMA_ADO_Set_SelectedDatum(SUMA_ALL_DO * ado,int sel,void * extra,void * extra2)13684 SUMA_Boolean SUMA_ADO_Set_SelectedDatum(SUMA_ALL_DO *ado, int sel,
13685 void *extra, void *extra2)
13686 {
13687 static char FuncName[]={"SUMA_ADO_Set_SelectedDatum"};
13688 if (!ado) return(0);
13689 switch(ado->do_type) {
13690 case SO_type: {
13691 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13692 if (!SO->SurfCont) return(0);
13693 SO->SelectedNode = sel;
13694 return(1);
13695 break; }
13696 case CDOM_type: {
13697 SUMA_CIFTI_DO *co = (SUMA_CIFTI_DO *)ado;
13698 SUMA_CIFTI_SAUX *CSaux = SUMA_ADO_CSaux(ado);
13699 int it, ip, ib, l1, *iv = (int *)extra;
13700 CSaux->PR->datum_index = sel;
13701 if (extra) {
13702 SUMA_S_Err("Not ready for extra");
13703 } else {
13704 /* Will need to setup other PR fields once we decide on extras */
13705 }
13706 break; }
13707 case GDSET_type: {
13708 SUMA_DSET *dset=(SUMA_DSET *)ado;
13709 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
13710 if (!GSaux) return(0);
13711 GSaux->PR->datum_index = sel;
13712 return(1);
13713 break; }
13714 case GRAPH_LINK_type: {
13715 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13716 SUMA_DSET *dset=NULL;
13717 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13718 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13719 SUMA_ADO_Label(ado));
13720 return(0);
13721 }
13722 return(SUMA_ADO_Set_SelectedDatum((SUMA_ALL_DO *)dset, sel,
13723 extra, extra2));
13724 break; }
13725 case TRACT_type: {
13726 SUMA_TractDO *tdo = (SUMA_TractDO *)ado;
13727 SUMA_TRACT_SAUX *TSaux = SUMA_ADO_TSaux(ado);
13728 int it, ip, ib, l1, *iv = (int *)extra;
13729 TSaux->PR->datum_index = sel;
13730 if (extra) {
13731 TSaux->PR->iAltSel[SUMA_NET_BUN] = iv[SUMA_NET_BUN];
13732 TSaux->PR->iAltSel[SUMA_BUN_TRC] = iv[SUMA_BUN_TRC];
13733 TSaux->PR->iAltSel[SUMA_TRC_PNT] = iv[SUMA_TRC_PNT];
13734 TSaux->PR->iAltSel[SUMA_NET_TRC] = iv[SUMA_NET_TRC];
13735 } else {
13736 TSaux->PR->iAltSel[SUMA_NET_BUN] = TSaux->PR->iAltSel[SUMA_BUN_TRC] =
13737 TSaux->PR->iAltSel[SUMA_TRC_PNT] =
13738 TSaux->PR->iAltSel[SUMA_NET_TRC] = -1;
13739 if (tdo && tdo->net) {
13740 if (Network_1P_to_PTB(tdo->net, sel, &ip, &it, &ib, &l1)) {
13741 TSaux->PR->iAltSel[SUMA_NET_BUN] = ib;
13742 TSaux->PR->iAltSel[SUMA_BUN_TRC] = it;
13743 TSaux->PR->iAltSel[SUMA_TRC_PNT] = ip;
13744 TSaux->PR->iAltSel[SUMA_NET_TRC] = l1;
13745 }
13746 }
13747 }
13748 break; }
13749 case VO_type: {
13750 SUMA_VolumeObject *vo = (SUMA_VolumeObject *)ado;
13751 SUMA_VOL_SAUX *VSaux = SUMA_ADO_VSaux(ado);
13752 SUMA_DSET *dset=NULL;
13753 int *iv = (int *)extra, *dims=NULL, iv4[4];
13754 int iv3[3];
13755 VSaux->PR->datum_index = sel;
13756 if (extra) {
13757 VSaux->PR->iAltSel[SUMA_VOL_I] = iv[SUMA_VOL_I];
13758 VSaux->PR->iAltSel[SUMA_VOL_J] = iv[SUMA_VOL_J];
13759 VSaux->PR->iAltSel[SUMA_VOL_K] = iv[SUMA_VOL_K];
13760 VSaux->PR->iAltSel[SUMA_VOL_IJK] = iv[SUMA_VOL_IJK];
13761 if (extra2) {
13762 float *fv = (float *)extra2;
13763 if (SUMA_PLANE_NOT_SET(fv+SUMA_VOL_SLC_EQ0)) {/* a sign that there
13764 is no good plane in input
13765 Try updating current plane */
13766 if (vo &&
13767 SUMA_PLANE_IS_SET(VSaux->PR->dAltSel+SUMA_VOL_SLC_EQ0)) {
13768 iv3[0] = (int)VSaux->PR->iAltSel[SUMA_VOL_I];
13769 iv3[1] = (int)VSaux->PR->iAltSel[SUMA_VOL_J];
13770 iv3[2] = (int)VSaux->PR->iAltSel[SUMA_VOL_K];
13771 SUMA_SHIFT_PLANE_TO_P(
13772 (VSaux->PR->dAltSel+SUMA_VOL_SLC_EQ0),
13773 SUMA_VO_PointXYZ(vo, -1, iv3, NULL));
13774 } else {
13775 /* Do nothing: Nothing set in the first place */
13776 }
13777 } else {
13778 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ0] = fv[SUMA_VOL_SLC_EQ0];
13779 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ1] = fv[SUMA_VOL_SLC_EQ1];
13780 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ2] = fv[SUMA_VOL_SLC_EQ2];
13781 VSaux->PR->dAltSel[SUMA_VOL_SLC_EQ3] = fv[SUMA_VOL_SLC_EQ3];
13782 }
13783 }
13784 } else {
13785 VSaux->PR->iAltSel[SUMA_VOL_I] = VSaux->PR->iAltSel[SUMA_VOL_J] =
13786 VSaux->PR->iAltSel[SUMA_VOL_K] =
13787 VSaux->PR->iAltSel[SUMA_VOL_IJK] = -1;
13788 SUMA_MARK_PLANE_NOT_SET(VSaux->PR->dAltSel+SUMA_VOL_SLC_EQ0);
13789 if (vo && (dset = SUMA_VO_dset(vo)) &&
13790 (dims = SUMA_GetDatasetDimensions(dset)) ) {
13791 Vox1D2Vox3D(sel, dims[0], dims[0]*dims[1], iv4);
13792 VSaux->PR->iAltSel[SUMA_VOL_I] = iv4[0];
13793 VSaux->PR->iAltSel[SUMA_VOL_J] = iv4[1];
13794 VSaux->PR->iAltSel[SUMA_VOL_K] = iv4[2];
13795 VSaux->PR->iAltSel[SUMA_VOL_IJK] = sel;
13796 if (SUMA_PLANE_IS_SET(VSaux->PR->dAltSel+SUMA_VOL_SLC_EQ0)) {
13797 iv3[0] = (int)VSaux->PR->iAltSel[SUMA_VOL_I];
13798 iv3[1] = (int)VSaux->PR->iAltSel[SUMA_VOL_J];
13799 iv3[2] = (int)VSaux->PR->iAltSel[SUMA_VOL_K];
13800 SUMA_SHIFT_PLANE_TO_P((VSaux->PR->dAltSel+SUMA_VOL_SLC_EQ0),
13801 SUMA_VO_PointXYZ (vo, -1, iv3, NULL));
13802 }
13803 }
13804 }
13805 return(0);
13806 break; }
13807 case MASK_type: {
13808 SUMA_S_Warn("Not ready for mask type");
13809 return(0);
13810 break; }
13811 default:
13812 return(0);
13813 }
13814 return(0);
13815 }
13816
SUMA_ADO_N_Datum(SUMA_ALL_DO * ado)13817 int SUMA_ADO_N_Datum(SUMA_ALL_DO *ado)
13818 {
13819 return(SUMA_ADO_N_Datum_Lev(ado, SUMA_ELEM_DAT));
13820 }
13821
SUMA_ADO_N_Datum_Lev(SUMA_ALL_DO * ado,SUMA_DATUM_LEVEL dtlvl)13822 int SUMA_ADO_N_Datum_Lev(SUMA_ALL_DO *ado, SUMA_DATUM_LEVEL dtlvl)
13823 {
13824 static char FuncName[]={"SUMA_ADO_N_Datum_Lev"};
13825 if (!ado) return(-1);
13826 switch(ado->do_type) {
13827 case SO_type: {
13828 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13829 return(SO->N_Node);
13830 break; }
13831 case VO_type: {
13832 SUMA_VolumeObject *VO = (SUMA_VolumeObject *)ado;
13833 SUMA_DSET *dset = SUMA_VE_dset(VO->VE, 0);
13834 return(dset ? SDSET_NVOX(dset):-1);
13835 break; }
13836 case MASK_type: {
13837 SUMA_MaskDO *MDO = (SUMA_MaskDO *)ado;
13838 if (MDO->SO &&
13839 (MDO_IS_SURF(MDO) || MDO_IS_BOX(MDO) || MDO_IS_SPH(MDO)) ) {
13840 return(MDO->SO->N_Node);
13841 } else if (MDO_IS_BOX(MDO)) {
13842 return(MDO->N_obj*8);
13843 } else if (MDO_IS_SPH(MDO)) {
13844 SUMA_S_Err("No SO on spheres mask. Need to create your surfs");
13845 return(-1);
13846 } else if (MDO_IS_SHADOW(MDO)){
13847 return(0);
13848 } else {
13849 SUMA_S_Err("Not ready for this combo type >%s<", MDO->mtype);
13850 return(-1);
13851 }
13852 return(-1);
13853 break; }
13854 case CDOM_type: {
13855 SUMA_CIFTI_DO *CO=(SUMA_CIFTI_DO *)ado;
13856 switch(dtlvl) {
13857 int i, nn;
13858 case SUMA_ELEM_DAT: /* The maximum possible number of data
13859 assuming all domains are filled to
13860 the max */
13861 nn = 0;
13862 for (i=0; i<CO->N_subdoms; ++i) {
13863 nn += SUMA_ADO_N_Datum(SUMA_CIFTI_subdom_ado(CO,i));
13864 }
13865 return(nn);
13866 break;
13867 default:
13868 SUMA_S_Err("Should not be here, not yet at least (dtlvl = %d)",
13869 dtlvl);
13870 return(-1);
13871 break;
13872 }
13873 return(-1);
13874 break; }
13875 case GDSET_type: {
13876 SUMA_DSET *dset=(SUMA_DSET *)ado;
13877 return(SDSET_VECLEN(dset));
13878 break; }
13879 case GRAPH_LINK_type: {
13880 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13881 SUMA_DSET *dset=NULL;
13882 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13883 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13884 SUMA_ADO_Label(ado));
13885 return(-1);
13886 }
13887 return(SUMA_ADO_N_Datum((SUMA_ALL_DO *)dset));
13888 break; }
13889 case TRACT_type: {
13890 SUMA_TractDO *tdo=(SUMA_TractDO *)ado;
13891 if (tdo->N_datum == -2) { /* initialize */
13892 tdo->N_datum = Network_N_points(tdo->net, 0);
13893 }
13894 switch(dtlvl) {
13895 default:
13896 case SUMA_ELEM_DAT:
13897 return(tdo->N_datum);
13898 break;
13899 case SUMA_LEV1_DAT:
13900 return(TDO_N_TRACTS(tdo));
13901 break;
13902 case SUMA_LEV2_DAT:
13903 return(TDO_N_BUNDLES(tdo));
13904 break;
13905 }
13906 break; }
13907 default:
13908 return(-1);
13909 }
13910 return(-1);
13911 }
13912
SUMA_ADO_Max_Datum_Index(SUMA_ALL_DO * ado)13913 int SUMA_ADO_Max_Datum_Index(SUMA_ALL_DO *ado)
13914 {
13915 if (!ado) return(-1);
13916 return(SUMA_ADO_Max_Datum_Index_Lev(ado, SUMA_ELEM_DAT));
13917 }
13918
13919 /*! This function needs revisiting for all objects.
13920 Its intention should be to return the highest index
13921 of a datum, but in a sparse set, this max could very
13922 well be different from the number of elements.
13923 Check use in code and replace with the maximum of the
13924 NodeDef element if change is needed */
SUMA_ADO_Max_Datum_Index_Lev(SUMA_ALL_DO * ado,SUMA_DATUM_LEVEL dtlvl)13925 int SUMA_ADO_Max_Datum_Index_Lev(SUMA_ALL_DO *ado, SUMA_DATUM_LEVEL dtlvl)
13926 {
13927 static char FuncName[]={"SUMA_ADO_Max_Datum_Index_Lev"};
13928 if (!ado) return(-1);
13929 switch(ado->do_type) {
13930 case SO_type: {
13931 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
13932 return(SO->N_Node-1);
13933 break; }
13934 case GDSET_type: {
13935 SUMA_DSET *dset=(SUMA_DSET *)ado;
13936 if (SUMA_isGraphDset(dset)) {
13937 int mm;
13938 GDSET_MAX_EDGE_INDEX(dset,mm);
13939 return(mm);
13940 } else {
13941 return(SDSET_VECLEN(dset)-1);
13942 }
13943 break; }
13944 case CDOM_type: {
13945 SUMA_S_Err("Riddle me this");
13946 return(-1);
13947 break; }
13948 case GRAPH_LINK_type: {
13949 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
13950 SUMA_DSET *dset=NULL;
13951 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
13952 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
13953 SUMA_ADO_Label(ado));
13954 return(-1);
13955 }
13956 return(SUMA_ADO_Max_Datum_Index_Lev((SUMA_ALL_DO *)dset, dtlvl));
13957 break; }
13958 case TRACT_type: {
13959 SUMA_TractDO *tdo=(SUMA_TractDO *)ado;
13960 if (tdo->N_datum == -2) { /* initialize */
13961 tdo->N_datum = Network_N_points(tdo->net, 0);
13962 }
13963 switch(dtlvl) {
13964 default:
13965 case SUMA_ELEM_DAT:
13966 return(tdo->N_datum-1);
13967 break;
13968 case SUMA_LEV1_DAT:
13969 return(TDO_N_TRACTS(tdo)-1);
13970 break;
13971 case SUMA_LEV2_DAT:
13972 return(TDO_N_BUNDLES(tdo)-1);
13973 break;
13974 }
13975 break; }
13976 case VO_type: {
13977 SUMA_VolumeObject *VO = (SUMA_VolumeObject *)ado;
13978 SUMA_DSET *dset = SUMA_VE_dset(VO->VE, 0);
13979 return(dset ? SDSET_NVOX(dset)-1:-1);
13980 }
13981 case MASK_type: {
13982 SUMA_MaskDO *MDO = (SUMA_MaskDO *)ado;
13983 if (MDO_IS_SURF(MDO) || MDO_IS_BOX(MDO) || MDO_IS_SPH(MDO)) {
13984 if (!MDO->SO) {
13985 SUMA_S_Err("Need my SO baby");
13986 return(-1);
13987 }
13988 return(MDO->SO->N_Node-1);
13989 } else {
13990 SUMA_S_Warn("Not ready");
13991 return(-1);
13992 }
13993 }
13994 default:
13995 return(-1);
13996 }
13997 return(-1);
13998
13999 }
14000
14001
SUMA_ADO_variant(SUMA_ALL_DO * ado)14002 char * SUMA_ADO_variant(SUMA_ALL_DO *ado) {
14003 static char FuncName[]={"SUMA_ADO_variant"};
14004 if (!ado) return("");
14005 switch(ado->do_type) {
14006 default: {
14007 return("");
14008 break; }
14009 case GRAPH_LINK_type: {
14010 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
14011 if (gldo->variant) {
14012 return(gldo->variant);
14013 }
14014 return("");
14015 break; }
14016 }
14017 return("");
14018 }
14019
SUMA_ADO_Label(SUMA_ALL_DO * ado)14020 char * SUMA_ADO_Label(SUMA_ALL_DO *ado)
14021 {
14022 static char FuncName[]={"SUMA_ADO_Label"};
14023 if (!ado) return(NULL);
14024 switch(ado->do_type) {
14025 default: {
14026 return(ado->private_Label);
14027 break; }
14028 case GDSET_type:
14029 case MD_DSET_type:
14030 case ANY_DSET_type: {
14031 SUMA_DSET *dset=(SUMA_DSET *)ado;
14032 return(SDSET_LABEL(dset));
14033 break; }
14034 }
14035 return(NULL);
14036 }
14037
14038 /* Like ADO_Label, but return empty string in err */
SUMA_ADO_sLabel(SUMA_ALL_DO * ado)14039 char *SUMA_ADO_sLabel(SUMA_ALL_DO *ado) {
14040 static char FuncName[]={"SUMA_ADO_sLabel"};
14041 char *cc = SUMA_ADO_Label(ado);
14042 if (!cc) return("");
14043 else return(cc);
14044 }
14045
SUMA_ADO_CropLabel(SUMA_ALL_DO * ado,int len)14046 char * SUMA_ADO_CropLabel(SUMA_ALL_DO *ado, int len)
14047 {
14048 static char FuncName[]={"SUMA_ADO_CropLabel"};
14049 static char s[10][130];
14050 static int icall=0;
14051 char *str=NULL;
14052
14053 ++icall;
14054 if (icall > 9) icall = 0;
14055 s[icall][0]='\0';
14056
14057 if (!ado) { SUMA_S_Err("NULL input"); return(s[icall]); }
14058 if (len > 127) {
14059 SUMA_S_Warn("Label max length is 128, will truncate");
14060 len = 128;
14061 }
14062
14063 str = SUMA_truncate_string(SUMA_ADO_Label(ado), len);
14064 if (!str) return(s[icall]);
14065
14066 strcpy(s[icall], str);
14067 SUMA_ifree(str);
14068
14069 return(s[icall]);
14070 }
14071
14072 /* compare labels, NULL=NULL --> OK */
SUMA_ADO_isLabel(SUMA_ALL_DO * ado,char * lbl)14073 SUMA_Boolean SUMA_ADO_isLabel(SUMA_ALL_DO *ado, char *lbl)
14074 {
14075 static char FuncName[]={"SUMA_ADO_isLabelSUMA_ALL_DO"};
14076 char *cc=NULL;
14077
14078 if (!ado) return(NOPE);
14079 cc = SUMA_ADO_Label(ado);
14080 if (!cc) {
14081 if (!lbl) return(YUP);
14082 } else {
14083 if (!strcmp(cc, lbl)) return(YUP);
14084 }
14085 return(NOPE);
14086 }
14087
14088 /* Because of the damned SUMA_DSET * object, which needs
14089 the Linked Pointer fields on the top, never access
14090 ado->idcode_str directly, but use this function
14091 instead*/
SUMA_ADO_idcode(SUMA_ALL_DO * ado)14092 char * SUMA_ADO_idcode(SUMA_ALL_DO *ado)
14093 {
14094 static char FuncName[]={"SUMA_ADO_idcode"};
14095 if (!ado) return(NULL);
14096 switch(ado->do_type) {
14097 default: {
14098 return(ado->private_idcode_str);
14099 break; }
14100 case ANY_DSET_type:
14101 case MD_DSET_type:
14102 case GDSET_type: {/* The special beast */
14103 SUMA_DSET *dset=(SUMA_DSET *)ado;
14104 return(SDSET_ID(dset));
14105 break; }
14106 }
14107 return(NULL);
14108 }
14109
SUMA_ADO_Parent_idcode(SUMA_ALL_DO * ado)14110 char * SUMA_ADO_Parent_idcode(SUMA_ALL_DO *ado)
14111 {
14112 static char FuncName[]={"SUMA_ADO_Parent_idcode"};
14113 if (!ado) return(NULL);
14114 switch(ado->do_type) {
14115 case ANY_DSET_type:
14116 case MD_DSET_type:
14117 case GDSET_type: {/* The special beast, as a DO, it is its own parent*/
14118 SUMA_DSET *dset=(SUMA_DSET *)ado;
14119 return(SDSET_ID(dset));
14120 break; }
14121 case GRAPH_LINK_type:
14122 return(((SUMA_GraphLinkDO*)ado)->Parent_idcode_str);
14123 break;
14124 case SP_type:
14125 return(((SUMA_SphereDO*)ado)->Parent_idcode_str);
14126 break;
14127 case TRACT_type:
14128 return(((SUMA_TractDO*)ado)->Parent_idcode_str);
14129 break;
14130 case MASK_type:
14131 return(((SUMA_MaskDO*)ado)->Parent_idcode_str);
14132 break;
14133 case NBLS_type:
14134 case NBOLS_type:
14135 case NBV_type:
14136 case ONBV_type:
14137 case NBSP_type:
14138 case NBT_type:
14139 return(((SUMA_NB_DO*)ado)->Parent_idcode_str);
14140 break;
14141 case NIDO_type:
14142 if (((SUMA_NIDO*)ado)->ngr) {
14143 return(NI_get_attribute(
14144 ((SUMA_NIDO*)ado)->ngr, "Parent_idcode_str"));
14145 } else return(NULL);
14146 break;
14147 case SO_type:
14148 return(((SUMA_SurfaceObject*)ado)->LocalDomainParentID);
14149 break;
14150 case ROIdO_type:
14151 return(((SUMA_DRAWN_ROI*)ado)->Parent_idcode_str);
14152 break;
14153 case AO_type: /* those are their own parents */
14154 case PL_type:
14155 case CDOM_type:
14156 case VO_type:
14157 return(ado->private_idcode_str);
14158 break;
14159 default: {
14160 SUMA_S_Errv("Not ready for parent of %s\n",
14161 SUMA_ObjectTypeCode2ObjectTypeName(ado->do_type));
14162 return(NULL);
14163 break; }
14164
14165 }
14166 return(NULL);
14167 }
14168
14169 /*!
14170 Return the "SurfaceController" for any DO
14171 */
SUMA_ADO_Cont(SUMA_ALL_DO * ado)14172 SUMA_X_SurfCont *SUMA_ADO_Cont(SUMA_ALL_DO *ado)
14173 {
14174 static char FuncName[]={"SUMA_ADO_Cont"};
14175 SUMA_Boolean LocalHead = NOPE;
14176
14177 if (!ado) return(NULL);
14178 SUMA_LHv("Here with %d (%s), %s\n",
14179 ado->do_type, ADO_TNAME(ado), SUMA_ADO_Label(ado));
14180
14181 switch(ado->do_type) {
14182 case SO_type: {
14183 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
14184 return(SO->SurfCont);
14185 break; }
14186 case CDOM_type: {
14187 SUMA_CIFTI_SAUX * CSaux = (SUMA_CIFTI_SAUX *)SUMA_ADO_Saux(ado);
14188 if (CSaux) return(CSaux->DOCont);
14189 else return(NULL);
14190 break; }
14191 case GDSET_type: {
14192 SUMA_DSET *dset=(SUMA_DSET *)ado;
14193 SUMA_GRAPH_SAUX *GSaux = SDSET_GSAUX(dset);
14194 if (!GSaux) return(NULL);
14195 return(GSaux->DOCont);
14196 break; }
14197 case GRAPH_LINK_type: {
14198 SUMA_DSET *dset=NULL;
14199 /* get the graph dset, which is the pointer holding
14200 the controller pointer */
14201 if (!(dset = SUMA_find_GLDO_Dset((SUMA_GraphLinkDO *)ado))) {
14202 SUMA_S_Err("No graph dset for GLDO???");
14203 return(NULL);
14204 }
14205 return(SUMA_ADO_Cont((SUMA_ALL_DO *)dset));
14206 break; }
14207 case TRACT_type: {
14208 SUMA_TRACT_SAUX * TSaux = (SUMA_TRACT_SAUX *)SUMA_ADO_Saux(ado);
14209 if (TSaux) return(TSaux->DOCont);
14210 else return(NULL);
14211 break; }
14212 case MASK_type: {
14213 SUMA_MASK_SAUX * MSaux = (SUMA_MASK_SAUX *)SUMA_ADO_Saux(ado);
14214 if (MSaux) return(MSaux->DOCont);
14215 else return(NULL);
14216 break; }
14217 case VO_type: {
14218 SUMA_VOL_SAUX * VSaux = (SUMA_VOL_SAUX *)SUMA_ADO_Saux(ado);
14219 SUMA_LH("Have %p", VSaux);
14220 if (VSaux) return(VSaux->DOCont);
14221 else return(NULL);
14222 break; }
14223 default:
14224 return(NULL);
14225 }
14226 return(NULL);
14227 }
14228
SUMA_ADO_ShowCurForeOnly(SUMA_ALL_DO * ado)14229 SUMA_Boolean SUMA_ADO_ShowCurForeOnly(SUMA_ALL_DO *ado)
14230 {
14231 static char FuncName[]={"SUMA_ADO_ShowCurForeOnly"};
14232 SUMA_X_SurfCont *sc=NULL;
14233
14234 if (!ado || !(sc = SUMA_ADO_Cont(ado))) return(NOPE);
14235
14236 return(sc->ShowCurForeOnly);
14237 }
14238
SUMA_Cont_ADO(SUMA_X_SurfCont * SurfCont)14239 SUMA_ALL_DO *SUMA_Cont_ADO(SUMA_X_SurfCont *SurfCont)
14240 {
14241 static char FuncName[]={"SUMA_Cont_ADO"};
14242 if (!SurfCont) return(NULL);
14243 return(SUMA_SurfCont_GetcurDOp(SurfCont));
14244 }
14245
SUMA_Cont_SO(SUMA_X_SurfCont * SurfCont)14246 SUMA_SurfaceObject *SUMA_Cont_SO(SUMA_X_SurfCont *SurfCont)
14247 {
14248 static char FuncName[]={"SUMA_Cont_SO"};
14249 SUMA_ALL_DO *ado=NULL;
14250 if (!SurfCont) return(NULL);
14251 ado = SUMA_SurfCont_GetcurDOp(SurfCont);
14252 if (ado->do_type == SO_type)
14253 return((SUMA_SurfaceObject *)ado);
14254 return(NULL);
14255 }
14256
14257 /*!
14258 SUMA_isCurColPlane: Is this color plane the current one ?
14259 This is meant to replace if (colp == SO->SurfCont->curColPlane)
14260 so that it would work for any DO that would have a colorplane.
14261 This query will always return yes for a DSET_type DO
14262
14263 You might want to consider the alternative SUMA_isTopColPlane()
14264 which is identical to SUMA_isCurColPlane() when using the old style
14265 multiple surface controller windows, versus the modern multi-page controller
14266 */
SUMA_isCurColPlane(SUMA_OVERLAYS * cp,SUMA_ALL_DO * ado)14267 SUMA_Boolean SUMA_isCurColPlane(SUMA_OVERLAYS *cp, SUMA_ALL_DO *ado)
14268 {
14269 static char FuncName[]={"SUMA_isCurColPlane"};
14270 if (!cp || !ado) return(NOPE);
14271 if (cp == SUMA_ADO_CurColPlane(ado)) return(YUP);
14272 return(NOPE);
14273 }
14274
SUMA_isTopColPlane(SUMA_OVERLAYS * cp,SUMA_ALL_DO * ado)14275 SUMA_Boolean SUMA_isTopColPlane(SUMA_OVERLAYS *cp, SUMA_ALL_DO *ado)
14276 {
14277 static char FuncName[]={"SUMA_isTopColPlane"};
14278 SUMA_X_SurfCont *SurfCont=NULL;
14279 if (!SUMAg_CF->X->UseSameSurfCont) return(SUMA_isCurColPlane(cp, ado));
14280 else if (SUMA_isCurColPlane(cp, ado) && (SurfCont = SUMA_ADO_Cont(ado))) {
14281 /* OK, so that plane is current in some fashion,
14282 is it the top page of the uber controller ? */
14283 return(SUMA_isCurrentContPage(SUMAg_CF->X->SC_Notebook, SurfCont->Page));
14284 }
14285 return(NOPE);
14286 }
14287
14288 /* Used to be MACRO SUMA_SURFCONT_CREATED */
SUMA_isADO_Cont_Created(SUMA_ALL_DO * ado)14289 SUMA_Boolean SUMA_isADO_Cont_Created(SUMA_ALL_DO *ado)
14290 {
14291 static char FuncName[]={"SUMA_isADO_Cont_Created"};
14292 SUMA_X_SurfCont *SurfCont=NULL;
14293
14294 if ((SurfCont = SUMA_ADO_Cont(ado)) && SurfCont->TLS ) return(1);
14295
14296 return(0);
14297 }
14298
14299 /* Used to be MACRO SUMA_SURFCONT_REALIZED */
SUMA_isADO_Cont_Realized(SUMA_ALL_DO * ado)14300 SUMA_Boolean SUMA_isADO_Cont_Realized(SUMA_ALL_DO *ado)
14301 {
14302 static char FuncName[]={"SUMA_isADO_Cont_Realized"};
14303 SUMA_X_SurfCont *SurfCont=NULL;
14304
14305 if ((SurfCont = SUMA_ADO_Cont(ado)) && SurfCont->TLS
14306 && XtIsRealized(SurfCont->TLS)) return(1);
14307
14308 return(0);
14309 }
14310
14311 #define NVALS_XYZ_NODE 3
SUMA_GDSET_NodeXYZ(SUMA_DSET * dset,int node,char * variant,float * here)14312 float *SUMA_GDSET_NodeXYZ(SUMA_DSET *dset, int node, char *variant, float *here)
14313 {
14314 static char FuncName[]={"SUMA_GDSET_NodeXYZ"};
14315 static int icall=0;
14316 static float fv[10][NVALS_XYZ_NODE];
14317 int N_Node=-1, *Node_Ind=NULL, cinode = -1;
14318 float *ff=NULL, *NodeList = NULL;
14319 SUMA_Boolean LocalHead = NOPE;
14320
14321 SUMA_ENTRY;
14322
14323 if (!here) {
14324 ++icall; if (icall > 9) icall = 0;
14325 here = (float *)(&fv[icall]);
14326 }
14327
14328 SUMA_GDSET_NodeXYZ_eng(dset, node, variant, here);
14329
14330 SUMA_RETURN(here);
14331 }
14332
SUMA_GDSET_NodeXYZ_eng(SUMA_DSET * dset,int node,char * variant,float * here)14333 SUMA_Boolean SUMA_GDSET_NodeXYZ_eng(SUMA_DSET *dset, int node,
14334 char *variant, float *here)
14335 {
14336 static char FuncName[]={"SUMA_GDSET_NodeXYZ_eng"};
14337 int N_Node=-1, *Node_Ind=NULL, cinode = -1;
14338 float *ff=NULL, *NodeList = NULL;
14339 SUMA_Boolean LocalHead = NOPE;
14340
14341 SUMA_ENTRY;
14342
14343 if (!here) {
14344 SUMA_S_Err("Need output pointer");
14345 SUMA_RETURN(NOPE);
14346 }
14347 here[0] = here[1] = here[2] = 0.0;
14348
14349 if (!dset || node < 0) SUMA_RETURN(NOPE);
14350
14351 if (!(NodeList = SUMA_GDSET_NodeList(dset, &N_Node, 0, &Node_Ind, variant)))
14352 SUMA_RETURN(NOPE);
14353
14354 /* get position of node n in NodeList */
14355 cinode = SUMA_NodeIndex_To_Index(Node_Ind, N_Node, node);
14356 SUMA_LHv("Node %d is in row %d of the nodelist of %d nodes\n",
14357 node, cinode, N_Node);
14358
14359 if (cinode >= 0 && cinode < N_Node) {
14360 ff = NodeList+3*cinode;
14361 here[0] = *ff; ++ff;
14362 here[1] = *ff; ++ff;
14363 here[2] = *ff;
14364 SUMA_RETURN(YUP);
14365 } else {
14366 SUMA_LHv("Node %d not found in node list\n", node);
14367 SUMA_RETURN(NOPE);
14368 }
14369
14370 SUMA_RETURN(NOPE);
14371 }
14372
SUMA_TDO_PointXYZ(SUMA_TractDO * tdo,int point,int * BTP,float * here)14373 float *SUMA_TDO_PointXYZ(SUMA_TractDO *tdo, int point, int *BTP, float *here)
14374 {
14375 static char FuncName[]={"SUMA_TDO_PointXYZ"};
14376 static int icall=0;
14377 static float fv[10][NVALS_XYZ_NODE];
14378 int N_Node=-1, *Node_Ind=NULL, cinode = -1;
14379 float *ff=NULL, *NodeList = NULL;
14380 SUMA_Boolean LocalHead = NOPE;
14381
14382 SUMA_ENTRY;
14383
14384 if (!here) {
14385 ++icall; if (icall > 9) icall = 0;
14386 here = (float *)(&fv[icall]);
14387 }
14388
14389 SUMA_TDO_PointXYZ_eng(tdo, point, BTP, here);
14390
14391 SUMA_RETURN(here);
14392 }
14393
SUMA_TDO_PointXYZ_eng(SUMA_TractDO * tdo,int point,int * BTP,float * here)14394 SUMA_Boolean SUMA_TDO_PointXYZ_eng(SUMA_TractDO *tdo, int point,
14395 int *BTP, float *here)
14396 {
14397 static char FuncName[]={"SUMA_TDO_PointXYZ_eng"};
14398 int N_Node=-1, *Node_Ind=NULL, cinode = -1, iv3[3], nn3;
14399 float *ff=NULL, *NodeList = NULL;
14400 SUMA_Boolean LocalHead = NOPE;
14401
14402 SUMA_ENTRY;
14403
14404 if (!here) {
14405 SUMA_S_Err("Need output pointer");
14406 SUMA_RETURN(NOPE);
14407 }
14408 here[0] = here[1] = here[2] = 0.0;
14409
14410 if (!tdo || !tdo->net || point < 0) SUMA_RETURN(NOPE);
14411
14412 if (BTP && BTP[0] >= 0 && BTP[1] >= 0 && BTP[2] >=0) {
14413 iv3[SUMA_NET_BUN] = BTP[SUMA_NET_BUN];
14414 iv3[SUMA_BUN_TRC] = BTP[SUMA_BUN_TRC];
14415 iv3[SUMA_TRC_PNT] = BTP[SUMA_TRC_PNT];
14416 } else if (point >= 0) {
14417 if (!Network_1P_to_PTB(tdo->net, point,
14418 iv3+SUMA_TRC_PNT, iv3+SUMA_BUN_TRC, iv3+SUMA_NET_BUN, NULL)) {
14419 SUMA_S_Err("Bad point index");
14420 SUMA_RETURN(NOPE);
14421 }
14422 }
14423
14424 if (iv3[SUMA_NET_BUN] < TDO_N_BUNDLES(tdo)) {
14425 if (iv3[SUMA_BUN_TRC] < tdo->net->tbv[iv3[SUMA_NET_BUN]]->N_tracts) {
14426 nn3 = iv3[SUMA_TRC_PNT]*3;
14427 if (nn3 <
14428 tdo->net->tbv[iv3[SUMA_NET_BUN]]->tracts[iv3[SUMA_BUN_TRC]].N_pts3){
14429 ff =
14430 tdo->net->tbv[iv3[SUMA_NET_BUN]]->tracts[iv3[SUMA_BUN_TRC]].pts+nn3;
14431 here[0] = ff[0];
14432 here[1] = ff[1];
14433 here[2] = ff[2];
14434 SUMA_RETURN(YUP);
14435 }
14436 }
14437 } else {
14438 SUMA_LHv("Point %d (B%d T%d P%d) not found in node list\n",
14439 point, iv3[SUMA_NET_BUN], iv3[SUMA_BUN_TRC], iv3[SUMA_TRC_PNT]);
14440 SUMA_RETURN(NOPE);
14441 }
14442
14443 SUMA_RETURN(NOPE);
14444 }
14445
SUMA_VO_PointXYZ(SUMA_VolumeObject * vo,int point,int * IJK,float * here)14446 float *SUMA_VO_PointXYZ(SUMA_VolumeObject *vo, int point, int *IJK, float *here)
14447 {
14448 static char FuncName[]={"SUMA_VO_PointXYZ"};
14449 static int icall=0;
14450 static float fv[10][NVALS_XYZ_NODE];
14451 int N_Node=-1, *Node_Ind=NULL, cinode = -1;
14452 float *ff=NULL, *NodeList = NULL;
14453 SUMA_Boolean LocalHead = NOPE;
14454
14455 SUMA_ENTRY;
14456
14457 if (!here) {
14458 ++icall; if (icall > 9) icall = 0;
14459 here = (float *)(&fv[icall]);
14460 }
14461
14462 SUMA_VO_PointXYZ_eng(vo, point, IJK, here);
14463
14464 SUMA_RETURN(here);
14465 }
14466
SUMA_VO_PointXYZ_eng(SUMA_VolumeObject * vo,int point,int * IJK,float * here)14467 SUMA_Boolean SUMA_VO_PointXYZ_eng(SUMA_VolumeObject *vo, int point,
14468 int *IJK, float *here)
14469 {
14470 static char FuncName[]={"SUMA_VO_PointXYZ_eng"};
14471 int N_Node=-1, *Node_Ind=NULL, cinode = -1, iv3[3]={0,0,0}, nn3;
14472 float *ff=NULL, *NodeList = NULL;
14473 float I[3];
14474 int *dims;
14475 SUMA_DSET *dset=NULL;
14476 SUMA_Boolean LocalHead = NOPE;
14477
14478
14479 SUMA_ENTRY;
14480
14481
14482 if (!here) {
14483 SUMA_S_Err("Need output pointer");
14484 SUMA_RETURN(NOPE);
14485 }
14486 here[0] = here[1] = here[2] = 0.0;
14487
14488 if (!vo ||
14489 (point < 0 && !(IJK && IJK[0] >= 0 && IJK[1] >= 0 && IJK[2] >=0) ))
14490 SUMA_RETURN(NOPE);
14491 if (!(dset = SUMA_VO_dset(vo)) ||
14492 !(dims = SUMA_GetDatasetDimensions(dset)) ||
14493 !vo->VE || !vo->VE[0]) {
14494 SUMA_S_Err("no valid ijk_to_dicom_real") ;
14495 SUMA_RETURN(NOPE);
14496 }
14497
14498
14499 if (IJK && IJK[0] >= 0 && IJK[1] >= 0 && IJK[2] >=0) {
14500 iv3[SUMA_VOL_I] = IJK[SUMA_VOL_I];
14501 iv3[SUMA_VOL_J] = IJK[SUMA_VOL_J];
14502 iv3[SUMA_VOL_K] = IJK[SUMA_VOL_K];
14503 } else if (point >= 0 && point < SDSET_NVOX(dset)) {
14504 Vox1D2Vox3D(point, dims[0], dims[0]*dims[1], (iv3+SUMA_VOL_I));
14505 }
14506
14507 if (iv3[SUMA_VOL_I] < dims[0]) {
14508 if (iv3[SUMA_VOL_J] < dims[1]) {
14509 if (iv3[SUMA_VOL_K] < dims[2] ) {
14510 AFF44_MULT_I(here, vo->VE[0]->I2X, (iv3+SUMA_VOL_I));
14511 SUMA_RETURN(YUP);
14512 }
14513 }
14514 } else {
14515 SUMA_LHv("Point %d (I%d J%d K%d) not found in grid\n",
14516 point, iv3[SUMA_VOL_I], iv3[SUMA_VOL_J], iv3[SUMA_VOL_K]);
14517 SUMA_RETURN(NOPE);
14518 }
14519
14520 SUMA_RETURN(NOPE);
14521 }
14522
SUMA_MDO_PointXYZ(SUMA_MaskDO * mo,int point,int * IJK,float * here)14523 float *SUMA_MDO_PointXYZ(SUMA_MaskDO *mo, int point, int *IJK, float *here)
14524 {
14525 static char FuncName[]={"SUMA_MDO_PointXYZ"};
14526 static int icall=0;
14527 static float fv[10][NVALS_XYZ_NODE];
14528 int N_Node=-1, *Node_Ind=NULL, cinode = -1;
14529 float *ff=NULL, *NodeList = NULL;
14530 SUMA_Boolean LocalHead = NOPE;
14531
14532 SUMA_ENTRY;
14533
14534 if (!here) {
14535 ++icall; if (icall > 9) icall = 0;
14536 here = (float *)(&fv[icall]);
14537 }
14538
14539 SUMA_MDO_PointXYZ_eng(mo, point, IJK, here);
14540
14541 SUMA_RETURN(here);
14542 }
14543
SUMA_MDO_PointXYZ_eng(SUMA_MaskDO * mo,int point,int * IJK,float * here)14544 SUMA_Boolean SUMA_MDO_PointXYZ_eng(SUMA_MaskDO *mo, int point,
14545 int *IJK, float *here)
14546 {
14547 static char FuncName[]={"SUMA_MDO_PointXYZ_eng"};
14548 int N_Node=-1, *Node_Ind=NULL, cinode = -1, iv3[3]={0,0,0}, nn3;
14549 float *ff=NULL, *NodeList = NULL;
14550 float I[3];
14551 int *dims;
14552 SUMA_Boolean LocalHead = NOPE;
14553
14554
14555 SUMA_ENTRY;
14556
14557 if (!here) {
14558 SUMA_S_Err("Need output pointer");
14559 SUMA_RETURN(NOPE);
14560 }
14561 here[0] = here[1] = here[2] = 0.0;
14562
14563 if (!mo || point < 0) SUMA_RETURN(NOPE);
14564
14565 if (MDO_IS_BOX(mo) || MDO_IS_SPH(mo)) {
14566 if (IJK && IJK[0] >= 0 && IJK[1] >= 0) { /* obj index and point within */
14567 point = 3*IJK[0]+IJK[1];
14568 }
14569 }
14570
14571 if (point < 0 || point >= SUMA_ADO_N_Datum((SUMA_ALL_DO *)mo))
14572 SUMA_RETURN(NOPE);
14573
14574 if (!mo->SO) {
14575 SUMA_S_Err("SO no formed yet");
14576 SUMA_RETURN(NOPE);
14577 }
14578
14579 here[0] = mo->SO->NodeList[3*point];
14580 here[1] = mo->SO->NodeList[3*point+1];
14581 here[2] = mo->SO->NodeList[3*point+2];
14582
14583 SUMA_RETURN(NOPE);
14584 }
14585
14586
SUMA_GDSET_XYZ_Range(SUMA_DSET * dset,char * variant,float * here)14587 float *SUMA_GDSET_XYZ_Range(SUMA_DSET *dset, char *variant, float *here)
14588 {
14589 static char FuncName[]={"SUMA_GDSET_XYZ_Range"};
14590 static int icall=0;
14591 static float fv[10][6];
14592 float *X, *Y, *Z;
14593 int *I;
14594 double nums[6];
14595 int iicoord;
14596 NI_element *nelxyz = NULL;
14597 char *ctmp=NULL, *rs=NULL, *cs=NULL, sbuf[24];
14598 SUMA_Boolean LocalHead = NOPE;
14599
14600 SUMA_ENTRY;
14601
14602 if (!here) {
14603 ++icall; if (icall > 9) icall = 0;
14604 here = (float *)(&fv[icall]);
14605 }
14606 here[0] = here[1] = here[2] = -10.0;
14607 here[0] = here[1] = here[2] = 10.0;
14608
14609 if (!dset || !variant) SUMA_RETURN(here);
14610
14611 if (!strcmp(variant,"G3D")) {
14612 if (!(nelxyz = SUMA_FindGDsetNodeListElement(dset))) {
14613 SUMA_S_Errv("Failed to find Dset %s's NodeListElement\n",
14614 SDSET_LABEL(dset));
14615 SUMA_RETURN(here);
14616 }
14617 if (!(cs = NI_get_attribute(nelxyz,"COLMS_LABS"))) {
14618 SUMA_S_Err("What can I say?");
14619 SUMA_RETURN(here);
14620 }
14621 if (!(rs = NI_get_attribute(nelxyz,"COLMS_RANGE"))) {
14622 SUMA_S_Err("Zut alors!");
14623 SUMA_RETURN(here);
14624 }
14625
14626 /* Get the X range */
14627 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode X"))<0) {
14628 SUMA_S_Err("Failed to find X");
14629 SUMA_RETURN(here);
14630 }
14631 ctmp = SUMA_Get_Sub_String(rs, SUMA_NI_CSS, iicoord);
14632 if (SUMA_StringToNum(ctmp, (void *)nums, 4, 2) != 4) {
14633 SUMA_SL_Err("Failed to read 6 nums from range.");
14634 SUMA_RETURN(here);
14635 }
14636 here[0]=nums[0]; here[1]=nums[1];
14637
14638 /* Get the Y range */
14639 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode Y"))<0) {
14640 SUMA_S_Err("Failed to find Y");
14641 SUMA_RETURN(here);
14642 }
14643 ctmp = SUMA_Get_Sub_String(rs, SUMA_NI_CSS, iicoord);
14644 if (SUMA_StringToNum(ctmp, (void *)nums, 4, 2) != 4) {
14645 SUMA_SL_Err("Failed to read 6 nums from range.");
14646 SUMA_RETURN(here);
14647 }
14648 here[2]=nums[0]; here[3]=nums[1];
14649
14650 /* Get the Z range */
14651 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode Z"))<0) {
14652 SUMA_S_Err("Failed to find Y");
14653 SUMA_RETURN(here);
14654 }
14655 ctmp = SUMA_Get_Sub_String(rs, SUMA_NI_CSS, iicoord);
14656 if (SUMA_StringToNum(ctmp, (void *)nums, 4, 2) != 4) {
14657 SUMA_SL_Err("Failed to read 6 nums from range.");
14658 SUMA_RETURN(here);
14659 }
14660 here[4]=nums[0]; here[5]=nums[1];
14661 } else if (!strcmp(variant,"GMATRIX")) {
14662 /* This would be the range of the FrameSO */
14663 SUMA_SurfaceObject *SO = SUMA_GDSET_FrameSO(dset);
14664 if (SO) {
14665 SUMA_LHv("%f -- %f, %f -- %f, %f -- %f\n",
14666 SO->MinDims[0], SO->MaxDims[0],
14667 SO->MinDims[1], SO->MaxDims[1],
14668 SO->MinDims[2], SO->MaxDims[2]);
14669 here[0] = SO->MinDims[0]; here[1] = SO->MaxDims[0];
14670 here[2] = SO->MinDims[1]; here[3] = SO->MaxDims[2];
14671 here[4] = SO->MinDims[2]; here[5] = SO->MaxDims[2];
14672 }
14673 SUMA_RETURN(here);
14674 } else if (!strcmp(variant,"GRELIEF")) {
14675 SUMA_S_Err("Not ready yet for GRELIEF");
14676 SUMA_RETURN(here);
14677 } else if (!strncmp(variant,"TheShadow", 9)) {
14678 SUMA_LH("Who knows what evil lurks in the hearts of men?");
14679 SUMA_RETURN(here);
14680 } else {
14681 SUMA_S_Errv("Bad draw variant >%s< for %s\n",
14682 variant, SDSET_LABEL(dset));
14683 SUMA_DUMP_TRACE("Bad draw variant");
14684 SUMA_RETURN(here);
14685 }
14686
14687 SUMA_RETURN(here);
14688 }
14689
SUMA_GDSET_XYZ_Center(SUMA_DSET * dset,char * variant,float * here)14690 float *SUMA_GDSET_XYZ_Center(SUMA_DSET *dset, char *variant, float *here)
14691 {
14692 static char FuncName[]={"SUMA_GDSET_XYZ_Center"};
14693 static int icall=0;
14694 static float fv[10][3];
14695 float *X, *Y, *Z, meanI;
14696 double nums[6];
14697 int iicoord, *I;
14698 NI_element *nelxyz = NULL;
14699 char *cen=NULL, *ctmp=NULL, *rs=NULL, *cs=NULL, *stmp=NULL, sbuf[24];
14700 SUMA_Boolean LocalHead = NOPE;
14701
14702 SUMA_ENTRY;
14703
14704 if (!here) {
14705 ++icall; if (icall > 9) icall = 0;
14706 here = (float *)(&fv[icall]);
14707 }
14708 here[0] = here[1] = here[2] = 0.0;
14709
14710 if (!dset || !variant) SUMA_RETURN(here);
14711
14712 if (!strcmp(variant,"G3D")) {
14713 if (!(nelxyz = SUMA_FindGDsetNodeListElement(dset))) {
14714 SUMA_S_Errv("Failed to find Dset %s's NodeListElement\n",
14715 SDSET_LABEL(dset));
14716 SUMA_RETURN(here);
14717 }
14718 /* create and store the thing */
14719 if (!(cs = NI_get_attribute(nelxyz,"COLMS_LABS"))) {
14720 SUMA_S_Err("What can I say?");
14721 SUMA_RETURN(here);
14722 }
14723 if (!(cen = NI_get_attribute(nelxyz,"COLMS_AVG"))) {
14724 /* Stupid but have to do it for COLMS_AVG */
14725 /* Get the I col */
14726 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS,
14727 "Gnode Index"))<0) {
14728 SUMA_S_Err("Failed to find I");
14729 SUMA_RETURN(here);
14730 }
14731 I = (int *)nelxyz->vec[iicoord];
14732 SUMA_MEAN_VEC(I, nelxyz->vec_len, meanI, 0);
14733 sprintf(sbuf,"%f", meanI);
14734 if (!SUMA_Set_Sub_String(&stmp, SUMA_NI_CSS, iicoord,sbuf)) {
14735 SUMA_LHv("Failed to set substring to %s\n", stmp);
14736 SUMA_RETURN(here);
14737 }
14738
14739 /* Get the X col */
14740 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode X"))<0) {
14741 SUMA_S_Err("Failed to find X");
14742 SUMA_RETURN(here);
14743 }
14744 X = (float *)nelxyz->vec[iicoord];
14745 SUMA_MEAN_VEC(X, nelxyz->vec_len, here[0], 0);
14746 sprintf(sbuf,"%f", here[0]);
14747 if (!SUMA_Set_Sub_String(&stmp, SUMA_NI_CSS, iicoord,sbuf)) {
14748 SUMA_LHv("Failed to set substring to %s\n", stmp);
14749 SUMA_RETURN(here);
14750 }
14751
14752 /* Get the Y col */
14753 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode Y"))<0) {
14754 SUMA_S_Err("Failed to find Y");
14755 SUMA_RETURN(here);
14756 }
14757 Y = (float *)nelxyz->vec[iicoord];
14758 SUMA_MEAN_VEC(Y, nelxyz->vec_len, here[1], 0);
14759 sprintf(sbuf,"%f", here[1]);
14760 if (!SUMA_Set_Sub_String(&stmp, SUMA_NI_CSS, iicoord,sbuf)) {
14761 SUMA_LHv("Failed to set substring to %s\n", stmp);
14762 SUMA_RETURN(here);
14763 }
14764
14765 /* Get the Z col */
14766 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode Z"))<0) {
14767 SUMA_S_Err("Failed to find Z");
14768 SUMA_RETURN(here);
14769 }
14770 Z = (float *)nelxyz->vec[iicoord];
14771 SUMA_MEAN_VEC(Z, nelxyz->vec_len, here[2], 0);
14772 sprintf(sbuf,"%f", here[2]);
14773 if (!SUMA_Set_Sub_String(&stmp, SUMA_NI_CSS, iicoord,sbuf)) {
14774 SUMA_LHv("Failed to set substring to %s\n", stmp);
14775 SUMA_RETURN(here);
14776 }
14777
14778 NI_set_attribute(nelxyz,"COLMS_AVG", stmp);
14779 SUMA_LHv("Computed for %s to be: %f %f %f: (stored in %s)\n",
14780 variant, here[0], here[1], here[2], stmp);
14781 SUMA_ifree(stmp);
14782 } else {
14783 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode X"))<0) {
14784 SUMA_S_Err("Failed to find X");
14785 SUMA_RETURN(here);
14786 }
14787 ctmp = SUMA_Get_Sub_String(cen, SUMA_NI_CSS, iicoord);
14788 if (SUMA_StringToNum(ctmp, (void *)nums, 1, 2) != 1) {
14789 SUMA_SL_Err("Failed to read 1 num from range.");
14790 SUMA_RETURN(here);
14791 }
14792 here[0]=nums[0];
14793
14794 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode Y"))<0) {
14795 SUMA_S_Err("Failed to find Y");
14796 SUMA_RETURN(here);
14797 }
14798 ctmp = SUMA_Get_Sub_String(cen, SUMA_NI_CSS, iicoord);
14799 if (SUMA_StringToNum(ctmp, (void *)nums, 1, 2) != 1) {
14800 SUMA_SL_Err("Failed to read 1 num from range.");
14801 SUMA_RETURN(here);
14802 }
14803 here[1]=nums[0];
14804
14805 if ((iicoord=SUMA_NI_find_in_cs_string(cs, SUMA_NI_CSS, "Gnode Z"))<0) {
14806 SUMA_S_Err("Failed to find Z");
14807 SUMA_RETURN(here);
14808 }
14809 ctmp = SUMA_Get_Sub_String(cen, SUMA_NI_CSS, iicoord);
14810 if (SUMA_StringToNum(ctmp, (void *)nums, 1, 2) != 1) {
14811 SUMA_SL_Err("Failed to read 1 num from range.");
14812 SUMA_RETURN(here);
14813 }
14814 here[2]=nums[0];
14815 SUMA_LHv("Retrieved (%s) from header for %s to be: %f %f %f:\n",
14816 cen, variant, here[0], here[1], here[2]);
14817 }
14818 } else if (!strcmp(variant,"GMATRIX")) {
14819 SUMA_SurfaceObject *SO=SUMA_GDSET_FrameSO(dset);
14820 if (!SO) {
14821 SUMA_S_Warnv("No Frame SO for %s?\n", SDSET_LABEL(dset));
14822 SUMA_RETURN(here);
14823 }
14824 here[0] = SO->Center[0]; here[1] = SO->Center[1]; here[2] = SO->Center[2];
14825 SUMA_LHv("From SO for %s : %f %f %f:\n",
14826 variant, here[0], here[1], here[2]);
14827 SUMA_RETURN(here);
14828 } else if (!strcmp(variant,"GRELIEF")) {
14829 SUMA_S_Err("Not ready yet for GRELIEF");
14830 SUMA_RETURN(here);
14831 } else if (!strncmp(variant,"TheShadow", 9)) {
14832 SUMA_LH("Who knows what evil lurks in the hearts of men?");
14833 SUMA_RETURN(here);
14834 } else {
14835 SUMA_S_Errv("Bad draw variant >%s< for %s\n",
14836 variant, SDSET_LABEL(dset));
14837 SUMA_DUMP_TRACE("Bad draw variant");
14838 SUMA_RETURN(here);
14839 }
14840
14841 SUMA_RETURN(here);
14842 }
14843
14844 #define NVALS_XYZ_EDGE 6
SUMA_GDSET_EdgeXYZ(SUMA_DSET * dset,int isel,char * variant,float * here)14845 float *SUMA_GDSET_EdgeXYZ(SUMA_DSET *dset, int isel, char *variant, float *here)
14846 {
14847 static char FuncName[]={"SUMA_GDSET_EdgeXYZ"};
14848 static int icall=0;
14849 static float fv[10][NVALS_XYZ_EDGE];
14850
14851 SUMA_ENTRY;
14852
14853 if (!here) {
14854 ++icall; if (icall > 9) icall = 0;
14855 here = (float *)(&fv[icall]);
14856 }
14857
14858 SUMA_GDSET_EdgeXYZ_eng(dset, isel, variant, here);
14859
14860 SUMA_RETURN(here);
14861 }
14862
SUMA_GDSET_EdgeXYZ_eng(SUMA_DSET * dset,int isel,char * variant,float * here)14863 SUMA_Boolean SUMA_GDSET_EdgeXYZ_eng(SUMA_DSET *dset, int isel,
14864 char *variant, float *here)
14865 {
14866 static char FuncName[]={"SUMA_GDSET_EdgeXYZ_eng"};
14867 int N_Node=-1, *ind0=NULL, *ind1=NULL, *inde=NULL, i1=-1, i2=0;
14868 SUMA_GraphLinkDO *gldo=NULL;
14869 SUMA_Boolean LocalHead = NOPE;
14870
14871 SUMA_ENTRY;
14872
14873 if (!here) {
14874 SUMA_S_Err("Must give me a pointer for results");
14875 SUMA_RETURN(NOPE);
14876 }
14877
14878 SUMA_LHv("Looking for XYZ of edge ID %d, variant %s on dset %s\n",
14879 isel, variant, SDSET_LABEL(dset));
14880
14881 here[0] = here[1] = here[2] =
14882 here[3] = here[4] = here[5] = 0.0;
14883
14884 if (!dset || isel < 0) SUMA_RETURN(NOPE);
14885 if (!variant) {
14886 SUMA_S_Err("No XYZ on dset without variant");
14887 SUMA_RETURN(NOPE);
14888 }
14889
14890 if (isel <= SUMA_GDSET_Max_Edge_Index(dset)) {
14891 SDSET_EDGE_NODE_INDEX_COLS(dset, inde, ind0, ind1);
14892 if (!ind0 || !ind1 || !inde) {
14893 SUMA_LH("No explicit node idexing information");
14894 SUMA_RETURN(NOPE);
14895 }
14896 if (inde[isel] != isel) {
14897 SUMA_LHv("Hard way for segment index %d: i1=%d, i2 = %d\n",
14898 isel, i1, i2);
14899 /* Fetch the indices of the nodes forming the edge */
14900 if (!SUMA_GDSET_SegIndexToPoints(dset, isel, &i1, &i2, NULL)) {
14901 SUMA_S_Errv("Failed to locate nodes of edge %d on dset %s\n",
14902 isel, SDSET_LABEL(dset));
14903 SUMA_RETURN(NOPE);
14904 }
14905 } else { /* the easy way */
14906 SUMA_LHv("Easy way: inde[%d]=%d [%d %d]\n",
14907 isel, inde[isel], ind0[isel], ind1[isel]);
14908 i1 = ind0[isel];
14909 i2 = ind1[isel];
14910 }
14911
14912 if (i1 < 0 || i2 < 0) SUMA_RETURN(NOPE);
14913
14914 if (!strcmp(variant,"GMATRIX")) {
14915 SUMA_LHv("Here looking for XYZ of %d %d\n", i1, i2);
14916 /* Get an edge coord based on the matrix being displayed */
14917 if (SUMA_GDSET_edgeij_to_GMATRIX_XYZ(dset, i1, i2, here, 0)) {
14918 /* duplicate the 1st three vals to make results consistent
14919 with G3D case */
14920 here[3] = here[0]; here[4]=here[1]; here[5]=here[2];
14921 } else {
14922 SUMA_S_Err("Should this happen ?");
14923 SUMA_RETURN(NOPE);
14924 }
14925 } else { /* the 3D one */
14926 if (!(SUMA_GDSET_NodeXYZ_eng(dset, i1, variant, here)))
14927 SUMA_RETURN(NOPE);
14928 if (!(SUMA_GDSET_NodeXYZ(dset, i2, variant, here+3)))
14929 SUMA_RETURN(NOPE);
14930 }
14931
14932 SUMA_LHv("Selection request for edge %d [%d %d] variant %s\n"
14933 "here=[%f %f %f %f %f %f]\n",
14934 isel, i1, i2, variant,
14935 here[0], here[1], here[2], here[3], here[4], here[5]);
14936 } else {
14937 SUMA_LHv("isel=%d, veclen=%d, max edge index %d\n",
14938 isel, SDSET_VECLEN(dset), SUMA_GDSET_Max_Edge_Index(dset));
14939 }
14940
14941 SUMA_RETURN(YUP);
14942 }
14943
SUMA_GDSET_FrameSO(SUMA_DSET * dset)14944 SUMA_SurfaceObject *SUMA_GDSET_FrameSO(SUMA_DSET *dset)
14945 {
14946 static char FuncName[]={"SUMA_GDSET_FrameSO"};
14947 SUMA_GRAPH_SAUX *GSaux = NULL;
14948
14949 SUMA_ENTRY;
14950
14951 if (!(GSaux = SDSET_GSAUX(dset))) {
14952 SUMA_S_Err("Cannot create an SO this early, or dset is not graph");
14953 SUMA_RETURN(NULL);
14954 }
14955 if (!GSaux->nido && !(GSaux->nido = SUMA_GDSET_matrix_nido(dset))) {
14956 SUMA_S_Err("No milk!");
14957 SUMA_DUMP_TRACE("%s", FuncName);
14958 SUMA_RETURN(NULL);
14959 }
14960
14961 if (!GSaux->FrameSO) {
14962 /* need to make one */
14963 GSaux->FrameSO = SUMA_Surface_Of_NIDO_Matrix(GSaux->nido);
14964 }
14965
14966 SUMA_RETURN(GSaux->FrameSO);
14967 }
14968
SUMA_GDSET_GMATRIX_Aff(SUMA_DSET * dset,double Aff[4][4],int I2X)14969 SUMA_Boolean SUMA_GDSET_GMATRIX_Aff(SUMA_DSET *dset, double Aff[4][4], int I2X)
14970 {
14971 static char FuncName[]={"SUMA_GDSET_GMATRIX_Aff"};
14972 SUMA_GRAPH_SAUX *GSaux=NULL;
14973 double V[12];
14974 SUMA_Boolean LocalHead = NOPE;
14975
14976 SUMA_ENTRY;
14977
14978 if (!(GSaux = SDSET_GSAUX(dset)) || !GSaux->nido) SUMA_RETURN(NOPE);
14979
14980 if (I2X) {
14981 NI_GET_DOUBLEv(GSaux->nido->ngr, "ijk_to_dicom_real", V, 12, LocalHead);
14982 if (!NI_GOT) {
14983 SUMA_S_Err("No ijk_to_dicom_real");
14984 SUMA_RETURN(NOPE);
14985 }
14986 V12_TO_AFF44(Aff, V);
14987 } else {
14988 NI_GET_DOUBLEv(GSaux->nido->ngr, "dicom_real_to_ijk", V, 12, LocalHead);
14989 if (!NI_GOT) {
14990 SUMA_S_Err("No dicom_real_to_ijk");
14991 SUMA_RETURN(NOPE);
14992 }
14993 V12_TO_AFF44(Aff, V);
14994 }
14995
14996 SUMA_RETURN(YUP);
14997 }
14998 /* Return coordinates of a datum, failure returns 0 0 0
14999 Note that what a datum represents will differ
15000 depending on the object*/
15001 #define NVALS_XYZ_DATUM 6
SUMA_ADO_DatumXYZ(SUMA_ALL_DO * ado,int isel,char * variant)15002 float *SUMA_ADO_DatumXYZ(SUMA_ALL_DO *ado, int isel, char *variant)
15003 {
15004 static char FuncName[]={"SUMA_ADO_DatumXYZ"};
15005 static int icall=0;
15006 static float fv[10][NVALS_XYZ_DATUM];
15007
15008 SUMA_ENTRY;
15009
15010 ++icall; if (icall > 9) icall = 0;
15011 fv[icall][0] = fv[icall][1] = fv[icall][2] =
15012 fv[icall][3] = fv[icall][4] = fv[icall][5] = 0.0;
15013
15014 if (!ado || isel < 0) SUMA_RETURN(fv[icall]);
15015 switch (ado->do_type) {
15016 case SO_type: {
15017 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
15018 if (SO->NodeList && isel < SO->N_Node) {
15019 float *ff = SO->NodeList+SO->NodeDim*isel;
15020 fv[icall][0] = *ff;++ff;
15021 if (SO->NodeDim > 1) fv[icall][1] = *ff;++ff;
15022 if (SO->NodeDim > 2) fv[icall][2] = *ff;++ff;
15023 }
15024 break; }
15025 case CDOM_type: {
15026 SUMA_S_Err("Not ready: 1- find domain from index.\n"
15027 " 2- find index on domain\n"
15028 " 3- return XYZ\n");
15029 return(NULL);
15030 break;
15031 }
15032 case GDSET_type: {
15033 SUMA_DSET *dset=(SUMA_DSET *)ado;
15034 if (!variant) {
15035 SUMA_S_Err("No XYZ without variant on dsets");
15036 } else {
15037 return(SUMA_GDSET_EdgeXYZ(dset, isel, variant,
15038 (float *)(&fv[icall])));
15039 }
15040 break; }
15041 case GRAPH_LINK_type: {
15042 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
15043 SUMA_DSET *dset=NULL;
15044 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
15045 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
15046 SUMA_ADO_Label(ado));
15047 SUMA_RETURN(fv[icall]);
15048 }
15049 if (!variant) variant = SUMA_ADO_variant(ado);
15050 return(SUMA_GDSET_EdgeXYZ(dset, isel, variant, (float *)(&fv[icall])));
15051 break; }
15052 default:
15053 /* no coords */
15054 break;
15055 }
15056
15057 SUMA_RETURN(fv[icall]);
15058 }
15059
15060 /*! Return the local domain parent for an ado */
SUMA_ADO_LDP(SUMA_ALL_DO * ado)15061 char *SUMA_ADO_LDP(SUMA_ALL_DO *ado)
15062 {
15063 static char FuncName[]={"SUMA_ADO_LDP"};
15064
15065 if (!ado) return(NULL);
15066 switch (ado->do_type) {
15067 case SO_type: {
15068 SUMA_SurfaceObject *SO=(SUMA_SurfaceObject *)ado;
15069 return(SO->LocalDomainParentID);
15070 break; }
15071 case ANY_DSET_type:
15072 case MD_DSET_type:
15073 case GDSET_type: {
15074 SUMA_DSET *dset = (SUMA_DSET *)ado;
15075 return(SDSET_ID(dset)); /* itself */
15076 break; }
15077 case GRAPH_LINK_type: {
15078 SUMA_GraphLinkDO *gldo=(SUMA_GraphLinkDO *)ado;
15079 SUMA_DSET *dset=NULL;
15080 if (!(dset=SUMA_find_GLDO_Dset(gldo))) {
15081 SUMA_S_Errv("Failed to find dset for gldo %s!!!\n",
15082 SUMA_ADO_Label(ado));
15083 return(NULL);
15084 }
15085 return(SUMA_ADO_LDP((SUMA_ALL_DO *)dset));
15086 break; }
15087 case CDOM_type: {
15088 SUMA_S_Warn("Not sure if this will apply yet.");
15089 return(NULL);
15090 break; }
15091 default:
15092 return(NULL);
15093 }
15094 return(NULL);
15095 }
15096
SUMA_ADO_CSaux(SUMA_ALL_DO * ado)15097 SUMA_CIFTI_SAUX *SUMA_ADO_CSaux(SUMA_ALL_DO *ado)
15098 {
15099 static char FuncName[]={"SUMA_ADO_CSaux"};
15100
15101 if (!ado) return(NULL);
15102 switch (ado->do_type) {
15103 case CDOM_type:
15104 return((SUMA_CIFTI_SAUX *)SUMA_ADO_Saux(ado));
15105 break;
15106 default:
15107 return(NULL);
15108 }
15109 return(NULL);
15110 }
15111
SUMA_ADO_GSaux(SUMA_ALL_DO * ado)15112 SUMA_GRAPH_SAUX *SUMA_ADO_GSaux(SUMA_ALL_DO *ado)
15113 {
15114 static char FuncName[]={"SUMA_ADO_GSaux"};
15115
15116 if (!ado) return(NULL);
15117 switch (ado->do_type) {
15118 case GDSET_type:
15119 case GRAPH_LINK_type:
15120 return((SUMA_GRAPH_SAUX *)SUMA_ADO_Saux(ado));
15121 break;
15122 default:
15123 return(NULL);
15124 }
15125 return(NULL);
15126 }
15127
SUMA_ADO_TSaux(SUMA_ALL_DO * ado)15128 SUMA_TRACT_SAUX *SUMA_ADO_TSaux(SUMA_ALL_DO *ado)
15129 {
15130 static char FuncName[]={"SUMA_ADO_TSaux"};
15131
15132 if (!ado) return(NULL);
15133 switch (ado->do_type) {
15134 case TRACT_type:
15135 return((SUMA_TRACT_SAUX *)SUMA_ADO_Saux(ado));
15136 break;
15137 default:
15138 return(NULL);
15139 }
15140 return(NULL);
15141 }
15142
SUMA_ADO_MSaux(SUMA_ALL_DO * ado)15143 SUMA_MASK_SAUX *SUMA_ADO_MSaux(SUMA_ALL_DO *ado)
15144 {
15145 static char FuncName[]={"SUMA_ADO_MSaux"};
15146
15147 if (!ado) return(NULL);
15148 switch (ado->do_type) {
15149 case MASK_type:
15150 return((SUMA_MASK_SAUX *)SUMA_ADO_Saux(ado));
15151 break;
15152 default:
15153 return(NULL);
15154 }
15155 return(NULL);
15156 }
15157
SUMA_ADO_SSaux(SUMA_ALL_DO * ado)15158 SUMA_SURF_SAUX *SUMA_ADO_SSaux(SUMA_ALL_DO *ado)
15159 {
15160 static char FuncName[]={"SUMA_SURF_SAUX"};
15161
15162 if (!ado) return(NULL);
15163 switch (ado->do_type) {
15164 case SO_type:
15165 return((SUMA_SURF_SAUX *)SUMA_ADO_Saux(ado));
15166 break;
15167 default:
15168 return(NULL);
15169 }
15170 return(NULL);
15171 }
15172
SUMA_ADO_VSaux(SUMA_ALL_DO * ado)15173 SUMA_VOL_SAUX *SUMA_ADO_VSaux(SUMA_ALL_DO *ado)
15174 {
15175 static char FuncName[]={"SUMA_ADO_VSaux"};
15176
15177 if (!ado) return(NULL);
15178 switch (ado->do_type) {
15179 case VO_type:
15180 return((SUMA_VOL_SAUX *)SUMA_ADO_Saux(ado));
15181 break;
15182 default:
15183 return(NULL);
15184 }
15185 return(NULL);
15186 }
15187
SUMA_ADO_Saux(SUMA_ALL_DO * ado)15188 void *SUMA_ADO_Saux(SUMA_ALL_DO *ado)
15189 {
15190 static char FuncName[]={"SUMA_ADO_Saux"};
15191
15192 if (!ado) return(NULL);
15193 switch (ado->do_type) {
15194 case SO_type:
15195 return((void *)SDO_SSAUX((SUMA_SurfaceObject *)ado));
15196 break;
15197 case CDOM_type:
15198 return((void *)CDO_CSAUX((SUMA_CIFTI_DO *)ado));
15199 break;
15200 case GDSET_type:
15201 return((void *)SDSET_GSAUX((SUMA_DSET *)ado));
15202 break;
15203 case GRAPH_LINK_type: {
15204 SUMA_DSET *dset = SUMA_find_GLDO_Dset((SUMA_GraphLinkDO *)ado);
15205 return((void *)SUMA_ADO_Saux((SUMA_ALL_DO *)dset));
15206 break; }
15207 case TRACT_type: {
15208 return((void *)TDO_TSAUX((SUMA_TractDO *)ado));
15209 break; }
15210 case MASK_type: {
15211 return((void *)MDO_MSAUX((SUMA_MaskDO *)ado));
15212 break; }
15213 case VO_type: {
15214 return((void *)VDO_VSAUX((SUMA_VolumeObject *)ado));
15215 break; }
15216 default:
15217 return(NULL);
15218 }
15219 return(NULL);
15220 }
15221
SUMA_ADO_Dset(SUMA_ALL_DO * ado)15222 SUMA_DSET *SUMA_ADO_Dset(SUMA_ALL_DO *ado)
15223 {
15224 static char FuncName[]={"SUMA_ADO_Dset"};
15225
15226 if (!ado) return(NULL);
15227 switch (ado->do_type) {
15228 case SO_type:
15229 return(NULL);
15230 break;
15231 case CDOM_type:
15232 SUMA_S_Note("Decide what should be done here. A CDOM is created from a "
15233 "certain CIFTI dataset that one could return. However it "
15234 "is envisioned that multiple CIFTI datasets can share the "
15235 "same CIFTI domain so then which dset to return in that "
15236 "instance. For now, let us return NULL");
15237 return(NULL);
15238 break;
15239 case ANY_DSET_type:
15240 case MD_DSET_type:
15241 case GDSET_type:
15242 return((SUMA_DSET *)ado);
15243 break;
15244 case GRAPH_LINK_type: {
15245 return(SUMA_find_GLDO_Dset((SUMA_GraphLinkDO *)ado));
15246 break; }
15247 default:
15248 return(NULL);
15249 }
15250 return(NULL);
15251 }
15252
15253 /*!
15254 How many and which DOs are anatomically correct ?
15255 */
SUMA_Anatomical_DOs(SUMA_DO * dov,int N_dov,int * rdov)15256 int SUMA_Anatomical_DOs(SUMA_DO *dov, int N_dov, int *rdov)
15257 {
15258 static char FuncName[]={"SUMA_Anatomical_DOs"};
15259 SUMA_ALL_DO *ado=NULL;
15260 int ii, N=0;
15261
15262 if (!dov) {
15263 dov = SUMAg_DOv;
15264 N_dov = SUMAg_N_DOv;
15265 }
15266 for (ii=0; ii<N_dov; ++ii) {
15267 ado = (SUMA_ALL_DO *)dov[ii].OP;
15268 if (SUMA_ADO_is_AnatCorrect(ado)) {
15269 ++N;
15270 if (rdov) rdov[N-1] = ii;
15271 }
15272 }
15273
15274 return(N);
15275
15276 }
15277