Index

Project

Screenshot

 Linux - MacOSX - Win32
Docs / TheLibrary

A brief overview on the library for those who want to include it in their own programs. The distribution is capable of creating a static and shared library on most architectures with the use of GNU's libtool. Here you can see an overview of the related man-page <medcon.3>. For more information you should look into the sourcecode itself. The library is intended to ease the use of read/write routines for the various medical image formats (primarily used in nuclear medicine). The FILEINFO structure holds all the interesting data and pointers to the images. A fast introduction:

 #include "medcon.h"

 -----------------------------------------------------------------------
 Important Global Variables
 -----------------------------------------------------------------------

 char prefix[MDC_MAX_PREFIX + 1]; 	/* prefix for output filenames */


 /* the command-line input data */ 	
 char *mdc_arg_files[]; 	        /* pointers to input files (files) */
 int   mdc_arg_convs[]; 	        /* conversions selected (counter) */
 int   mdc_arg_total[]; 	        /* totals of files & conversions */


 /* options set from command-line */ 	
 Int8 MDC_INFO; 	                /* print image info */
 Int8 MDC_INTERACTIVE; 	                /* interactive read */
 Int8 MDC_CONVERT; 	                /* do conversion */
 Int8 MDC_EXTRACT; 	                /* extract images */
 Int8 MDC_PIXELS;  	                /* print pixel values */
 Int8 MDC_SKIP_PREVIEW;                 /* skip first preview image */
 Int8 MDC_DICOM_MOSAIC;                 /* support mosaic files */
 Int8 MDC_DICOM_CONTRAST; 	        /* enable contrast window center/width */
 Int8 MDC_TRUE_GAP; 	                /* spacing is true gap/overlap */
 Int8 MDC_DEBUG; 	                /* show debug info */
 Int8 MDC_ANLZ_REV; 	                /* analyze reverse images */
 Int8 MDC_ANLZ_SPM;                     /* analyze for SPM */
 Int8 MDC_GIF_OPTIONS;                  /* define gif options */
 Int8 MDC_COLOR_MAP;                    /* gray colormap selected */
 Int8 MDC_MAKE_GRAY; 	                /* force remap to grayscale */
 Int8 MDC_DITHER_COLOR; 	        /* dither color reduction */
 Int8 MDC_FORCE_INT;              	/* force writing BIT?_? pixs*/
 Int8 MDC_ALIAS NAME;             	/* use alias name based on ID's */
 Int8 MDC_PREFIX_DISABLED;        	/* prevent the prefix in names */
 Int8 MDC_PATIENT_ANON;           	/* make patient anonymous */
 Int8 MDC_FLIP_HORIZONTAL;         	/* flip horizontal (x) */
 Int8 MDC_FLIP_VERTICAL;          	/* flip vertical (y) */
 Int8 MDC_NEGATIVE;              	/* preserve negative pixels */
 Int8 MDC_QUANTIFY;              	/* preserve quantification (one factor) */
 Int8 MDC_CALIBRATE; 	                /* preserve calibration (two factors) */
 Int8 MDC_VERBOSE;                 	/* verbose mode */
 Int8 MDC_NORM_OVER_FRAMES;         	/* normalize over frames */
 /* `QUANTIFY' & `CALIBRATE' may NOT be ON at the same time! */  

 ----------------------------------------------------------------------
 Important Defines
 -----------------------------------------------------------------------

 /* supported formats */ 	
 #define MDC_FRMT_NONE 	0 	/* unsupported format */
 #define MDC_FRMT_RAW 	1 	/* Read Interactive */

 /* Write RAW Binary */
 #define MDC_FRMT_ASCII 2 	/* Write RAW Ascii */
 #define MDC_FRMT_GIF 	3 	/* GIF89a or GIF87a */
 #define MDC_FRMT_ACR 	4 	/* Acr/Nema 2.0 (Papyrus) */
 #define MDC_FRMT_INW 	5 	/* INW (RUG) */
 #define MDC_FRMT_ECAT6 6 	/* Siemens CTI ECAT 6.4 */
 #define MDC_FRMT_ECAT7 7 	/* Siemens CTI ECAT 7 */
 #define MDC_FRMT_INTF 	8 	/* InterFile 3.3*/
 #define MDC_FRMT_ANLZ 	9 	/* Analyze */
 #define MDC_FRMT_DICM 	10 	/* DICOM */
 #define MDC_FRMT_PNG 	11 	/* PNG */
 #define MDC_FRMT_CONC 	12 	/* Concorde/ÁPET */
 #define MDC_MAX_FMTS 	13 	/* total + 1 */

 /* supported color maps */ 	
 #define MDC_MAP_PRESENT 	0 	/* 256 RGB colormap */
 #define MDC_MAP_GRAY 	        1 	/* grayscale colormap */
 #define MDC_MAP_INVERTED 	2 	/* inverted colormap */
 #define MDC_MAP_RAINBOW 	3 	/* rainbow colormap */
 #define MDC_MAP_COMBINED 	4 	/* combined colormap */
 #define MDC_MAP_HOTMETAL 	5 	/* hotmetal colormap */
 #define MDC_MAP_LOADED         6 	/* external LUT loaded */

 -----------------------------------------------------------------------
 Important Definitions
 -----------------------------------------------------------------------


 typedef struct Gated_Data_t { 	

    Int8  gspect_nesting; 	/* gated spect nesting   */
    float  nr_projections; 	/* number of projections */
    float  extent_rotation; 	/* extent of rotation    */
    float study_duration; 	/* study duration (ms)   */
    float image_duration; 	/* image duration (ms)   */
    float time_per_proj; 	/* time per proj  (ms)   */
    float window_low; 	        /* lower  limit   (ms)   */
    float window_high; 	        /* higher limit   (ms)   */
    float cycles_observed; 	/* cycles observed       */
    float cycles_acquired; 	/* cycles acquired       */

 } GATED_DATA; 	


 typedef struct Acquisition_Data_t { 	

    Int16 rotation_direction; 	/* direction of rotation */
    Int16 detector_motion; 	/* type detector motion */
    float angle_start; 	        /* start angle (interfile = 180 - dicom) */
    float angle_step; 	        /* angular step */
    float scan_arc;      	/* angular range */

 } ACQ_DATA; 	


 typedef struct Dynamic_Data_t {

    Uint32 nr_of_slices;	/* images in time frame */
    float time_frame_start;     /* start time frame (ms) */
    float time_frame_delay;	/* delay this frame (ms) */
    float time_frame_duration;	/* duration   frame (ms) */
    float delay_slices;  	/* delay each slice (ms) */

 } DYNAMIC_DATA;

 typedef struct Image_Data_t {

  /* ** general data ** */
    Uint32 width, height; 	/* image dimension */
    Int16 bits,type;     	/* bits/pixel & datatype */
    Uint16 flags;        	/* extra flag */
    double min, max;     	/* min/max pixelvalue */
    double qmin, qmax;  	/* quantified min/max */
    double fmin, fmax;   	/* min/max in whole frame */
    double qfmin, qfmax; 	/* in whole frame (quant) */
    float rescale_slope; 	/* rescale slope */
    float rescale_intercept; 	/* rescale intercept */
    Uint8 *buf;          	/* pointer to raw image */
  /* ** internal items ** */
    Int16 rescaled;      	/* rescaled YES or NO */
    double rescaled_min; 	/* new rescaled max */
    double rescaled_max; 	/* new rescaled min */
    double rescaled_fctr;  	/* new rescale fctr */
    double rescaled_slope;  	/* new rescaled slope */
    double rescaled_intercept; 	/* new rescaled intercept */
  /* ** ecat64 items ** */
    Int16 quant_units; 	        /* quantification units */
    Int16 calibr_units; 	/* calibration units */
    float quant_scale;   	/* quantification scale */
    float calibr_fctr;  	/* calibration factor */
    float intercept;    	/* scale intercept */
    float pixel_xsize;   	/* pixel size X (mm) */
    float pixel_ysize;   	/* pixel size Y (mm) */
    float slice_width;  	/* slice width (mm) */
    Uint32 frame_number;	/* part of frame # (1-based) */
    float slice_start;   	/* start of slice (ms) */
    float recon_scale;  	/* recon magnification */
  /* ** Acr/Nema items ** */
    char image_mod[3];  	/* images modality */
    float image_pos_dev[3]; 	/* image pos. device (mm) */
    float image_orient_dev[6]; 	/* image orient device (mm) */
    float image_pos_pat[3]; 	/* image pos. patient (mm) */
    float image_orient_dev[6]; 	/* image orient patient (mm) */
    float slice_spacing; 	/* space btw centres (mm) */
    float ct_zoom_fctr; 	/* CT image zoom factor */

 } IMG_DATA; 	


 typedef struct File_Info_t { 	
    FILE *ifp;                      	/* pointer to input file */
    FILE *ofp;                  	/* pointer to output file */
    char ipath[MDC_MAX_PATH + 1]; 	/* path to input file */
    char opath[MDC_MAX_PATH + 1]; 	/* path to output file */
    char *idir;                  	/* dir to input file */
    char *odir;                    	/* dir to output file */
    char *ifname;                    	/* name of input file */
    char *ofname;                	/* name of output file */
    int rawconv; 	                /* FRMT_RAW | FRMT_ASCII */
    int endian;                 	/* endian type of file */
    int compression;             	/* file compression */
    int truncated; 	                /* truncated ? */
    int diff_type; 	                /* images with diff type */
    int diff_size; 	                /* images with diff size */
    Uint32 number; 	                /* total number of images */
    Uint32 mwidth, mheight; 	        /* global max dimensions */
    Uint16 bits, type; 	                /* global bits & datatype */
    Int16 dim[8]; 	                /* [0] = # of dimensions */
                                   	/* [1] = X-dim (pixels) */
                                  	/* [2] = Y-dim (pixels) */
                                  	/* [3] = Z-dim (planes) */
                                 	/* [4] = (frames) */
                                  	/* [5] = (gates) */
                                 	/* [6] = (beds) */
                                   	/* ... */
                                	/* values must be 1-based */
    float pixdim[8]; 	                /* [0] = # of dimensions */
                                  	/* [1] = X-dim (mm) */
                                 	/* [2] = Y-dim (mm) */
                                 	/* [3] = Z-dim (mm) */
                                	/* [4] = time (ms) */
                                	/* ... */
    double glmin, glmax; 	        /* global min/max value */
    double qglmin, qglmax; 	        /* quantified min/max */
    Int8 pat_slice_orient;         	/* combined flag */
    char pat_pos[MDC_MAXSTR];         	/* patient position */
    char pat_orient[MDC_MAXSTR]; 	/* patient orientation */
    char patient_sex[MDC_MAXSTR]; 	/* sex of patient */
    char patient_name[MDC_MAXSTR]; 	/* name of patient */
    char patient_id[MDC_MAXSTR]; 	/* id of patient */
    char patient_dob[MDC_MAXSTR]; 	/* birth of patient YYYYMMDD */
    float patient_weight;           	/* weight of patient (kg) */
    char study_descr[MDC_MAXSTR]; 	/* study description */
    char study_id[MDC_MAXSTR];   	/* study id */
    Int16 study_date_day;       	/* day of study */
    Int16 study_date_month;     	/* month of study */
    Int16 study_date_year;      	/* year of study */
    Int16 study_time_hour; 	        /* hour of study */
    Int16 study_time_minute;    	/* minute of study */
    Int16 study_time_second;    	/* second of study */
    Int16 nr_series;            	/* number of series */
    Int16 nr_acquisition;       	/* number of acquisition */
    Int16 nr_instance; 	                /* number of instance (image) */
    Int16 decay_corrected;            	/* decay corrected ? */
    Int16 flood_corrected;           	/* flood corrected ? */
    Int16 acquisition_type;         	/* acquisition type */
    Int16 reconstructed;             	/* reconstructed ? */
    char recon_method[MDC_MAXSTR]; 	/* reconstruction method */
    Int16 rotation_direction;    	/* direction of rotation */
    Int16 detector_motion;        	/* type detector motion */
    char institution[MDC_MAXSTR]; 	/* name of institution */
    char manufacturer[MDC_MAXSTR]; 	/* name of manufacturer */
    char series_descr[MDC_MAXSTR]; 	/* series description */
    char radiopharma[MDC_MAXSTR]; 	/* radiopharmaceutical */
    char filter_type[MDC_MAXSTR]; 	/* filter type */
    char isotope_code[MDC_MAXSTR]; 	/* isotope */
    float isotope_halflife;          	/* halflife of isotope */
    float injected_dose;           	/* amount injected (MBq) */
    float gantry_tilt;          	/* gantry tilt */
    Uint8 map; 	                        /* index 256 colormap */
    Uint8 palette[768]; 	        /* global palette */
    char *comment; 	                /* whatever comment */
    Uint32 comm_length;            	/* length of comment */
    Uint32 gatednr;             	/* number of gated entries */
    GATED_DATA *gdata;           	/* array of GATED_DATA */
    Uint32 acqnr;                  	/* number of acq. data entries */
    ACQ_DATA *acqdata;               	/* array of ACQ_DATA entries */
    Uint32 dynnr;                  	/* number of dynamic data entries */
    DYNAMIC_DATA *dyndata; 	        /* array of DYNAMIC_DATA entries */
    IMG_DATA *image;            	/* array of IMG_DATA images */

 } FILEINFO; 	

 ------------------------------------------------------------------------
 Important Functions
 ------------------------------------------------------------------------

 void MdcInit(void), void MdcFinish(void);
