1 /*=========================================================================
2 *
3 * Copyright Insight Software Consortium
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0.txt
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 *=========================================================================*/
18
19 #include <fstream>
20 #include "itkRawImageIO.h"
21 #include "itkImageFileReader.h"
22 #include "itkImageLinearIteratorWithIndex.h"
23
24
25 // Specific ImageIO test
26
27
28 // Helper class for reading a file and checking the content
29 template< typename TImageType >
30 class RawImageIOReadFileTester
31 {
32 public:
33 // Only single method of this class
Read(const char * filename,bool ReadBigEndian,unsigned int dims[])34 int Read( const char *filename , bool ReadBigEndian, unsigned int dims[] )
35 {
36
37 const unsigned int ImageDimension = TImageType::ImageDimension;
38
39 using PixelType = typename TImageType::PixelType;
40 using ReaderType = itk::ImageFileReader<TImageType>;
41 using IOType = itk::RawImageIO<PixelType,ImageDimension>;
42
43 typename IOType::Pointer io = IOType::New();
44
45 io->SetFileTypeToBinary();
46
47 if( ReadBigEndian )
48 {
49 io->SetByteOrderToBigEndian();
50 }
51 else
52 {
53 io->SetByteOrderToLittleEndian();
54 }
55
56 for( unsigned int j = 0; j < TImageType::ImageDimension; j++ )
57 {
58 io->SetDimensions( j, dims[j] );
59 }
60
61 typename ReaderType::Pointer reader = ReaderType::New();
62 reader->SetFileName( filename );
63 reader->SetImageIO( io );
64
65 try
66 {
67 reader->Update();
68 }
69 catch( itk::ExceptionObject & excp )
70 {
71 std::cerr << "Exception while reading file " << filename << std::endl;
72 std::cerr << excp << std::endl;
73 return EXIT_FAILURE;
74 }
75
76 std::cout << "Reading file " << filename << " succeeded " << std::endl;
77
78 using Iterator = itk::ImageLinearIteratorWithIndex<TImageType>;
79 Iterator it( reader->GetOutput(), reader->GetOutput()->GetBufferedRegion() );
80
81 it.GoToBegin();
82 it.SetDirection( 0 );
83
84
85 PixelType value = itk::NumericTraits< PixelType >::ZeroValue();
86 while ( !it.IsAtEnd() )
87 {
88 while ( !it.IsAtEndOfLine() )
89 {
90 PixelType readValue = it.Get();
91 std::cout << readValue << " ";
92 if( readValue != value )
93 {
94 std::cerr << "At index " << it.GetIndex() << std::endl;
95 std::cerr << "the value " << value << " was expected " << std::endl;
96 std::cerr << "but value " << readValue << " was read " << std::endl;
97 return EXIT_FAILURE;
98 }
99 ++it;
100 ++value;
101 }
102 std::cout << std::endl;
103 it.NextLine();
104 }
105 return EXIT_SUCCESS;
106 }
107
108 };
109
itkRawImageIOTest4(int argc,char * argv[])110 int itkRawImageIOTest4(int argc, char*argv[])
111 {
112
113 using PixelType = unsigned short;
114 constexpr unsigned int ImageDimension = 2;
115
116 using ImageType = itk::Image<PixelType,ImageDimension>;
117
118 unsigned int dims[ImageDimension] = { 5, 5 };
119
120 using ComponentType = itk::PixelTraits< PixelType >::ValueType;
121 using ByteSwapperType = itk::ByteSwapper< ComponentType >;
122
123 PixelType value = itk::NumericTraits< PixelType >::ZeroValue();
124 unsigned int numberOfPixels = dims[0] * dims[1];
125
126 if(argc < 3)
127 {
128 std::cerr << "Usage: " << argv[0] << " Output1 Output2\n";
129 return EXIT_FAILURE;
130 }
131
132
133 // Create the BigEndian binary file
134 std::ofstream outputFile1(argv[1], std::ios::out);
135 outputFile1.close();
136 #ifdef _WIN32
137 outputFile1.open( argv[1] , std::ios::out | std::ios::binary );
138 #else
139 outputFile1.open( argv[1] );
140 #endif
141
142 if( outputFile1.fail() )
143 {
144 std::cerr << "itkRawImageIOTest4:Error writing the test file" << std::endl;
145 return EXIT_FAILURE;
146 }
147
148 for( unsigned int i = 0; i < numberOfPixels; i++ )
149 {
150 PixelType swappedValue = value;
151 // make sure that the file is written in
152 // BigEndian regardless of the platform
153 ByteSwapperType::SwapFromSystemToBigEndian( &swappedValue );
154 outputFile1.write( reinterpret_cast<char*>(&swappedValue),
155 sizeof(swappedValue) );
156 ++value;
157 }
158 outputFile1.close();
159
160 if( outputFile1.fail() )
161 {
162 std::cerr << "itkRawImageIOTest4:Error writing the test file" << std::endl;
163 return EXIT_FAILURE;
164 }
165
166 // Create the LittleEndian binary file
167 std::ofstream outputFile2(argv[2], std::ios::out);
168 outputFile2.close();
169 #ifdef _WIN32
170 outputFile2.open( argv[2] , std::ios::out | std::ios::binary );
171 #else
172 outputFile2.open( argv[2] );
173 #endif
174
175 if( outputFile2.fail() )
176 {
177 std::cerr << "itkRawImageIOTest4:Error writing the test file" << std::endl;
178 return EXIT_FAILURE;
179 }
180
181 value = itk::NumericTraits< PixelType >::ZeroValue();
182 for( unsigned int i = 0; i < numberOfPixels; i++ )
183 {
184 PixelType swappedValue = value;
185 // make sure that the file is written in
186 // LittleEndian regardless of the platform
187 ByteSwapperType::SwapFromSystemToLittleEndian( &swappedValue );
188 outputFile2.write( reinterpret_cast<char*>(&swappedValue),
189 sizeof(swappedValue) );
190 ++value;
191 }
192 outputFile2.close();
193
194 if( outputFile2.fail() )
195 {
196 std::cerr << "itkRawImageIOTest4:Error writing the test file" << std::endl;
197 return EXIT_FAILURE;
198 }
199
200 RawImageIOReadFileTester<ImageType> readTester;
201
202
203 int status;
204
205 std::cout << "Testing read of Big Endian File" << std::endl;
206 bool fileIsBigEndian = true;
207 status = readTester.Read( argv[1], fileIsBigEndian, dims );
208 if( status==EXIT_FAILURE )
209 {
210 std::cerr << "Reading Raw BigEndian FAILED !!" << std::endl;
211 return EXIT_FAILURE;
212 }
213 else
214 {
215 std::cout << "Reading Raw BigEndian PASSED !!" << std::endl << std::endl;
216 }
217
218 std::cout << "Testing read of Little Endian File" << std::endl;
219 fileIsBigEndian = false;
220 status = readTester.Read( argv[2], fileIsBigEndian, dims );
221 if( status==EXIT_FAILURE )
222 {
223 std::cerr << "Reading Raw LittleEndian FAILED !!" << std::endl;
224 return EXIT_FAILURE;
225 }
226 else
227 {
228 std::cout << "Reading Raw LittleEndian PASSED !!" << std::endl << std::endl;
229 }
230
231 std::cout << "Test PASSED !!" << std::endl << std::endl;
232
233 return EXIT_SUCCESS;
234
235 }
236