Ejemplo n.º 1
0
/*!
 * Fill IMG struct header information from Analyze 7.5 database files.
 *  SIF file is read if available. Information concerning separate frames
 *  or planes is not filled though.
 *
 * @param dbname name of Analyze database, may contain filename extension
 * @param img pointer to the initiated IMG data
 * @return errstatus, which is STATUS_OK (0) when call was successful,
 * and >0 in case of an error.
 */
int imgReadAnalyzeHeader(const char *dbname, IMG *img) {
  char hdrfile[FILENAME_MAX], siffile[FILENAME_MAX];
  ANALYZE_DSR ana_header;
  SIF sif;
  double f;
  int ret;

  if(IMG_TEST) printf("\nimgReadAnalyzeHeader(%s, *img)\n", dbname);
  
  /* Check the input */
  if(img==NULL) return STATUS_FAULT;
  if(img->status!=IMG_STATUS_INITIALIZED) return STATUS_FAULT;
  imgSetStatus(img, STATUS_FAULT);
  if(dbname==NULL) return STATUS_FAULT;

  /* Determine the names of hdr and sif files */
  ret=anaDatabaseExists(dbname, hdrfile, NULL, siffile);
  if(ret==0) return STATUS_NOFILE;
  
  /* Read Analyze header file */
  ret=anaReadHeader(hdrfile, &ana_header);
  if(ret!=0) {
    if(IMG_TEST>1) printf("anaReadHeader() return value := %d\n", ret);
    if(ret==1) return STATUS_FAULT;
    else if(ret==2) return STATUS_NOHEADERFILE;
    else return STATUS_UNSUPPORTED;
    return(STATUS_FAULT);
  }
  /* and set IMG contents */
  ret=imgGetAnalyzeHeader(img, &ana_header);
  if(ret!=0) {
    imgSetStatus(img, ret);
    return(ret);
  }

  /* If SIF does not exist, then that's it */
  if(!siffile[0]) {
    imgSetStatus(img, STATUS_OK);
    return STATUS_OK;
  }

  /* SIF is available, so read that too */
  sifInit(&sif); ret=0;
  if(sifRead(siffile, &sif)!=0) return STATUS_OK;
  /* Copy scan time */
  img->scanStart=sif.scantime;
  /* Study number, if not yet defined */
  if(!img->studyNr[0] && strlen(sif.studynr)>1 )
    strncpy(img->studyNr, sif.studynr, MAX_STUDYNR_LEN);
  /* Isotope half-life, if not yet defined */
  f=hlFromIsotope(sif.isotope_name);
  if(img->isotopeHalflife<=0.0 && f>0.0) img->isotopeHalflife=60.0*f;
  sifEmpty(&sif);

  return STATUS_OK;
}
Ejemplo n.º 2
0
/*!
 * Remove header and data files belonging to specified Analyze 7.5 database.
 * SIF is not deleted in any case.
 * @return 0 when call was successful, 1 if header file deletion failed, 
 * 2 if data file deletion failed.
 * Call is considered successful, if database does not exist initially.
 */
int anaRemove(const char *dbname) {
  char datfile[FILENAME_MAX], hdrfile[FILENAME_MAX], siffile[FILENAME_MAX];

  if(ANALYZE_TEST) printf("anaRemove(%s)\n", dbname);
  if(anaDatabaseExists(dbname, hdrfile, datfile, siffile)==0) return 0;
  if(ANALYZE_TEST>2) printf("  removing %s and %s\n", hdrfile, datfile);
  if(remove(hdrfile)!=0) return 1;
  if(remove(datfile)!=0) return 2;
  return 0;
}
Ejemplo n.º 3
0
/*!
 * Write one PET frame from IMG data struct into Analyze 7.5 database file.
 *  This function can be called repeatedly to write all frames one at a time
 *  to conserve memory. This function does not write SIF.
 *
 * @param dbname name of file where IMG contents will be written.
 *  If file does not exist, it is created.
 *  Make sure to delete existing file, unless you want to add data
 * @param frame_to_write PET frame number (1..frameNr) which will be written:
 *  If set to 0, frame data will be written to an existing or new PET file as
 *  a new frame, never overwriting existing data.
 *  If >0, then frame data is written as specified frame number, overwriting
 *  any data existing with the same frame number
 * @param img pointer to the IMG data struct
 * @param frame_index IMG frame index (0..dimt-1) which will be written
 * @param fmin minimum pixel value in all frames that will be written;
 *  used only when writing the first frame
 * @param fmax maximum pixel value in all frames that will be written;
 *  used only when writing the first frame
 * @return errstatus, which is STATUS_OK (0) when call was successful,
 * and >0 in case of an error.
 */
