Doxygen Source Code Documentation
afni_sumafunc.c File Reference
#include "afni.h"Go to the source code of this file.
Defines | |
| #define | MAKE_SURF_ROW(ii) |
Functions | |
| int | AFNI_vnlist_func_overlay (Three_D_View *im3d, int ks, SUMA_irgba **map, int *nvused) |
| int | AFNI_find_closest_node (int num_ixyz, SUMA_ixyz *ixyz, float xtarg, float ytarg, float ztarg, float xbot, float xtop, float ybot, float ytop, float zbot, float ztop) |
| void | AFNI_surf_done_CB (Widget, XtPointer, XtPointer) |
| void | AFNI_surf_redraw_CB (MCW_arrowval *, XtPointer) |
| AFNI_make_surface_widgets (Three_D_View *, int) | |
| void | AFNI_surf_bbox_CB (Widget, XtPointer, XtPointer) |
| void | AFNI_update_surface_widgets (Three_D_View *im3d) |
| void | AFNI_update_all_surface_widgets (THD_session *sess) |
| void | AFNI_choose_surface_CB (Widget w, XtPointer cd, XtPointer cbs) |
Define Documentation
|
|
Make the widgets for one row of the surface control panel. The row itself will not be managed at this time; that comes later. Definition at line 454 of file afni_sumafunc.c. Referenced by AFNI_make_surface_widgets(), and AFNI_update_surface_widgets(). |
Function Documentation
|
||||||||||||||||
|
Callback for Switch Surface pushbutton [19 Aug 2002]. -------------------------------------------------------------------------- Definition at line 775 of file afni_sumafunc.c. References AFNI_make_surface_widgets(), AFNI_update_surface_widgets(), ENTRY, IM3D_OPEN, AFNI_surface_widgets::rowcol, Three_D_View::ss_now, THD_session::su_num, AFNI_viewing_widgets::swid, AFNI_widget_set::view, Three_D_View::vwid, WAIT_for_window, and AFNI_surface_widgets::wtop.
00776 {
00777 Three_D_View *im3d = (Three_D_View *) cd ;
00778 AFNI_surface_widgets *swid ;
00779 int num , ii , nwid,nall ;
00780
00781 ENTRY("AFNI_choose_surface_CB") ;
00782
00783 if( !IM3D_OPEN(im3d) || im3d->ss_now == NULL ) EXRETURN ; /* bad */
00784
00785 num = im3d->ss_now->su_num ;
00786 swid = im3d->vwid->view->swid ;
00787
00788 /* no surfaces ==> nothing to do */
00789
00790 if( num == 0 ) EXRETURN ;
00791
00792 /* make widgets? */
00793
00794 if( swid == NULL ){
00795 AFNI_make_surface_widgets(im3d,num) ;
00796 swid = im3d->vwid->view->swid ;
00797 }
00798
00799 /* make control panel visible, if it isn't already */
00800
00801 XtMapWidget( swid->wtop ) ;
00802 XRaiseWindow( XtDisplay(swid->wtop), XtWindow(swid->wtop) ) ;
00803
00804 /* put proper labels on widgets, etc. */
00805
00806 AFNI_update_surface_widgets(im3d) ;
00807
00808 /* Mac OS X mangles up the widgets on first display,
00809 so unmanage and remanage them -- this solves that problem */
00810
00811 WAIT_for_window( swid->rowcol ) ;
00812 XtUnmanageChild( swid->rowcol ) ;
00813 WAIT_for_window( swid->rowcol ) ;
00814 XtManageChild ( swid->rowcol ) ;
00815
00816 /* wait for user to press some button */
00817
00818 EXRETURN ;
00819 }
|
|
||||||||||||||||||||||||||||||||||||||||||||||||
|
Find node in surface closest to given DICOM vector, with limitation that node's x is in range xbot..xtop, etc. Return value is node index into ixyz array (not necessarily node ID), -1 if none is found. ------------------------------------------------------------------------- Definition at line 409 of file afni_sumafunc.c. References ENTRY, RETURN, SUMA_ixyz::x, SUMA_ixyz::y, and SUMA_ixyz::z. Referenced by AFNI_get_xhair_node().
00414 {
00415 int ii , ibest=-1 ;
00416 float x,y,z , dbest, d ;
00417
00418 ENTRY("AFNI_find_closest_node") ;
00419
00420 if( num_ixyz <= 0 || ixyz == NULL ) RETURN(-1) ; /* bad inputs */
00421
00422 /* if search ranges are incoherent, make them very wide */
00423
00424 if( xbot >= xtop ){ xbot = -WAY_BIG; xtop = WAY_BIG; }
00425 if( ybot >= ytop ){ ybot = -WAY_BIG; ytop = WAY_BIG; }
00426 if( zbot >= ztop ){ zbot = -WAY_BIG; ztop = WAY_BIG; }
00427
00428 for( ii=0 ; ii < num_ixyz ; ii++ ){
00429 x = ixyz[ii].x; y = ixyz[ii].y; z = ixyz[ii].z;
00430 if( x < xbot || x > xtop ||
00431 y < ybot || y > ytop ||
00432 z < zbot || z > ztop ) continue ; /* outside box */
00433
00434 d = (xtarg-x)*(xtarg-x) + (ytarg-y)*(ytarg-y) + (ztarg-z)*(ztarg-z) ;
00435 if( ibest < 0 || d < dbest ){ ibest = ii; dbest = d; }
00436 }
00437
00438 RETURN(ibest) ;
00439 }
|
|
||||||||||||
|
Make surface widgets for an AFNI controller [19 Aug 2002]. Called only once to create the initial set of widgets. AFNI_update_surface_widgets() is used to update the list when something changes. -------------------------------------------------------------------------- Definition at line 513 of file afni_sumafunc.c. References AFNI_controller_label(), AFNI_surf_done_CB(), AFNI_surf_redraw_CB(), AFNI_surface_widgets::boxsize_av, Three_D_View::dc, DC_find_closest_overlay_color(), DC_yokify(), MCW_DC::display, AFNI_surface_widgets::done_pb, getenv(), AFNI_surface_widgets::linewidth_av, MAKE_SURF_ROW, MCW_reghelp_children(), MCW_reghint_children(), MCW_register_hint(), MCW_set_widget_bg(), MIN, myXtNew, AFNI_surface_widgets::nall, MCW_DCOV::ncol_ov, new_MCW_optmenu(), AFNI_surface_widgets::nrow, MCW_DC::ovc, AFNI_surface_widgets::rowcol, AFNI_surface_widgets::surf_bbox, AFNI_surface_widgets::surf_ledg_av, AFNI_surface_widgets::surf_line_av, AFNI_surface_widgets::surf_node_av, AFNI_surface_widgets::surf_rc, AFNI_viewing_widgets::swid, AFNI_surface_widgets::top_lab, AFNI_widget_set::view, Three_D_View::vwid, MCW_arrowval::wrowcol, AFNI_surface_widgets::wtop, and XtCalloc. Referenced by AFNI_choose_surface_CB().
00514 {
00515 AFNI_surface_widgets *swid ;
00516 Widget ww , rc ;
00517 XmString xstr ;
00518 char str[32] , *eee ;
00519 int ii , line_col, box_col ;
00520
00521 im3d->vwid->view->swid = swid = myXtNew( AFNI_surface_widgets ) ;
00522
00523 /* shell to hold it all */
00524
00525 sprintf(str,"AFNI Surface Controls %s",AFNI_controller_label(im3d)) ;
00526
00527 swid->wtop = XtVaAppCreateShell(
00528 "AFNI" , "AFNI" ,
00529 topLevelShellWidgetClass , im3d->dc->display ,
00530 XmNallowShellResize , True ,
00531 XmNtitle , str ,
00532 XmNmappedWhenManaged , False , /* manage manually */
00533 XmNdeleteResponse , XmDO_NOTHING , /* deletion handled below */
00534 NULL ) ;
00535 DC_yokify( swid->wtop , im3d->dc ) ;
00536
00537 XtVaSetValues( swid->wtop ,
00538 XmNmwmDecorations , MWM_DECOR_ALL | MWM_DECOR_MAXIMIZE ,
00539 NULL ) ;
00540
00541 XmAddWMProtocolCallback( /* make "Close" window menu work */
00542 swid->wtop ,
00543 XmInternAtom( im3d->dc->display , "WM_DELETE_WINDOW" , False ) ,
00544 AFNI_surf_done_CB , im3d ) ;
00545
00546 /* vertical rowcol to hold it all */
00547
00548 swid->rowcol =
00549 XtVaCreateWidget(
00550 "dialog" , xmRowColumnWidgetClass , swid->wtop ,
00551 XmNpacking , XmPACK_TIGHT ,
00552 XmNorientation , XmVERTICAL ,
00553 XmNtraversalOn , False ,
00554 NULL ) ;
00555
00556 /* top label to say what session we are dealing with */
00557
00558 xstr = XmStringCreateLtoR( "xxxxxxxxxAxxxxxxxxxAxxxxxxxxxAxxxxxxxxxAxxxxxxxxxA [x] " ,
00559 XmFONTLIST_DEFAULT_TAG ) ;
00560 swid->top_lab = XtVaCreateManagedWidget(
00561 "dialog" , xmLabelWidgetClass , swid->rowcol ,
00562 XmNrecomputeSize , False ,
00563 XmNlabelString , xstr ,
00564 XmNtraversalOn , False ,
00565 NULL ) ;
00566 XmStringFree(xstr) ;
00567
00568 /* Separator from other widgets */
00569
00570 (void) XtVaCreateManagedWidget( "dialog", xmSeparatorWidgetClass,swid->rowcol,
00571 XmNseparatorType , XmSHADOW_ETCHED_IN ,
00572 XmNshadowThickness , 5 ,
00573 NULL ) ;
00574
00575 /* horiz rowcol for top controls [23 Feb 2003] */
00576
00577 rc = XtVaCreateWidget(
00578 "dialog" , xmRowColumnWidgetClass , swid->rowcol ,
00579 XmNpacking , XmPACK_TIGHT ,
00580 XmNorientation , XmHORIZONTAL ,
00581 XmNtraversalOn , False ,
00582 NULL ) ;
00583
00584 /* boxsize control [23 Feb 2003] */
00585
00586 swid->boxsize_av = new_MCW_optmenu( rc , "BoxSize" ,
00587 1,19,2,0 ,
00588 AFNI_surf_redraw_CB , im3d ,
00589 NULL , NULL ) ;
00590 MCW_reghint_children( swid->boxsize_av->wrowcol ,
00591 "Size of boxes drawn at nodes" ) ;
00592 MCW_reghelp_children( swid->boxsize_av->wrowcol ,
00593 "This sets the size of the\n"
00594 "boxes used to draw the\n"
00595 "surface nodes that are\n"
00596 "in the current slice volume." ) ;
00597
00598 /* linewidth control [23 Feb 2003] */
00599
00600 (void) XtVaCreateManagedWidget( "dialog", xmSeparatorWidgetClass, rc ,
00601 XmNorientation , XmVERTICAL ,
00602 XmNseparatorType , XmDOUBLE_LINE ,
00603 NULL ) ;
00604
00605 swid->linewidth_av = new_MCW_optmenu( rc , "LineWidth" ,
00606 0,19,0,0 ,
00607 AFNI_surf_redraw_CB , im3d ,
00608 NULL , NULL ) ;
00609 MCW_reghint_children( swid->linewidth_av->wrowcol ,
00610 "Width of lines drawn for surface" ) ;
00611 MCW_reghelp_children( swid->linewidth_av->wrowcol ,
00612 "This sets the thickness of\n"
00613 "the lines used to draw the\n"
00614 "intersection of the surface\n"
00615 "with the slice plane." ) ;
00616
00617
00618 /* Done button */
00619
00620 (void) XtVaCreateManagedWidget( "dialog", xmSeparatorWidgetClass, rc ,
00621 XmNorientation , XmVERTICAL ,
00622 XmNseparatorType , XmDOUBLE_LINE ,
00623 NULL ) ;
00624
00625 xstr = XmStringCreateLtoR( "Done" , XmFONTLIST_DEFAULT_TAG ) ;
00626 swid->done_pb =
00627 XtVaCreateManagedWidget(
00628 "dialog" , xmPushButtonWidgetClass , rc ,
00629 XmNlabelString , xstr ,
00630 XmNtraversalOn , False ,
00631 NULL ) ;
00632 XmStringFree(xstr) ;
00633 XtAddCallback( swid->done_pb, XmNactivateCallback, AFNI_surf_done_CB, im3d );
00634 MCW_set_widget_bg( swid->done_pb, MCW_hotcolor(swid->done_pb), 0 ) ;
00635 MCW_register_hint( swid->done_pb, "Close window" ) ;
00636
00637 XtManageChild(rc) ;
00638
00639 /* Separator from other widgets */
00640
00641 (void) XtVaCreateManagedWidget( "dialog", xmSeparatorWidgetClass,swid->rowcol,
00642 XmNseparatorType , XmSHADOW_ETCHED_IN ,
00643 XmNshadowThickness , 5 ,
00644 NULL ) ;
00645
00646 /* Now create rows of widgets to control the surfaces */
00647
00648 swid->nall = num ;
00649 swid->nrow = 0 ; /* none are managed at this time */
00650
00651 swid->surf_rc = (Widget *) XtCalloc( num , sizeof(Widget) ) ;
00652 swid->surf_bbox = (MCW_bbox **) XtCalloc( num , sizeof(MCW_bbox *) ) ;
00653 swid->surf_node_av = (MCW_arrowval **) XtCalloc( num , sizeof(MCW_arrowval *) ) ;
00654 swid->surf_line_av = (MCW_arrowval **) XtCalloc( num , sizeof(MCW_arrowval *) ) ;
00655 swid->surf_ledg_av = (MCW_arrowval **) XtCalloc( num , sizeof(MCW_arrowval *) ) ;
00656
00657 eee = getenv( "AFNI_SUMA_LINECOLOR" ) ;
00658 line_col = DC_find_closest_overlay_color( im3d->dc, eee ) ;
00659 if( line_col < 0 ) line_col = MIN(6,im3d->dc->ovc->ncol_ov-1) ;
00660
00661 eee = getenv( "AFNI_SUMA_BOXCOLOR" ) ;
00662 box_col = DC_find_closest_overlay_color( im3d->dc, eee ) ;
00663 if( box_col < 0 ) box_col = 0 ;
00664
00665 for( ii=0 ; ii < num ; ii++ ){
00666 MAKE_SURF_ROW(ii) ;
00667 }
00668
00669 XtManageChild(swid->rowcol) ;
00670 XtRealizeWidget(swid->wtop) ;
00671 EXRETURN ;
00672 }
|
|
||||||||||||||||
|
Callback for press of a toggle button on the surface controls. All this does is to force a redraw of the images. Definition at line 867 of file afni_sumafunc.c. References AFNI_set_viewpoint(), ENTRY, IM3D_OPEN, REDISPLAY_OVERLAY, AFNI_viewing_widgets::swid, AFNI_widget_set::view, Three_D_View::vwid, and AFNI_surface_widgets::wtop.
00868 {
00869 Three_D_View *im3d = (Three_D_View *) cd ;
00870 AFNI_surface_widgets *swid ;
00871
00872 ENTRY("AFNI_surf_bbox_CB") ;
00873
00874 if( im3d == NULL ) EXRETURN ;
00875 swid = im3d->vwid->view->swid ;
00876 if( swid == NULL ) EXRETURN ; /* should be impossible */
00877
00878 if( !IM3D_OPEN(im3d) ){ /* bad user! */
00879 XtUnmapWidget( swid->wtop ) ;
00880 EXRETURN ;
00881 }
00882
00883 AFNI_set_viewpoint( im3d , -1,-1,-1 , REDISPLAY_OVERLAY ) ;
00884
00885 EXRETURN ;
00886 }
|
|
||||||||||||||||
|
Callback for "Done" button for surface control panel. Definition at line 824 of file afni_sumafunc.c. References ENTRY, IM3D_OPEN, AFNI_viewing_widgets::swid, AFNI_widget_set::view, Three_D_View::vwid, and AFNI_surface_widgets::wtop. Referenced by AFNI_make_surface_widgets().
00825 {
00826 Three_D_View *im3d = (Three_D_View *) cd ;
00827 AFNI_surface_widgets *swid ;
00828
00829 ENTRY("AFNI_surf_done_CB") ;
00830
00831 if( !IM3D_OPEN(im3d) ) EXRETURN ;
00832 swid = im3d->vwid->view->swid ;
00833 if( swid != NULL ) XtUnmapWidget( swid->wtop ) ;
00834 EXRETURN ;
00835 }
|
|
||||||||||||
|
Definition at line 842 of file afni_sumafunc.c. References AFNI_set_viewpoint(), ENTRY, IM3D_OPEN, REDISPLAY_OVERLAY, AFNI_viewing_widgets::swid, AFNI_widget_set::view, Three_D_View::vwid, and AFNI_surface_widgets::wtop. Referenced by AFNI_make_surface_widgets().
00843 {
00844 Three_D_View *im3d = (Three_D_View *) cd ;
00845 AFNI_surface_widgets *swid ;
00846
00847 ENTRY("AFNI_surf_redraw_CB") ;
00848
00849 if( im3d == NULL ) EXRETURN ;
00850 swid = im3d->vwid->view->swid ;
00851 if( swid == NULL ) EXRETURN ; /* should be impossible */
00852
00853 if( !IM3D_OPEN(im3d) ){ /* bad user, bad bad bad! */
00854 XtUnmapWidget( swid->wtop ) ;
00855 EXRETURN ;
00856 }
00857
00858 AFNI_set_viewpoint( im3d , -1,-1,-1 , REDISPLAY_OVERLAY ) ;
00859
00860 EXRETURN ;
00861 }
|
|
|
Update all surface widgets everywhere that touch this session. Definition at line 758 of file afni_sumafunc.c. References AFNI_update_surface_widgets(), AFNI_library_type::controllers, ENTRY, GLOBAL_library, IM3D_OPEN, MAX_CONTROLLERS, and Three_D_View::ss_now. Referenced by process_NIML_Node_ROI(), and process_NIML_SUMA_ixyz().
00759 {
00760 int ii ;
00761 Three_D_View *im3d ;
00762 ENTRY("AFNI_update_all_surface_widgets") ;
00763 for( ii=0 ; ii < MAX_CONTROLLERS ; ii++ ){
00764 im3d = GLOBAL_library.controllers[ii] ;
00765 if( IM3D_OPEN(im3d) && im3d->ss_now == sess )
00766 AFNI_update_surface_widgets( im3d ) ;
00767 }
00768 EXRETURN ;
00769 }
|
|
|
Update surface widgets for this controller; that is, set labels, manage/unmanage widget rows, et cetera. Definition at line 678 of file afni_sumafunc.c. References AFNI_controller_label(), AFNI_viewing_widgets::choose_surf_pb, Three_D_View::dc, DC_find_closest_overlay_color(), ENTRY, getenv(), IM3D_OPEN, SUMA_surface::label, MAKE_SURF_ROW, MCW_register_hint(), MCW_set_widget_label(), MIN, AFNI_surface_widgets::nall, MCW_DCOV::ncol_ov, AFNI_surface_widgets::nrow, SUMA_surface::num_ijk, SUMA_surface::num_ixyz, MCW_DC::ovc, SENSITIZE, THD_session::sessname, SESSTRAIL, Three_D_View::ss_now, THD_session::su_num, THD_session::su_surf, AFNI_surface_widgets::surf_bbox, AFNI_surface_widgets::surf_ledg_av, AFNI_surface_widgets::surf_line_av, AFNI_surface_widgets::surf_node_av, AFNI_surface_widgets::surf_rc, AFNI_viewing_widgets::swid, THD_MAX_NAME, THD_trailname(), AFNI_surface_widgets::top_lab, AFNI_widget_set::view, Three_D_View::vwid, MCW_bbox::wbut, and XtRealloc. Referenced by AFNI_choose_surface_CB(), AFNI_setup_viewing(), and AFNI_update_all_surface_widgets().
00679 {
00680 AFNI_surface_widgets *swid ;
00681 int num , ii , nwid,nall ;
00682 char str[64] , nam[THD_MAX_NAME] , *tnam ;
00683
00684 ENTRY("AFNI_update_surface_widgets") ;
00685
00686 if( !IM3D_OPEN(im3d) || im3d->ss_now == NULL ) EXRETURN ; /* bad */
00687
00688 num = im3d->ss_now->su_num ; /* # of surfaces in current session */
00689 swid = im3d->vwid->view->swid ; /* pointer to surface widget struct */
00690
00691 SENSITIZE( im3d->vwid->view->choose_surf_pb , (Boolean)(num > 0) ) ;
00692
00693 if( swid == NULL ) EXRETURN ; /* nothing to update */
00694
00695 /* put session label in top of panel */
00696
00697 strcpy( nam , im3d->ss_now->sessname ) ;
00698 tnam = THD_trailname(nam,SESSTRAIL+1) ;
00699 ii = strlen(tnam) ; if( ii > 50 ) tnam += (ii-50) ;
00700 sprintf(str ,"%-.50s %s" , tnam, AFNI_controller_label(im3d) ) ;
00701 MCW_set_widget_label( swid->top_lab , str ) ;
00702
00703 /* make more widget rows? (1 per surface is needed) */
00704
00705 if( swid->nall < num ){
00706 char *eee ; int line_col,box_col ;
00707
00708 swid->surf_rc = (Widget *) XtRealloc( (char *)swid->surf_rc ,num*sizeof(Widget) );
00709 swid->surf_bbox = (MCW_bbox **) XtRealloc( (char *)swid->surf_bbox ,num*sizeof(MCW_bbox *) );
00710 swid->surf_node_av = (MCW_arrowval **) XtRealloc( (char *)swid->surf_node_av,num*sizeof(MCW_arrowval *) );
00711 swid->surf_line_av = (MCW_arrowval **) XtRealloc( (char *)swid->surf_line_av,num*sizeof(MCW_arrowval *) );
00712 swid->surf_ledg_av = (MCW_arrowval **) XtRealloc( (char *)swid->surf_line_av,num*sizeof(MCW_arrowval *) );
00713
00714
00715 eee = getenv( "AFNI_SUMA_LINECOLOR" ) ;
00716 line_col = DC_find_closest_overlay_color( im3d->dc, eee ) ;
00717 if( line_col < 0 ) line_col = MIN(6,im3d->dc->ovc->ncol_ov-1) ;
00718
00719 eee = getenv( "AFNI_SUMA_BOXCOLOR" ) ;
00720 box_col = DC_find_closest_overlay_color( im3d->dc, eee ) ;
00721 if( box_col < 0 ) box_col = 0 ;
00722
00723 for( ii=swid->nall ; ii < num ; ii++ ){
00724 MAKE_SURF_ROW(ii) ;
00725 }
00726 swid->nall = num ;
00727 }
00728
00729 /* map or unmap widget rows? (1 per surface is needed) */
00730
00731 if( swid->nrow < num ){
00732 for( ii=swid->nrow ; ii < num ; ii++ )
00733 XtManageChild( swid->surf_rc[ii] ) ;
00734 } else if( swid->nrow > num ){
00735 for( ii=num ; ii < swid->nrow ; ii++ )
00736 XtUnmanageChild( swid->surf_rc[ii] ) ;
00737 }
00738 swid->nrow = num ; /* # of managed rows */
00739
00740 /* change labels for each row */
00741
00742 for( ii=0 ; ii < num ; ii++ ){
00743 sprintf(str,"%-14.14s: ",im3d->ss_now->su_surf[ii]->label) ;
00744 MCW_set_widget_label( swid->surf_bbox[ii]->wbut[0] , str ) ;
00745
00746 sprintf(str,"%d Nodes; %d Triangles", /* 20 Aug 2002: */
00747 im3d->ss_now->su_surf[ii]->num_ixyz , /* put a hint */
00748 im3d->ss_now->su_surf[ii]->num_ijk ) ; /* on each label */
00749 MCW_register_hint( swid->surf_bbox[ii]->wbut[0] , str ) ;
00750 }
00751
00752 EXRETURN ;
00753 }
|
|
||||||||||||||||||||
|
Create a nodal color overlay from a voxel map.
Definition at line 29 of file afni_sumafunc.c. References SUMA_irgba::a, AFNI_GOOD_FUNC_DTYPE, rgbyte::b, SUMA_irgba::b, MCW_pbar::bigbot, MCW_pbar::bigcolor, MCW_pbar::bigmode, MCW_pbar::bigtop, cmap, THD_3dim_dataset::daxes, Three_D_View::dc, DCOV_BLUEBYTE, DCOV_GREENBYTE, DCOV_REDBYTE, SUMA_vnlist::dset, DSET_BRICK, DSET_BRICK_FACTOR, DSET_load, DSET_LOADED, DSET_NVALS, ENTRY, EQUIV_DATAXES, AFNI_view_info::fim_autorange, AFNI_view_info::fim_index, Three_D_View::fim_now, AFNI_view_info::fim_range, free, AFNI_widget_set::func, AFNI_view_info::func_thresh_top, AFNI_view_info::func_threshold, rgbyte::g, SUMA_irgba::g, SUMA_ixyz::id, SUMA_irgba::id, IM3D_VALID, ind, AFNI_function_widgets::inten_pbar, SUMA_surface::ixyz, MRI_IMAGE::kind, malloc, mmm, MRI_BYTE_PTR, MRI_FLOAT_PTR, MRI_RGB_PTR, MRI_SHORT_PTR, SUMA_vnlist::nlist, NPANE_BIG, NPANE_MAX, SUMA_surface::num_ixyz, MCW_pbar::num_panes, SUMA_vnlist::numnod, SUMA_vnlist::nvox, MCW_pbar::ov_index, MCW_pbar::pval, rgbyte::r, SUMA_irgba::r, r, realloc, RETURN, Three_D_View::ss_now, THD_session::su_num, THD_session::su_surf, SUMA_destroy_vnlist(), SUMA_make_vnlist(), AFNI_view_info::thr_index, AFNI_view_info::use_posfunc, Three_D_View::vinfo, SUMA_surface::vn, SUMA_vnlist::voxijk, and Three_D_View::vwid.
00031 {
00032 MRI_IMAGE *im_thr , *im_fim ;
00033 short fim_ovc[NPANE_MAX+1] ;
00034 byte ovc_r[NPANE_MAX+1], ovc_g[NPANE_MAX+1], ovc_b[NPANE_MAX+1] ;
00035 int ii,jj,nn , lp , num_lp , ival ;
00036 float scale_factor , scale_thr=1.0 , scale_fim=1.0 ;
00037 MCW_pbar * pbar ;
00038 int simult_thr , need_thr ;
00039 THD_3dim_dataset *fdset ;
00040 SUMA_irgba *mmm ;
00041 SUMA_ixyz *ixyz ;
00042 int nvox,nnod,nout , *numnod , *voxijk , *nlist ;
00043 int *vlist ;
00044 int nvout ; /* 13 Mar 2002 */
00045
00046 int bm , zbot=0 , kk ; /* 02 Feb 2003: colorscale stuff */
00047 float fbot=0.0,ftop=0.0,ffac=0.0 , val ;
00048 rgbyte *cmap=NULL ;
00049
00050 THD_session *ss ; /* 22 Jan 2004 */
00051 SUMA_surface *surf ;
00052 SUMA_vnlist *vn ;
00053
00054 ENTRY("AFNI_vnlist_func_overlay") ;
00055
00056 /* check inputs for goodness sakes */
00057
00058 if( map == NULL || !IM3D_VALID(im3d) ) RETURN(-1) ; /* that was easy */
00059
00060 if( nvused != NULL ) *nvused = 0 ; /* set default return value here */
00061
00062 /* check datasets for goodness */
00063 /* 12 Dec 2002: ks is now input (we used to compute it) */
00064
00065 ss = im3d->ss_now ; /* session must */
00066 if( ss == NULL || /* have surface #ks */
00067 ss->su_num == 0 ||
00068 ks < 0 ||
00069 ss->su_num <= ks ||
00070 ss->su_surf[ks] == NULL ) RETURN(-1) ;
00071
00072 surf = ss->su_surf[ks] ; /* the surface in question */
00073
00074 fdset = im3d->fim_now ; if( fdset == NULL ) RETURN(-1) ;
00075
00076 ival = im3d->vinfo->thr_index ; /* threshold sub-brick index */
00077
00078 /* get the component images */
00079
00080 need_thr = im3d->vinfo->func_threshold > 0.0 ;
00081
00082 if( need_thr ) im_thr = DSET_BRICK(fdset,ival) ;
00083 else im_thr = NULL ;
00084
00085 if( im_thr != NULL && !AFNI_GOOD_FUNC_DTYPE(im_thr->kind) ) im_thr = NULL ;
00086
00087 if( im_thr != NULL ){
00088 scale_thr = DSET_BRICK_FACTOR(fdset,ival) ;
00089 if( scale_thr == 0.0 || im_thr->kind == MRI_float ) scale_thr = 1.0 ;
00090 }
00091
00092 { int ind ;
00093
00094 ind = im3d->vinfo->fim_index ;
00095 if( ind >= DSET_NVALS(fdset) )
00096 ind = DSET_NVALS(fdset) - 1 ;
00097
00098 im_fim = DSET_BRICK(fdset,ind) ; /* the sub-brick to show */
00099 scale_factor = im3d->vinfo->fim_range ;
00100 if( scale_factor == 0.0 ) scale_factor = im3d->vinfo->fim_autorange ;
00101 if( scale_factor == 0.0 ) scale_factor = 1.0 ;
00102
00103 scale_fim = DSET_BRICK_FACTOR(fdset,ind) ;
00104 if( scale_fim == 0.0 ) scale_fim = 1.0 ;
00105
00106 }
00107
00108 /* if component images not good, quit now */
00109
00110 if( im_fim == NULL ) RETURN(-1) ; /* no function!? */
00111
00112 if( !AFNI_GOOD_FUNC_DTYPE(im_fim->kind) ){
00113 RETURN(-1) ; /* bad function - no soup for you */
00114 }
00115
00116 /* maybe need to build a voxel-to-node list for func dataset */
00117 /* (this is where the 3D-to-2D mapping is encapsulated, Ziad) */
00118
00119 if( surf->vn == NULL ||
00120 !EQUIV_DATAXES(surf->vn->dset->daxes,fdset->daxes) ){
00121
00122 /* if have an old one
00123 (that doesn't match current dataset grid),
00124 then delete it from the Universe */
00125
00126 if( surf->vn != NULL ) SUMA_destroy_vnlist( surf->vn ) ;
00127
00128 /* make the new list */
00129
00130 surf->vn = SUMA_make_vnlist( surf , fdset ) ;
00131 if( surf->vn == NULL ) RETURN(-1) ;
00132 }
00133
00134 vn = surf->vn ; /* voxel-to-node list for this surface */
00135
00136 /* create array of voxel indexes (vlist);
00137 will put in there the voxels that are above threshold */
00138
00139 nvox = vn->nvox ; if( nvox < 1 ) RETURN(0);
00140 voxijk = vn->voxijk ; /* list of voxels with surface nodes */
00141 numnod = vn->numnod ; /* number of nodes in each voxel */
00142
00143 nnod = surf->num_ixyz ; if( nnod < 1 ) RETURN(0);
00144 ixyz = surf->ixyz ; /* array of surface nodes */
00145
00146 DSET_load(fdset) ; /* if isn't in memory now */
00147 if( !DSET_LOADED(fdset) ) RETURN(-1) ; /* what the hell? */
00148
00149 /** if don't have threshold, will process all voxels for color **/
00150
00151 if( im_thr == NULL ){
00152
00153 vlist = voxijk ; /* list of voxels to process = all voxels */
00154 nout = nnod ; /* number of output nodes */
00155
00156 /** if have threshold, cut out voxels below threshold (set vlist[]=-1) **/
00157
00158 } else {
00159
00160 vlist = (int *) malloc(sizeof(int)*nvox) ; /* copy voxel list */
00161 memcpy( vlist , voxijk , sizeof(int)*nvox ) ; /* then prune it */
00162
00163 switch( im_thr->kind ){
00164 case MRI_short:{
00165 float thresh = im3d->vinfo->func_threshold
00166 * im3d->vinfo->func_thresh_top / scale_thr ;
00167 short *ar_thr = MRI_SHORT_PTR(im_thr) ;
00168 for( ii=0 ; ii < nvox ; ii++ ){ /* voxel cutting time */
00169 jj = vlist[ii] ; /* actual voxel index in func brick */
00170 if( ar_thr[jj] > -thresh && ar_thr[jj] < thresh ) vlist[ii] = -1 ;
00171 }
00172 }
00173 break ;
00174
00175 case MRI_byte:{
00176 float thresh = im3d->vinfo->func_threshold
00177 * im3d->vinfo->func_thresh_top / scale_thr ;
00178 byte *ar_thr = MRI_BYTE_PTR(im_thr) ;
00179 for( ii=0 ; ii < nvox ; ii++ ){
00180 jj = vlist[ii] ;
00181 if( ar_thr[jj] < thresh ) vlist[ii] = -1 ;
00182 }
00183 }
00184 break ;
00185
00186 case MRI_float:{
00187 float thresh = im3d->vinfo->func_threshold
00188 * im3d->vinfo->func_thresh_top / scale_thr ;
00189 float *ar_thr = MRI_FLOAT_PTR(im_thr) ;
00190 for( ii=0 ; ii < nvox ; ii++ ){
00191 jj = vlist[ii] ;
00192 if( ar_thr[jj] > -thresh && ar_thr[jj] < thresh ) vlist[ii] = -1 ;
00193 }
00194 }
00195 break ;
00196 } /* end of switch on threshold sub-brick type */
00197
00198 /* count surviving voxels; exit if there aren't any */
00199
00200 for( jj=ii=0 ; ii < nvox ; ii++ )
00201 if( vlist[ii] >= 0 ) jj++ ;
00202 if( jj == 0 ){ free(vlist) ; RETURN(0) ; }
00203
00204 /* count output nodes inside each surviving voxel */
00205
00206 for( nout=ii=0 ; ii < nvox ; ii++ )
00207 if( vlist[ii] >= 0 ) nout += numnod[ii] ;
00208
00209 } /* end of if on existence of threshold sub-brick */
00210
00211 /** allocate output structure (maybe too big, but will clip it later) **/
00212
00213 mmm = (SUMA_irgba *) malloc( sizeof(SUMA_irgba) * nout ) ;
00214
00215 /** set overlay colors **/
00216
00217 pbar = im3d->vwid->func->inten_pbar ;
00218 num_lp = pbar->num_panes ;
00219 bm = pbar->bigmode ; /* 02 Feb 2003 */
00220
00221 if( !bm ){ /* indexed colors */
00222 for( lp=0 ; lp < num_lp ; lp++ ) /* overlay color indexes */
00223 fim_ovc[lp] = pbar->ov_index[lp] ; /* run from top of pbar down */
00224
00225 /* overlay color index for values below bottom of pbar */
00226
00227 fim_ovc[num_lp] = (im3d->vinfo->use_posfunc) ? (0) : (fim_ovc[num_lp-1]) ;
00228
00229 /* get the actual RGB colors of each pane on the pbar */
00230
00231 for( lp=0 ; lp <= num_lp ; lp++ ){
00232 ovc_r[lp] = DCOV_REDBYTE (im3d->dc,fim_ovc[lp]) ;
00233 ovc_g[lp] = DCOV_GREENBYTE(im3d->dc,fim_ovc[lp]) ;
00234 ovc_b[lp] = DCOV_BLUEBYTE (im3d->dc,fim_ovc[lp]) ;
00235 }
00236
00237 } else { /* colorscale colors - 02 Feb 2003 */
00238 fbot = (scale_factor/scale_fim)*pbar->bigbot ;
00239 ftop = (scale_factor/scale_fim)*pbar->bigtop ;
00240 ffac = NPANE_BIG / (ftop-fbot) ;
00241 cmap = pbar->bigcolor ;
00242 zbot = (fbot == 0.0) ;
00243 }
00244
00245 /** process im_fim into overlay, depending on data type **/
00246
00247 switch( im_fim->kind ){
00248
00249 default: nvout = nout = 0 ; break ; /* should never happen! */
00250
00251 case MRI_rgb:{ /* 17 Apr 2002 */
00252 byte *ar_fim = MRI_RGB_PTR(im_fim); /* colors direct from fim */
00253 byte r,g,b ;
00254
00255 nvout = nout = 0 ; /* num output nodes & voxels */
00256 for( ii=0 ; ii < nvox ; ii++ ){
00257 jj = vlist[ii] ; if( jj < 0 ) continue ; /* skip voxel? */
00258 r = ar_fim[3*jj]; g = ar_fim[3*jj+1]; b = ar_fim[3*jj+2];
00259 if( r == 0 && g ==0 && b == 0 ) continue ; /* uncolored */
00260 nlist = vn->nlist[ii] ; /* list of nodes */
00261 for( nn=0 ; nn < numnod[ii] ; nn++ ){ /* loop over nodes */
00262 mmm[nout].id = ixyz[nlist[nn]].id ;
00263 mmm[nout].r = r ; mmm[nout].g = g ;
00264 mmm[nout].b = b ; mmm[nout].a = 255 ; nout++ ;
00265 }
00266 nvout++ ; /* number of voxels used */
00267 }
00268 }
00269 break ;
00270
00271 case MRI_short:{
00272 short * ar_fim = MRI_SHORT_PTR(im_fim) ;
00273 float fim_thr[NPANE_MAX] ;
00274 byte r,g,b ;
00275
00276 if( !bm ){ /* indexed colors from panes */
00277 for( lp=0 ; lp < num_lp ; lp++ ) /* thresholds for each pane */
00278 fim_thr[lp] = (scale_factor/scale_fim) * pbar->pval[lp+1] ;
00279 }
00280
00281 nvout = nout = 0 ; /* num output nodes & voxels */
00282 for( ii=0 ; ii < nvox ; ii++ ){
00283 jj = vlist[ii] ; if( jj < 0 ) continue ; /* skip voxel? */
00284 if( ar_fim[jj] == 0 ) continue ; /* no func? */
00285 if( !bm ){ /* find pane this voxel is in */
00286 for( lp=0; lp < num_lp && ar_fim[jj] < fim_thr[lp]; lp++ ) ; /*nada*/
00287 if( fim_ovc[lp] == 0 ) continue ; /* uncolored pane */
00288 r = ovc_r[lp]; g = ovc_g[lp]; b = ovc_b[lp];
00289 } else { /* colorscale - 02 Feb 2003 */
00290 if( zbot && ar_fim[jj] < 0 ) continue ;
00291 val = ffac*(ftop-ar_fim[jj]) ;
00292 if( val < 0.0 ) val = 0.0;
00293 kk = (int)(val+0.49); if( kk >= NPANE_BIG ) kk = NPANE_BIG-1;
00294 r = cmap[kk].r; g = cmap[kk].g; b = cmap[kk].b;
00295 if( r == 0 && g ==0 && b == 0 ) continue ; /* black == uncolored */
00296 }
00297 nlist = vn->nlist[ii] ; /* list of nodes */
00298 for( nn=0 ; nn < numnod[ii] ; nn++ ){ /* loop over nodes */
00299 mmm[nout].id = ixyz[nlist[nn]].id ;
00300 mmm[nout].r = r ; mmm[nout].g = g ;
00301 mmm[nout].b = b ; mmm[nout].a = 255 ; nout++ ;
00302 }
00303 nvout++ ; /* number of voxels used */
00304 }
00305 }
00306 break ;
00307
00308 case MRI_byte:{
00309 byte * ar_fim = MRI_BYTE_PTR(im_fim) ;
00310 float fim_thr[NPANE_MAX] ;
00311 byte r,g,b ;
00312
00313 if( !bm ){ /* indexed colors from panes */
00314 for( lp=0 ; lp < num_lp ; lp++ )
00315 if( pbar->pval[lp+1] <= 0.0 )
00316 fim_thr[lp] = 0 ;
00317 else
00318 fim_thr[lp] = (scale_factor/scale_fim) * pbar->pval[lp+1] ;
00319 }
00320
00321 nvout = nout = 0 ; /* num output nodes */
00322 for( ii=0 ; ii < nvox ; ii++ ){
00323 jj = vlist[ii] ; if( jj < 0 ) continue ; /* skip voxel? */
00324 if( ar_fim[jj] == 0 ) continue ; /* no func? */
00325 if( !bm ){ /* find pane this voxel is in */
00326 for( lp=0; lp < num_lp && ar_fim[jj] < fim_thr[lp]; lp++ ) ; /*nada*/
00327 if( fim_ovc[lp] == 0 ) continue ; /* uncolored pane */
00328 r = ovc_r[lp]; g = ovc_g[lp]; b = ovc_b[lp];
00329 } else { /* colorscale - 02 Feb 2003 */
00330 val = ffac*(ftop-ar_fim[jj]) ;
00331 if( val < 0.0 ) val = 0.0;
00332 kk = (int)(val+0.49); if( kk >= NPANE_BIG ) kk = NPANE_BIG-1;
00333 r = cmap[kk].r; g = cmap[kk].g; b = cmap[kk].b;
00334 if( r == 0 && g ==0 && b == 0 ) continue ; /* black == uncolored */
00335 }
00336 nlist = vn->nlist[ii] ; /* list of nodes */
00337 for( nn=0 ; nn < numnod[ii] ; nn++ ){ /* loop over nodes */
00338 mmm[nout].id = ixyz[nlist[nn]].id ;
00339 mmm[nout].r = r ; mmm[nout].g = g ;
00340 mmm[nout].b = b ; mmm[nout].a = 255 ; nout++ ;
00341 }
00342 nvout++ ; /* number of voxels used */
00343 }
00344 }
00345 break ;
00346
00347 case MRI_float:{
00348 float * ar_fim = MRI_FLOAT_PTR(im_fim) ;
00349 float fim_thr[NPANE_MAX] ;
00350 byte r,g,b ;
00351
00352 if( !bm ){ /* indexed colors from panes */
00353 for( lp=0 ; lp < num_lp ; lp++ )
00354 fim_thr[lp] = (scale_factor/scale_fim) * pbar->pval[lp+1] ;
00355 }
00356
00357 nvout = nout = 0 ; /* num output nodes */
00358 for( ii=0 ; ii < nvox ; ii++ ){
00359 jj = vlist[ii] ; if( jj < 0 ) continue ; /* skip voxel? */
00360 if( ar_fim[jj] == 0.0 ) continue ; /* no func? */
00361 if( !bm ){ /* find pane this voxel is in */
00362 for( lp=0; lp < num_lp && ar_fim[jj] < fim_thr[lp]; lp++ ) ; /*nada*/
00363 if( fim_ovc[lp] == 0 ) continue ; /* uncolored pane */
00364 r = ovc_r[lp]; g = ovc_g[lp]; b = ovc_b[lp];
00365 } else { /* colorscale - 02 Feb 2003 */
00366 if( zbot && ar_fim[jj] < 0.0 ) continue ;
00367 val = ffac*(ftop-ar_fim[jj]) ;
00368 if( val < 0.0 ) val = 0.0;
00369 kk = (int)(val+0.49); if( kk >= NPANE_BIG ) kk = NPANE_BIG-1;
00370 r = cmap[kk].r; g = cmap[kk].g; b = cmap[kk].b;
00371 if( r == 0 && g ==0 && b == 0 ) continue ; /* black == uncolored */
00372 }
00373 nlist = vn->nlist[ii] ; /* list of nodes */
00374 for( nn=0 ; nn < numnod[ii] ; nn++ ){ /* loop over nodes */
00375 mmm[nout].id = ixyz[nlist[nn]].id ;
00376 mmm[nout].r = r ; mmm[nout].g = g ;
00377 mmm[nout].b = b ; mmm[nout].a = 255 ; nout++ ;
00378 }
00379 nvout++ ; /* number of voxels used */
00380 }
00381 }
00382 break ;
00383
00384 } /* end of switch on fim data type */
00385
00386 /** finished: clean up and exit **/
00387
00388 if( vlist != voxijk ) free(vlist) ; /* toss trash, if it is trash */
00389
00390 if( nout == 0 ){ free(mmm); RETURN(0); } /* no overlay? */
00391
00392 /* map gets the array of node IDs + colors */
00393
00394 *map = (SUMA_irgba *) realloc( mmm , sizeof(SUMA_irgba)*nout ) ;
00395
00396 /* nvused gets the number of voxels used */
00397
00398 if( nvused != NULL ) *nvused = nvout ; /* 13 Mar 2002 */
00399
00400 RETURN(nout) ; /* number of entries in map */
00401 }
|