Commit 3d0b6243c6e8fe045c1aeef57b785c1a32711531

Authored by David Mayerich
1 parent 2aa68315

fixed hsiproc bugs, added insert() method into stim::filename, added Matlab func…

…tion to save ENVI files
stim/envi/binary.h
... ... @@ -81,7 +81,7 @@ protected:
81 81  
82 82 //if the file isn't open, the user may only have read access
83 83 if(!file.is_open()){
84   - std::cout<<"class BINARY - failed to open file, trying for read only"<<std::endl;
  84 + std::cout<<"class STIM::BINARY - failed to open file, trying for read only"<<std::endl;
85 85 file.open(filename.c_str(), std::ios::in | std::ios::binary);
86 86 if(!file.is_open()){
87 87 std::cout<<" still unable to load the file"<<std::endl;
... ...
stim/envi/bsq.h
... ... @@ -776,49 +776,46 @@ public:
776 776 return true;
777 777 }
778 778  
779   - /// Saves only those pixels in a band corresponding to the mask value != 0
780   - /// @param array is a pointer to the destination array used to store the data
781   - /// @param i is the band index
782   - /// @p is a pointer to the mask data
783   - bool sift_band(T* values, unsigned long b, unsigned char* p){
  779 + /// Copies all spectra corresponding to nonzero values of a mask into a pre-allocated matrix of size (B x P)
  780 + /// where P is the number of masked pixels and B is the number of bands. The allocated memory can be accessed
  781 + /// using the following indexing: i = p*B + b
  782 + /// @param matrix is the destination for the pixel data
  783 + /// @param mask is the mask
  784 + bool sift(T* matrix, unsigned char* mask){
784 785 unsigned long long XY = X() * Y(); //Number of XY pixels
785 786 unsigned long long L = XY * sizeof(T); //size of XY plane (in bytes)
786   -
787   - unsigned long long vi = 0; //create an index into the values array
788   -
789   - unsigned long long start, end; //start and end indices of a block of masked pixels in the band
790   - bool reading = false;
791   - unsigned long long l, i; //length of the masked region
792   -
793   - for(unsigned long long xy = 0; xy < XY; xy++){ //for each pixel in the band
794   -
795   - if(reading){ //if we are currently iterating through a block of masked pixels
796   - if(p[xy]) end++; //if the current pixel is part of that block, increment the end index
797   - else{ //otherwise, terminate the block
798   - reading = false; //stop reading
799   - i = b * XY + start;
800   - file.seekg( i * sizeof(T) + header); //skip all of the unmasked pixels up to this point
801   - l = (end - start);
802   - file.read((char *)&values[vi], l * sizeof(T)); //write the values between start and end to the values array
803   - vi += l; //increment the pointer into the values array
804   - }
  787 +
  788 + //calculate the number of pixels in the mask
  789 + unsigned long long P = 0;
  790 + if(mask == NULL) P = XY;
  791 + else{
  792 + for(unsigned long long xy = 0; xy < XY; xy++){
  793 + if(mask[xy] != 0) P++;
805 794 }
806   - else{ //if we are currently iterating through a block of empty pixels
807   - if(p[xy]){ //if the next pixel is masked, start a new block for reading
808   - reading = true;
809   - start = xy; //set the start and end indices to the beginning of this new block
810   - end = start + 1;
  795 + }
  796 +
  797 + T* band_image = (T*) malloc( XY * sizeof(T)); //allocate space for a single band
  798 +
  799 + unsigned long long i; //pixel index into the sifted array
  800 + for(unsigned long long b = 0; b < Z(); b++){ //for each band in the data set
  801 + band_index(band_image, b); //retrieve an image of that band
  802 +
  803 + i = 0;
  804 + for(unsigned long long xy = 0; xy < XY; xy++){
  805 + if(mask == NULL || mask[xy] != 0){ //if the pixel is valid
  806 + matrix[i*Z() + b] = band_image[xy]; //copy it to the appropriate point in the values[] array
  807 + i++;
811 808 }
812 809 }
813 810 }
814   -
  811 +
815 812 return true;
816 813 }
817 814  
818 815 /// Saves only those spectra corresponding to mask value != 0 to pre-allocated memory
819 816 /// @param matrix is the destination for the sifted pixels
820 817 /// @param p is the mask file used for sifting
821   - bool sift(T* matrix, unsigned char* p){
  818 + /*bool sift(T* matrix, unsigned char* p){
822 819  
823 820 // open a band (XY plane)
824 821 unsigned long XY = X() * Y(); //Number of XY pixels
... ... @@ -845,7 +842,7 @@ public:
845 842  
846 843 free(bandvals); //clean up temporary memory
847 844 return true;
848   - }
  845 + }*/
849 846  
850 847 /// Saves to disk only those spectra corresponding to mask values != 0
851 848 /// @param outfile is the name of the sifted ENVI file to be written to disk
... ...
stim/envi/envi.h
... ... @@ -465,7 +465,9 @@ public:
465 465 return false;
466 466 }
467 467  
468   - /// sift copies all spectra corresponding to nonzero values of a mask into a pre-allocated matrix
  468 + /// Copies all spectra corresponding to nonzero values of a mask into a pre-allocated matrix of size (P x B)
  469 + /// where P is the number of masked pixels and B is the number of bands. The allocated memory can be accessed
  470 + /// using the following indexing: i = b*P + p
469 471 /// @param matrix is the destination for the pixel data
470 472 /// @param p is the mask
471 473 bool sift(void* matrix, unsigned char* p){
... ... @@ -478,11 +480,20 @@ public:
478 480 else
479 481 std::cout << "ERROR: unidentified data type" << std::endl;
480 482 }
  483 +
  484 + if (header.interleave == envi_header::BIP){
  485 + std::cout<<"Memory sifting not supported for BIP files"<<std::endl;
  486 + exit(1);
  487 + }
  488 + if (header.interleave == envi_header::BIL){
  489 + std::cout<<"Memory sifting not supported for BIL files"<<std::endl;
  490 + exit(1);
  491 + }
481 492 return false;
482 493  
483 494 }
484 495  
485   - /// sift-mask saves in an array only those spectra corresponding to nonzero values of the mask.
  496 + /// Saves in an array only those spectra corresponding to nonzero values of the mask.
486 497 /// @param outfile is the name of the sifted output file
487 498 /// @param p is the mask
488 499 bool sift(std::string outfile, unsigned char* p)
... ...
stim/envi/envi_header.h
... ... @@ -77,6 +77,9 @@ struct envi_header
77 77 }
78 78  
79 79 std::string trim(std::string line){
  80 +
  81 + if(line.length() == 0)
  82 + return line;
80 83 //trims whitespace from the beginning and end of line
81 84 unsigned int start_i, end_i;
82 85 for(start_i=0; start_i < line.length(); start_i++)
... ...
stim/image/image.h
... ... @@ -94,6 +94,24 @@ public:
94 94  
95 95 }
96 96  
  97 + T& operator()(unsigned x, unsigned y, unsigned z = 0, unsigned c = 0){
  98 + return img(x, y, z, c);
  99 + }
  100 +
  101 + /// Set all elements in the image to a given scalar value
  102 +
  103 + /// @param v is the value used to set all values in the image
  104 + image<T> operator=(T v){
  105 +
  106 + unsigned int X = width() * height() * depth() * channels();
  107 +
  108 + for(unsigned x = 0; x < X; x++)
  109 + img.data()[x] = v;
  110 +
  111 + return *this;
  112 +
  113 + }
  114 +
97 115 /// Copy the given data to the specified channel
98 116  
99 117 /// @param c is the channel number that the data will be copied to
... ... @@ -134,6 +152,10 @@ public:
134 152 return img.height();
135 153 }
136 154  
  155 + unsigned int depth(){
  156 + return img.depth();
  157 + }
  158 +
137 159 T* data(){
138 160  
139 161 return img.data();
... ...
stim/parser/filename.h
... ... @@ -15,6 +15,7 @@
15 15  
16 16 #include <string>
17 17 #include <sstream>
  18 +#include <iomanip>
18 19 #include <vector>
19 20 #include <stack>
20 21 #include <algorithm>
... ... @@ -290,6 +291,25 @@ public:
290 291 return result;
291 292 }
292 293  
  294 + /// This function replaces a wildcard in the prefix with the specified string
  295 + stim::filename insert(std::string str){
  296 +
  297 + stim::filename result = *this; //initialize the result filename to the current filename
  298 + size_t loc = result.prefix.find('*'); //find a wild card in the string
  299 + if(loc == std::string::npos) //if a wildcard isn't found
  300 + return result; //return the original string
  301 +
  302 + result.prefix.replace(loc, 1, str); //replace the wildcard with the string
  303 + return result; //return the result
  304 + }
  305 +
  306 + stim::filename insert(unsigned i, unsigned int n = 2){
  307 +
  308 + std::stringstream ss;
  309 + ss << std::setw(n) << std::setfill('0') << i;
  310 + return insert(ss.str());
  311 + }
  312 +
293 313 bool is_relative(){
294 314 return !absolute;
295 315 }
... ...