int imgWriteAnalyzeFrame(
  const char *dbname, int frame_to_write, IMG *img, int frame_index,
  float fmin, float fmax
) {
  IMG test_img;
  int ret=0, pxlNr, zi, xi, yi, little;
  FILE *fp;
  short int *sdata=NULL, *sptr;
  char datfile[FILENAME_MAX], hdrfile[FILENAME_MAX], siffile[FILENAME_MAX];
  ANALYZE_DSR dsr;
  float scale_factor=1.0;


  if(IMG_TEST) printf("\nimgWriteAnalyzeFrame(%s, %d, *img, %d, %g, %g)\n",
    dbname, frame_to_write, frame_index, fmin, fmax);

  /*
   *  Check the input 
   */
  if(dbname==NULL) return STATUS_FAULT;
  if(img==NULL) return STATUS_FAULT;
  if(img->status!=IMG_STATUS_OCCUPIED) return STATUS_FAULT;
  if(frame_to_write<0) return STATUS_FAULT;
  if(frame_index<0 || frame_index>=img->dimt) return STATUS_FAULT;
  if(img->_fileFormat!=IMG_ANA_L && img->_fileFormat!=IMG_ANA)
    return STATUS_FAULT;

  /*
   *  If database does not exist, then create it with new header,
   *  and if it does exist, then read and check header information.
   *  Create or edit header to contain correct frame nr.
   *  Determine the global scaling factor.   
   */
  imgInit(&test_img);
  if(anaDatabaseExists(dbname, hdrfile, datfile, siffile)==0) { // not existing

    /* Create database filenames */
    sprintf(hdrfile, "%s.hdr", dbname);
    sprintf(datfile, "%s.img", dbname);
    sprintf(siffile, "%s.sif", dbname);

    /* Set main header */
    imgSetAnalyzeHeader(img, dbname, &dsr, fmin, fmax);
    if(frame_to_write==0) frame_to_write=1;
    dsr.dime.dim[4]=frame_to_write;
    scale_factor=dsr.dime.funused1;
    if(fabs(scale_factor)>1.0E-20) scale_factor=1.0/scale_factor;

    /* Write Analyze header */
    ret=anaWriteHeader(hdrfile, &dsr);
    if(ret && IMG_TEST) printf("anaWriteHeader() := %d\n", ret);
    if(ret) return STATUS_CANTWRITEHEADERFILE;

    /* Remove datafile if necessary */
    if(access(datfile, 0) != -1) remove(datfile);

  } else { /* database does exist */
  
    /* Read header information for checking */
    ret=imgReadAnalyzeHeader(dbname, &test_img);
    if(ret!=0) {imgEmpty(&test_img); return ret;}
    /* Check that file format is the same */
    if(img->_fileFormat!=test_img._fileFormat || img->type!=test_img.type) {
      imgEmpty(&test_img); return STATUS_WRONGFILETYPE;}
    /* Check that matrix sizes are the same */
    if(img->dimz!=test_img.dimz || img->dimx!=test_img.dimx ||
       img->dimy!=test_img.dimy) {
      imgEmpty(&test_img); return STATUS_VARMATSIZE;}
    imgEmpty(&test_img);

    /* Read the header, set new frame number, and write it back */
    /* Get also the scale factor */
    if((ret=anaReadHeader(hdrfile, &dsr))!=0) return STATUS_NOMAINHEADER;
    scale_factor=1.0/dsr.dime.funused1;
    if(frame_to_write==0) frame_to_write=dsr.dime.dim[4]+1;
    if(dsr.dime.dim[4]<frame_to_write) {
      if(dsr.dime.dim[4]+1<frame_to_write) return STATUS_MISSINGMATRIX;
      dsr.dime.dim[4]=frame_to_write;
    }
    if((ret=anaWriteHeader(hdrfile, &dsr))!=0) return STATUS_NOWRITEPERM;
  }
  if(IMG_TEST>2) {
    printf("frame_to_write := %d\n", frame_to_write);
    printf("hdrfile := %s\n", hdrfile);
    printf("datfile := %s\n", datfile);
    printf("siffile := %s\n", siffile);
  }

  /* Allocate memory for matrix short int data (one plane) */
  pxlNr=img->dimx*img->dimy;
  sdata=(short int*)malloc(pxlNr*sizeof(short int));
  if(sdata==NULL) return STATUS_NOMEMORY;

  /* Open datafile, not removing possible old contents */
  if(frame_to_write==1) fp=fopen(datfile, "wb"); else fp=fopen(datfile, "r+b");
  if(fp==NULL) {free(sdata); return STATUS_CANTWRITEIMGFILE;}
  /* Move file pointer to the place of current frame */
  if(fseek(fp, (frame_to_write-1)*pxlNr*img->dimz*sizeof(short int),
           SEEK_SET)!=0) {
    free(sdata); fclose(fp); return STATUS_MISSINGMATRIX;}
  little=little_endian();
  /* Copy, scale and write data plane-by-plane */
  if(anaFlipping()==0) {
    for(zi=0; zi<img->dimz; zi++) {
      sptr=sdata;
     /*printf("plane := %d\n  scale_factor := %g\n", zi+1, scale_factor);*/
      for(yi=img->dimy-1; yi>=0; yi--) for(xi=img->dimx-1; xi>=0; xi--) {
        *sptr=temp_roundf(scale_factor*img->m[zi][yi][xi][frame_index]); sptr++;
      }
      /* Change byte order if necessary */
      sptr=sdata; if(little!=dsr.little) swabip(sptr, pxlNr*sizeof(short int));
      /* Write image data */
      sptr=sdata;
      if(fwrite(sptr, sizeof(short int), pxlNr, fp) != pxlNr) {
        free(sdata); fclose(fp); return STATUS_CANTWRITEIMGFILE;
      }
    }
  } else {
    for(zi=img->dimz-1; zi>=0; zi--) {
      sptr=sdata;
      for(yi=img->dimy-1; yi>=0; yi--) for(xi=img->dimx-1; xi>=0; xi--) {
        *sptr=temp_roundf(scale_factor*img->m[zi][yi][xi][frame_index]); sptr++;
      }
      /* Change byte order if necessary */
      sptr=sdata; if(little!=dsr.little) swabip(sptr, pxlNr*sizeof(short int));
      /* Write image data */
      sptr=sdata;
      if(fwrite(sptr, sizeof(short int), pxlNr, fp) != pxlNr) {
        free(sdata); fclose(fp); return STATUS_CANTWRITEIMGFILE;
      }
    }
  }
  free(sdata);
  fclose(fp);

  return STATUS_OK;
}
Ejemplo n.º 4
0
/*!
 * Read a specified frame from an Analyze 7.5 database into preallocated IMG
 *  data structure. Analyze database consists of two or three files in the same 
 *  directory: fname.hdr, fname.img, and optionally fname.sif.
 *  IMG header is assumed to be filled correctly before calling this function,
 *  except for information concerning separate planes and this frame,
 *  which is filled here.
 *  If frame does not exist, then and only then STATUS_NOMATRIX is returned.
 *
 * @param fname name of Analyze database from which IMG contents will be read
 * @param frame_to_read frame which will be read [1..frameNr]
 * @param img pointer to the IMG data. Place for the frame must be preallocated
 * @param frame_index IMG frame index [0..dimt-1] where data will be placed
 * @return errstatus, which is STATUS_OK (0) when call was successful,
 * and >0 in case of an error.
 */ 
