1 /**********************************************************
2 * Version $Id: raw.cpp 1921 2014-01-09 10:24:11Z oconrad $
3 *********************************************************/
4
5 ///////////////////////////////////////////////////////////
6 // //
7 // SAGA //
8 // //
9 // System for Automated Geoscientific Analyses //
10 // //
11 // Tool Library //
12 // Grid_IO //
13 // //
14 //-------------------------------------------------------//
15 // //
16 // Raw.cpp //
17 // //
18 // Copyright (C) 2003 by //
19 // Olaf Conrad //
20 // //
21 //-------------------------------------------------------//
22 // //
23 // This file is part of 'SAGA - System for Automated //
24 // Geoscientific Analyses'. SAGA is free software; you //
25 // can redistribute it and/or modify it under the terms //
26 // of the GNU General Public License as published by the //
27 // Free Software Foundation, either version 2 of the //
28 // License, or (at your option) any later version. //
29 // //
30 // SAGA is distributed in the hope that it will be //
31 // useful, but WITHOUT ANY WARRANTY; without even the //
32 // implied warranty of MERCHANTABILITY or FITNESS FOR A //
33 // PARTICULAR PURPOSE. See the GNU General Public //
34 // License for more details. //
35 // //
36 // You should have received a copy of the GNU General //
37 // Public License along with this program; if not, see //
38 // <http://www.gnu.org/licenses/>. //
39 // //
40 //-------------------------------------------------------//
41 // //
42 // e-mail: oconrad@saga-gis.org //
43 // //
44 // contact: Olaf Conrad //
45 // Institute of Geography //
46 // University of Goettingen //
47 // Goldschmidtstr. 5 //
48 // 37077 Goettingen //
49 // Germany //
50 // //
51 ///////////////////////////////////////////////////////////
52
53 //---------------------------------------------------------
54
55
56 ///////////////////////////////////////////////////////////
57 // //
58 // //
59 // //
60 ///////////////////////////////////////////////////////////
61
62 //---------------------------------------------------------
63 #include "raw.h"
64
65
66 ///////////////////////////////////////////////////////////
67 // //
68 // //
69 // //
70 ///////////////////////////////////////////////////////////
71
72 //---------------------------------------------------------
CRaw_Import(void)73 CRaw_Import::CRaw_Import(void)
74 {
75 //-----------------------------------------------------
76 Set_Name (_TL("Import Binary Raw Data"));
77
78 Set_Author ("O.Conrad (c) 2003");
79
80 Set_Description (_TW(
81 "Imports grid from binary raw data."
82 ));
83
84 //-----------------------------------------------------
85 Parameters.Add_Grid_Output("",
86 "GRID" , _TL("Grid"),
87 _TL("")
88 );
89
90 Parameters.Add_FilePath("",
91 "FILE" , _TL("File"),
92 _TL("")
93 );
94
95 //-----------------------------------------------------
96 Parameters.Add_Int("",
97 "NX" , _TL("Number of Columns"),
98 _TL(""),
99 1, 1, true
100 );
101
102 Parameters.Add_Int("",
103 "NY" , _TL("Number of Rows"),
104 _TL(""),
105 1, 1, true
106 );
107
108 Parameters.Add_Double("",
109 "CELLSIZE" , _TL("Cell Size"),
110 _TL(""),
111 1.0, 0.0, true
112 );
113
114 Parameters.Add_Choice("",
115 "POS_VECTOR" , _TL("Position Vector"),
116 _TL(""),
117 CSG_String::Format("%s|%s|",
118 _TL("cell's center"),
119 _TL("cell's corner")
120 )
121 );
122
123 Parameters.Add_Double("POS_VECTOR",
124 "POS_X" , _TL("X"),
125 _TL("")
126 );
127
128 Parameters.Add_Choice("POS_X",
129 "POS_X_SIDE" , _TL("Side"),
130 _TL(""),
131 CSG_String::Format("%s|%s|",
132 _TL("left"),
133 _TL("right")
134 )
135 );
136
137 Parameters.Add_Double("POS_VECTOR",
138 "POS_Y" , _TL("Y"),
139 _TL("")
140 );
141
142 Parameters.Add_Choice("POS_Y",
143 "POS_Y_SIDE" , _TL("Side"),
144 _TL(""),
145 CSG_String::Format("%s|%s|",
146 _TL("top"),
147 _TL("bottom")
148 )
149 );
150
151 //-----------------------------------------------------
152 Parameters.Add_Choice("",
153 "DATA_TYPE" , _TL("Data Type"),
154 _TL(""),
155 CSG_String::Format("%s|%s|%s|%s|%s|%s|%s|%s|",
156 _TL("8 bit unsigned integer"),
157 _TL("8 bit signed integer"),
158 _TL("16 bit unsigned integer"),
159 _TL("16 bit signed integer"),
160 _TL("32 bit unsigned integer"),
161 _TL("32 bit signed integer"),
162 _TL("32 bit floating point"),
163 _TL("64 bit floating point")
164 )
165 );
166
167 Parameters.Add_Choice("",
168 "BYTEORDER" , _TL("Byte Order"),
169 _TL(""),
170 CSG_String::Format("%s|%s|",
171 _TL("Little Endian (Intel)"),
172 _TL("Big Endian (Motorola)")
173 ), 0
174 );
175
176 Parameters.Add_String("",
177 "UNIT" , _TL("Unit"),
178 _TL(""),
179 ""
180 );
181
182 Parameters.Add_Double("",
183 "ZFACTOR" , _TL("Z-Scale"),
184 _TL(""),
185 1.0
186 );
187
188 Parameters.Add_Double("",
189 "NODATA" , _TL("No Data Value"),
190 _TL(""),
191 -99999
192 );
193
194 //-----------------------------------------------------
195 Parameters.Add_Int("",
196 "DATA_OFFSET" , _TL("Data Offset (Bytes)"),
197 _TL("")
198 );
199
200 Parameters.Add_Int("",
201 "LINE_OFFSET" , _TL("Record Offset (Bytes)"),
202 _TL("")
203 );
204
205 Parameters.Add_Int("",
206 "LINE_ENDSET" , _TL("Record Endset (Bytes)"),
207 _TL("")
208 );
209
210 Parameters.Add_Choice("",
211 "ORDER" , _TL("Value Order"),
212 _TL(""),
213 CSG_String::Format("%s|%s|",
214 _TL("columns by rows"),
215 _TL("rows by columns")
216 ), 0
217 );
218
219 Parameters.Add_Bool("",
220 "TOPDOWN" , _TL("Invert Row Order"),
221 _TL(""),
222 true
223 );
224
225 Parameters.Add_Bool("",
226 "LEFTRIGHT" , _TL("Invert Column Order"),
227 _TL(""),
228 false
229 );
230 }
231
232
233 ///////////////////////////////////////////////////////////
234 // //
235 ///////////////////////////////////////////////////////////
236
237 //---------------------------------------------------------
On_Execute(void)238 bool CRaw_Import::On_Execute(void)
239 {
240 //-----------------------------------------------------
241 CSG_File Stream;
242
243 if( !Stream.Open(Parameters("FILE")->asString(), SG_FILE_R, true) )
244 {
245 Error_Fmt("%s [%s]", _TL("could not open file"), Parameters("FILE")->asString());
246
247 return( false );
248 }
249
250 Skip(Stream, Parameters("DATA_OFFSET")->asInt());
251
252 //-----------------------------------------------------
253 CSG_Grid *pGrid = Get_Grid();
254
255 if( !pGrid )
256 {
257 Error_Set(_TL("could not create grid"));
258
259 return( false );
260 }
261
262 pGrid->Set_Name(SG_File_Get_Name(Parameters("FILE")->asString(), false));
263
264 Parameters("GRID")->Set_Value(pGrid);
265
266 //-----------------------------------------------------
267 bool bRecIsRow = Parameters("ORDER" )->asInt() == 0;
268 bool bRecInvert = Parameters("TOPDOWN" )->asBool() == false;
269 bool bColInvert = Parameters("LEFTRIGHT")->asBool() == false;
270
271 int nRecords = bRecIsRow ? pGrid->Get_NY() : pGrid->Get_NX();
272 int nValues = bRecIsRow ? pGrid->Get_NX() : pGrid->Get_NY();
273
274 CSG_Array Record(SG_Data_Type_Get_Size(pGrid->Get_Type()), nValues);
275
276 bool bBigOrder = Record.Get_Value_Size() > 1 && Parameters("BYTEORDER")->asInt() == 1;
277
278 int Record_Head = Parameters("LINE_OFFSET")->asInt();
279 int Record_Tail = Parameters("LINE_ENDSET")->asInt();
280
281 //-----------------------------------------------------
282 for(int iRecord=0; !Stream.is_EOF() && iRecord<nRecords && Set_Progress(iRecord, nRecords); iRecord++)
283 {
284 Skip(Stream, Record_Head);
285
286 Stream.Read(Record.Get_Array(), Record.Get_Value_Size() * Record.Get_Size());
287
288 for(int iValue=0; iValue<nValues; iValue++)
289 {
290 if( bBigOrder )
291 {
292 SG_Swap_Bytes(Record.Get_Entry(iValue), Record.Get_Value_Size());
293 }
294
295 int y = bRecIsRow ? iRecord : iValue; if( bRecInvert ) y = pGrid->Get_NY() - 1 - y;
296 int x = bRecIsRow ? iValue : iRecord; if( bColInvert ) x = pGrid->Get_NX() - 1 - x;
297
298 switch( pGrid->Get_Type() )
299 {
300 default: break;
301 case SG_DATATYPE_Byte : pGrid->Set_Value(x, y, *(unsigned char *)Record.Get_Entry(iValue)); break;
302 case SG_DATATYPE_Char : pGrid->Set_Value(x, y, *(signed char *)Record.Get_Entry(iValue)); break;
303 case SG_DATATYPE_Word : pGrid->Set_Value(x, y, *(unsigned short *)Record.Get_Entry(iValue)); break;
304 case SG_DATATYPE_Short : pGrid->Set_Value(x, y, *(signed short *)Record.Get_Entry(iValue)); break;
305 case SG_DATATYPE_DWord : pGrid->Set_Value(x, y, *(unsigned int *)Record.Get_Entry(iValue)); break;
306 case SG_DATATYPE_Int : pGrid->Set_Value(x, y, *(signed int *)Record.Get_Entry(iValue)); break;
307 case SG_DATATYPE_Float : pGrid->Set_Value(x, y, *(float *)Record.Get_Entry(iValue)); break;
308 case SG_DATATYPE_Double: pGrid->Set_Value(x, y, *(double *)Record.Get_Entry(iValue)); break;
309 }
310 }
311
312 Skip(Stream, Record_Tail);
313 }
314
315 //-----------------------------------------------------
316 pGrid->Set_Unit (Parameters("UNIT" )->asString());
317 pGrid->Set_Scaling (Parameters("ZFACTOR")->asDouble());
318 pGrid->Set_NoData_Value(Parameters("NODATA" )->asDouble());
319
320 //-----------------------------------------------------
321 return( true );
322 }
323
324
325 ///////////////////////////////////////////////////////////
326 // //
327 ///////////////////////////////////////////////////////////
328
329 //---------------------------------------------------------
Skip(CSG_File & Stream,size_t nBytes)330 bool CRaw_Import::Skip(CSG_File &Stream, size_t nBytes)
331 {
332 for(size_t i=0; i<nBytes && !Stream.is_EOF(); i++)
333 {
334 Stream.Read_Char();
335 }
336
337 return( !Stream.is_EOF() );
338 }
339
340
341 ///////////////////////////////////////////////////////////
342 // //
343 ///////////////////////////////////////////////////////////
344
345 //---------------------------------------------------------
Get_Grid(void)346 CSG_Grid * CRaw_Import::Get_Grid(void)
347 {
348 TSG_Data_Type Type;
349
350 switch( Parameters("DATA_TYPE")->asInt() )
351 {
352 default: return( NULL );
353 case 0: Type = SG_DATATYPE_Byte ; break;
354 case 1: Type = SG_DATATYPE_Char ; break;
355 case 2: Type = SG_DATATYPE_Word ; break;
356 case 3: Type = SG_DATATYPE_Short ; break;
357 case 4: Type = SG_DATATYPE_DWord ; break;
358 case 5: Type = SG_DATATYPE_Int ; break;
359 case 6: Type = SG_DATATYPE_Float ; break;
360 case 7: Type = SG_DATATYPE_Double; break;
361 }
362
363 //-----------------------------------------------------
364 int nx = Parameters("NX")->asInt();
365 int ny = Parameters("NY")->asInt();
366
367 double cs = Parameters("CELLSIZE")->asDouble();
368
369 bool bCorner = Parameters("POS_VECTOR")->asInt() == 1;
370
371 //-----------------------------------------------------
372 double x = Parameters("POS_X")->asDouble();
373
374 if( Parameters("POS_X_SIDE")->asInt() == 1 ) // right
375 {
376 x -= cs * nx;
377
378 if( bCorner )
379 {
380 x -= cs / 2.0;
381 }
382
383 }
384 else if( bCorner )
385 {
386 x += cs / 2.0;
387 }
388
389 //-----------------------------------------------------
390 double y = Parameters("POS_Y")->asDouble();
391
392 if( Parameters("POS_Y_SIDE")->asInt() == 0 ) // top
393 {
394 y -= cs * ny;
395
396 if( bCorner )
397 {
398 y -= cs / 2.0;
399 }
400 }
401 else if( bCorner )
402 {
403 y += cs / 2.0;
404 }
405
406 //-----------------------------------------------------
407 return( SG_Create_Grid(Type, nx, ny, cs, x, y) );
408 }
409
410
411 ///////////////////////////////////////////////////////////
412 // //
413 // //
414 // //
415 ///////////////////////////////////////////////////////////
416
417 //---------------------------------------------------------
418