Ejemplo n.º 1
0
int
_alanPerIteration(alanContext *actx, int iter) {
  char me[]="_alanPerIteration", fname[AIR_STRLEN_MED];
  Nrrd *nslc, *nimg;
  
  if (!(actx->saveInterval || actx->frameInterval)) {
    if (actx->verbose && !(iter % 100)) {
      fprintf(stderr, "%s: iter = %d, averageChange = %g\n",
              me, iter, actx->averageChange);
    }
  }
  if (actx->saveInterval && !(iter % actx->saveInterval)) {
    sprintf(fname, "%06d.nrrd", actx->constFilename ? 0 : iter);
    nrrdSave(fname, actx->_nlev[(iter+1) % 2], NULL);
    fprintf(stderr, "%s: iter = %d, averageChange = %g, saved %s\n",
            me, iter, actx->averageChange, fname);
  }
  if (actx->frameInterval && !(iter % actx->frameInterval)) {
    nrrdSlice(nslc=nrrdNew(), actx->_nlev[(iter+1) % 2], 0, 0);
    nrrdQuantize(nimg=nrrdNew(), nslc, NULL, 8);
    sprintf(fname, (2 == actx->dim ? "%06d.png" : "%06d.nrrd"),
            actx->constFilename ? 0 : iter);
    nrrdSave(fname, nimg, NULL);
    fprintf(stderr, "%s: iter = %d, averageChange = %g, saved %s\n",
            me, iter, actx->averageChange, fname);
    nrrdNuke(nslc);
    nrrdNuke(nimg);
  }
  return 0;
}
Ejemplo n.º 2
0
/*
******** coilOutputGet
**
** slice the present intermediate volume to get an output.
**
** No, this does not do quantization or rounding to match the input
** type (of cctx->nin).  The reason is that after filtering, it is often
** the case that subtle differences in values emerge, and it may be
** reckless to dump them back into the limited type or value range
** that they started with.  That sort of operation should be under
** explicit user control.
*/
int
coilOutputGet(Nrrd *nout, coilContext *cctx) {
  static const char me[]="coilOutputGet";
  int baseDim;

  if (!(nout && cctx)) {
    biffAddf(COIL, "%s: got NULL pointer", me);
    return 1;
  }
  baseDim = (1 == cctx->kind->valLen ? 0 : 1);
  if (nrrdSlice(nout, cctx->nvol, baseDim, 0)
      || nrrdAxisInfoCopy(nout, cctx->nin, NULL, NRRD_AXIS_INFO_NONE)
      || nrrdBasicInfoCopy(nout, cctx->nin,
                           NRRD_BASIC_INFO_DATA_BIT
                           | NRRD_BASIC_INFO_TYPE_BIT
                           | NRRD_BASIC_INFO_BLOCKSIZE_BIT
                           | NRRD_BASIC_INFO_DIMENSION_BIT
                           | NRRD_BASIC_INFO_CONTENT_BIT
                           | NRRD_BASIC_INFO_COMMENTS_BIT
                           | (nrrdStateKeyValuePairsPropagate
                              ? 0
                              : NRRD_BASIC_INFO_KEYVALUEPAIRS_BIT))) {
    biffMovef(COIL, NRRD, "%s: trouble getting output", me);
    return 1;
  }
  return 0;
}
Ejemplo n.º 3
0
Archivo: dice.c Proyecto: BRAINSia/teem
int
unrrdu_diceMain(int argc, const char **argv, const char *me,
                hestParm *hparm) {
  hestOpt *opt = NULL;
  char *base, *err, fnout[AIR_STRLEN_MED], /* file name out */
    fffname[AIR_STRLEN_MED],  /* format for filename */
    *ftmpl;                   /* format template */
  Nrrd *nin, *nout;
  int pret, fit;
  unsigned int axis, start, pos, top, size, sanity;
  airArray *mop;

  OPT_ADD_AXIS(axis, "axis to slice along");
  OPT_ADD_NIN(nin, "input nrrd");
  hestOptAdd(&opt, "s,start", "start", airTypeUInt, 1, 1, &start, "0",
             "integer value to start numbering with");
  hestOptAdd(&opt, "ff,format", "form", airTypeString, 1, 1, &ftmpl, "",
             "a printf-style format to use for generating all "
             "filenames.  Use this to override the number of characters "
             "used to represent the slice position, or the file format "
             "of the output, e.g. \"-ff %03d.ppm\" for 000.ppm, "
             "001.ppm, etc. By default (not using this option), slices "
             "are saved in NRRD format (or PNM or PNG where possible) "
             "with shortest possible filenames.");
  /* the fact that we're using unsigned int instead of size_t is
     its own kind of sanity check */
  hestOptAdd(&opt, "l,limit", "max#", airTypeUInt, 1, 1, &sanity, "9999",
             "a sanity check on how many slice files should be saved "
             "out, to prevent accidentally dicing the wrong axis "
             "or the wrong array. Can raise this value if needed.");
  hestOptAdd(&opt, "o,output", "prefix", airTypeString, 1, 1, &base, NULL,
             "output filename prefix (excluding info set via \"-ff\"), "
             "basically to set path of output files (so be sure to end "
             "with \"/\".");

  mop = airMopNew();
  airMopAdd(mop, opt, (airMopper)hestOptFree, airMopAlways);

  USAGE(_unrrdu_diceInfoL);
  PARSE();
  airMopAdd(mop, opt, (airMopper)hestParseFree, airMopAlways);

  if (!( axis < nin->dim )) {
    fprintf(stderr, "%s: given axis (%u) outside range [0,%u]\n",
            me, axis, nin->dim-1);
    airMopError(mop);
    return 1;
  }
  if (nin->axis[axis].size > sanity) {
    char stmp[AIR_STRLEN_SMALL];
    fprintf(stderr, "%s: axis %u size %s > sanity limit %u; "
            "increase via \"-l\"\n", me,
            axis, airSprintSize_t(stmp, nin->axis[axis].size), sanity);
    airMopError(mop);
    return 1;
  }
  size = AIR_UINT(nin->axis[axis].size);

  /* HEY: this should use nrrdSaveMulti(), and if there's additional
     smarts here, they should be moved into nrrdSaveMulti() */
  if (airStrlen(ftmpl)) {
    if (!( _nrrdContainsPercentThisAndMore(ftmpl, 'd')
           || _nrrdContainsPercentThisAndMore(ftmpl, 'u') )) {
      fprintf(stderr, "%s: given filename format \"%s\" doesn't seem to "
              "have the converstion specification to print an integer\n",
              me, ftmpl);
      airMopError(mop);
      return 1;
    }
    sprintf(fffname, "%%s%s", ftmpl);
  } else {
    unsigned int dignum=0, tmps;
    tmps = top = start + size - 1;
    do {
      dignum++;
      tmps /= 10;
    } while (tmps);
    /* sprintf the number of digits into the string that will be used
       to sprintf the slice number into the filename */
    sprintf(fffname, "%%s%%0%uu.nrrd", dignum);
  }
  nout = nrrdNew();
  airMopAdd(mop, nout, (airMopper)nrrdNuke, airMopAlways);

  for (pos=0; pos<size; pos++) {
    if (nrrdSlice(nout, nin, axis, pos)) {
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
      fprintf(stderr, "%s: error slicing nrrd:%s\n", me, err);
      airMopError(mop);
      return 1;
    }
    if (0 == pos && !airStrlen(ftmpl)) {
      /* See if these slices would be better saved as PNG or PNM images.
         Altering the file name will tell nrrdSave() to use a different
         file format.  We wait till now to check this so that we can
         work from the actual slice */
      if (nrrdFormatPNG->fitsInto(nout, nrrdEncodingRaw, AIR_FALSE)) {
        strcpy(fffname + strlen(fffname) - 4, "png");
      } else {
        fit = nrrdFormatPNM->fitsInto(nout, nrrdEncodingRaw, AIR_FALSE);
        if (2 == fit) {
          strcpy(fffname + strlen(fffname) - 4, "pgm");
        } else if (3 == fit) {
          strcpy(fffname + strlen(fffname) - 4, "ppm");
        }
      }
    }
    sprintf(fnout, fffname, base, pos+start);
    fprintf(stderr, "%s: %s ...\n", me, fnout);
    if (nrrdSave(fnout, nout, NULL)) {
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
      fprintf(stderr, "%s: error writing nrrd to \"%s\":%s\n",
              me, fnout, err);
      airMopError(mop);
      return 1;
    }
  }

  airMopOkay(mop);
  return 0;
}
Ejemplo n.º 4
0
int
tend_estimThresholdFind(double *threshP, Nrrd *nbmat, Nrrd *nin4d) {
  char me[]="tend_estimThresholdFind", err[BIFF_STRLEN];
  Nrrd **ndwi;
  airArray *mop;
  unsigned int slIdx, slNum, dwiAx, dwiNum,
    rangeAxisNum, rangeAxisIdx[NRRD_DIM_MAX];
  double *bmat, bten[7], bnorm;
  int dwiIdx;

  mop = airMopNew();

  if (!(threshP && nbmat && nin4d)) {
    sprintf(err, "%s: got NULL pointer", me);
    biffAdd(TEN, err); airMopError(mop); return 1;
  }
  if (tenBMatrixCheck(nbmat, nrrdTypeDouble, 6)) {
    sprintf(err, "%s: problem within given b-matrix", me);
    biffAdd(TEN, err); airMopError(mop); return 1;
  }

  /* HEY: copied from tenEpiRegister4D() */
  rangeAxisNum = nrrdRangeAxesGet(nin4d, rangeAxisIdx);
  if (0 == rangeAxisNum) {
    /* we fall back on old behavior */
    dwiAx = 0;
  } else if (1 == rangeAxisNum) {
    /* thankfully there's exactly one range axis */
    dwiAx = rangeAxisIdx[0];
  } else {
    sprintf(err, "%s: have %u range axes instead of 1, don't know which "
            "is DWI axis", me, rangeAxisNum);
    biffAdd(TEN, err); airMopError(mop); return 1;
  }

  slNum = nin4d->axis[dwiAx].size;
  bmat = AIR_CAST(double *, nbmat->data);
  dwiNum = 0;
  for (slIdx=0; slIdx<slNum; slIdx++) {
    TEN_T_SET(bten, 1.0,
              bmat[0], bmat[1], bmat[2],
              bmat[3], bmat[4],
              bmat[5]);
    bnorm = TEN_T_NORM(bten);
    dwiNum += bnorm > 0.0;
    bmat += 6;
  }
  if (0 == dwiNum) {
    sprintf(err, "%s: somehow got zero DWIs", me);
    biffAdd(TEN, err); airMopError(mop); return 1;
  }
  ndwi = AIR_CAST(Nrrd **, calloc(dwiNum, sizeof(Nrrd *)));
  airMopAdd(mop, ndwi, (airMopper)airFree, airMopAlways);
  bmat = AIR_CAST(double *, nbmat->data);
  dwiIdx = -1;
  for (slIdx=0; slIdx<slNum; slIdx++) {
    TEN_T_SET(bten, 1.0,
              bmat[0], bmat[1], bmat[2],
              bmat[3], bmat[4],
              bmat[5]);
    bnorm = TEN_T_NORM(bten);
    if (bnorm > 0.0) {
      dwiIdx++;
      ndwi[dwiIdx] = nrrdNew();
      airMopAdd(mop, ndwi[dwiIdx], (airMopper)nrrdNuke, airMopAlways);
      if (nrrdSlice(ndwi[dwiIdx], nin4d, dwiAx, slIdx)) {
        sprintf(err, "%s: trouble slicing DWI at index %u", me, slIdx);
        biffMove(TEN, err, NRRD); airMopError(mop); return 1;
      }
    }
    bmat += 6;
  }
  if (_tenEpiRegThresholdFind(threshP, ndwi, dwiNum, AIR_FALSE, 1.5)) {
    sprintf(err, "%s: trouble finding thresh", me);
    biffAdd(TEN, err); airMopError(mop); return 1;
  }
  
  airMopOkay(mop);
  return 0;
}
Ejemplo n.º 5
0
int
unrrdu_diceMain(int argc, char **argv, char *me, hestParm *hparm) {
  hestOpt *opt = NULL;
  char *base, *err, fnout[AIR_STRLEN_MED], /* file name out */
    fffname[AIR_STRLEN_MED],  /* format for filename */
    *ftmpl;                   /* format template */
  Nrrd *nin, *nout;
  int top, pret, start, fit;
  unsigned int axis;
  size_t pos;
  airArray *mop;

  OPT_ADD_AXIS(axis, "axis to slice along");
  OPT_ADD_NIN(nin, "input nrrd");
  hestOptAdd(&opt, "s,start", "start", airTypeInt, 1, 1, &start, "0",
             "integer value to start numbering with");
  hestOptAdd(&opt, "ff,format", "form", airTypeString, 1, 1, &ftmpl, "",
             "a printf-style format to use for generating all "
             "filenames.  Use this to override the number of characters "
             "used to represent the slice position, or the file format "
             "of the output, e.g. \"-ff %03d.ppm\" for 000.ppm, "
             "001.ppm, etc. By default (not using this option), slices "
             "are saved in NRRD format (or PNM or PNG where possible) "
             "with shortest possible filenames.");
  hestOptAdd(&opt, "o,output", "prefix", airTypeString, 1, 1, &base, NULL,
             "output filename prefix (excluding info set via \"-ff\"), "
             "basically to set path of output files (so be sure to end "
             "with \"/\".");

  mop = airMopNew();
  airMopAdd(mop, opt, (airMopper)hestOptFree, airMopAlways);

  USAGE(_unrrdu_diceInfoL);
  PARSE();
  airMopAdd(mop, opt, (airMopper)hestParseFree, airMopAlways);

  if (start < 0) {
    fprintf(stderr, "%s: given start index (%d) less than zero\n", me, start);
    airMopError(mop);
    return 1;
  }
  if (!( axis < nin->dim )) {
    fprintf(stderr, "%s: given axis (%u) outside range [0,%u]\n",
            me, axis, nin->dim-1);
    airMopError(mop);
    return 1;
  }
  
  /* HEY: this should use nrrdSaveMulti(), and if there's additional
     smarts here, they should be moved into nrrdSaveMulti() */
  if (airStrlen(ftmpl)) {
    if (!( _nrrdContainsPercentThisAndMore(ftmpl, 'd') 
           || _nrrdContainsPercentThisAndMore(ftmpl, 'u') )) {
      fprintf(stderr, "%s: given filename format \"%s\" doesn't seem to "
              "have the converstion specification to print an integer\n",
              me, ftmpl);
      airMopError(mop);
      return 1;
    }
    sprintf(fffname, "%%s%s", ftmpl);
  } else {
    top = start + nin->axis[axis].size-1;
    if (top > 9999999) {
      sprintf(fffname, "%%s%%08d.nrrd");
    } else if (top > 999999) {
      sprintf(fffname, "%%s%%07d.nrrd");
    } else if (top > 99999) {
      sprintf(fffname, "%%s%%06d.nrrd");
    } else if (top > 9999) {
      sprintf(fffname, "%%s%%05d.nrrd");
    } else if (top > 999) {
      sprintf(fffname, "%%s%%04d.nrrd");
    } else if (top > 99) {
      sprintf(fffname, "%%s%%03d.nrrd");
    } else if (top > 9) {
      sprintf(fffname, "%%s%%02d.nrrd");
    } else {
      sprintf(fffname, "%%s%%01d.nrrd");
    }
  }
  nout = nrrdNew();
  airMopAdd(mop, nout, (airMopper)nrrdNuke, airMopAlways);

  for (pos=0; pos<nin->axis[axis].size; pos++) {
    if (nrrdSlice(nout, nin, axis, pos)) {
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
      fprintf(stderr, "%s: error slicing nrrd:%s\n", me, err);
      airMopError(mop);
      return 1;
    }
    if (0 == pos && !airStrlen(ftmpl)) {
      /* See if these slices would be better saved as PNG or PNM images.
         Altering the file name will tell nrrdSave() to use a different
         file format. */
      if (nrrdFormatPNG->fitsInto(nout, nrrdEncodingRaw, AIR_FALSE)) {
        strcpy(fffname + strlen(fffname) - 4, "png");
      } else {
        fit = nrrdFormatPNM->fitsInto(nout, nrrdEncodingRaw, AIR_FALSE);
        if (2 == fit) {
          strcpy(fffname + strlen(fffname) - 4, "pgm");
        } else if (3 == fit) {
          strcpy(fffname + strlen(fffname) - 4, "ppm");
        }
      }
    }
    sprintf(fnout, fffname, base, pos+start);
    fprintf(stderr, "%s: %s ...\n", me, fnout);
    if (nrrdSave(fnout, nout, NULL)) {
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
      fprintf(stderr, "%s: error writing nrrd to \"%s\":%s\n",
              me, fnout, err);
      airMopError(mop);
      return 1;
    }
  }

  airMopOkay(mop);
  return 0;
}
Ejemplo n.º 6
0
int
unrrdu_cmedianMain(int argc, char **argv, char *me, hestParm *hparm) {
  hestOpt *opt = NULL;
  char *out, *err;
  Nrrd *nin, *nout, *ntmp, **mnout;
  int pad, pret, mode, chan, ni, nsize;
  unsigned int bins, radius;
  airArray *mop;
  float wght;

  hestOptAdd(&opt, "r,radius", "radius", airTypeUInt, 1, 1, &radius, NULL,
             "how big a window to filter over. \"-r 1\" leads to a "
             "3x3 window in an image, and a 3x3x3 window in a volume");
  hestOptAdd(&opt, "mode", NULL, airTypeInt, 0, 0, &mode, NULL,
             "By default, median filtering is done.  Using this option "
             "enables mode filtering, in which the most common value is "
             "used as output");
  hestOptAdd(&opt, "b,bins", "num", airTypeUInt, 1, 1, &bins, "256",
             "# of bins in histogram.  It is in your interest to minimize "
             "this number, since big histograms mean slower execution "
             "times.  8-bit data needs at most 256 bins.");
  hestOptAdd(&opt, "w,weight", "weight", airTypeFloat, 1, 1, &wght, "1.0",
             "How much higher to preferentially weight samples that are "
             "closer to the center of the window.  \"1.0\" weight means that "
             "all samples are uniformly weighted over the window, which "
             "facilitates a simple speed-up. ");
  hestOptAdd(&opt, "p,pad", NULL, airTypeInt, 0, 0, &pad, NULL,
             "Pad the input (with boundary method \"bleed\"), "
             "and crop the output, so as to "
             "overcome our cheapness and correctly "
             "handle the border.  Obviously, this takes more memory.");
  hestOptAdd(&opt, "c,channel", NULL, airTypeInt, 0, 0, &chan, NULL,
             "Slice the input along axis 0, run filtering on all slices, "
             "and join the results back together.  This is the way you'd "
             "want to process color (multi-channel) images or volumes.");
  OPT_ADD_NIN(nin, "input nrrd");
  OPT_ADD_NOUT(out, "output nrrd");

  mop = airMopNew();
  airMopAdd(mop, opt, (airMopper)hestOptFree, airMopAlways);

  USAGE(_unrrdu_cmedianInfoL);
  PARSE();
  airMopAdd(mop, opt, (airMopper)hestParseFree, airMopAlways);
  
  nout = nrrdNew();
  airMopAdd(mop, nout, (airMopper)nrrdNuke, airMopAlways);

  if (chan) {
    nsize = nin->axis[0].size;
    mnout = (Nrrd **)calloc(nsize, sizeof(Nrrd));
    airMopAdd(mop, mnout, airFree, airMopAlways);
    ntmp = nrrdNew();
    airMopAdd(mop, ntmp, (airMopper)nrrdNuke, airMopAlways);
    for (ni=0; ni<nsize; ni++) {
      if (nrrdSlice(ntmp, nin, 0, ni)) {
        airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
        fprintf(stderr, "%s: error slicing input at pos = %d:\n%s",
                me, ni, err);
        airMopError(mop);
        return 1;
      }
      airMopAdd(mop, mnout[ni] = nrrdNew(), (airMopper)nrrdNuke, airMopAlways);
      if (nrrdCheapMedian(mnout[ni], ntmp, pad, mode, radius, wght, bins)) {
        airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
        fprintf(stderr, "%s: error doing cheap median:\n%s", me, err);
        airMopError(mop);
        return 1;
      }
    }
    if (nrrdJoin(nout, (const Nrrd**)mnout, nsize, 0, AIR_TRUE)) {
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
      fprintf(stderr, "%s: error doing final join:\n%s", me, err);
      airMopError(mop);
      return 1;
    }
  } else {
    if (nrrdCheapMedian(nout, nin, pad, mode, radius, wght, bins)) {
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
      fprintf(stderr, "%s: error doing cheap median:\n%s", me, err);
      airMopError(mop);
      return 1;
    }
  }

  SAVE(out, nout, NULL);

  airMopOkay(mop);
  return 0;
}
Ejemplo n.º 7
0
int
unrrdu_lut2Main(int argc, char **argv, char *me, hestParm *hparm) {
  hestOpt *opt = NULL;
  char *out, *err;
  Nrrd *nin, *nlut, *nout, *ntmp[2];
  airArray *mop;
  int typeOut, rescale[2], pret, blind8BitRange;
  double min[2], max[2];
  NrrdRange *range[2]={NULL,NULL};
  unsigned int mapAxis, rai;

  hestOptAdd(&opt, "m,map", "lut", airTypeOther, 1, 1, &nlut, NULL,
             "lookup table to map input nrrd through",
             NULL, NULL, nrrdHestNrrd);
  hestOptAdd(&opt, "r,rescale", "bool bool", airTypeBool, 2, 2, rescale,
             "false false",
             "rescale one or both of the input values from the "
             "input range to the lut domain.  The lut domain is either "
             "explicitly defined by the axis min,max along axis 0 or 1, "
             "or, it is implicitly defined as zero to the length of that axis "
             "minus one.");
  hestOptAdd(&opt, "min,minimum", "min0 min1", airTypeDouble, 2, 2, min,
             "nan nan",
             "Low ends of input range. Defaults to lowest values "
             "found in input nrrd.  Explicitly setting this is useful "
             "only with rescaling (\"-r\")");
  hestOptAdd(&opt, "max,maximum", "max0 max1", airTypeDouble, 2, 2, max,
             "nan nan",
             "High end of input range. Defaults to highest values "
             "found in input nrrd.  Explicitly setting this is useful "
             "only with rescaling (\"-r\")");
  hestOptAdd(&opt, "blind8", "bool", airTypeBool, 1, 1, &blind8BitRange,
             nrrdStateBlind8BitRange ? "true" : "false",
             "Whether to know the range of 8-bit data blindly "
             "(uchar is always [0,255], signed char is [-128,127]). "
             "Explicitly setting this is useful only with rescaling (\"-r\")");
  hestOptAdd(&opt, "t,type", "type", airTypeOther, 1, 1, &typeOut, "default",
             "specify the type (\"int\", \"float\", etc.) of the "
             "output nrrd. "
             "By default (not using this option), the output type "
             "is the lut's type.",
             NULL, NULL, &unrrduHestMaybeTypeCB);
  OPT_ADD_NIN(nin, "input nrrd");
  OPT_ADD_NOUT(out, "output nrrd");

  mop = airMopNew();
  airMopAdd(mop, opt, (airMopper)hestOptFree, airMopAlways);

  USAGE(_unrrdu_lut2InfoL);
  PARSE();
  airMopAdd(mop, opt, (airMopper)hestParseFree, airMopAlways);

  nout = nrrdNew();
  airMopAdd(mop, nout, (airMopper)nrrdNuke, airMopAlways);

  if (!( nin->dim > 1 && 2 == nin->axis[0].size )) {
    fprintf(stderr, "%s: input nrrd dim must be > 1, and axis[0].size "
            "must be 2 (not " _AIR_SIZE_T_CNV ")", me, nin->axis[0].size);
    airMopError(mop);
    return 1;
  }
  mapAxis = nlut->dim - 2;
  if (!(0 == mapAxis || 1 == mapAxis)) {
    fprintf(stderr, "%s: dimension of lut should be 2 or 3, not %d", 
            me, nlut->dim);
    airMopError(mop);
    return 1;
  }

  /* see comment in rmap.c */
  for (rai=0; rai<=1; rai++) {
    if (!( AIR_EXISTS(nlut->axis[mapAxis + rai].min) && 
           AIR_EXISTS(nlut->axis[mapAxis + rai].max) )) {
      rescale[rai] = AIR_TRUE;
    }
    if (rescale[rai]) {
      ntmp[rai] = nrrdNew();
      airMopAdd(mop, ntmp[rai], AIR_CAST(airMopper, nrrdNuke), airMopAlways);
      if (nrrdSlice(ntmp[rai], nin, 0, rai)) {
        airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
        fprintf(stderr, "%s: trouble slicing input value %u:\n%s",
                me, rai, err);
        airMopError(mop);
        return 1;
      }
      range[rai] = nrrdRangeNew(min[rai], max[rai]);
      airMopAdd(mop, range[rai], (airMopper)nrrdRangeNix, airMopAlways);
      nrrdRangeSafeSet(range[rai], ntmp[rai], blind8BitRange);
    }
  }
  if (nrrdTypeDefault == typeOut) {
    typeOut = nlut->type;
  }
  if (nrrdApply2DLut(nout, nin, 0, range[0], range[1], nlut, typeOut,
                     rescale[0], rescale[1])) {
    airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
    fprintf(stderr, "%s: trouble applying 2-D LUT:\n%s", me, err);
    airMopError(mop);
    return 1;
  }

  SAVE(out, nout, NULL);

  airMopOkay(mop);
  return 0;
}
Ejemplo n.º 8
0
int
main(int argc, char *argv[]) {
  char *me, *err;
  hestOpt *hopt=NULL;
  airArray *mop;

  char *outTenS, *outCovarS, *outRmvS;
  int seed, E;
  unsigned int NN;
  Nrrd *_ninTen, *ninTen, *ngrad, *_ninB0, *ninB0, *nmask,
    *noutCovar, *noutTen, *noutRmv, *ntbuff;
  float sigma, bval;
  size_t sizeX, sizeY, sizeZ;
  tenEstimateContext *tec;
  int axmap[NRRD_DIM_MAX], randrot;

  mop = airMopNew();
  me = argv[0];
  hestOptAdd(&hopt, "i", "ten", airTypeOther, 1, 1, &_ninTen, NULL,
             "input tensor volume", NULL, NULL, nrrdHestNrrd);
  hestOptAdd(&hopt, "n", "#sim", airTypeUInt, 1, 1, &NN, "100",
             "number of simulations to run");
  hestOptAdd(&hopt, "seed", "seed", airTypeInt, 1, 1, &seed, "42",
             "seed value for RNG which creates noise");
  hestOptAdd(&hopt, "r", "reference field", airTypeOther, 1, 1, &_ninB0, NULL,
             "reference anatomical scan, with no diffusion weighting",
             NULL, NULL, nrrdHestNrrd);
  hestOptAdd(&hopt, "rr", NULL, airTypeOther, 0, 0, &randrot, NULL,
             "randomize gradient set orientation");
  hestOptAdd(&hopt, "g", "grad list", airTypeOther, 1, 1, &ngrad, "",
             "gradient list, one row per diffusion-weighted image", 
             NULL, NULL, nrrdHestNrrd);
  hestOptAdd(&hopt, "b", "b", airTypeFloat, 1, 1, &bval, "1000",
             "b value for simulated scan");
  hestOptAdd(&hopt, "sigma", "sigma", airTypeFloat, 1, 1, &sigma, "0.0",
             "Rician noise parameter");
  hestOptAdd(&hopt, "ot", "filename", airTypeString, 1, 1, &outTenS, 
             "tout.nrrd", "file to write output tensor nrrd to");
  hestOptAdd(&hopt, "oc", "filename", airTypeString, 1, 1, &outCovarS, 
             "cout.nrrd", "file to write output covariance nrrd to");
  hestOptAdd(&hopt, "or", "filename", airTypeString, 1, 1, &outRmvS, 
             "rout.nrrd", "file to write output R_i means, variances to");
  hestParseOrDie(hopt, argc-1, argv+1, NULL,
                 me, info, AIR_TRUE, AIR_TRUE, AIR_TRUE);
  airMopAdd(mop, hopt, (airMopper)hestOptFree, airMopAlways);
  airMopAdd(mop, hopt, (airMopper)hestParseFree, airMopAlways);

  if (tenGradientCheck(ngrad, nrrdTypeDefault, 7)) {
    airMopAdd(mop, err = biffGetDone(TEN), airFree, airMopAlways);
    fprintf(stderr, "%s: problem with gradient list:\n%s\n", me, err);
    airMopError(mop); 
    return 1;
  }
  if (tenTensorCheck(_ninTen, nrrdTypeDefault, AIR_TRUE, AIR_TRUE)) {
    airMopAdd(mop, err = biffGetDone(TEN), airFree, airMopAlways);
    fprintf(stderr, "%s: didn't like input:\n%s\n", me, err);
    airMopError(mop); 
    return 1;
  }
  sizeX = _ninTen->axis[1].size;
  sizeY = _ninTen->axis[2].size;
  sizeZ = _ninTen->axis[3].size;
  if (!(3 == _ninB0->dim &&
        sizeX == _ninB0->axis[0].size &&
        sizeY == _ninB0->axis[1].size &&
        sizeZ == _ninB0->axis[2].size)) {
    fprintf(stderr, "%s: given B0 (%u-D) volume not 3-D " _AIR_SIZE_T_CNV
            "x" _AIR_SIZE_T_CNV "x" _AIR_SIZE_T_CNV, me, _ninB0->dim,
            sizeX, sizeY, sizeZ);
    airMopError(mop); 
    return 1;
  }

  ninTen = nrrdNew();
  airMopAdd(mop, ninTen, (airMopper)nrrdNuke, airMopOnError);
  nmask = nrrdNew();
  airMopAdd(mop, nmask, (airMopper)nrrdNuke, airMopOnError);
  ninB0 = nrrdNew();
  airMopAdd(mop, ninB0, (airMopper)nrrdNuke, airMopOnError);
  noutCovar = nrrdNew();
  airMopAdd(mop, noutCovar, (airMopper)nrrdNuke, airMopOnError);
  noutTen = nrrdNew();
  airMopAdd(mop, noutTen, (airMopper)nrrdNuke, airMopOnError);
  noutRmv = nrrdNew();
  airMopAdd(mop, noutRmv, (airMopper)nrrdNuke, airMopOnError);
  ntbuff = nrrdNew();
  airMopAdd(mop, ntbuff, (airMopper)nrrdNuke, airMopOnError);

  if (nrrdConvert(ninTen, _ninTen, nrrdTypeDouble)
      || nrrdSlice(nmask, ninTen, 0, 0)
      || nrrdConvert(ninB0, _ninB0, nrrdTypeDouble)
      || nrrdMaybeAlloc_va(noutTen, nrrdTypeDouble, 4, 
                           AIR_CAST(size_t, 7), sizeX, sizeY, sizeZ)
      || nrrdMaybeAlloc_va(noutCovar, nrrdTypeDouble, 4, 
                           AIR_CAST(size_t, 21), sizeX, sizeY, sizeZ)
      || nrrdMaybeAlloc_va(noutRmv, nrrdTypeDouble, 4, 
                           AIR_CAST(size_t, 6), sizeX, sizeY, sizeZ)
      || nrrdMaybeAlloc_va(ntbuff, nrrdTypeDouble, 2,
                           AIR_CAST(size_t, 7), NN)) {
    airMopAdd(mop, err=biffGetDone(NRRD), airFree, airMopAlways);
    fprintf(stderr, "%s: trouble setting up tec:\n%s\n", me, err);
    airMopError(mop);
    return 1;
  }

  tec = tenEstimateContextNew();
  airMopAdd(mop, tec, (airMopper)tenEstimateContextNix, airMopAlways);

  E = 0;
  if (!E) E |= tenEstimateMethodSet(tec, tenEstimate1MethodLLS);
  if (!E) E |= tenEstimateValueMinSet(tec, 0.000000001);
  if (!E) E |= tenEstimateGradientsSet(tec, ngrad, bval, AIR_TRUE);
  if (!E) E |= tenEstimateThresholdSet(tec, 0, 0);
  if (!E) E |= tenEstimateUpdate(tec);
  if (E) {
    airMopAdd(mop, err=biffGetDone(TEN), airFree, airMopAlways);
    fprintf(stderr, "%s: trouble setting up tec:\n%s\n", me, err);
    airMopError(mop);
    return 1;
  }

  airSrandMT(seed);

  fprintf(stderr, "!%s: randrot = %d\n", me, randrot);
  if (1) {
    unsigned int II;
    unsigned int nsamp;
    double *inTen, *outTen, *outCovar, *outRmv, 
      *dwibuff, (*lup)(const void *, size_t);
    char doneStr[AIR_STRLEN_SMALL];

    dwibuff = AIR_CAST(double *, calloc(ngrad->axis[1].size, sizeof(double)));
    airMopAdd(mop, dwibuff, airFree, airMopAlways);
    nsamp = sizeX*sizeY*sizeZ;
    inTen = AIR_CAST(double *, ninTen->data);
    lup  = nrrdDLookup[nrrdTypeDouble];
    outTen = AIR_CAST(double *, noutTen->data);
    outCovar = AIR_CAST(double *, noutCovar->data);
    outRmv = AIR_CAST(double *, noutRmv->data);
    fprintf(stderr, "!%s: simulating ...       ", me);
    fflush(stderr);
    for (II=0; II<nsamp; II++) {
      if (!(II % sizeX)) {
        fprintf(stderr, "%s", airDoneStr(0, II, nsamp, doneStr));
        fflush(stderr);
      }
      if (csimDo(outTen, outCovar, outRmv + 0, outRmv + 3, ntbuff,
                 tec, dwibuff, sigma,
                 bval, lup(ninB0->data, II), NN, randrot, inTen)) {
        airMopAdd(mop, err=biffGetDone(TEN), airFree, airMopAlways);
        fprintf(stderr, "%s: trouble:\n%s\n", me, err);
        airMopError(mop);
        return 1;
      }
      inTen += 7;
      outTen += 7;
      outCovar += 21;
      outRmv += 6;
    }
    fprintf(stderr, "%s\n", airDoneStr(0, II, nsamp, doneStr));
  }