int imgReadAnalyzeFrame(
  const char *fname, int frame_to_read, IMG *img, int frame_index
) {
  FILE *fp;
  int ret, pi, xi, yi;
  float *fdata=NULL, *fptr;
  ANALYZE_DSR dsr;
  char datfile[FILENAME_MAX], hdrfile[FILENAME_MAX], siffile[FILENAME_MAX];
  SIF sif;


  if(IMG_TEST) printf("\nimgReadAnalyzeFrame(%s, %d, *img, %d)\n",
    fname, frame_to_read, frame_index);
    
  /* Check the input */
  if(img==NULL) return STATUS_FAULT;
  if(img->status!=IMG_STATUS_OCCUPIED) return STATUS_FAULT;
  if(fname==NULL) return STATUS_FAULT;
  if(frame_index<0 || frame_index>img->dimt-1) return STATUS_FAULT;
  if(frame_to_read<1) return STATUS_FAULT;
  imgSetStatus(img, STATUS_FAULT);
  
  /* Determine the names of hdr, data and sif files */
  ret=anaDatabaseExists(fname, hdrfile, datfile, siffile);
  if(ret==0) return STATUS_NOFILE;

  /* Read Analyze header file */
  ret=anaReadHeader(hdrfile, &dsr);
  if(ret!=0) {
    if(ret==1) return STATUS_FAULT;
    else if(ret==2) return STATUS_NOHEADERFILE;
    else return STATUS_UNSUPPORTED;
    return(STATUS_FAULT);
  }

  /* Open image datafile */
  if(IMG_TEST>2) fprintf(stdout, "reading image data %s\n", datfile);
  if((fp=fopen(datfile, "rb")) == NULL) return STATUS_NOIMGDATA;

  /* Allocate memory for one image frame */
  fdata=malloc(img->dimx*img->dimy*img->dimz*sizeof(float));
  if(fdata==NULL) {fclose(fp); return STATUS_NOMEMORY;}

  /* Read the required image frame */
  fptr=fdata;
  ret=anaReadImagedata(fp, &dsr, frame_to_read, fptr);
  fclose(fp);
  if(ret==3) {free(fdata); return STATUS_NOMATRIX;} /* no more frames */
  if(ret!=0) {free(fdata); return STATUS_UNSUPPORTED;}

  /* Copy pixel values to IMG */
  fptr=fdata;
  if(anaFlipping()==0) { /* no flipping in z-direction */
    for(pi=0; pi<img->dimz; pi++)
      for(yi=img->dimy-1; yi>=0; yi--)
        for(xi=img->dimx-1; xi>=0; xi--)
          img->m[pi][yi][xi][frame_index]=*fptr++;
  } else {
    for(pi=img->dimz-1; pi>=0; pi--)
      for(yi=img->dimy-1; yi>=0; yi--)
        for(xi=img->dimx-1; xi>=0; xi--)
          img->m[pi][yi][xi][frame_index]=*fptr++;
  }
  free(fdata);

  /* Set decay correction factor to zero */
  img->decayCorrFactor[frame_index]=0.0;

  imgSetStatus(img, STATUS_OK); /* If the rest is failed, no problem */

  /* 
   *  Try to read frame time information from SIF file
   */
  sifInit(&sif);
  if(sifRead(siffile, &sif)!=0) return STATUS_OK;
  /* Frame information */
  if(sif.frameNr>=frame_to_read) {
    img->start[frame_index]=sif.x1[frame_to_read-1];
    img->end[frame_index]=sif.x2[frame_to_read-1];
    img->mid[frame_index]=0.5*(img->start[frame_index]+img->end[frame_index]);
    img->prompts[frame_index]=sif.prompts[frame_to_read-1];
    img->randoms[frame_index]=sif.randoms[frame_to_read-1];
  }
  sifEmpty(&sif);

  return STATUS_OK;
}