The very first and very last function to call when using this library. Currently, changes occur to the signal handler for floating point exceptions and the program's locale.
 int  MdcHandleArgs ( FILEINFO *fi, int argc, char *argv[], int MAXFILES );
The function to parse the command-line arguments. The last argument of the function specifies the maximum of input files your program allows. The absolute maximum is defined in MDC_MAX_FILES.
 void MdcPrintUsage ( char *pgrname );
Print out possible command-line options and terminates the program.
 int  MdcOpenFile ( FILEINFO *fi, char *path );
Initializes FILEINFO struct and opens the file with or without decompression (gzip or compress).
 int  MdcReadFile ( FILEINFO *fi, int filenr, char *(*ReadFunc)(FILEINFO *fi));
Reads the (decompressed) file with format autodetection or by trying a fallback format, initializes a (grayscale) colormap and does the obligated pixel handling in the MdcImagesPixelFiddle() function. The last argument enables the use of an external read function.
 int  MdcWriteFile ( FILEINFO *fi, int format, int prefixnr, char *(*WriteFunc)(FILEINFO *fi));
Writes a file in the supplied format. Last argument is a number used in the prefix of the output filename. Give a negative value when a self-made prefix was prepared. The last argument enables the use of an external write function.
 void MdcCloseFile ( FILE *fp );
