VBandInterp VImageColorInterp (VImage image) { VLong interp; VGetAttrResult result; if (VImageNBands (image) != (VImageNFrames (image) * VImageNViewpoints (image) * VImageNColors (image) * VImageNComponents (image))) VWarning ("VImageColorInterp: No. bands (%d) conflicts with no. " "of frames, etc. (%d %d %d %d)", VImageNBands (image), VImageNFrames (image), VImageNViewpoints (image), VImageNColors (image), VImageNComponents (image)); if (! VImageAttrList (image) || (result = VGetAttr (VImageAttrList (image), VColorInterpAttr, VBandInterpDict, VLongRepn, & interp)) == VAttrMissing) return VImageNColors (image) > 1 ? VBandInterpOther : VBandInterpNone; if (result == VAttrBadValue) return VBandInterpOther; switch (interp) { case VBandInterpRGB: if (VImageNColors (image) != 3) { VWarning ("VBandColorInterp: RGB image has %d color dimension(s)", VImageNColors (image)); return VBandInterpOther; } return VBandInterpRGB; } return VBandInterpOther; }
VImage VSelectDestImage (VStringConst routine, VImage dest, int nbands, int nrows, int ncolumns, VRepnKind pixel_repn) { /* If no destination image was specified, allocate one: */ if (! dest) return VCreateImage (nbands, nrows, ncolumns, pixel_repn); /* Otherwise check that the destination provided has the appropriate characteristics: */ if (VImageNBands (dest) != nbands) { VWarning ("%s: Destination image has %d bands; %d expected", routine, VImageNBands (dest), nbands); return NULL; } if (VImageNRows (dest) != nrows) { VWarning ("%s: Destination image has %d rows; %d expected", routine, VImageNRows (dest), nrows); return NULL; } if (VImageNColumns (dest) != ncolumns) { VWarning ("%s: Destination image has %d columns; %d expected", routine, VImageNColumns (dest), ncolumns); return NULL; } if (VPixelRepn (dest) != pixel_repn) { VWarning ("%s: Destination image has %s pixels; %s expected", routine, VPixelRepnName (dest), VRepnName (pixel_repn)); return NULL; } return dest; }
VBoolean VExtractAttr (VAttrList list, VStringConst name, VDictEntry *dict, VRepnKind repn, VPointer value, VBooleanPromoted required) { VAttrListPosn posn; /* If the attribute is in the list... */ if (VLookupAttr (list, name, & posn)) { if (value) { /* Get its value: */ if (! VGetAttrValue (& posn, dict, repn, value)) { VWarning ("VExtractAttr: %s attribute has bad value", name); return FALSE; } /* Clone or hide the value if we're about to delete it: */ if (repn == VStringRepn) * (VString *) value = VNewString (* (VString *) value); } /* Remove it from the list: */ VDeleteAttr (& posn); return TRUE; } /* Otherwise complain if the attribute was a required one: */ if (required) VWarning ("VExtractAttr: %s attribute missing", name); return ! required; }
VGraph VCreateGraph (int size, int nfields, VRepnKind repn, int useW) { VGraph graph; /* Check parameters: */ if (size < 1 || nfields < 1) VWarning ("VCreateGraph: Invalid number of nodes or fields."); /* Allocate memory for the VGraph, and the node table: */ graph = VMalloc (sizeof (VGraphRec)); if (graph == NULL) return NULL; graph->table = VCalloc(size, sizeof(VNode)); if (graph->table == NULL) { VFree(graph); return NULL; }; /* Initialize the VGraph: */ graph->nnodes = 0; graph->nfields = nfields; graph->node_repn = repn; graph->attributes = VCreateAttrList (); graph->lastUsed = 0; graph->size = size; graph->useWeights = useW; graph->iter = 0; return graph; }
static VBoolean WriteString (FILE *f, const char *str) { const char *cp; int ch; /* Test for the presence of funny characters in the string value: */ for (cp = str; (ch = *cp) != 0; cp++) if (! isalnum (ch) && ch != '.' && ch != '-' && ch != '+' && ch != '_') break; /* If funny characters are present, output the string in quotes: */ if (ch) { FailTest (fputc ('"', f)); for (cp = (char *) str; (ch = *cp) != 0; cp++) switch (ch) { case '\n': FailTest (fputs ("\\n\\\n", f)); break; case '"': FailTest (fputs ("\\\"", f)); break; default: FailTest (fputc (ch, f)); } FailTest (fputc ('"', f)); } else FailTest (fputs (str, f)); return TRUE; Fail: VWarning ("VWriteFile: Write to stream failed"); return FALSE; }
VAttrList VReadFile (FILE *f, VReadFileFilterProc *filter) { VAttrList list; long offset; int i; /* Ensure that the correct FIL_Vista data file header is there: */ if (! ReadHeader (f)) return NULL; /* Read all attributes in the file: */ if (! (list = ReadAttrList (f))) return NULL; /* Swallow the delimiter and read the binary data following it: */ offset = 0; if (! ReadDelimiter (f) || ! ReadData (f, list, filter, &offset)) { VDestroyAttrList (list); return NULL; } /* Now we should be at the end of the file: */ i = fgetc (f); if (i != EOF) { ungetc (i, f); VWarning ("VReadFile: File continues beyond expected EOF"); } return list; }
VBoolean VUnpackData (VRepnKind repn, size_t nels, VPointer packed, VPackOrder packed_order, size_t *length, VPointer *unpacked, VBoolean *alloced) { VPackOrder unpacked_order; size_t unpacked_elsize = VRepnSize (repn) * CHAR_BIT; size_t packed_elsize = VRepnPrecision (repn); size_t unpacked_length = nels * VRepnSize (repn); /* If a space for the unpacked data was supplied, ensure there's enough of it: */ if (! alloced && unpacked_length > *length) { VWarning ("VUnpackData: Insufficient space for unpacked data"); return FALSE; } *length = unpacked_length; /* Determine the present machine's internal byte order: */ unpacked_order = MachineByteOrder (); /* If the desired byte order matches that of the present machine's, and the unpacked and packed data element sizes are identical, just return the packed data: */ if (unpacked_order == packed_order && unpacked_elsize == packed_elsize) { if (alloced) { *unpacked = packed; *alloced = FALSE; } else if (packed != *unpacked) memcpy (*unpacked, packed, unpacked_length); return TRUE; } /* Unpack data elements into the buffer: */ if (packed_elsize == unpacked_elsize) { /* If the packed and unpacked are the same size, do a straight copy: */ if (packed != *unpacked) memcpy (*unpacked, packed, unpacked_length); /* Swap bytes if necessary: */ if (packed_order != unpacked_order && packed_elsize > 8) SwapBytes (nels, packed_elsize / 8, (char *) *unpacked); } else if (packed_elsize == 1) { /* If the elements are VBits, this unpacks them: */ VUnpackBits (nels, packed_order, (char *) packed, (char *) *unpacked); } else /* Unpacking multi-byte integers or floats is currently not supported: */ VError ("VUnpackData: " "Unpacking %s from %d to %d bits is not supported", VRepnName (repn), packed_elsize, unpacked_elsize); return TRUE; }
static char *ReadString (FILE *f, char ch, VStringConst name) { VBoolean escaped = (ch == '"'); size_t len = 0; char *cp; size_t max_len; char *buf; buf = VMalloc (StringAllocIncrement); max_len = StringAllocIncrement; if (! escaped) ungetc (ch, f); cp = buf; while (1) { ch = fgetc (f); /* Check for premature EOF: */ if (ch == EOF) { VWarning ("VReadFile: EOF encountered in %s attribute", name); return NULL; } /* Check for closing " or escape sequence: */ if (escaped) { if (ch == '"') break; if (ch == '\\') switch (ch = fgetc (f)) { case '\n': continue; case 'n': ch = '\n'; } } else if (isspace (ch)) break; /* If the buffer in which we're accumulating the value is full, allocate a larger one: */ if (++len == max_len) { buf = VRealloc (buf, max_len += StringAllocIncrement); cp = buf + len - 1; } /* Store the character in the current buffer: */ *cp++ = ch; } *cp = 0; /* Allocate a node of the correct size, or trim one already allocated so it is the correct size: */ return buf; }
VBoolean VCopyBand (VImage src, VBand src_band, VImage dest, VBand dest_band) { int nbands, src_npixels, dest_npixels; VPointer src_pixels, dest_pixels; /* The destination image must exist: */ if (! dest) { VWarning ("VCopyBand: No destination specified"); return FALSE; } /* VAllBands not accepted for destination band: */ if (dest_band < 0 || dest_band >= VImageNBands (dest)) { VWarning ("VCopyBand: Band %d referenced in image of %d bands", (int) dest_band, (int) VImageNBands (dest)); return FALSE; } /* Ensure that the destination image has the appropriate dimensions and pixel representation: */ nbands = dest_band; if (src_band == VAllBands) nbands += VImageNBands (src) - 1; if (nbands < VImageNBands (dest)) nbands = VImageNBands (dest); if (! VSelectDestImage ("VCopyBand", dest, nbands, VImageNRows (src), VImageNColumns (src), VPixelRepn (src))) return FALSE; /* Locate the specified source and destination bands: */ if (! VSelectBand ("VCopyBand", src, src_band, & src_npixels, & src_pixels)) return FALSE; if (! VSelectBand ("VCopyBand", dest, dest_band, & dest_npixels, & dest_pixels)) return FALSE; /* Copy from the source band to the destination band: */ memcpy (dest_pixels, src_pixels, src_npixels * VPixelSize (src)); return TRUE; }
static VBoolean ReadHeader (FILE *f) { int version; if (fscanf (f, VFileHeader " %d", & version) != 1) { VWarning ("VReadFile: FIL_Vista data file header not found"); return FALSE; } if (version == VFileVersion) return TRUE; if (version == 1 && VFileVersion == 2) { VWarning ("VReadFile: Obsolete data file -- pipe it thru v1to2"); return TRUE; } VWarning ("VReadFile: FIL_Vista data file isn't version %d", VFileVersion); return FALSE; }
/* ** read several bands of data from a file */ VBoolean VReadBandDataFD (int fd,VImageInfo *imageInfo, int band,int num_bands,VImage *buf) { size_t band1; size_t offset; size_t ncolumns,nrows,nbands; size_t size,nitems,nbytes; VPointer *dest_pp; size = imageInfo->pixelSize; ncolumns = imageInfo->ncolumns; nrows = imageInfo->nrows; nbands = imageInfo->nbands; /* Seek start of binary data */ lseek(fd,0L,SEEK_SET); if (lseek(fd,imageInfo->offsetHdr,SEEK_SET) == -1) { return FALSE; } band1 = num_bands + band; if (band1 > nbands) { VWarning(" illegal band addr: %d",band1); band1 = nbands; num_bands = band1 - band; } /* read all rows and all columns */ nitems = ncolumns * nrows * num_bands; nbytes = nitems * size; offset = imageInfo->data + (nrows * ncolumns * (size_t)band) * size; if (lseek(fd,offset,SEEK_CUR) == -1) { return FALSE; } dest_pp = (VPointer*)VPixelPtr((*buf),0,0,0); if (read(fd,dest_pp,nbytes) < 0) { return FALSE; } /* if little-endian, then swap bytes: */ if (MachineByteOrder() == VLsbFirst) { dest_pp = (VPointer*)VPixelPtr((*buf),0,0,0); SwapBytes(nitems,size,(char*)dest_pp); } return TRUE; }
static VBoolean ReadDelimiter (FILE *f) { int ch; const char *cp; static char *msg = "VReadFile: FIL_Vista data file delimiter not found"; /* Skip whitespace up to the first character of the delimeter: */ while ((ch = fgetc (f)) != VFileDelimiter[0]) if (ch == EOF || ! isspace (ch & 0x7F)) { VWarning (msg); return FALSE; } /* Swallow remaining characters of the delimiter: */ for (cp = & VFileDelimiter[1]; *cp; cp++) if (*cp != fgetc (f)) { VWarning (msg); return FALSE; } return TRUE; }
float CVImage::getVoxelSize( Direction dir, VImage img ) { float res[3]; char *value; const char *voxel = getStringAttrib( "voxel", img ); if( !voxel || !sscanf( voxel, "%f %f %f", &res[0], &res[1], &res[2] ) ) { VWarning( "Cannot find voxel attribute. Using \"1 1 1\"" ); std::fill_n( res, 3, 1 ); } return res[dir]; }
/* ** read several bands of data from a file */ VBoolean VReadBandData (FILE *fp,VImageInfo *imageInfo, int band,int num_bands,VImage *buf) { int band1; size_t offset,ncolumns,nrows,nbands; size_t size,nitems; VPointer *dest_pp; size = imageInfo->pixelSize; ncolumns = imageInfo->ncolumns; nrows = imageInfo->nrows; nbands = imageInfo->nbands; /* fprintf(stderr," size; %d, ncol: %d nrows: %d, nb: %d, band: %d data: %d \n", size,ncolumns,nrows,nbands,band,imageInfo->data); */ /* Seek start of binary data */ fseek(fp,0L,SEEK_SET); if (fseek(fp,(long)imageInfo->offsetHdr,SEEK_SET) != 0) return FALSE; band1 = num_bands + band; if (band1 > nbands) { VWarning(" illegal band addr: %d",band1); band1 = nbands; num_bands = band1 - band; } /* read all rows and all columns */ nitems = ncolumns * nrows * num_bands; offset = imageInfo->data + (nrows * ncolumns * band) * size; if (fseek(fp,offset,SEEK_CUR) != 0) return FALSE; dest_pp = (VPointer*)VPixelPtr((*buf),0,0,0); if (fread(dest_pp,size,nitems,fp) <= 0) return FALSE; /* if little-endian, then swap bytes: */ if (MachineByteOrder() == VLsbFirst) { dest_pp = (VPointer*)VPixelPtr((*buf),0,0,0); SwapBytes(nitems,size,(char*)dest_pp); } return TRUE; }
void VParseFilterCmd (int noptions, VOptionDescRec opts[], int argc, char **argv, FILE **inp, FILE **outp) { static VStringConst in_file, out_file; static VBoolean in_found, out_found; static VOptionDescRec io_opts[] = { { "in", VStringRepn, 1, & in_file, & in_found, NULL, "Input file" }, { "out", VStringRepn, 1, & out_file, & out_found, NULL, "Output file" } }; int i, n; VOptionDescRec options[100]; /* Check that number of options will not overflow the options array. */ if (noptions >= 98) { VWarning("VParseFilterCmd: Too many options allowed"); noptions = 98; } /* Copy options into a new list and add the "in" and "out" options. */ n = 0; if (inp) options[n++] = io_opts[0]; if (outp) options[n++] = io_opts[1]; for (i = 0; i < noptions; i++, n++) options[n] = opts[i]; /* Parse command line arguments and identify the input and output files: */ if (! VParseCommand (n, options, & argc, argv) || (inp && ! VIdentifyFiles (n, options, "in", & argc, argv, 0)) || (outp && ! VIdentifyFiles (n, options, "out", & argc, argv, 1))) goto Usage; /* Any remaining unparsed arguments are erroneous: */ if (argc > 1) { VReportBadArgs (argc, argv); Usage: VReportUsage (argv[0], n, options, inp ? (outp ? "[infile] [outfile]" : "[infile]") : (outp ? "[outfile]" : NULL)); exit (EXIT_FAILURE); } /* Open the input and output files: */ if (inp) *inp = VOpenInputFile (in_file, TRUE); if (outp) *outp = VOpenOutputFile (out_file, TRUE); }
static void LoadHelpFile (void) { FILE *f; size_t len, incr; Topic *topic; char buf[100]; ntopics = 0; topics = topic = VMalloc (sizeof (Topic) * maxTopics); if (! (f = fopen (helpFilename, "r"))) { VWarning ("Unable to open help database %s", helpFilename); ntopics = 1; topic->topic = "(No help topics)"; topic->text = "(No help text)"; topic->len = strlen (topic->text); return; } do { fgets (buf, sizeof (buf), f); } while (! feof (f) && buf[0] != '@'); while (! feof (f) && ntopics < maxTopics) { len = strlen (buf); if (buf[len - 1] == '\n') buf[len - 1] = 0; topic->topic = VNewString (buf + 1); topic->text = NULL; len = 0; while (1) { fgets (buf, sizeof (buf), f); if (feof (f) || buf[0] == '@') break; incr = strlen (buf); topic->text = VRealloc ((XtPointer) topic->text, len + incr + 1); strcpy (topic->text + len, buf); len += incr; } while (len > 0 && isspace (topic->text[len - 1])) len--; topic->text[len] = 0; topic->len = len; ntopics++; topic++; } fclose (f); }
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; }
int main (int argc, char *argv[]) { static VShort band; static VOptionDescRec options[] = { { "band", VShortRepn, 1, & band, VOptionalOpt, NULL,"Image band to convert" } }; FILE *infile, *outfile; int nimages; VAttrList attributes; VImage *images, image; char prg[50]; sprintf(prg,"vtopgm V%s", getVersion()); fprintf (stderr, "%s\n", prg); /* Parse command line arguments and identify the input and output files */ VParseFilterCmd (VNumber (options), options, argc, argv, & infile, & outfile); /* Read all images from the input file */ if ((nimages = VReadImages (infile, & attributes, & images)) == 0) exit (EXIT_FAILURE); /* no images found */ fclose (infile); /* Ensure that the specified band exists: */ if (nimages != 1) VWarning ("Only the first of %d images will be converted", nimages); if (band < 0 || band >= VImageNBands (images[0])) VError ("Image of %d band(s) has no band %d", VImageNBands (images[0]), band); /* Convert the image to UByte: */ if (VPixelRepn(images[0]) != VUByteRepn) { image = VConvertImageRange (images[0], NULL, (VBand) band, VUByteRepn); if (! image) exit (EXIT_FAILURE); band = 0; } else image = images[0]; /* Output the first image as a pgm file. */ WritePgmFile (outfile, image, (VBand) band); return EXIT_SUCCESS; }
int main(int argc, char *argv[]) { static VBoolean x_axis = FALSE; static VBoolean y_axis = FALSE; static VBoolean z_axis = FALSE; static VOptionDescRec options[] = { { "x", VBooleanRepn, 1, (VPointer) &x_axis, VOptionalOpt, NULL, "Flip x-axis" }, { "y", VBooleanRepn, 1, (VPointer) &y_axis, VOptionalOpt, NULL, "Flip y-axis" }, { "z", VBooleanRepn, 1, (VPointer) &z_axis, VOptionalOpt, NULL, "Flip z-axis" }, }; FILE *in_file, *out_file; VAttrList list; VAttrListPosn posn; VImage src = NULL, result = NULL; char prg_name[100]; char ver[100]; getLipsiaVersion(ver, sizeof(ver)); sprintf(prg_name, "vflip3d V%s", ver); fprintf(stderr, "%s\n", prg_name); VWarning("It is recommended to use the program vswapdim since vflip3d does not support extended header informations"); /* Parse command line arguments and identify files: */ VParseFilterCmd(VNumber(options), options, argc, argv, &in_file, &out_file); /* Read the input file: */ list = VReadFile(in_file, NULL); if(! list) exit(1); /* For each attribute read... */ for(VFirstAttr(list, & posn); VAttrExists(& posn); VNextAttr(& posn)) { if(VGetAttrRepn(& posn) != VImageRepn) continue; VGetAttrValue(& posn, NULL, VImageRepn, & src); result = Flip3dImage(src, NULL, VAllBands, x_axis, y_axis, z_axis); if(! result) exit(1); VSetAttrValue(& posn, NULL, VImageRepn, result); VDestroyImage(src); } /* Write out the results: */ if(! VWriteFile(out_file, list)) exit(1); fprintf(stderr, "%s: done.\n", argv[0]); return 0; }
VBoolean VSelectBand (VStringConst routine, VImage image, VBand band, int *npixels, VPointer *first_pixel) { if (band == VAllBands) { if (npixels) *npixels = VImageNPixels (image); if (first_pixel) *first_pixel = VImageData (image); } else if (band >= 0 && band < VImageNBands (image)) { if (npixels) *npixels = VImageNRows (image) * VImageNColumns (image); if (first_pixel) *first_pixel = image->band_index[band][0]; } else { VWarning ("%s: Band %d referenced in image of %d band(s)", routine, band, VImageNBands (image)); return FALSE; } return TRUE; }
void VDestroyAttrList (VAttrList list) { VAttrRec *a, *a_next; if (! list) { VWarning ("VDestroyAttrList: Called with NULL list"); return; } /* For each attribute in the list: */ for (a = list->next; a; a = a_next) { a_next = a->next; /* Free any storage used for the attribute's value: */ FreeAttrValue ("VDestroyAttrList", a); /* Free the attribute record itself: */ VFree (a); } VFree (list); }
int VReadObjects (FILE *file, VRepnKind repn, VAttrList *attributes, VPointer **objects) { VAttrList list; VAttrListPosn posn; int i, nobjects = 0; VPointer *vector; /* Read the file's contents: */ list = VReadFile (file, NULL); if (! list) return FALSE; /* Count the objects found: */ for (VFirstAttr (list, & posn); VAttrExists (& posn); VNextAttr (& posn)) nobjects += (VGetAttrRepn (& posn) == repn); if (nobjects == 0) { VWarning ("VReadObjects: No %s objects present in stream", VRepnName (repn)); VDestroyAttrList (list); return FALSE; } /* Allocate a vector of that many object pointers: */ vector = VMalloc (nobjects * sizeof (VPointer)); /* Extract the objects from the attribute list and place them in the vector: */ for (VFirstAttr (list, & posn), i = 0; VAttrExists (& posn); ) if (VGetAttrRepn (& posn) == repn) { VGetAttrValue (& posn, NULL, repn, vector + i); VDeleteAttr (& posn); i++; } else VNextAttr (& posn); /* Return the objects and the remaining attributes: */ *attributes = list; *objects = vector; return nobjects; }
static VBoolean WriteAttrList (FILE *f, VAttrList list, int indent, VList *data_list, long *offset) { VAttrListPosn posn; int i; /* Write the { marking the beginning of the attribute list: */ FailTest (fputs ("{\n", f)); /* Write each attribute in the list: */ for (VFirstAttr (list, & posn); VAttrExists (& posn); VNextAttr (& posn)) if (! WriteAttr (f, & posn, indent, data_list, offset)) return FALSE; /* Write the } marking the end of the attribute list: */ for (i = indent - 1; i > 0; i--) FailTest (fputc ('\t', f)); FailTest (fputc ('}', f)); return TRUE; Fail: VWarning ("VWriteFile: Write to stream failed"); return FALSE; }
VEdges VCreateEdges (int nrows, int ncolumns, int nedge_fields, int npoint_fields) { VEdges edges; /* Check parameters: */ if (nrows < 1 || ncolumns < 1) VWarning ("VCreateEdges: Invalid number of rows or columns."); /* Allocate memory for the VEdges, its indices, and pixel values: */ edges = VMalloc (sizeof (VEdgesRec)); /* Initialize the VEdges: */ edges->nrows = nrows; edges->ncolumns = ncolumns; edges->attributes = VCreateAttrList (); edges->nedge_fields = nedge_fields; edges->npoint_fields = npoint_fields; edges->nedges = edges->npoints = 0; edges->first = edges->last = NULL; edges->free = NULL; return edges; }
int main(int argc, char *argv[]) { static VFloat reso = -1.0; static VLong itype = 0; static VBoolean flip = TRUE; static VBoolean reorder = TRUE; static VOptionDescRec options[] = { { "reso", VFloatRepn, 1, (VPointer) &reso, VOptionalOpt, NULL, "New voxel resolution in mm, def: -1 means min(1.0,\"best source resolution\")" }, { "flip", VBooleanRepn, 1, (VPointer) &flip, VOptionalOpt, NULL, "Whether to flip to natural convention" }, { "reorder", VBooleanRepn, 1, (VPointer) &reorder, VOptionalOpt, NULL, "Whether to reorder axial slices from axial source image" }, { "interpolation", VLongRepn, 1, & itype, VOptionalOpt, ITYPDict, "Type of interpolation (0: linear, 1: nearest neighbour, 2: cubic spline)" } }; FILE *in_file, *out_file; VAttrList list; VAttrListPosn posn; int nobjects = 0; VImage src = NULL, dest = NULL, result = NULL; int i, b, r, c, nbands, nrows, ncols; VString str, newstr, fixpointString, caString, cpString; float fix_c, fix_r, fix_b; float ca_c, ca_r, ca_b; float cp_c, cp_r, cp_b; float x, y, z, min; VDouble v, scale_band, scale_row, scale_col; float scale[3], shift[3]; /* print information */ char prg_name[100]; char ver[100]; getLipsiaVersion(ver, sizeof(ver)); sprintf(prg_name, "visotrop V%s", ver); fprintf(stderr, "%s\n", prg_name); fflush(stderr); /* Parse command line arguments: */ VParseFilterCmd(VNumber(options), options, argc, argv, & in_file, & out_file); /* Read source image(s): */ if(!(list = VReadFile(in_file, NULL))) exit(EXIT_FAILURE); /* Scale each object: */ for(VFirstAttr(list, & posn); VAttrExists(& posn); VNextAttr(& posn)) { switch(VGetAttrRepn(& posn)) { case VImageRepn: VGetAttrValue(& posn, NULL, VImageRepn, & src); if(VGetAttr(VImageAttrList(src), "voxel", NULL, VStringRepn, (VPointer) & str) == VAttrFound) { sscanf(str, "%f %f %f", &x, &y, &z); fprintf(stderr, " voxel: %f %f %f\n", x, y, z); min = x < y ? x : y; min = z < min ? z : min; /* if resolution is not set, use default value 1 or smaler value if the image resolution is better */ if(reso < 0.0) reso = min < 1.0 ? min : 1.0; if(reso <= 0.0) exit(EXIT_FAILURE); fprintf(stderr, " new resolution: %f \n", reso); scale_col = x / reso; scale_row = y / reso; scale_band = z / reso; nbands = VImageNBands(src) * scale_band; nrows = VImageNRows(src) * scale_row; ncols = VImageNColumns(src) * scale_col; if(VImageNBands(src) == nbands && VImageNRows(src) == nrows && VImageNColumns(src) == ncols) { itype = 0; } fprintf(stderr, " interpolation type: %s\n", ITYPDict[itype].keyword); fprintf(stderr, " old dim: %3d %3d %3d\n", VImageNBands(src), VImageNRows(src), VImageNColumns(src)); for(i = 0; i < 3; i++) shift[i] = scale[i] = 0; scale[0] = scale_band; scale[1] = scale_row; scale[2] = scale_col; switch(itype) { /* trilinear interpolation resampling */ case 0: dest = VTriLinearScale3d(src, NULL, (int)nbands, (int)nrows, (int)ncols, shift, scale); break; /* nearest neightbour resampling */ case 1: dest = VNNScale3d(src, NULL, (int)nbands, (int)nrows, (int)ncols, shift, scale); break; /* cubic spline */ case 2: dest = VCubicSplineScale3d(src, NULL, (int)nbands, (int)nrows, (int)ncols, shift, scale); break; case 3: /* no interpolation, just reshuffle */ dest = VCopyImage(src, NULL, VAllBands); break; default: VError(" unknown resampling type %d", itype); } if(! dest) exit(EXIT_FAILURE); /*aa 2003/09/11 added function not to rotate siemens data*/ if(! VGetAttr(VImageAttrList(src), "orientation", NULL, VStringRepn, (VPointer) & str) == VAttrFound) VError(" attribute 'orientation' missing"); if(strcmp(str, "axial") == 0) { fprintf(stderr, " new dim: %3d %3d %3d\n", nbands, nrows, ncols); result = VCreateImage(nbands, nrows, ncols, VPixelRepn(src)); VFillImage(result, VAllBands, 0); for(b = 0; b < nbands; b++) for(r = 0; r < nrows; r++) for(c = 0; c < ncols; c++) { v = VGetPixel(dest, b, r, c); if((flip == FALSE) && (reorder == FALSE)) VSetPixel(result, b, r, ncols - c - 1, v); else if((flip == TRUE) && (reorder == FALSE)) VSetPixel(result, b, r, c, v); else if((flip == FALSE) && (reorder == TRUE)) VSetPixel(result, nbands - b - 1, r, ncols - c - 1, v); else if((flip == TRUE) && (reorder == TRUE)) VSetPixel(result, nbands - b - 1, r, c, v); } } else if(strcmp(str, "sagittal") == 0) { /* re-arrange from sagittal to axial orientation */ fprintf(stderr, " new dim: %3d %3d %3d\n", nrows, ncols, nbands); result = VCreateImage(nrows, ncols, nbands, VPixelRepn(src)); VFillImage(result, VAllBands, 0); for(b = 0; b < nbands; b++) for(r = 0; r < nrows; r++) for(c = 0; c < ncols; c++) { v = VGetPixel(dest, b, r, c); if(flip == FALSE) VSetPixel(result, r, c, nbands - b - 1, v); else VSetPixel(result, r, c, b, v); } } else if(strcmp(str, "coronal") == 0) { /* re-arrange from coronal to axial orientation */ fprintf(stderr, " new dim: %3d %3d %3d\n", nrows, nbands, ncols); result = VCreateImage(nrows, nbands, ncols, VPixelRepn(src)); VFillImage(result, VAllBands, 0); for(b = 0; b < nbands; b++) for(r = 0; r < nrows; r++) for(c = 0; c < ncols; c++) { v = VGetPixel(dest, b, r, c); if(flip == FALSE) VSetPixel(result, r, b, ncols - c - 1, v); else VSetPixel(result, r, b, c, v); } } else { VError(" unknown resampling type %d", itype); exit(EXIT_FAILURE); } /* copy attributes from source image */ VCopyImageAttrs(src, result); // [TS] 08/03/27 // correct 'fixpoint', 'ca' and 'cp' if they exist in the source image // // NOTE: // this is only done when no flipping or reordering is requested :-( // (WARNING!!!!) '-flip true' actually means that no flipping is done (WHAAAAT ????) // and therefore we test for reorder = false and flip = true fixpointString = VMalloc(80); caString = VMalloc(80); cpString = VMalloc(80); VBoolean _issueWarning = FALSE; if(VGetAttr(VImageAttrList(src), "fixpoint", NULL, VStringRepn, (VPointer)&fixpointString) == VAttrFound) { if(reorder == FALSE && flip == TRUE) { sscanf(fixpointString, "%f %f %f", &fix_c, &fix_r, &fix_b); fix_c *= scale_col; fix_r *= scale_row; fix_b *= scale_band; sprintf((char *)fixpointString, "%f %f %f", fix_c, fix_r, fix_b); VSetAttr(VImageAttrList(result), "fixpoint", NULL, VStringRepn, fixpointString); } else { _issueWarning = TRUE; } } if(VGetAttr(VImageAttrList(src), "ca", NULL, VStringRepn, (VPointer)&caString) == VAttrFound) { if(reorder == FALSE && flip == TRUE) { sscanf(caString, "%f %f %f", &ca_c, &ca_r, &ca_b); ca_c *= scale_col; ca_r *= scale_row; ca_b *= scale_band; sprintf((char *)caString, "%f %f %f", ca_c, ca_r, ca_b); VSetAttr(VImageAttrList(result), "ca", NULL, VStringRepn, caString); } else { _issueWarning = TRUE; } } if(VGetAttr(VImageAttrList(src), "cp", NULL, VStringRepn, (VPointer)&cpString) == VAttrFound) { if(reorder == FALSE && flip == TRUE) { sscanf(cpString, "%f %f %f", &cp_c, &cp_r, &cp_b); cp_c *= scale_col; cp_r *= scale_row; cp_b *= scale_band; sprintf((char *)cpString, "%f %f %f", cp_c, cp_r, cp_b); VSetAttr(VImageAttrList(result), "cp", NULL, VStringRepn, cpString); } else { _issueWarning = TRUE; } } if(_issueWarning) { VWarning("Attributes 'fixpoint', 'ca' and 'cp' exist but were not corrected and are therefore likely to be wrong"); VWarning("This was caused by setting -flip to false or -reorder to true"); VWarning("Please correct the values manually using vattredit"); } /* set the attributes to the changed values */ newstr = VMalloc(80); sprintf((char *)newstr, "%f %f %f", reso, reso, reso); VSetAttr(VImageAttrList(result), "voxel", NULL, VStringRepn, newstr); VSetAttr(VImageAttrList(result), "orientation", NULL, VStringRepn, "axial"); if(flip) VSetAttr(VImageAttrList(result), "convention", NULL, VStringRepn, "natural"); else VSetAttr(VImageAttrList(result), "convention", NULL, VStringRepn, "radiologic"); } VSetAttrValue(& posn, NULL, VImageRepn, result); VDestroyImage(src); break; default: continue; } nobjects++; } /* Make History */ VHistory(VNumber(options), options, prg_name, &list, &list); /* Write the results to the output file: */ if(! VWriteFile(out_file, list)) exit(EXIT_FAILURE); fprintf(stderr, "%s: done.\n", argv[0]); return EXIT_SUCCESS; }
int main(int argc, char *argv[]) { static VArgVector in_files; static VString out_filename; static VString filename; static VShort minval = 0; static VFloat fwhm = 4.0; static VOptionDescRec options[] = { {"in", VStringRepn, 0, & in_files, VRequiredOpt, NULL, "Input files" }, {"out", VStringRepn, 1, & out_filename, VRequiredOpt, NULL, "Output file" }, {"design", VStringRepn, 1, (VPointer) &filename, VRequiredOpt, NULL, "Design file"}, { "fwhm", VFloatRepn, 1, (VPointer) &fwhm, VOptionalOpt, NULL, "FWHM of temporal Gaussian filter in seconds" }, {"minval", VShortRepn, 1, (VPointer) &minval, VOptionalOpt, NULL, "Signal threshold"} }; FILE *fp = NULL, *f = NULL; VStringConst in_filename; VString ifilename; VAttrList list = NULL, list1 = NULL; VAttrList out_list = NULL, history_list = NULL; VAttrListPosn posn; VImage design = NULL; ListInfo *linfo; VLong itr = 0; VFloat sigma = 0, tr = 0; int i, n, nimages; char prg_name[100]; char ver[100]; getLipsiaVersion(ver, sizeof(ver)); sprintf(prg_name, "vcolorglm V%s", ver); fprintf(stderr, "%s\n", prg_name); /* ** parse command line */ if(! VParseCommand(VNumber(options), options, & argc, argv)) { VReportUsage(argv[0], VNumber(options), options, NULL); exit(EXIT_FAILURE); } if(argc > 1) { VReportBadArgs(argc, argv); exit(EXIT_FAILURE); } /* ** read design matrix */ fp = VOpenInputFile(filename, TRUE); list1 = VReadFile(fp, NULL); if(! list1) VError("Error reading design file"); fclose(fp); n = 0; for(VFirstAttr(list1, & posn); VAttrExists(& posn); VNextAttr(& posn)) { if(VGetAttrRepn(& posn) != VImageRepn) continue; VGetAttrValue(& posn, NULL, VImageRepn, & design); if(VPixelRepn(design) != VFloatRepn /* && VPixelRepn(design) != VDoubleRepn */) continue; n++; break; } if(n == 0) VError(" design matrix not found "); /* ** get pre-coloring info */ if(VGetAttr(VImageAttrList(design), "repetition_time", NULL, VLongRepn, &itr) != VAttrFound) VError(" TR info missing in header"); tr = (float) itr / 1000.0; sigma = 0; if(tr > 0.001 && fwhm > 0.001) { fprintf(stderr, " TR: %.3f seconds\n", tr); sigma = fwhm / 2.35482; sigma /= tr; if(sigma < 0.1) { VWarning(" 'fwhm/sigma' too small (%.3f / %.3f), will be set to zero", fwhm, sigma); sigma = 0; } } /* ** Read each input file */ nimages = in_files.number; linfo = (ListInfo *) VMalloc(sizeof(ListInfo) * nimages); for(i = 0; i < nimages; i++) { in_filename = ((VStringConst *) in_files.vector)[i]; ifilename = VNewString(in_filename); fprintf(stderr, " file: %s\n", ifilename); list = GetListInfo(ifilename, &linfo[i]); /* Create history */ if(i == 0) { history_list = VReadHistory(&list); if(history_list == NULL) history_list = VCreateAttrList(); VPrependHistory(VNumber(options), options, prg_name, &history_list); } } /* ** GLM */ out_list = VRegression(linfo, nimages, minval, design, sigma, itr); /* ** Output: */ VPrependAttr(out_list, "history", NULL, VAttrListRepn, history_list); f = VOpenOutputFile(out_filename, TRUE); if(!f) VError(" error opening outout file %s", out_filename); if(! VWriteFile(f, out_list)) exit(1); fprintf(stderr, "%s: done.\n", argv[0]); return 0; }
static VAttrList ReadAttrList (FILE *f) { VAttrList sublist, list = VCreateAttrList (); VAttrRec *a; int ch = 0; size_t name_size; VBundle b; char buf[2], *str, name_buf[VMaxAttrNameLength + 1]; /* Swallow a { marking the start of the attribute list: */ if (fscanf (f, " %1s", buf) != 1 || buf[0] != '{') { VWarning ("VReadFile: Missing {"); goto Fail; } /* For each attribute up to the next "}": */ while (fscanf (f, " %[^}: \t\n]", name_buf) == 1) { name_size = strlen (name_buf); /* Read a : and the first character of the attribute's value: */ if (fscanf (f, " %1s", buf) != 1 || buf[0] != ':' || fscanf (f, " %1s", buf) != 1) { VWarning ("VReadFile: Invalid %s attribute", name_buf); goto Fail; } /* The first character of the value tells us whether its an attribute list, quoted string, or unquoted string: */ if (buf[0] == '{') { /* The attribute value is another list of attributes: */ ungetc ('{', f); if (! (sublist = ReadAttrList (f))) goto Fail; a = VMalloc (sizeof (VAttrRec) + name_size); a->value = sublist; a->repn = VAttrListRepn; } else { /* The value doesn't start with '{' -- parse a word or string: */ if (! (str = ReadString (f, buf[0], name_buf))) goto Fail; while ((ch = fgetc (f)) && (ch == ' ' || ch == '\t')) ; ungetc (ch, f); /* If the word is followed by an '{'... */ if (ch == '{') { /* ...then it's a typed value -- the word is it's type name and the { is the start of it's attribute list value. */ b = VCreateBundle (str, NULL, 0, NULL); if (! (sublist = ReadAttrList (f))) { VFree (b); goto Fail; } b->list = sublist; a = VMalloc (sizeof (VAttrRec) + name_size); a->repn = VBundleRepn; a->value = b; } else { /* ...otherwise store it as a simple string value: */ a = VMalloc (sizeof (VAttrRec) + name_size + strlen (str) + 1); a->repn = VStringRepn; a->value = a->name + name_size + 1; strcpy (a->value, str); } VFree(str); } /* Copy the attribute's name into the newly allocated node: */ strcpy (a->name, name_buf); /* Place the new node on the end of the growing attribute list: */ a->next = NULL; a->prev = list->prev; if (a->prev) a->prev->next = a; else list->next = a; list->prev = a; } /* Swallow the terminating "}": */ if (fscanf (f, " %1s", buf) != 1 || buf[0] != '}') { VWarning ("VReadFile: Missing }"); Fail: VDestroyAttrList (list); return NULL; } return list; }
static VBoolean ReadData (FILE *f, VAttrList list, VReadFileFilterProc *filter, long *offset) { VAttrListPosn posn, subposn; VAttrList sublist; VBundle b; VRepnKind repn; VBoolean read_data, data_found, length_found; VLong data, length; VTypeMethods *methods; VPointer value; for (VFirstAttr (list, & posn); VAttrExists (& posn); VNextAttr (& posn)) { switch (VGetAttrRepn (& posn)) { case VAttrListRepn: /* Recurse on nested attribute list: */ VGetAttrValue (& posn, NULL, VAttrListRepn, & sublist); if (! ReadData (f, sublist, filter, offset)) return FALSE; break; case VBundleRepn: VGetAttrValue (& posn, NULL, VBundleRepn, & b); repn = VLookupType (b->type_name); /* If a filter routine was supplied, ask it whether to bother with the binary data: */ read_data = ! filter || (*filter) (b, repn); /* Extract any data and length attributes in the object's value: */ data_found = VLookupAttr (b->list, VDataAttr, & subposn); if (data_found) { if (! VGetAttrValue (& subposn, NULL, VLongRepn, & data)) { VWarning ("VReadFile: " "%s attribute's data attribute incorrect", VGetAttrName (& posn)); return FALSE; } VDeleteAttr (& subposn); } length_found = VLookupAttr (b->list, VLengthAttr, & subposn); if (length_found) { if (! VGetAttrValue (& subposn, NULL, VLongRepn, & length)) { VWarning ("VReadFile: " "%s attribute's length attribute incorrect", VGetAttrName (& posn)); return FALSE; } VDeleteAttr (& subposn); } /* None or both must be present: */ if (data_found ^ length_found) { VWarning ("VReadFile: %s attribute has %s but not %s", VGetAttrName (& posn), data_found ? "data" : "length", data_found ? "length" : "data"); return FALSE; } /* Read the binary data associated with the object: */ if (data_found) { if (data < *offset) { VWarning ("VReadFile: " "%s attribute's data attribute incorrect", VGetAttrName (& posn)); return FALSE; } if (! read_data) data += length; /* To seek forward to the start of the data block we first try fseek. That will fail on a pipe, in which case we seek by reading. */ if (data != *offset && fseek (f, (long) data - *offset, SEEK_CUR) == -1 && errno == ESPIPE && ! MySeek (f, data - *offset)) { VSystemWarning ("VReadFile: Seek within file failed"); return FALSE; } if (read_data) { b->data = VMalloc (b->length = length); if (fread (b->data, 1, length, f) != length) { VWarning ("VReadFile: Read from stream failed"); return FALSE; } *offset = data + length; } else /* bug: read error occured when bundle was not read by a filter function. FK 24/03/98 */ *offset = data; } /* Recurse to read binary data for sublist attributes: */ if (! ReadData (f, b->list, filter, offset)) return FALSE; /* If the object's type is registered and has a decode method, invoke it to decode the binary data: */ if (read_data && repn != VUnknownRepn && (methods = VRepnMethods (repn)) && methods->decode) { if (! (value = (methods->decode) (VGetAttrName (& posn), b))) return FALSE; /* Replace the old typed value with the newly decoded one: */ VSetAttrValue (& posn, NULL, repn, value); VDestroyBundle (b); } break; default: break; } } return TRUE; }
VBoolean VWriteFile (FILE *f, VAttrList list) { DataBlock *db; VBundle b; VTypeMethods *methods; VRepnKind repn; VPointer value, ptr; VBoolean result, free_it; VList data_list; /* Write the FIL_Vista data file header, attribute list, and delimeter while queuing on data_list any binary data blocks to be written: */ long offset = 0; data_list = VListCreate (); FailTest (fprintf (f, "%s %d ", VFileHeader, VFileVersion)); if (! WriteAttrList (f, list, 1, &data_list, &offset)) { VListDestroy (data_list, VFree); return FALSE; } FailTest (fputs ("\n" VFileDelimiter, f)); fflush (f); /* Traverse data_list to write the binary data blocks: */ for (db = VListFirst (data_list); db; db = VListNext (data_list)) { repn = VGetAttrRepn (& db->posn); if (repn == VBundleRepn) { /* A typed value includes its binary data block explicitly: */ VGetAttrValue (& db->posn, NULL, VBundleRepn, & b); ptr = b->data; free_it = FALSE; } else { /* For any other representation, obtain the binary data block from its encode_data method: */ VGetAttrValue (& db->posn, NULL, repn, & value); methods = VRepnMethods (repn); ptr = (methods->encode_data) (value, db->list, db->length, & free_it); if (! ptr) goto Fail; } /* Write the binary data and free the buffer containing it if it was allocated temporarily by an encode_data method: */ if (db->length > 0) { result = fwrite (ptr, 1, db->length, f) == db->length; if (free_it) VFree (ptr); if (! result) goto Fail; } } VListDestroy (data_list, VFree); return TRUE; Fail: VWarning ("VWriteFile: Write to stream failed"); VListDestroy (data_list, VFree); return FALSE; }
static VBoolean WriteAttr (FILE *f, VAttrListPosn *posn, int indent, VList *data_list, long *offset) { int i; char *str; VRepnKind repn; VAttrList sublist; VBundle b; DataBlock *db; VTypeMethods *methods; size_t length; VPointer value; VBoolean result; VAttrListPosn subposn; /* Indent by the specified amount: */ for (i = 0; i < indent; i++) FailTest (fputc ('\t', f)); indent++; /* Output the attribute's name: */ FailTest (fprintf (f, "%s: ", VGetAttrName (posn))); /* Ouput its value: */ switch (repn = VGetAttrRepn (posn)) { case VAttrListRepn: VGetAttrValue (posn, NULL, VAttrListRepn, (VPointer) & sublist); result = WriteAttrList (f, sublist, indent, data_list, offset); break; case VBundleRepn: VGetAttrValue (posn, NULL, VBundleRepn, (VBundle) & b); if (! WriteString (f, b->type_name)) return FALSE; FailTest (fputc (' ', f)); /* If it's a typed value with binary data... */ if (b->length > 0) { /* Include "data" and "length" attributes in its attribute list: */ VPrependAttr (b->list, VLengthAttr, NULL, VLongRepn, (VLong) b->length); VPrependAttr (b->list, VDataAttr, NULL, VLongRepn, (VLong) *offset); /* Add it to the queue of binary data blocks to be written: */ *offset += b->length; db = VNew (DataBlock); db->posn = *posn; db->list = b->list; db->length = b->length; VListAppend (*data_list, db); } /* Write the typed value's attribute list: */ result = WriteAttrList (f, b->list, indent, data_list, offset); /* Remove the "data" and "length" attributes added earlier: */ if (b->length > 0) { VFirstAttr (b->list, & subposn); VDeleteAttr (& subposn); VDeleteAttr (& subposn); } break; case VStringRepn: VGetAttrValue (posn, NULL, VStringRepn, (VPointer) & str); result = WriteString (f, str); break; default: if (! (methods = VRepnMethods (repn)) || ! methods->encode_attr || ! methods->encode_data) { VWarning ("VWriteFile: " "%s attribute has unwriteable representation: %s", VGetAttrName (posn), VRepnName (repn)); return FALSE; } /* Write the type name: */ if (! WriteString (f, VRepnName (repn))) return FALSE; FailTest (fputc (' ', f)); /* Invoke the object type's encode_attr method to obtain an attribute list: */ VGetAttrValue (posn, NULL, repn, & value); sublist = (methods->encode_attr) (value, & length); /* If binary data is indicated... */ if (length > 0) { /* Include "data" and "length" attributes in the attr list: */ VPrependAttr (sublist, VLengthAttr, NULL, VLongRepn, (VLong) length); VPrependAttr (sublist, VDataAttr, NULL, VLongRepn, (VLong) *offset); *offset += length; } /* Add the object to the queue of binary data blocks to be written: */ db = VNew (DataBlock); db->posn = *posn; db->list = sublist; db->length = length; VListAppend (*data_list, db); /* Write the typed value's attribute list: */ result = WriteAttrList (f, sublist, indent, data_list, offset); /* Remove the "data" and "length" attributes added earlier: */ if (length > 0) { VFirstAttr (sublist, & subposn); VDeleteAttr (& subposn); VDeleteAttr (& subposn); } } /* Output a trailing newline: */ if (result) FailTest (fputc ('\n', f)); return result; Fail: VWarning ("VWriteFile: Write to stream failed"); return FALSE; }