VBoolean VSetBandInterp (VImage image, VBandInterp frame_interp, int nframes, VBandInterp viewpoint_interp, int nviewpoints, VBandInterp color_interp, int ncolors, VBandInterp component_interp, int ncomponents) { VBoolean result = TRUE; VString str; if (VImageNBands (image) != nframes * nviewpoints * ncolors * ncomponents) { VWarning ("VSetBandInterp: No. bands (%d) conflicts with no. " "of frames, etc. (%d %d %d %d)", VImageNBands (image), nframes, nviewpoints, ncolors, ncomponents); result = FALSE; } if (frame_interp == VBandInterpNone) result &= VExtractAttr (VImageAttrList (image), VFrameInterpAttr, NULL, VStringRepn, & str, FALSE); else VSetAttr (VImageAttrList (image), VFrameInterpAttr, VBandInterpDict, VLongRepn, (VLong) frame_interp); VImageNFrames (image) = nframes; if (viewpoint_interp == VBandInterpNone) result &= VExtractAttr (VImageAttrList (image), VViewpointInterpAttr, NULL, VStringRepn, & str, FALSE); else VSetAttr (VImageAttrList (image), VViewpointInterpAttr, VBandInterpDict, VLongRepn, (VLong) viewpoint_interp); VImageNViewpoints (image) = nviewpoints; if (color_interp == VBandInterpNone) result &= VExtractAttr (VImageAttrList (image), VColorInterpAttr, NULL, VStringRepn, & str, FALSE); else VSetAttr (VImageAttrList (image), VColorInterpAttr, VBandInterpDict, VLongRepn, (VLong) color_interp); VImageNColors (image) = ncolors; if (component_interp == VBandInterpNone) result &= VExtractAttr (VImageAttrList (image), VComponentInterpAttr, NULL, VStringRepn, & str, FALSE); else VSetAttr (VImageAttrList (image), VComponentInterpAttr, VBandInterpDict, VLongRepn, (VLong) component_interp); VImageNComponents (image) = ncomponents; return result; }
VImage VCopyImageAttrs (VImage src, VImage dest) { VAttrList list; if (src == dest) return dest; if (! dest) { dest = VCreateImage (VImageNBands (src), VImageNRows (src), VImageNColumns (src), VPixelRepn (src)); if (! dest) return NULL; } /* Clone the source image's attribute list if it isn't empty: */ if (! VAttrListEmpty (VImageAttrList (src))) { list = VImageAttrList (dest); VImageAttrList (dest) = VCopyAttrList (VImageAttrList (src)); } else if (! VAttrListEmpty (VImageAttrList (dest))) { list = VImageAttrList (dest); VImageAttrList (dest) = VCreateAttrList (); } else list = NULL; if (list) VDestroyAttrList (list); /* Preserve band interpretation attributes only if the source and destination images have the same number of bands: */ if (VImageNBands (src) > 1 && VImageNBands (dest) == VImageNBands (src)) { VImageNFrames (dest) = VImageNFrames (src); VImageNViewpoints (dest) = VImageNViewpoints (src); VImageNColors (dest) = VImageNColors (src); VImageNComponents (dest) = VImageNComponents (src); } else { VExtractAttr (VImageAttrList (dest), VFrameInterpAttr, NULL, VBitRepn, NULL, FALSE); VExtractAttr (VImageAttrList (dest), VViewpointInterpAttr, NULL, VBitRepn, NULL, FALSE); VExtractAttr (VImageAttrList (dest), VColorInterpAttr, NULL, VBitRepn, NULL, FALSE); VExtractAttr (VImageAttrList (dest), VComponentInterpAttr, NULL, VBitRepn, NULL, FALSE); VImageNComponents (dest) = VImageNColors (dest) = VImageNViewpoints (dest) = 1; VImageNFrames (dest) = VImageNBands (dest); } return dest; }
/* ** slicetime correction for non-constant TR */ void VSlicetime_NC(VAttrList list, VShort minval, VFloat tdel, VBoolean slicetime_correction, float *onset_array, VString filename) { FILE *fp = NULL; VImage src; VAttrListPosn posn; VString buf, str; int b, r, c, i, j, nt = 0, mt = 0, val, del = 0; double xmin, xmax, sum, nx, estim_tr = 0; double *xx = NULL, *yy = NULL, xi, yi, slicetime = 0, u = 0; gsl_interp_accel *acc = NULL; gsl_spline *spline = NULL; xmin = (VShort) VRepnMinValue(VShortRepn); xmax = (VShort) VRepnMaxValue(VShortRepn); buf = VMalloc(LEN); /* ** read scan times from file, non-constant TR */ if(strlen(filename) > 2) { fp = fopen(filename, "r"); if(!fp) VError(" error opening file %s", filename); i = 0; while(!feof(fp)) { for(j = 0; j < LEN; j++) buf[j] = '\0'; fgets(buf, LEN, fp); if(buf[0] == '%' || buf[0] == '#') continue; if(strlen(buf) < 2) continue; i++; } rewind(fp); nt = i; fprintf(stderr, " num timesteps: %d\n", nt); xx = (double *) VCalloc(nt, sizeof(double)); yy = (double *) VCalloc(nt, sizeof(double)); i = 0; sum = 0; while(!feof(fp)) { for(j = 0; j < LEN; j++) buf[j] = '\0'; fgets(buf, LEN, fp); if(buf[0] == '%' || buf[0] == '#') continue; if(strlen(buf) < 2) continue; if(sscanf(buf, "%lf", &u) != 1) VError(" line %d: illegal input format", i + 1); xx[i] = u * 1000.0; /* convert to millisec */ if(i > 1) sum += xx[i] - xx[i - 1]; i++; } fclose(fp); estim_tr = sum / (double)(nt - 2); fprintf(stderr, " average scan interval = %.3f sec\n", estim_tr / 1000.0); } /* ** process data */ b = -1; for(VFirstAttr(list, & posn); VAttrExists(& posn); VNextAttr(& posn)) { if(VGetAttrRepn(& posn) != VImageRepn) continue; VGetAttrValue(& posn, NULL, VImageRepn, & src); if(VPixelRepn(src) != VShortRepn) continue; VSetAttr(VImageAttrList(src), "repetition_time", NULL, VLongRepn, (VLong)estim_tr); VExtractAttr(VImageAttrList(src), "MPIL_vista_0", NULL, VStringRepn, &str, FALSE); b++; if(VImageNRows(src) < 2) continue; /* ** get header info */ if(VGetAttr(VImageAttrList(src), "slice_time", NULL, VDoubleRepn, (VPointer) & slicetime) != VAttrFound && slicetime_correction && onset_array == NULL) VError(" 'slice_time' info missing"); if(onset_array != NULL) slicetime = onset_array[b]; if(nt != VImageNBands(src)) VError(" inconsistent number of time steps, %d %d", nt, VImageNBands(src)); if(acc == NULL && slicetime_correction) { acc = gsl_interp_accel_alloc(); spline = gsl_spline_alloc(gsl_interp_akima, nt); for(i = 0; i < 5; i++) { if(xx[i] / 1000.0 > tdel) break; } del = i; fprintf(stderr, " The first %.2f secs (%d timesteps) will be replaced.\n", tdel, del); } /* ** loop through all voxels in current slice */ if(slicetime_correction) fprintf(stderr, " slice: %3d, %10.3f ms\r", b, slicetime); for(r = 0; r < VImageNRows(src); r++) { for(c = 0; c < VImageNColumns(src); c++) { if(VPixel(src, 0, r, c, VShort) < minval) continue; /* replace first few time steps by average */ if(del > 0) { mt = del + 10; if(mt > nt) mt = nt; sum = nx = 0; for(i = del; i < mt; i++) { sum += VPixel(src, i, r, c, VShort); nx++; } if(nx < 1) continue; val = sum / nx; for(i = 0; i < del; i++) { VPixel(src, i, r, c, VShort) = val; } } if(!slicetime_correction) continue; /* correct for slicetime offsets using cubic spline interpolation */ for(i = 0; i < nt; i++) { yy[i] = VPixel(src, i, r, c, VShort); } gsl_spline_init(spline, xx, yy, nt); for(i = 1; i < nt; i++) { xi = xx[i] - slicetime; yi = gsl_spline_eval(spline, xi, acc); val = (int)(yi + 0.49); if(val > xmax) val = xmax; if(val < xmin) val = xmin; VPixel(src, i, r, c, VShort) = val; } } } } fprintf(stderr, "\n"); }