Closes the file and sets pointer to NULL.
 void MdcInitFI ( FILEINFO *fi, char *path );
Initializes the FILEINFO structure.
 void MdcFreeIDs ( FILEINFO *fi );
Cleans the IMG_DATA structures by freeing all allocated memory.
 void MdcCleanUpFI ( FILEINFO *fi );
Cleans the FILEINFO structure. The routine makes use of FreeIDs().
 void MdcResetIDs ( FILEINFO *fi );
Resets the IMG_DATA structures. This is necessary after each conversion.
 void MdcPrintFI ( FILEINFO *fi );
Prints the content of the FILEINFO structure. Useful for debug purposes.
 void MdcSplitPath ( char path[], char **dir, char **fname );
Splits the path in a string pointer to directory and filename.
 int MdcGetFrmt ( FILEINFO *fi );
Checks the format of the file. For the return value, see the representation of the supported formats under the section `Important Defines'. With the INTERACTIVE variable ON, the function returns MDC_FRMT_RAW; see also ReadRaw().
 void MdcGetColorMap ( int map, Uint8 palette[] );
Fills a 256 byte RGB palette with the requested grayscale colormap. Supported maps are gray, inverted, hotmetal & rainbow.
 char *MdcImagesPixelFiddle ( FILEINFO *fi);
Performs all the pixel by pixel processes such as swapping bytes, make positive values, quantitation, rescaling, filling the FILEINFO structure with global & image variables and perform some sanity checks. This important function gets called from MdcReadFile() automatically.
 void MdcPrntMesg ( char *fmt, ... );
Prints a message. Argument is a variable parameter list.
 void MdcPrntWarn ( char *fmt, ... );
Prints a warning. Argument is a variable parameter list.
 void MdcPrntErr ( int code, char *fmt, ... );
Prints an error and quits the program. The first argument is the error code.
 char *MdcReadRAW ( FILEINFO *fi );
 char *MdcWriteRAW ( FILEINFO *fi );
Reads files of an unknown format interactively and writes raw image arrays without headers. MdcReadInterActive() is an alias for MdcReadRAW().
 char *MdcReadGIF ( FILEINFO *fi );
 char *MdcWriteGIF ( FILEINFO *fi );
Reads GIF87a & GIF89a, writes annimated GIF89a files.
 char *MdcReadACR ( FILEINFO *fi );
 char *MdcWriteACR ( FILEINFO *fi );
Reads and writes Acr/Nema files.
 char *MdcReadINW ( FILEINFO *fi );
 char *MdcWriteINW ( FILEINFO *fi );
Reads and writes RUG INW files.
 char *MdcReadECAT6 ( FILEINFO *fi ), *MdcReadECAT7 ( FILEINFO *fi );
 char *MdcWriteECAT6 ( FILEINFO *fi );
Reads ECAT 6 (resp. 7). Writes ECAT 6.4 files.
 char *MdcReadINTF ( FILEINFO *fi );
 char *MdcWriteINTF ( FILEINFO *fi );
Reads and writes InterFile 3.3 files.
 char *MdcReadANLZ ( FILEINFO *fi );
 char *MdcWriteANLZ ( FILEINFO *fi );
Reads and writes Analyze (SPM) files.
 char *MdcReadDICM ( FILEINFO *fi );
 char *MdcWriteDICM ( FILEINFO *fi );
Reads and writes DICOM files. Only the writing of NM or PT module are supported.
 char *MdcReadCONC ( FILEINFO *fi );
 char *MdcWriteCONC ( FILEINFO *fi );
Reads and writes Concorde mircoPET format.

A sample C-source code to show the usage of the most basic functions. Little MedCon so to speak:

-----------------------------------------------------------------------
/*
 * filename: testit.c
 */

#include <stdio.h>

#include "medcon.h"

#undef VERSION /* prevent any conflict */
#define VERSION "TestIt v2.3"

void NewPrefix(int n)
{
    sprintf(prefix,"my%02d-",n); /* max of MDC_MAX_PREFIX (5) chars */
}

int main(int argc, char *argv[])
{
  FILEINFO fi;
  int   *total = mdc_arg_total;  /* total arguments of files & conversions  */
  int   *convs = mdc_arg_convs;  /* counter for each conversion format      */
  char **files = mdc_arg_files;  /* array of pointers to input filenames    */
  int    f, c;                   /* some counters                           */
  int    t=0;                    /* counter for the output name prefix      */
  int    convert, err=MDC_OK;    /* some variables                          */

  /* check arguments */
  if (argc < 2) {
    printf("%s - %s\n",VERSION,MdcGetLibLongVersion());
    MdcPrintUsage(argv[0]);
  }

  /* init library */
  MdcInit();

  /* handle arguments, last one determines max inputfiles */
  if (MdcHandleArgs(&fi,argc,argv,MDC_MAX_FILES) != MDC_OK)
    MdcPrintUsage(argv[0]);

  /* check output/conversion formats */
  if (total[MDC_CONVS] == 0) {
    printf("\n%s: ERROR : No output format specified\n\n",argv[0]);
    return(MDC_BAD_CODE);
  }

  /* do the stuff for each input file */
  for (f=0; f<total[MDC_FILES]; f++) {

     if ((err = MdcOpenFile(&fi, files[f]))  != MDC_OK) return(err);

     if ((err = MdcReadFile(&fi, f+1, NULL)) != MDC_OK) return(err);

     /* do the conversions */
     if (total[MDC_CONVS] > 0) {

       /* go through conversion formats */
       for (c=1; c<MDC_MAX_FRMTS; c++) {
          convert = convs[c];
          /* write output format when selected */
          while (convert -- > 0) {
               if ((err = MdcWriteFile(&fi, c, t++, NULL)) != MDC_OK) {
                 MdcCleanUpFI(&fi);
                 return(err);
               }
          }
       }
     }

     /* clean up FILEINFO struct */
     MdcCleanUpFI(&fi);

  }

  /* finish library */
  MdcFinish();

  return(err);

}

-----------------------------------------------------------------------

Example `Makefile' for compiling `testit.c':

-----------------------------------------------------------------------
#
# filename: Makefile
#
  CC = gcc
  CCOPTS = -Wall -g
  CFLAGS = $(CCOPTS)

  INCS = `xmedcon-config --cflags`
  LIBS = `xmedcon-config --libs`

  testit: testit.c
      $(CC) $(CFLAGS) $(INCS) -o testit testit.c $(LIBS)

# don't forget to put a <tab> before $(CC). You can loose this with copy & paste
----------------------------------------------------------------------- 

<< Introduction | Documentation | Program - CLI >>

Page last modified on January 30, 2007, at 12:01 AM