/src/gdal/frmts/pcidsk/sdk/segment/cpcidskephemerissegment.cpp
Line | Count | Source (jump to first uncovered line) |
1 | | /****************************************************************************** |
2 | | * |
3 | | * Purpose: Implementation of the CPCIDSKEphemerisSegment class. |
4 | | * |
5 | | ****************************************************************************** |
6 | | * Copyright (c) 2009 |
7 | | * PCI Geomatics, 90 Allstate Parkway, Markham, Ontario, Canada. |
8 | | * |
9 | | * SPDX-License-Identifier: MIT |
10 | | ****************************************************************************/ |
11 | | |
12 | | #include "segment/cpcidsksegment.h" |
13 | | #include "core/pcidsk_utils.h" |
14 | | #include "segment/cpcidskephemerissegment.h" |
15 | | #include "pcidsk_exception.h" |
16 | | #include "core/pcidsk_utils.h" |
17 | | |
18 | | #include <vector> |
19 | | #include <string> |
20 | | #include <cassert> |
21 | | #include <cstring> |
22 | | #include <memory> |
23 | | |
24 | | using namespace PCIDSK; |
25 | | |
26 | 0 | PCIDSKEphemerisSegment::~PCIDSKEphemerisSegment() = default; |
27 | | |
28 | | namespace |
29 | | { |
30 | | /** |
31 | | * Function to get the minimum value of two values. |
32 | | * |
33 | | * @param a The first value. |
34 | | * @param b The second value. |
35 | | * |
36 | | * @return The minimum value of the two specified values. |
37 | | */ |
38 | | int MinFunction(int a,int b) |
39 | 0 | { |
40 | 0 | return (a<b)?a:b; |
41 | 0 | } |
42 | | } |
43 | | |
44 | | /** |
45 | | * Ephemeris Segment constructor |
46 | | * @param fileIn the PCIDSK file |
47 | | * @param segmentIn the segment index |
48 | | * @param segment_pointer the segment pointer |
49 | | * @param bLoad true to load the segment, else false (default true) |
50 | | */ |
51 | | CPCIDSKEphemerisSegment::CPCIDSKEphemerisSegment(PCIDSKFile *fileIn, |
52 | | int segmentIn, |
53 | | const char *segment_pointer, |
54 | | bool bLoad) : |
55 | 0 | CPCIDSKSegment(fileIn, segmentIn, segment_pointer), |
56 | 0 | loaded_(false),mbModified(false) |
57 | 0 | { |
58 | 0 | mpoEphemeris = nullptr; |
59 | 0 | if(bLoad) |
60 | 0 | { |
61 | 0 | Load(); |
62 | 0 | } |
63 | 0 | } Unexecuted instantiation: PCIDSK::CPCIDSKEphemerisSegment::CPCIDSKEphemerisSegment(PCIDSK::PCIDSKFile*, int, char const*, bool) Unexecuted instantiation: PCIDSK::CPCIDSKEphemerisSegment::CPCIDSKEphemerisSegment(PCIDSK::PCIDSKFile*, int, char const*, bool) |
64 | | |
65 | | |
66 | | CPCIDSKEphemerisSegment::~CPCIDSKEphemerisSegment() |
67 | 0 | { |
68 | 0 | delete mpoEphemeris; |
69 | 0 | } |
70 | | |
71 | | /** |
72 | | * Load the contents of the segment |
73 | | */ |
74 | | void CPCIDSKEphemerisSegment::Load() |
75 | 0 | { |
76 | | // Check if we've already loaded the segment into memory |
77 | 0 | if (loaded_) { |
78 | 0 | return; |
79 | 0 | } |
80 | | |
81 | 0 | seg_data.SetSize((int)data_size - 1024); |
82 | |
|
83 | 0 | if(data_size == 1024) |
84 | 0 | return; |
85 | | |
86 | 0 | ReadFromFile(seg_data.buffer, 0, data_size - 1024); |
87 | | |
88 | | // We test the name of the binary segment before starting to read |
89 | | // the buffer. |
90 | 0 | if (!STARTS_WITH(seg_data.buffer, "ORBIT ")) |
91 | 0 | { |
92 | 0 | seg_data.Put("ORBIT ",0,8); |
93 | 0 | loaded_ = true; |
94 | 0 | return ; |
95 | 0 | } |
96 | | |
97 | 0 | mpoEphemeris = BinaryToEphemeris(0); |
98 | | |
99 | | // We've now loaded the structure up with data. Mark it as being loaded |
100 | | // properly. |
101 | 0 | loaded_ = true; |
102 | 0 | } |
103 | | |
104 | | /** |
105 | | * Write the segment on disk |
106 | | */ |
107 | | void CPCIDSKEphemerisSegment::Write(void) |
108 | 0 | { |
109 | | //We are not writing if nothing was loaded. |
110 | 0 | if (!loaded_) { |
111 | 0 | return; |
112 | 0 | } |
113 | | |
114 | 0 | EphemerisToBinary( mpoEphemeris, 0); |
115 | |
|
116 | 0 | seg_data.Put("ORBIT ",0,8); |
117 | |
|
118 | 0 | WriteToFile(seg_data.buffer,0,seg_data.buffer_size); |
119 | |
|
120 | 0 | mbModified = false; |
121 | 0 | } |
122 | | |
123 | | /** |
124 | | * Synchronize the segment, if it was modified then |
125 | | * write it into disk. |
126 | | */ |
127 | | void CPCIDSKEphemerisSegment::Synchronize() |
128 | 0 | { |
129 | 0 | if(mbModified) |
130 | 0 | { |
131 | 0 | this->Write(); |
132 | 0 | } |
133 | 0 | } |
134 | | |
135 | | /************************************************************************/ |
136 | | /* ConvertDeg() */ |
137 | | /************************************************************************/ |
138 | | /** |
139 | | * if mode is 0, convert angle from 0 to 360 to 0 to 180 and 0 to -180 |
140 | | * if mode is 1, convert angle from 0 to 180 and 0 to -180 to 0 to 360 |
141 | | * |
142 | | * @param degree the degree |
143 | | * @param mode the mode |
144 | | */ |
145 | | double CPCIDSKEphemerisSegment::ConvertDeg(double degree, int mode) |
146 | 0 | { |
147 | 0 | double result; |
148 | |
|
149 | 0 | if (mode == 0) |
150 | 0 | { |
151 | | /* -------------------------------------------------------------------- */ |
152 | | /* degree is in range of 0 to 360 */ |
153 | | /* -------------------------------------------------------------------- */ |
154 | 0 | if (degree > 180) |
155 | 0 | result = degree - 360; |
156 | 0 | else |
157 | 0 | result = degree; |
158 | 0 | } |
159 | 0 | else |
160 | 0 | { |
161 | | /* -------------------------------------------------------------------- */ |
162 | | /* degree is in range of 0 to 180 and 0 to -180 */ |
163 | | /* -------------------------------------------------------------------- */ |
164 | 0 | if (degree < 0) |
165 | 0 | result = 360 + degree; |
166 | 0 | else |
167 | 0 | result = degree; |
168 | 0 | } |
169 | 0 | return (result); |
170 | 0 | } |
171 | | |
172 | | /************************************************************************/ |
173 | | /* ReadAvhrrEphemerisSegment() */ |
174 | | /************************************************************************/ |
175 | | /** |
176 | | * Read the contents of blocks 9, 11, and onwards from the orbit |
177 | | * segment into the EphemerisSeg_t structure. |
178 | | * @param nStartBlock where to start to read in the buffer |
179 | | * @param psEphSegRec the structure to populate with information. |
180 | | */ |
181 | | void |
182 | | CPCIDSKEphemerisSegment::ReadAvhrrEphemerisSegment(int nStartBlock, |
183 | | EphemerisSeg_t *psEphSegRec) |
184 | 0 | { |
185 | 0 | int nBlock = 0, nLine = 0; |
186 | 0 | int nPos = 0; |
187 | |
|
188 | 0 | int nDataLength = seg_data.buffer_size; |
189 | | /* -------------------------------------------------------------------- */ |
190 | | /* Allocate the AVHRR segment portion of EphemerisSeg_t. */ |
191 | | /* -------------------------------------------------------------------- */ |
192 | 0 | psEphSegRec->AvhrrSeg = new AvhrrSeg_t(); |
193 | 0 | AvhrrSeg_t* as = psEphSegRec->AvhrrSeg; |
194 | | |
195 | | /* -------------------------------------------------------------------- */ |
196 | | /* Read in the Ninth Block which contains general info + ephemeris */ |
197 | | /* info as well. */ |
198 | | /* -------------------------------------------------------------------- */ |
199 | 0 | nPos = nStartBlock + 8*512; |
200 | |
|
201 | 0 | as->szImageFormat = seg_data.Get(nPos, 16); |
202 | 0 | as->nImageXSize = seg_data.GetInt(nPos+16, 16); |
203 | 0 | as->nImageYSize = seg_data.GetInt(nPos+32, 16); |
204 | |
|
205 | 0 | if ( STARTS_WITH(seg_data.Get(nPos+48,9), "ASCENDING") ) |
206 | 0 | as->bIsAscending = true; |
207 | 0 | else |
208 | 0 | as->bIsAscending = false; |
209 | 0 | if ( STARTS_WITH(seg_data.Get(nPos+64,7), "ROTATED") ) |
210 | 0 | as->bIsImageRotated = true; |
211 | 0 | else |
212 | 0 | as->bIsImageRotated = false; |
213 | |
|
214 | 0 | as->szOrbitNumber = seg_data.Get(nPos+80, 16); |
215 | 0 | as->szAscendDescendNodeFlag = seg_data.Get(nPos+96,16); |
216 | 0 | as->szEpochYearAndDay = seg_data.Get(nPos+112,16); |
217 | 0 | as->szEpochTimeWithinDay = seg_data.Get(nPos+128,16); |
218 | 0 | as->szTimeDiffStationSatelliteMsec = seg_data.Get(nPos+144,16); |
219 | 0 | as->szActualSensorScanRate = seg_data.Get(nPos+160,16); |
220 | 0 | as->szIdentOfOrbitInfoSource = seg_data.Get(nPos+176,16); |
221 | 0 | as->szInternationalDesignator = seg_data.Get(nPos+192,16); |
222 | 0 | as->szOrbitNumAtEpoch = seg_data.Get(nPos+208,16); |
223 | 0 | as->szJulianDayAscendNode = seg_data.Get(nPos+224,16); |
224 | 0 | as->szEpochYear = seg_data.Get(nPos+240,16); |
225 | 0 | as->szEpochMonth = seg_data.Get(nPos+256,16); |
226 | 0 | as->szEpochDay = seg_data.Get(nPos+272,16); |
227 | 0 | as->szEpochHour = seg_data.Get(nPos+288,16); |
228 | 0 | as->szEpochMinute = seg_data.Get(nPos+304,16); |
229 | 0 | as->szEpochSecond = seg_data.Get(nPos+320,16); |
230 | 0 | as->szPointOfAriesDegrees = seg_data.Get(nPos+336,16); |
231 | 0 | as->szAnomalisticPeriod = seg_data.Get(nPos+352,16); |
232 | 0 | as->szNodalPeriod = seg_data.Get(nPos+368,16); |
233 | 0 | as->szEccentricity = seg_data.Get(nPos+384,16); |
234 | 0 | as->szArgumentOfPerigee = seg_data.Get(nPos+400,16); |
235 | 0 | as->szRAAN = seg_data.Get(nPos+416,16); |
236 | 0 | as->szInclination = seg_data.Get(nPos+432,16); |
237 | 0 | as->szMeanAnomaly = seg_data.Get(nPos+448,16); |
238 | 0 | as->szSemiMajorAxis = seg_data.Get(nPos+464,16); |
239 | | |
240 | | /* -------------------------------------------------------------------- */ |
241 | | /* Skip the 10th block which is reserved for future use. */ |
242 | | /* -------------------------------------------------------------------- */ |
243 | | |
244 | | /* -------------------------------------------------------------------- */ |
245 | | /* Read in the 11th block, which contains indexing info. */ |
246 | | /* -------------------------------------------------------------------- */ |
247 | 0 | nPos = nStartBlock + 512*10; |
248 | |
|
249 | 0 | as->nRecordSize = seg_data.GetInt(nPos, 16); |
250 | 0 | as->nBlockSize = seg_data.GetInt(nPos+16, 16); |
251 | 0 | as->nNumRecordsPerBlock = seg_data.GetInt(nPos+32, 16); |
252 | 0 | as->nNumBlocks = seg_data.GetInt(nPos+48, 16); |
253 | 0 | as->nNumScanlineRecords = seg_data.GetInt(nPos+64, 16); |
254 | | |
255 | | /* -------------------------------------------------------------------- */ |
256 | | /* Allocate the scanline records. */ |
257 | | /* -------------------------------------------------------------------- */ |
258 | 0 | if ( as->nNumScanlineRecords == 0 ) |
259 | 0 | return; |
260 | | |
261 | | /* -------------------------------------------------------------------- */ |
262 | | /* Now read the 12th block and onward. */ |
263 | | /* -------------------------------------------------------------------- */ |
264 | 0 | nBlock = 12; |
265 | |
|
266 | 0 | if ( as->nNumRecordsPerBlock == 0 ) |
267 | 0 | return; |
268 | | |
269 | 0 | for(nLine = 0; nLine < as->nNumScanlineRecords; |
270 | 0 | nLine += as->nNumRecordsPerBlock) |
271 | 0 | { |
272 | 0 | int nNumRecords = MinFunction(as->nNumRecordsPerBlock, |
273 | 0 | as->nNumScanlineRecords - nLine); |
274 | 0 | nPos = nStartBlock + 512*(nBlock-1); |
275 | 0 | if( nDataLength < 512*nBlock ) |
276 | 0 | { |
277 | 0 | break; |
278 | 0 | } |
279 | | |
280 | 0 | for(int i = 0; i < nNumRecords; ++i) |
281 | 0 | { |
282 | 0 | AvhrrLine_t sLine; |
283 | 0 | ReadAvhrrScanlineRecord(nPos+i*80, &sLine); |
284 | 0 | as->Line.push_back(sLine); |
285 | 0 | } |
286 | |
|
287 | 0 | ++nBlock; |
288 | 0 | } |
289 | 0 | } |
290 | | |
291 | | /************************************************************************/ |
292 | | /* ReadAvhrrScanlineRecord() */ |
293 | | /************************************************************************/ |
294 | | /** |
295 | | * Read from a byte buffer in order to set a scanline record. |
296 | | * @param nPos position in buffer |
297 | | * @param psScanlineRecord the record to read. |
298 | | */ |
299 | | void |
300 | | CPCIDSKEphemerisSegment::ReadAvhrrScanlineRecord(int nPos, |
301 | | AvhrrLine_t *psScanlineRecord) |
302 | 0 | { |
303 | 0 | int i; |
304 | 0 | AvhrrLine_t *sr = psScanlineRecord; |
305 | |
|
306 | 0 | sr->nScanLineNum = ReadAvhrrInt32((unsigned char*)seg_data.Get(nPos,4)); |
307 | 0 | sr->nStartScanTimeGMTMsec = ReadAvhrrInt32((unsigned char*)seg_data.Get(nPos+4,4)); |
308 | |
|
309 | 0 | for(i = 0; i < 10; ++i) |
310 | 0 | sr->abyScanLineQuality[i] = static_cast<unsigned char>(seg_data.GetInt(nPos+8+i,1)); |
311 | |
|
312 | 0 | for(i = 0; i < 5; ++i) |
313 | 0 | { |
314 | 0 | sr->aabyBadBandIndicators[i][0] = static_cast<unsigned char>(seg_data.GetInt(nPos+18+2*i,1)); |
315 | 0 | sr->aabyBadBandIndicators[i][1] = static_cast<unsigned char>(seg_data.GetInt(nPos+18+2*i+1,1)); |
316 | 0 | } |
317 | |
|
318 | 0 | for(i = 0; i < 8; ++i) |
319 | 0 | sr->abySatelliteTimeCode[i] = static_cast<unsigned char>(seg_data.GetInt(nPos+28+i,1)); |
320 | |
|
321 | 0 | for(i = 0; i < 3; ++i) |
322 | 0 | sr->anTargetTempData[i] = ReadAvhrrInt32((unsigned char*)seg_data.Get(nPos+36+i*4,4)); |
323 | 0 | for(i = 0; i < 3; ++i) |
324 | 0 | sr->anTargetScanData[i] = ReadAvhrrInt32((unsigned char*)seg_data.Get(nPos+48+i*4,4)); |
325 | 0 | for(i = 0; i < 5; ++i) |
326 | 0 | sr->anSpaceScanData[i] = ReadAvhrrInt32((unsigned char*)seg_data.Get(nPos+60+i*4,4)); |
327 | 0 | } |
328 | | |
329 | | /************************************************************************/ |
330 | | /* ReadAvhrrInt32() */ |
331 | | /************************************************************************/ |
332 | | /** |
333 | | * Read an integer from a given buffer of at least 4 bytes. |
334 | | * @param pbyBuf the buffer that contains the value. |
335 | | * @return the value |
336 | | */ |
337 | | int |
338 | | CPCIDSKEphemerisSegment::ReadAvhrrInt32(unsigned char* pbyBuf) |
339 | 0 | { |
340 | 0 | int nValue = 0; |
341 | 0 | unsigned char* b = pbyBuf; |
342 | 0 | nValue = (int)((b[0]<<24) | (b[1]<<16) | (b[2]<<8) | b[3]); |
343 | |
|
344 | 0 | return( nValue ); |
345 | 0 | } |
346 | | |
347 | | /************************************************************************/ |
348 | | /* WriteAvhrrEphemerisSegment() */ |
349 | | /************************************************************************/ |
350 | | /** |
351 | | * Write the contents of blocks 9, 10, and onwards to the orbit |
352 | | * segment from fields in the EphemerisSeg_t structure. |
353 | | * @param nStartBlock where to start to write the information in the buffer |
354 | | * @param psEphSegRec the information to write. |
355 | | */ |
356 | | void |
357 | | CPCIDSKEphemerisSegment::WriteAvhrrEphemerisSegment(int nStartBlock, |
358 | | EphemerisSeg_t *psEphSegRec) |
359 | 0 | { |
360 | 0 | int nBlock = 0, nLine = 0; |
361 | 0 | int nPos = 0; |
362 | | /* -------------------------------------------------------------------- */ |
363 | | /* Check that the AvhrrSeg is not NULL. */ |
364 | | /* -------------------------------------------------------------------- */ |
365 | 0 | AvhrrSeg_t* as = psEphSegRec->AvhrrSeg; |
366 | |
|
367 | 0 | if ( as == nullptr) |
368 | 0 | { |
369 | 0 | return ThrowPCIDSKException("The AvhrrSeg is NULL."); |
370 | 0 | } |
371 | | |
372 | | /* -------------------------------------------------------------------- */ |
373 | | /* Realloc the data buffer large enough to hold all the AVHRR */ |
374 | | /* information, and zero it. */ |
375 | | /* -------------------------------------------------------------------- */ |
376 | 0 | int nToAdd = 512 * |
377 | 0 | (((as->nNumScanlineRecords + as->nNumRecordsPerBlock-1) / |
378 | 0 | as->nNumRecordsPerBlock) |
379 | 0 | +4); |
380 | 0 | seg_data.SetSize(seg_data.buffer_size + nToAdd); |
381 | |
|
382 | 0 | nPos = nStartBlock; |
383 | 0 | memset(seg_data.buffer+nPos,' ',nToAdd); |
384 | | |
385 | | /* -------------------------------------------------------------------- */ |
386 | | /* Write the first avhrr Block. */ |
387 | | /* -------------------------------------------------------------------- */ |
388 | |
|
389 | 0 | seg_data.Put(as->szImageFormat.c_str(),nPos,16); |
390 | |
|
391 | 0 | seg_data.Put(as->nImageXSize,nPos+16,16); |
392 | 0 | seg_data.Put(as->nImageYSize,nPos+32,16); |
393 | |
|
394 | 0 | if ( as->bIsAscending ) |
395 | 0 | seg_data.Put("ASCENDING",nPos+48,9); |
396 | 0 | else |
397 | 0 | seg_data.Put("DESCENDING",nPos+48,10); |
398 | |
|
399 | 0 | if ( as->bIsImageRotated ) |
400 | 0 | seg_data.Put("ROTATED",nPos+64,7); |
401 | 0 | else |
402 | 0 | seg_data.Put("NOT ROTATED",nPos+64,11); |
403 | |
|
404 | 0 | seg_data.Put(as->szOrbitNumber.c_str(),nPos+80,16); |
405 | 0 | seg_data.Put(as->szAscendDescendNodeFlag.c_str(),nPos+96,16,true); |
406 | 0 | seg_data.Put(as->szEpochYearAndDay.c_str(),nPos+112,16,true); |
407 | 0 | seg_data.Put(as->szEpochTimeWithinDay.c_str(),nPos+128,16,true); |
408 | 0 | seg_data.Put(as->szTimeDiffStationSatelliteMsec.c_str(),nPos+144,16,true); |
409 | 0 | seg_data.Put(as->szActualSensorScanRate.c_str(),nPos+160,16,true); |
410 | 0 | seg_data.Put(as->szIdentOfOrbitInfoSource.c_str(),nPos+176,16,true); |
411 | 0 | seg_data.Put(as->szInternationalDesignator.c_str(),nPos+192,16,true); |
412 | 0 | seg_data.Put(as->szOrbitNumAtEpoch.c_str(),nPos+208,16,true); |
413 | 0 | seg_data.Put(as->szJulianDayAscendNode.c_str(),nPos+224,16,true); |
414 | 0 | seg_data.Put(as->szEpochYear.c_str(),nPos+240,16,true); |
415 | 0 | seg_data.Put(as->szEpochMonth.c_str(),nPos+256,16,true); |
416 | 0 | seg_data.Put(as->szEpochDay.c_str(),nPos+272,16,true); |
417 | 0 | seg_data.Put(as->szEpochHour.c_str(),nPos+288,16,true); |
418 | 0 | seg_data.Put(as->szEpochMinute.c_str(),nPos+304,16,true); |
419 | 0 | seg_data.Put(as->szEpochSecond.c_str(),nPos+320,16,true); |
420 | 0 | seg_data.Put(as->szPointOfAriesDegrees.c_str(),nPos+336,16,true); |
421 | 0 | seg_data.Put(as->szAnomalisticPeriod.c_str(),nPos+352,16,true); |
422 | 0 | seg_data.Put(as->szNodalPeriod.c_str(),nPos+368,16,true); |
423 | 0 | seg_data.Put(as->szEccentricity.c_str(), nPos+384,16,true); |
424 | 0 | seg_data.Put(as->szArgumentOfPerigee.c_str(),nPos+400,16,true); |
425 | 0 | seg_data.Put(as->szRAAN.c_str(),nPos+416,16,true); |
426 | 0 | seg_data.Put(as->szInclination.c_str(),nPos+432,16,true); |
427 | 0 | seg_data.Put(as->szMeanAnomaly.c_str(),nPos+448,16,true); |
428 | 0 | seg_data.Put(as->szSemiMajorAxis.c_str(),nPos+464,16,true); |
429 | | |
430 | | /* -------------------------------------------------------------------- */ |
431 | | /* second avhrr block is all zeros. */ |
432 | | /* -------------------------------------------------------------------- */ |
433 | | |
434 | | /* -------------------------------------------------------------------- */ |
435 | | /* Write the 3rd avhrr Block. */ |
436 | | /* -------------------------------------------------------------------- */ |
437 | 0 | nPos = nStartBlock + 512*2; |
438 | |
|
439 | 0 | seg_data.Put(as->nRecordSize,nPos,16); |
440 | 0 | seg_data.Put(as->nBlockSize,nPos+16,16); |
441 | 0 | seg_data.Put(as->nNumRecordsPerBlock,nPos+32,16); |
442 | 0 | seg_data.Put(as->nNumBlocks,nPos+48,16); |
443 | 0 | seg_data.Put(as->nNumScanlineRecords,nPos+64,16); |
444 | | |
445 | | /* -------------------------------------------------------------------- */ |
446 | | /* Write the fourth avhrr block onwards. */ |
447 | | /* -------------------------------------------------------------------- */ |
448 | 0 | if ( as->Line.empty() ) |
449 | 0 | return; |
450 | | |
451 | 0 | nBlock = 4; |
452 | |
|
453 | 0 | if ( as->nNumRecordsPerBlock == 0 ) |
454 | 0 | return; |
455 | | |
456 | 0 | for(nLine = 0; nLine < as->nNumScanlineRecords; |
457 | 0 | nLine += as->nNumRecordsPerBlock) |
458 | 0 | { |
459 | 0 | int nNumRecords = MinFunction(as->nNumRecordsPerBlock, |
460 | 0 | as->nNumScanlineRecords - nLine); |
461 | 0 | nPos = nStartBlock + (nBlock-1) * 512; |
462 | |
|
463 | 0 | for(int i = 0; i < nNumRecords; ++i) |
464 | 0 | { |
465 | 0 | WriteAvhrrScanlineRecord(&(as->Line[nLine+i]), nPos + i*80); |
466 | 0 | } |
467 | |
|
468 | 0 | ++nBlock; |
469 | 0 | } |
470 | 0 | } |
471 | | |
472 | | /************************************************************************/ |
473 | | /* WriteAvhrrScanlineRecord() */ |
474 | | /************************************************************************/ |
475 | | /** |
476 | | * Write a scanline record to a byte buffer. |
477 | | * @param psScanlineRecord the record to write |
478 | | * @param nPos position in buffer |
479 | | */ |
480 | | void |
481 | | CPCIDSKEphemerisSegment::WriteAvhrrScanlineRecord( |
482 | | AvhrrLine_t *psScanlineRecord, |
483 | | int nPos) |
484 | 0 | { |
485 | 0 | int i; |
486 | 0 | AvhrrLine_t *sr = psScanlineRecord; |
487 | 0 | unsigned char* b = (unsigned char*)&(seg_data.buffer[nPos]); |
488 | |
|
489 | 0 | WriteAvhrrInt32(sr->nScanLineNum, b); |
490 | 0 | WriteAvhrrInt32(sr->nStartScanTimeGMTMsec, b+4); |
491 | |
|
492 | 0 | for(i=0 ; i < 10 ; i++) |
493 | 0 | seg_data.Put(sr->abyScanLineQuality[i],nPos+8+i,1); |
494 | |
|
495 | 0 | for(i = 0; i < 5; ++i) |
496 | 0 | { |
497 | 0 | seg_data.Put(sr->aabyBadBandIndicators[i][0],nPos+18+i*2,1); |
498 | 0 | seg_data.Put(sr->aabyBadBandIndicators[i][1],nPos+18+i*2+1,1); |
499 | 0 | } |
500 | |
|
501 | 0 | for(i=0 ; i < 8 ; i++) |
502 | 0 | seg_data.Put(sr->abySatelliteTimeCode[i],nPos+28+i,1); |
503 | |
|
504 | 0 | for(i = 0; i < 3; ++i) |
505 | 0 | WriteAvhrrInt32(sr->anTargetTempData[i], b+(36+i*4)); |
506 | 0 | for(i = 0; i < 3; ++i) |
507 | 0 | WriteAvhrrInt32(sr->anTargetScanData[i], b+(48+i*4)); |
508 | 0 | for(i = 0; i < 5; ++i) |
509 | 0 | WriteAvhrrInt32(sr->anSpaceScanData[i], b+(60+i*4)); |
510 | |
|
511 | 0 | } |
512 | | |
513 | | /************************************************************************/ |
514 | | /* WriteAvhrrInt32() */ |
515 | | /************************************************************************/ |
516 | | /** |
517 | | * Write an integer into a given buffer of at least 4 bytes. |
518 | | * @param nValue the value to write |
519 | | * @param pbyBuf the buffer to write into. |
520 | | */ |
521 | | void CPCIDSKEphemerisSegment::WriteAvhrrInt32(int nValue, |
522 | | unsigned char* pbyBuf) |
523 | 0 | { |
524 | 0 | pbyBuf[0] = static_cast<unsigned char>((nValue & 0xff000000) >> 24); |
525 | 0 | pbyBuf[1] = static_cast<unsigned char>((nValue & 0x00ff0000) >> 16); |
526 | 0 | pbyBuf[2] = static_cast<unsigned char>((nValue & 0x0000ff00) >> 8); |
527 | 0 | pbyBuf[3] = static_cast<unsigned char>(nValue & 0x000000ff); |
528 | 0 | } |
529 | | |
530 | | |
531 | | /************************************************************************/ |
532 | | /* BinaryToEphemeris() */ |
533 | | /************************************************************************/ |
534 | | /** |
535 | | * Read binary information from a binary buffer to create an |
536 | | * EphemerisSeg_t structure. The caller is responsible to free the memory |
537 | | * of the returned structure with delete. |
538 | | * |
539 | | * @param nStartBlock where to start read the orbit info into the buffer. |
540 | | * @return the orbit information. |
541 | | */ |
542 | | EphemerisSeg_t * |
543 | | CPCIDSKEphemerisSegment::BinaryToEphemeris( int nStartBlock ) |
544 | | |
545 | 0 | { |
546 | 0 | int i; |
547 | 0 | int nPos = nStartBlock; |
548 | |
|
549 | 0 | std::unique_ptr<EphemerisSeg_t> l_segment(new EphemerisSeg_t()); |
550 | | |
551 | | /* -------------------------------------------------------------------- */ |
552 | | /* Process first block. */ |
553 | | /* -------------------------------------------------------------------- */ |
554 | |
|
555 | 0 | l_segment->SatelliteDesc = seg_data.Get(nPos+8,32); |
556 | 0 | l_segment->SceneID = seg_data.Get(nPos+40, 32); |
557 | | |
558 | | /* -------------------------------------------------------------------- */ |
559 | | /* Process the second block. */ |
560 | | /* -------------------------------------------------------------------- */ |
561 | 0 | nPos = nStartBlock + 512; |
562 | |
|
563 | 0 | l_segment->SatelliteSensor = seg_data.Get(nPos, 16); |
564 | 0 | for (i=0; i<16; i++) |
565 | 0 | { |
566 | 0 | if (l_segment->SatelliteSensor[i] == ' ') |
567 | 0 | { |
568 | 0 | l_segment->SatelliteSensor = l_segment->SatelliteSensor.substr(0,i); |
569 | 0 | break; |
570 | 0 | } |
571 | 0 | } |
572 | |
|
573 | 0 | l_segment->SensorNo = seg_data.Get(nPos+22, 2); |
574 | 0 | l_segment->DateImageTaken = seg_data.Get(nPos+44, 22); |
575 | |
|
576 | 0 | if (seg_data.buffer[nPos+66] == 'Y' || |
577 | 0 | seg_data.buffer[nPos+66] == 'y') |
578 | 0 | l_segment->SupSegExist = true; |
579 | 0 | else |
580 | 0 | l_segment->SupSegExist = false; |
581 | 0 | l_segment->FieldOfView = seg_data.GetDouble(nPos+88, 22); |
582 | 0 | l_segment->ViewAngle = seg_data.GetDouble(nPos+110, 22); |
583 | 0 | l_segment->NumColCentre = seg_data.GetDouble(nPos+132, 22); |
584 | 0 | l_segment->RadialSpeed = seg_data.GetDouble(nPos+154, 22); |
585 | 0 | l_segment->Eccentricity = seg_data.GetDouble(nPos+176, 22); |
586 | 0 | l_segment->Height = seg_data.GetDouble(nPos+198, 22); |
587 | 0 | l_segment->Inclination = seg_data.GetDouble(nPos+220, 22); |
588 | 0 | l_segment->TimeInterval = seg_data.GetDouble(nPos+242, 22); |
589 | 0 | l_segment->NumLineCentre = seg_data.GetDouble(nPos+264, 22); |
590 | 0 | l_segment->LongCentre = seg_data.GetDouble(nPos+286, 22); |
591 | 0 | l_segment->AngularSpd = seg_data.GetDouble(nPos+308, 22); |
592 | 0 | l_segment->AscNodeLong = seg_data.GetDouble(nPos+330, 22); |
593 | 0 | l_segment->ArgPerigee = seg_data.GetDouble(nPos+352, 22); |
594 | 0 | l_segment->LatCentre = seg_data.GetDouble(nPos+374, 22); |
595 | 0 | l_segment->EarthSatelliteDist = seg_data.GetDouble(nPos+396, 22); |
596 | 0 | l_segment->NominalPitch = seg_data.GetDouble(nPos+418, 22); |
597 | 0 | l_segment->TimeAtCentre = seg_data.GetDouble(nPos+440, 22); |
598 | 0 | l_segment->SatelliteArg = seg_data.GetDouble(nPos+462, 22); |
599 | 0 | l_segment->bDescending = true; |
600 | 0 | if (seg_data.buffer[nPos+484] == 'A') |
601 | 0 | l_segment->bDescending = false; |
602 | | |
603 | | /* -------------------------------------------------------------------- */ |
604 | | /* Process the third block. */ |
605 | | /* -------------------------------------------------------------------- */ |
606 | 0 | nPos = nStartBlock + 2*512; |
607 | |
|
608 | 0 | l_segment->XCentre = seg_data.GetDouble(nPos, 22); |
609 | 0 | l_segment->YCentre = seg_data.GetDouble(nPos+22, 22); |
610 | 0 | l_segment->UtmXCentre = seg_data.GetDouble(nPos+44, 22); |
611 | 0 | l_segment->UtmYCentre = seg_data.GetDouble(nPos+66, 22); |
612 | 0 | l_segment->PixelRes = seg_data.GetDouble(nPos+88, 22); |
613 | 0 | l_segment->LineRes = seg_data.GetDouble(nPos+110, 22); |
614 | 0 | if (seg_data.buffer[nPos+132] == 'Y' || |
615 | 0 | seg_data.buffer[nPos+132] == 'y') |
616 | 0 | l_segment->CornerAvail = true; |
617 | 0 | else |
618 | 0 | l_segment->CornerAvail = false; |
619 | 0 | l_segment->MapUnit = seg_data.Get(nPos+133, 16); |
620 | |
|
621 | 0 | l_segment->XUL = seg_data.GetDouble(nPos+149, 22); |
622 | 0 | l_segment->YUL = seg_data.GetDouble(nPos+171, 22); |
623 | 0 | l_segment->XUR = seg_data.GetDouble(nPos+193, 22); |
624 | 0 | l_segment->YUR = seg_data.GetDouble(nPos+215, 22); |
625 | 0 | l_segment->XLR = seg_data.GetDouble(nPos+237, 22); |
626 | 0 | l_segment->YLR = seg_data.GetDouble(nPos+259, 22); |
627 | 0 | l_segment->XLL = seg_data.GetDouble(nPos+281, 22); |
628 | 0 | l_segment->YLL = seg_data.GetDouble(nPos+303, 22); |
629 | 0 | l_segment->UtmXUL = seg_data.GetDouble(nPos+325, 22); |
630 | 0 | l_segment->UtmYUL = seg_data.GetDouble(nPos+347, 22); |
631 | 0 | l_segment->UtmXUR = seg_data.GetDouble(nPos+369, 22); |
632 | 0 | l_segment->UtmYUR = seg_data.GetDouble(nPos+391, 22); |
633 | 0 | l_segment->UtmXLR = seg_data.GetDouble(nPos+413, 22); |
634 | 0 | l_segment->UtmYLR = seg_data.GetDouble(nPos+435, 22); |
635 | 0 | l_segment->UtmXLL = seg_data.GetDouble(nPos+457, 22); |
636 | 0 | l_segment->UtmYLL = seg_data.GetDouble(nPos+479, 22); |
637 | | |
638 | | /* -------------------------------------------------------------------- */ |
639 | | /* Process the 4th block (Corner lat/long coordinates) */ |
640 | | /* -------------------------------------------------------------------- */ |
641 | 0 | nPos = nStartBlock + 3*512; |
642 | |
|
643 | 0 | l_segment->LongCentreDeg = seg_data.GetDouble(nPos, 16); |
644 | 0 | l_segment->LatCentreDeg = seg_data.GetDouble(nPos+16, 16); |
645 | 0 | l_segment->LongUL = seg_data.GetDouble(nPos+32, 16); |
646 | 0 | l_segment->LatUL = seg_data.GetDouble(nPos+48, 16); |
647 | 0 | l_segment->LongUR = seg_data.GetDouble(nPos+64, 16); |
648 | 0 | l_segment->LatUR = seg_data.GetDouble(nPos+80, 16); |
649 | 0 | l_segment->LongLR = seg_data.GetDouble(nPos+96, 16); |
650 | 0 | l_segment->LatLR = seg_data.GetDouble(nPos+112, 16); |
651 | 0 | l_segment->LongLL = seg_data.GetDouble(nPos+128, 16); |
652 | 0 | l_segment->LatLL = seg_data.GetDouble(nPos+144, 16); |
653 | 0 | l_segment->HtCentre = seg_data.GetDouble(nPos+160, 16); |
654 | 0 | l_segment->HtUL = seg_data.GetDouble(nPos+176, 16); |
655 | 0 | l_segment->HtUR = seg_data.GetDouble(nPos+192, 16); |
656 | 0 | l_segment->HtLR = seg_data.GetDouble(nPos+208, 16); |
657 | 0 | l_segment->HtLL = seg_data.GetDouble(nPos+224, 16); |
658 | | |
659 | | /* -------------------------------------------------------------------- */ |
660 | | /* Process the 5th block. */ |
661 | | /* -------------------------------------------------------------------- */ |
662 | 0 | nPos = nStartBlock + 512*4; |
663 | |
|
664 | 0 | l_segment->ImageRecordLength = seg_data.GetInt(nPos, 16); |
665 | 0 | l_segment->NumberImageLine = seg_data.GetInt(nPos+16, 16); |
666 | 0 | l_segment->NumberBytePerPixel = seg_data.GetInt(nPos+32, 16); |
667 | 0 | l_segment->NumberSamplePerLine = seg_data.GetInt(nPos+48, 16); |
668 | 0 | l_segment->NumberPrefixBytes = seg_data.GetInt(nPos+64, 16); |
669 | 0 | l_segment->NumberSuffixBytes = seg_data.GetInt(nPos+80, 16); |
670 | | |
671 | | /* -------------------------------------------------------------------- */ |
672 | | /* Process the 6th and 7th block. */ |
673 | | /* -------------------------------------------------------------------- */ |
674 | 0 | nPos = nStartBlock + 5*512; |
675 | |
|
676 | 0 | l_segment->SPNCoeff = 0; |
677 | |
|
678 | 0 | if(STARTS_WITH(seg_data.Get(nPos,8), "SPOT1BOD") || |
679 | 0 | STARTS_WITH(seg_data.Get(nPos,8), "SPOT1BNW")) |
680 | 0 | { |
681 | 0 | l_segment->SPNCoeff = seg_data.GetInt(nPos+22, 22); |
682 | 0 | for (i=0; i<20; i++) |
683 | 0 | { |
684 | 0 | l_segment->SPCoeff1B[i] = |
685 | 0 | seg_data.GetDouble(nPos+(i+2)*22, 22); |
686 | 0 | } |
687 | |
|
688 | 0 | if (STARTS_WITH(seg_data.Get(nPos,8), "SPOT1BNW")) |
689 | 0 | { |
690 | 0 | nPos = nStartBlock + 6*512; |
691 | |
|
692 | 0 | for (i=0; i<19; i++) |
693 | 0 | { |
694 | 0 | l_segment->SPCoeff1B[i+20] = |
695 | 0 | seg_data.GetDouble(nPos+i*22, 22); |
696 | 0 | } |
697 | 0 | l_segment->SPCoeffSg[0] = seg_data.GetInt(nPos+418, 8); |
698 | 0 | l_segment->SPCoeffSg[1] = seg_data.GetInt(nPos+426, 8); |
699 | 0 | l_segment->SPCoeffSg[2] = seg_data.GetInt(nPos+434, 8); |
700 | 0 | l_segment->SPCoeffSg[3] = seg_data.GetInt(nPos+442, 8); |
701 | 0 | } |
702 | 0 | } |
703 | | |
704 | | /* -------------------------------------------------------------------- */ |
705 | | /* 6th and 7th block of ORBIT segment are blank. */ |
706 | | /* Read in the 8th block. */ |
707 | | /* -------------------------------------------------------------------- */ |
708 | 0 | nPos = nStartBlock + 7*512; |
709 | |
|
710 | 0 | if (STARTS_WITH(seg_data.Get(nPos,8), "ATTITUDE")) |
711 | 0 | l_segment->Type = OrbAttitude; |
712 | 0 | else if (STARTS_WITH(seg_data.Get(nPos,8), "RADAR ")) |
713 | 0 | l_segment->Type = OrbLatLong; |
714 | 0 | else if (STARTS_WITH(seg_data.Get(nPos,8), "AVHRR ")) |
715 | 0 | l_segment->Type = OrbAvhrr; |
716 | 0 | else if (STARTS_WITH(seg_data.Get(nPos,8), "NO_DATA ")) |
717 | 0 | l_segment->Type = OrbNone; |
718 | 0 | else |
719 | 0 | return (EphemerisSeg_t*)ThrowPCIDSKExceptionPtr("Invalid Orbit type found: [%s]", |
720 | 0 | seg_data.Get(nPos,8)); |
721 | | |
722 | | /* -------------------------------------------------------------------- */ |
723 | | /* Orbit segment is a Satellite Attitude Segment(ATTITUDE) only */ |
724 | | /* for SPOT 1A. */ |
725 | | /* -------------------------------------------------------------------- */ |
726 | 0 | if (l_segment->Type == OrbAttitude) |
727 | 0 | { |
728 | 0 | AttitudeSeg_t *AttitudeSeg; |
729 | 0 | int nBlock, nData; |
730 | |
|
731 | 0 | AttitudeSeg = l_segment->AttitudeSeg = new AttitudeSeg_t(); |
732 | | |
733 | | /* -------------------------------------------------------------------- */ |
734 | | /* Read in the 9th block. */ |
735 | | /* -------------------------------------------------------------------- */ |
736 | 0 | nPos = nStartBlock + 512*8; |
737 | |
|
738 | 0 | AttitudeSeg->Roll = seg_data.GetDouble(nPos, 22); |
739 | 0 | AttitudeSeg->Pitch = seg_data.GetDouble(nPos+22, 22); |
740 | 0 | AttitudeSeg->Yaw = seg_data.GetDouble(nPos+44, 22); |
741 | 0 | AttitudeSeg->NumberOfLine = seg_data.GetInt(nPos+88, 22); |
742 | 0 | if (AttitudeSeg->NumberOfLine % ATT_SEG_LINE_PER_BLOCK != 0) |
743 | 0 | AttitudeSeg->NumberBlockData = 1 + |
744 | 0 | AttitudeSeg->NumberOfLine / ATT_SEG_LINE_PER_BLOCK; |
745 | 0 | else |
746 | 0 | AttitudeSeg->NumberBlockData = |
747 | 0 | AttitudeSeg->NumberOfLine / ATT_SEG_LINE_PER_BLOCK; |
748 | | |
749 | | /* -------------------------------------------------------------------- */ |
750 | | /* Read in the line required. */ |
751 | | /* -------------------------------------------------------------------- */ |
752 | 0 | for (nBlock=0, nData=0; nBlock<AttitudeSeg->NumberBlockData; |
753 | 0 | nBlock++) |
754 | 0 | { |
755 | | /* -------------------------------------------------------------------- */ |
756 | | /* Read in 10+nBlock th block as required. */ |
757 | | /* -------------------------------------------------------------------- */ |
758 | 0 | nPos = nStartBlock + 512*(9+nBlock); |
759 | | |
760 | | /* -------------------------------------------------------------------- */ |
761 | | /* Fill in the lines as required. */ |
762 | | /* -------------------------------------------------------------------- */ |
763 | 0 | for (i=0; |
764 | 0 | i<ATT_SEG_LINE_PER_BLOCK |
765 | 0 | && nData < AttitudeSeg->NumberOfLine; |
766 | 0 | i++, nData++) |
767 | 0 | { |
768 | 0 | AttitudeLine_t oAttitudeLine; |
769 | 0 | oAttitudeLine.ChangeInAttitude |
770 | 0 | = seg_data.GetDouble(nPos+i*44, 22); |
771 | 0 | oAttitudeLine.ChangeEarthSatelliteDist |
772 | 0 | = seg_data.GetDouble(nPos+i*44+22, 22); |
773 | 0 | AttitudeSeg->Line.push_back(oAttitudeLine); |
774 | 0 | } |
775 | 0 | } |
776 | |
|
777 | 0 | if (nData != AttitudeSeg->NumberOfLine) |
778 | 0 | { |
779 | 0 | return (EphemerisSeg_t*)ThrowPCIDSKExceptionPtr("Number of data line read (%d) " |
780 | 0 | "does not matches with what is specified in " |
781 | 0 | "the segment (%d).\n", nData, |
782 | 0 | AttitudeSeg->NumberOfLine); |
783 | 0 | } |
784 | 0 | } |
785 | | /* -------------------------------------------------------------------- */ |
786 | | /* Radar segment (LATLONG) */ |
787 | | /* -------------------------------------------------------------------- */ |
788 | 0 | else if (l_segment->Type == OrbLatLong) |
789 | 0 | { |
790 | 0 | RadarSeg_t *RadarSeg; |
791 | 0 | int nBlock, nData; |
792 | |
|
793 | 0 | RadarSeg = l_segment->RadarSeg = new RadarSeg_t(); |
794 | | /* -------------------------------------------------------------------- */ |
795 | | /* Read in the 9th block. */ |
796 | | /* -------------------------------------------------------------------- */ |
797 | 0 | nPos = nStartBlock + 512*8; |
798 | |
|
799 | 0 | RadarSeg->Identifier = seg_data.Get(nPos, 16); |
800 | 0 | RadarSeg->Facility = seg_data.Get(nPos+16, 16); |
801 | 0 | RadarSeg->Ellipsoid = seg_data.Get(nPos+32, 16); |
802 | |
|
803 | 0 | RadarSeg->EquatorialRadius = seg_data.GetDouble(nPos+48, 16); |
804 | 0 | RadarSeg->PolarRadius = seg_data.GetDouble(nPos+64, 16); |
805 | 0 | RadarSeg->IncidenceAngle = seg_data.GetDouble(nPos+80, 16); |
806 | 0 | RadarSeg->LineSpacing = seg_data.GetDouble(nPos+96, 16); |
807 | 0 | RadarSeg->PixelSpacing = seg_data.GetDouble(nPos+112, 16); |
808 | 0 | RadarSeg->ClockAngle = seg_data.GetDouble(nPos+128, 16); |
809 | | |
810 | | /* -------------------------------------------------------------------- */ |
811 | | /* Read in the 10th block. */ |
812 | | /* -------------------------------------------------------------------- */ |
813 | 0 | nPos = nStartBlock + 9*512; |
814 | |
|
815 | 0 | RadarSeg->NumberBlockData = seg_data.GetInt(nPos, 8); |
816 | 0 | RadarSeg->NumberData = seg_data.GetInt(nPos+8, 8); |
817 | | |
818 | | /* -------------------------------------------------------------------- */ |
819 | | /* Read in the 11-th through 11+RadarSeg->NumberBlockData th block */ |
820 | | /* for the ancillary data present. */ |
821 | | /* -------------------------------------------------------------------- */ |
822 | 0 | for (nBlock = 0, nData = 0; |
823 | 0 | nBlock < RadarSeg->NumberBlockData; nBlock++) |
824 | 0 | { |
825 | | /* -------------------------------------------------------------------- */ |
826 | | /* Read in one block of data. */ |
827 | | /* -------------------------------------------------------------------- */ |
828 | 0 | nPos = nStartBlock + 512*(10+nBlock); |
829 | |
|
830 | 0 | for (i=0; |
831 | 0 | i<ANC_DATA_PER_BLK && nData < RadarSeg->NumberData; |
832 | 0 | i++, nData++) |
833 | 0 | { |
834 | 0 | int offset; |
835 | 0 | char *currentindex; |
836 | 0 | void *currentptr; |
837 | 0 | double tmp; |
838 | 0 | int32 tmpInt; |
839 | 0 | const double million = 1000000.0; |
840 | | |
841 | | /* -------------------------------------------------------------------- */ |
842 | | /* Reading in one ancillary data at a time. */ |
843 | | /* -------------------------------------------------------------------- */ |
844 | 0 | AncillaryData_t oData; |
845 | 0 | offset = i*ANC_DATA_SIZE; |
846 | |
|
847 | 0 | currentindex = (char *)seg_data.Get(nPos+offset,4); |
848 | 0 | currentptr = (char *) currentindex; |
849 | 0 | SwapData(currentptr,4,1); |
850 | 0 | tmpInt = *((int32 *) currentptr); |
851 | 0 | oData.SlantRangeFstPixel = tmpInt; |
852 | |
|
853 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+4,4); |
854 | 0 | currentptr = (char *) currentindex; |
855 | 0 | SwapData(currentptr,4,1); |
856 | 0 | tmpInt = *((int32 *) currentptr); |
857 | 0 | oData.SlantRangeLastPixel = tmpInt; |
858 | |
|
859 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+8,4); |
860 | 0 | currentptr = (char *) currentindex; |
861 | 0 | SwapData(currentptr,4,1); |
862 | 0 | tmpInt = *((int32 *) currentptr); |
863 | 0 | tmp = (double) tmpInt / million; |
864 | 0 | oData.FstPixelLat |
865 | 0 | = (float) ConvertDeg(tmp, 0); |
866 | |
|
867 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+12,4); |
868 | 0 | currentptr = (char *) currentindex; |
869 | 0 | SwapData(currentptr,4,1); |
870 | 0 | tmpInt = *((int32 *) currentptr); |
871 | 0 | tmp = (double) tmpInt / million; |
872 | 0 | oData.MidPixelLat |
873 | 0 | = (float) ConvertDeg(tmp, 0); |
874 | |
|
875 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+16,4); |
876 | 0 | currentptr = (char *) currentindex; |
877 | 0 | SwapData(currentptr,4,1); |
878 | 0 | tmpInt = *((int32 *) currentptr); |
879 | 0 | tmp = (double) tmpInt / million; |
880 | 0 | oData.LstPixelLat |
881 | 0 | = (float) ConvertDeg(tmp, 0); |
882 | |
|
883 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+20,4); |
884 | 0 | currentptr = (char *) currentindex; |
885 | 0 | SwapData(currentptr,4,1); |
886 | 0 | tmpInt = *((int32 *) currentptr); |
887 | 0 | tmp = (double) tmpInt / million; |
888 | 0 | oData.FstPixelLong |
889 | 0 | = (float) ConvertDeg(tmp, 0); |
890 | |
|
891 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+24,4); |
892 | 0 | currentptr = (char *) currentindex; |
893 | 0 | SwapData(currentptr,4,1); |
894 | 0 | tmpInt = *((int32 *) currentptr); |
895 | 0 | tmp = (double) tmpInt / million; |
896 | 0 | oData.MidPixelLong |
897 | 0 | = (float) ConvertDeg(tmp, 0); |
898 | |
|
899 | 0 | currentindex = (char *)seg_data.Get(nPos+offset+28,4); |
900 | 0 | currentptr = (char *) currentindex; |
901 | 0 | SwapData(currentptr,4,1); |
902 | 0 | tmpInt = *((int32 *) currentptr); |
903 | 0 | tmp = (double) tmpInt / million; |
904 | 0 | oData.LstPixelLong |
905 | 0 | = (float) ConvertDeg(tmp, 0); |
906 | |
|
907 | 0 | RadarSeg->Line.push_back(oData); |
908 | 0 | } |
909 | 0 | } |
910 | |
|
911 | 0 | if (RadarSeg->NumberData != nData) |
912 | 0 | { |
913 | 0 | return (EphemerisSeg_t*)ThrowPCIDSKExceptionPtr("Number " |
914 | 0 | "of data lines read (%d) does not match with" |
915 | 0 | "\nwhat is specified in segment (%d).\n", nData, |
916 | 0 | RadarSeg->NumberData); |
917 | 0 | } |
918 | 0 | } |
919 | | /* -------------------------------------------------------------------- */ |
920 | | /* AVHRR segment */ |
921 | | /* -------------------------------------------------------------------- */ |
922 | 0 | else if (l_segment->Type == OrbAvhrr) |
923 | 0 | { |
924 | 0 | ReadAvhrrEphemerisSegment( nStartBlock, l_segment.get()); |
925 | 0 | } |
926 | | |
927 | 0 | return l_segment.release(); |
928 | 0 | } |
929 | | |
930 | | /************************************************************************/ |
931 | | /* EphemerisToBinary() */ |
932 | | /************************************************************************/ |
933 | | /** |
934 | | * Write an Orbit segment information into a binary buffer of size 4096. |
935 | | * The caller is responsible to free this memory with delete []. |
936 | | * |
937 | | * @param psOrbit the orbit information to write into the binary |
938 | | * @param nStartBlock where to start writing in the buffer. |
939 | | */ |
940 | | void |
941 | | CPCIDSKEphemerisSegment::EphemerisToBinary( EphemerisSeg_t * psOrbit, |
942 | | int nStartBlock ) |
943 | | |
944 | 0 | { |
945 | 0 | int i,j; |
946 | | |
947 | | /* -------------------------------------------------------------------- */ |
948 | | /* The binary data must be at least 8 blocks (4096 bytes) long */ |
949 | | /* for the common information. */ |
950 | | /* -------------------------------------------------------------------- */ |
951 | 0 | seg_data.SetSize(nStartBlock+4096); |
952 | 0 | memset(seg_data.buffer+nStartBlock,' ',4096); |
953 | |
|
954 | 0 | int nPos = nStartBlock; |
955 | | |
956 | | /* -------------------------------------------------------------------- */ |
957 | | /* Write the first block */ |
958 | | /* -------------------------------------------------------------------- */ |
959 | |
|
960 | 0 | seg_data.Put("ORBIT ",nPos,8); |
961 | 0 | seg_data.Put(psOrbit->SatelliteDesc.c_str(), nPos+8,32,true); |
962 | 0 | seg_data.Put(psOrbit->SceneID.c_str(), nPos+40,32,true); |
963 | | |
964 | | /* -------------------------------------------------------------------- */ |
965 | | /* Write the second block */ |
966 | | /* -------------------------------------------------------------------- */ |
967 | 0 | nPos = nStartBlock + 1*512; |
968 | |
|
969 | 0 | seg_data.Put(psOrbit->SatelliteSensor.c_str(), nPos,16); |
970 | 0 | seg_data.Put(psOrbit->SensorNo.c_str(),nPos+22,2,true); |
971 | 0 | seg_data.Put(psOrbit->DateImageTaken.c_str(), nPos+44,22,true); |
972 | |
|
973 | 0 | if (psOrbit->SupSegExist) |
974 | 0 | seg_data.Put("Y",nPos+66,1); |
975 | 0 | else |
976 | 0 | seg_data.Put("N",nPos+66,1); |
977 | |
|
978 | 0 | seg_data.Put(psOrbit->FieldOfView,nPos+88,22,"%22.14f"); |
979 | 0 | seg_data.Put(psOrbit->ViewAngle,nPos+110,22,"%22.14f"); |
980 | 0 | seg_data.Put(psOrbit->NumColCentre,nPos+132,22,"%22.14f"); |
981 | 0 | seg_data.Put(psOrbit->RadialSpeed,nPos+154,22,"%22.14f"); |
982 | 0 | seg_data.Put(psOrbit->Eccentricity,nPos+176,22,"%22.14f"); |
983 | 0 | seg_data.Put(psOrbit->Height,nPos+198,22,"%22.14f"); |
984 | 0 | seg_data.Put(psOrbit->Inclination,nPos+220,22,"%22.14f"); |
985 | 0 | seg_data.Put(psOrbit->TimeInterval,nPos+242,22,"%22.14f"); |
986 | 0 | seg_data.Put(psOrbit->NumLineCentre,nPos+264,22,"%22.14f"); |
987 | 0 | seg_data.Put(psOrbit->LongCentre,nPos+286,22,"%22.14f"); |
988 | 0 | seg_data.Put(psOrbit->AngularSpd,nPos+308,22,"%22.14f"); |
989 | 0 | seg_data.Put(psOrbit->AscNodeLong,nPos+330,22,"%22.14f"); |
990 | 0 | seg_data.Put(psOrbit->ArgPerigee,nPos+352,22,"%22.14f"); |
991 | 0 | seg_data.Put(psOrbit->LatCentre,nPos+374,22,"%22.14f"); |
992 | 0 | seg_data.Put(psOrbit->EarthSatelliteDist,nPos+396,22,"%22.14f"); |
993 | 0 | seg_data.Put(psOrbit->NominalPitch,nPos+418,22,"%22.14f"); |
994 | 0 | seg_data.Put(psOrbit->TimeAtCentre,nPos+440,22,"%22.14f"); |
995 | 0 | seg_data.Put(psOrbit->SatelliteArg,nPos+462,22,"%22.14f"); |
996 | |
|
997 | 0 | if (psOrbit->bDescending) |
998 | 0 | seg_data.Put("DESCENDING",nPos+484,10); |
999 | 0 | else |
1000 | 0 | seg_data.Put("ASCENDING ",nPos+484,10); |
1001 | | |
1002 | | /* -------------------------------------------------------------------- */ |
1003 | | /* Write the third block */ |
1004 | | /* -------------------------------------------------------------------- */ |
1005 | 0 | nPos = nStartBlock + 512*2; |
1006 | |
|
1007 | 0 | seg_data.Put(psOrbit->XCentre,nPos,22,"%22.14f"); |
1008 | 0 | seg_data.Put(psOrbit->YCentre,nPos+22,22,"%22.14f"); |
1009 | 0 | seg_data.Put(psOrbit->UtmXCentre,nPos+44,22,"%22.14f"); |
1010 | 0 | seg_data.Put(psOrbit->UtmYCentre,nPos+66,22,"%22.14f"); |
1011 | 0 | seg_data.Put(psOrbit->PixelRes,nPos+88,22,"%22.14f"); |
1012 | 0 | seg_data.Put(psOrbit->LineRes,nPos+110,22,"%22.14f"); |
1013 | |
|
1014 | 0 | if (psOrbit->CornerAvail == true) |
1015 | 0 | seg_data.Put("Y",nPos+132,1); |
1016 | 0 | else |
1017 | 0 | seg_data.Put("N",nPos+132,1); |
1018 | |
|
1019 | 0 | seg_data.Put(psOrbit->MapUnit.c_str(),nPos+133,16,true); |
1020 | |
|
1021 | 0 | seg_data.Put(psOrbit->XUL,nPos+149,22,"%22.14f"); |
1022 | 0 | seg_data.Put(psOrbit->YUL,nPos+171,22,"%22.14f"); |
1023 | 0 | seg_data.Put(psOrbit->XUR,nPos+193,22,"%22.14f"); |
1024 | 0 | seg_data.Put(psOrbit->YUR,nPos+215,22,"%22.14f"); |
1025 | 0 | seg_data.Put(psOrbit->XLR,nPos+237,22,"%22.14f"); |
1026 | 0 | seg_data.Put(psOrbit->YLR,nPos+259,22,"%22.14f"); |
1027 | 0 | seg_data.Put(psOrbit->XLL,nPos+281,22,"%22.14f"); |
1028 | 0 | seg_data.Put(psOrbit->YLL,nPos+303,22,"%22.14f"); |
1029 | 0 | seg_data.Put(psOrbit->UtmXUL,nPos+325,22,"%22.14f"); |
1030 | 0 | seg_data.Put(psOrbit->UtmYUL,nPos+347,22,"%22.14f"); |
1031 | 0 | seg_data.Put(psOrbit->UtmXUR,nPos+369,22,"%22.14f"); |
1032 | 0 | seg_data.Put(psOrbit->UtmYUR,nPos+391,22,"%22.14f"); |
1033 | 0 | seg_data.Put(psOrbit->UtmXLR,nPos+413,22,"%22.14f"); |
1034 | 0 | seg_data.Put(psOrbit->UtmYLR,nPos+435,22,"%22.14f"); |
1035 | 0 | seg_data.Put(psOrbit->UtmXLL,nPos+457,22,"%22.14f"); |
1036 | 0 | seg_data.Put(psOrbit->UtmYLL,nPos+479,22,"%22.14f"); |
1037 | | |
1038 | | /* -------------------------------------------------------------------- */ |
1039 | | /* Write the fourth block */ |
1040 | | /* -------------------------------------------------------------------- */ |
1041 | 0 | nPos = nStartBlock + 512*3; |
1042 | |
|
1043 | 0 | seg_data.Put(psOrbit->LongCentreDeg,nPos,22,"%16.7f"); |
1044 | 0 | seg_data.Put(psOrbit->LatCentreDeg,nPos+16,22,"%16.7f"); |
1045 | 0 | seg_data.Put(psOrbit->LongUL,nPos+32,22,"%16.7f"); |
1046 | 0 | seg_data.Put(psOrbit->LatUL,nPos+48,22,"%16.7f"); |
1047 | 0 | seg_data.Put(psOrbit->LongUR,nPos+64,22,"%16.7f"); |
1048 | 0 | seg_data.Put(psOrbit->LatUR,nPos+80,22,"%16.7f"); |
1049 | 0 | seg_data.Put(psOrbit->LongLR,nPos+96,22,"%16.7f"); |
1050 | 0 | seg_data.Put(psOrbit->LatLR,nPos+112,22,"%16.7f"); |
1051 | 0 | seg_data.Put(psOrbit->LongLL,nPos+128,22,"%16.7f"); |
1052 | 0 | seg_data.Put(psOrbit->LatLL,nPos+144,22,"%16.7f"); |
1053 | 0 | seg_data.Put(psOrbit->HtCentre,nPos+160,22,"%16.7f"); |
1054 | 0 | seg_data.Put(psOrbit->HtUL,nPos+176,22,"%16.7f"); |
1055 | 0 | seg_data.Put(psOrbit->HtUR,nPos+192,22,"%16.7f"); |
1056 | 0 | seg_data.Put(psOrbit->HtLR,nPos+208,22,"%16.7f"); |
1057 | 0 | seg_data.Put(psOrbit->HtLL,nPos+224,22,"%16.7f"); |
1058 | | |
1059 | | /* -------------------------------------------------------------------- */ |
1060 | | /* Write the fifth block */ |
1061 | | /* -------------------------------------------------------------------- */ |
1062 | 0 | nPos = nStartBlock + 512*4; |
1063 | |
|
1064 | 0 | seg_data.Put(psOrbit->ImageRecordLength,nPos,16); |
1065 | 0 | seg_data.Put(psOrbit->NumberImageLine,nPos+16,16); |
1066 | 0 | seg_data.Put(psOrbit->NumberBytePerPixel,nPos+32,16); |
1067 | 0 | seg_data.Put(psOrbit->NumberSamplePerLine,nPos+48,16); |
1068 | 0 | seg_data.Put(psOrbit->NumberPrefixBytes,nPos+64,16); |
1069 | 0 | seg_data.Put(psOrbit->NumberSuffixBytes,nPos+80,16); |
1070 | | |
1071 | | /* -------------------------------------------------------------------- */ |
1072 | | /* Write the sixth and seventh block (blanks) */ |
1073 | | /* For SPOT it is not blank */ |
1074 | | /* -------------------------------------------------------------------- */ |
1075 | 0 | nPos = nStartBlock + 512*5; |
1076 | |
|
1077 | 0 | if (psOrbit->SPNCoeff > 0) |
1078 | 0 | { |
1079 | 0 | if (psOrbit->SPNCoeff == 20) |
1080 | 0 | { |
1081 | 0 | seg_data.Put("SPOT1BOD",nPos,8); |
1082 | 0 | seg_data.Put(psOrbit->SPNCoeff,nPos+22,22); |
1083 | |
|
1084 | 0 | j = 44; |
1085 | 0 | for (i=0; i<20; i++) |
1086 | 0 | { |
1087 | 0 | seg_data.Put(psOrbit->SPCoeff1B[i], |
1088 | 0 | nPos+j,22,"%22.14f"); |
1089 | 0 | j += 22; |
1090 | 0 | } |
1091 | 0 | } |
1092 | 0 | else |
1093 | 0 | { |
1094 | 0 | seg_data.Put("SPOT1BNW",nPos,8); |
1095 | 0 | seg_data.Put(psOrbit->SPNCoeff,nPos+22,22); |
1096 | |
|
1097 | 0 | j = 44; |
1098 | 0 | for (i=0; i<20; i++) |
1099 | 0 | { |
1100 | 0 | seg_data.Put(psOrbit->SPCoeff1B[i], |
1101 | 0 | nPos+j,22,"%22.14f"); |
1102 | 0 | j += 22; |
1103 | 0 | } |
1104 | |
|
1105 | 0 | nPos = nStartBlock + 512*6; |
1106 | |
|
1107 | 0 | j = 0; |
1108 | 0 | for (i=20; i<39; i++) |
1109 | 0 | { |
1110 | 0 | seg_data.Put(psOrbit->SPCoeff1B[i], |
1111 | 0 | nPos+j,22,"%22.14f"); |
1112 | 0 | j += 22; |
1113 | 0 | } |
1114 | |
|
1115 | 0 | seg_data.Put(psOrbit->SPCoeffSg[0],nPos+418,8); |
1116 | 0 | seg_data.Put(psOrbit->SPCoeffSg[1],nPos+426,8); |
1117 | 0 | seg_data.Put(psOrbit->SPCoeffSg[2],nPos+434,8); |
1118 | 0 | seg_data.Put(psOrbit->SPCoeffSg[3],nPos+442,8); |
1119 | 0 | } |
1120 | 0 | } |
1121 | | |
1122 | | /* -------------------------------------------------------------------- */ |
1123 | | /* Write the eighth block. */ |
1124 | | /* -------------------------------------------------------------------- */ |
1125 | 0 | nPos = nStartBlock + 512*7; |
1126 | |
|
1127 | 0 | if (psOrbit->Type == OrbAttitude) |
1128 | 0 | seg_data.Put("ATTITUDE",nPos,8); |
1129 | 0 | else if (psOrbit->Type == OrbLatLong) |
1130 | 0 | seg_data.Put("RADAR ",nPos,8); |
1131 | 0 | else if (psOrbit->Type == OrbAvhrr) |
1132 | 0 | seg_data.Put("AVHRR ",nPos,8); |
1133 | 0 | else if (psOrbit->Type == OrbNone) |
1134 | 0 | seg_data.Put("NO_DATA ",nPos,8); |
1135 | 0 | else |
1136 | 0 | { |
1137 | 0 | return ThrowPCIDSKException("Invalid Orbit type."); |
1138 | 0 | } |
1139 | | |
1140 | | /* ==================================================================== */ |
1141 | | /* Orbit segment is a Satellite Attitude Segment(ATTITUDE) only */ |
1142 | | /* for SPOT 1A. */ |
1143 | | /* ==================================================================== */ |
1144 | 0 | if (psOrbit->Type == OrbAttitude) |
1145 | 0 | { |
1146 | 0 | AttitudeSeg_t *AttitudeSeg; |
1147 | 0 | int nBlock, nData; |
1148 | |
|
1149 | 0 | AttitudeSeg = psOrbit->AttitudeSeg; |
1150 | |
|
1151 | 0 | if (AttitudeSeg == nullptr) |
1152 | 0 | { |
1153 | 0 | return ThrowPCIDSKException("The AttitudeSeg is NULL."); |
1154 | 0 | } |
1155 | | |
1156 | | /* -------------------------------------------------------------------- */ |
1157 | | /* Add one block */ |
1158 | | /* -------------------------------------------------------------------- */ |
1159 | 0 | seg_data.SetSize(seg_data.buffer_size + 512); |
1160 | |
|
1161 | 0 | nPos = nStartBlock + 512*8; |
1162 | 0 | memset(seg_data.buffer+nPos,' ',512); |
1163 | | |
1164 | | /* -------------------------------------------------------------------- */ |
1165 | | /* Write the ninth block. */ |
1166 | | /* -------------------------------------------------------------------- */ |
1167 | |
|
1168 | 0 | seg_data.Put(AttitudeSeg->Roll,nPos,22,"%22.14f"); |
1169 | 0 | seg_data.Put(AttitudeSeg->Pitch,nPos+22,22,"%22.14f"); |
1170 | 0 | seg_data.Put(AttitudeSeg->Yaw,nPos+44,22,"%22.14f"); |
1171 | |
|
1172 | 0 | if (AttitudeSeg->NumberOfLine % ATT_SEG_LINE_PER_BLOCK != 0) |
1173 | 0 | AttitudeSeg->NumberBlockData = 1 + |
1174 | 0 | AttitudeSeg->NumberOfLine / ATT_SEG_LINE_PER_BLOCK; |
1175 | 0 | else |
1176 | 0 | AttitudeSeg->NumberBlockData = |
1177 | 0 | AttitudeSeg->NumberOfLine / ATT_SEG_LINE_PER_BLOCK; |
1178 | |
|
1179 | 0 | seg_data.Put(AttitudeSeg->NumberBlockData,nPos+66,22); |
1180 | 0 | seg_data.Put(AttitudeSeg->NumberOfLine,nPos+88,22); |
1181 | | |
1182 | | /* -------------------------------------------------------------------- */ |
1183 | | /* Add NumberBlockData blocks to array. */ |
1184 | | /* -------------------------------------------------------------------- */ |
1185 | 0 | seg_data.SetSize(seg_data.buffer_size + |
1186 | 0 | 512 * AttitudeSeg->NumberBlockData); |
1187 | |
|
1188 | 0 | nPos = nStartBlock + 512*9; |
1189 | 0 | memset(seg_data.buffer+nPos,' ', |
1190 | 0 | 512 * AttitudeSeg->NumberBlockData); |
1191 | | |
1192 | | /* -------------------------------------------------------------------- */ |
1193 | | /* Write out the line required. */ |
1194 | | /* -------------------------------------------------------------------- */ |
1195 | 0 | for (nBlock=0, nData=0; nBlock<AttitudeSeg->NumberBlockData; |
1196 | 0 | nBlock++) |
1197 | 0 | { |
1198 | 0 | nPos = nStartBlock + 512*(nBlock + 9); |
1199 | | |
1200 | | /* -------------------------------------------------------------------- */ |
1201 | | /* Fill in buffer as required. */ |
1202 | | /* -------------------------------------------------------------------- */ |
1203 | 0 | for (i=0; |
1204 | 0 | i<ATT_SEG_LINE_PER_BLOCK |
1205 | 0 | && nData < AttitudeSeg->NumberOfLine; |
1206 | 0 | i++, nData++) |
1207 | 0 | { |
1208 | 0 | seg_data.Put( |
1209 | 0 | AttitudeSeg->Line[nData].ChangeInAttitude, |
1210 | 0 | nPos+i*44,22,"%22.14f"); |
1211 | 0 | seg_data.Put( |
1212 | 0 | AttitudeSeg->Line[nData].ChangeEarthSatelliteDist, |
1213 | 0 | nPos+i*44+22,22,"%22.14f"); |
1214 | 0 | } |
1215 | 0 | } |
1216 | |
|
1217 | 0 | if (nData != AttitudeSeg->NumberOfLine) |
1218 | 0 | { |
1219 | 0 | return ThrowPCIDSKException("Number of data line written" |
1220 | 0 | " (%d) does not match with\nwhat is specified " |
1221 | 0 | " in the segment (%d).\n", |
1222 | 0 | nData, AttitudeSeg->NumberOfLine); |
1223 | 0 | } |
1224 | 0 | } |
1225 | | |
1226 | | /* ==================================================================== */ |
1227 | | /* Radar segment (LATLONG) */ |
1228 | | /* ==================================================================== */ |
1229 | 0 | else if (psOrbit->Type == OrbLatLong) |
1230 | 0 | { |
1231 | 0 | RadarSeg_t *RadarSeg; |
1232 | 0 | int nBlock, nData; |
1233 | |
|
1234 | 0 | RadarSeg = psOrbit->RadarSeg; |
1235 | |
|
1236 | 0 | if (RadarSeg == nullptr) |
1237 | 0 | { |
1238 | 0 | return ThrowPCIDSKException("The RadarSeg is NULL."); |
1239 | 0 | } |
1240 | | |
1241 | | /* -------------------------------------------------------------------- */ |
1242 | | /* Add two blocks. */ |
1243 | | /* -------------------------------------------------------------------- */ |
1244 | 0 | seg_data.SetSize(seg_data.buffer_size + 512*2); |
1245 | |
|
1246 | 0 | nPos = nStartBlock + 512*8; |
1247 | 0 | memset(seg_data.buffer+nPos,' ', 512*2); |
1248 | | |
1249 | | /* -------------------------------------------------------------------- */ |
1250 | | /* Write out the ninth block. */ |
1251 | | /* -------------------------------------------------------------------- */ |
1252 | 0 | seg_data.Put(RadarSeg->Identifier.c_str(), nPos,16); |
1253 | 0 | seg_data.Put(RadarSeg->Facility.c_str(), nPos+16,16); |
1254 | 0 | seg_data.Put(RadarSeg->Ellipsoid.c_str(), nPos+32,16); |
1255 | |
|
1256 | 0 | seg_data.Put(RadarSeg->EquatorialRadius,nPos+48,16,"%16.7f"); |
1257 | 0 | seg_data.Put(RadarSeg->PolarRadius,nPos+64,16,"%16.7f"); |
1258 | 0 | seg_data.Put(RadarSeg->IncidenceAngle,nPos+80,16,"%16.7f"); |
1259 | 0 | seg_data.Put(RadarSeg->LineSpacing,nPos+96,16,"%16.7f"); |
1260 | 0 | seg_data.Put(RadarSeg->PixelSpacing,nPos+112,16,"%16.7f"); |
1261 | 0 | seg_data.Put(RadarSeg->ClockAngle,nPos+128,16,"%16.7f"); |
1262 | | |
1263 | | /* -------------------------------------------------------------------- */ |
1264 | | /* Write out the tenth block. */ |
1265 | | /* -------------------------------------------------------------------- */ |
1266 | 0 | nPos = nStartBlock + 512*9; |
1267 | |
|
1268 | 0 | seg_data.Put(RadarSeg->NumberBlockData,nPos,8); |
1269 | 0 | seg_data.Put(RadarSeg->NumberData,nPos+8,8); |
1270 | | |
1271 | | /* -------------------------------------------------------------------- */ |
1272 | | /* Make room for all the following per-line data. */ |
1273 | | /* -------------------------------------------------------------------- */ |
1274 | 0 | seg_data.SetSize(seg_data.buffer_size + |
1275 | 0 | 512 * RadarSeg->NumberBlockData); |
1276 | |
|
1277 | 0 | nPos = nStartBlock + 512*10; |
1278 | 0 | memset(seg_data.buffer+nPos,' ', |
1279 | 0 | 512 * RadarSeg->NumberBlockData); |
1280 | | |
1281 | | /* -------------------------------------------------------------------- */ |
1282 | | /* Write out the 11-th through 11+psOrbit->NumberBlockData block */ |
1283 | | /* for the ancillary data present. */ |
1284 | | /* -------------------------------------------------------------------- */ |
1285 | 0 | for (nBlock = 0, nData = 0; |
1286 | 0 | nBlock < RadarSeg->NumberBlockData; nBlock++) |
1287 | 0 | { |
1288 | 0 | for (i=0; |
1289 | 0 | i<ANC_DATA_PER_BLK && nData < RadarSeg->NumberData; |
1290 | 0 | i++, nData++) |
1291 | 0 | { |
1292 | 0 | int offset; |
1293 | 0 | char *currentptr, *currentindex; |
1294 | 0 | double tmp, tmpDouble; |
1295 | 0 | const double million = 1000000.0; |
1296 | 0 | int32 tmpInt; |
1297 | | |
1298 | | /* -------------------------------------------------------------------- */ |
1299 | | /* Point to correct block */ |
1300 | | /* -------------------------------------------------------------------- */ |
1301 | 0 | nPos = nStartBlock + 512*(10+nBlock); |
1302 | | |
1303 | | /* -------------------------------------------------------------------- */ |
1304 | | /* Writing out one ancillary data at a time. */ |
1305 | | /* -------------------------------------------------------------------- */ |
1306 | 0 | offset = i*ANC_DATA_SIZE; |
1307 | |
|
1308 | 0 | currentptr = |
1309 | 0 | (char *) &(RadarSeg->Line[nData].SlantRangeFstPixel); |
1310 | 0 | SwapData(currentptr,4,1); |
1311 | 0 | currentindex = &(seg_data.buffer[nPos+offset]); |
1312 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1313 | |
|
1314 | 0 | currentptr = |
1315 | 0 | (char *) &(RadarSeg->Line[nData].SlantRangeLastPixel); |
1316 | 0 | SwapData(currentptr,4,1); |
1317 | 0 | currentindex += 4; |
1318 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1319 | |
|
1320 | 0 | tmp = ConvertDeg(RadarSeg->Line[nData].FstPixelLat, 1); |
1321 | 0 | tmpDouble = tmp * million; |
1322 | 0 | tmpInt = (int32) tmpDouble; |
1323 | 0 | currentptr = (char *) &tmpInt; |
1324 | 0 | SwapData(currentptr,4,1); |
1325 | 0 | currentindex += 4; |
1326 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1327 | |
|
1328 | 0 | tmp = ConvertDeg(RadarSeg->Line[nData].MidPixelLat, 1); |
1329 | 0 | tmpDouble = tmp * million; |
1330 | 0 | tmpInt = (int32) tmpDouble; |
1331 | 0 | currentptr = (char *) &tmpInt; |
1332 | 0 | SwapData(currentptr,4,1); |
1333 | 0 | currentindex += 4; |
1334 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1335 | |
|
1336 | 0 | tmp = ConvertDeg(RadarSeg->Line[nData].LstPixelLat, 1); |
1337 | 0 | tmpDouble = tmp * million; |
1338 | 0 | tmpInt = (int32) tmpDouble; |
1339 | 0 | currentptr = (char *) &tmpInt; |
1340 | 0 | SwapData(currentptr,4,1); |
1341 | 0 | currentindex += 4; |
1342 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1343 | |
|
1344 | 0 | tmp = ConvertDeg(RadarSeg->Line[nData].FstPixelLong, 1); |
1345 | 0 | tmpDouble = tmp * million; |
1346 | 0 | tmpInt = (int32) tmpDouble; |
1347 | 0 | currentptr = (char *) &tmpInt; |
1348 | 0 | SwapData(currentptr,4,1); |
1349 | 0 | currentindex += 4; |
1350 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1351 | |
|
1352 | 0 | tmp = ConvertDeg(RadarSeg->Line[nData].MidPixelLong, 1); |
1353 | 0 | tmpDouble = tmp * million; |
1354 | 0 | tmpInt = (int32) tmpDouble; |
1355 | 0 | currentptr = (char *) &tmpInt; |
1356 | 0 | SwapData(currentptr,4,1); |
1357 | 0 | currentindex += 4; |
1358 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1359 | |
|
1360 | 0 | tmp = ConvertDeg(RadarSeg->Line[nData].LstPixelLong, 1); |
1361 | 0 | tmpDouble = tmp * million; |
1362 | 0 | tmpInt = (int32) tmpDouble; |
1363 | 0 | currentptr = (char *) &tmpInt; |
1364 | 0 | SwapData(currentptr,4,1); |
1365 | 0 | currentindex += 4; |
1366 | 0 | std::memcpy((void *) currentindex,currentptr, 4); |
1367 | 0 | } |
1368 | 0 | } |
1369 | 0 | } |
1370 | | |
1371 | | /* ==================================================================== */ |
1372 | | /* AVHRR segment */ |
1373 | | /* ==================================================================== */ |
1374 | 0 | else if ( psOrbit->Type == OrbAvhrr && |
1375 | 0 | psOrbit->AvhrrSeg->nNumRecordsPerBlock > 0 ) |
1376 | 0 | { |
1377 | 0 | WriteAvhrrEphemerisSegment(nStartBlock + 8*512 , psOrbit); |
1378 | 0 | } |
1379 | 0 | } |