19 #include <gsl/gsl_errno.h>
20 #include <gsl/gsl_spline.h>
21 #include <gsl/gsl_sort_double.h>
24 #define CDLFILE "OCI_Level-1B_Data_Structure.cdl"
25 #define NBANDS 61 // number of OCI bands
33 #define VERSION "1.00"
35 size_t interpLt(
size_t startJ,
size_t npixels,
size_t k,
size_t nbMax,
36 float ociaWavelength,
size_t iwave, aviris4ocia_t*
data,
37 gsl_interp_accel* acc,
float* Lt) {
39 size_t i0 = startJ, i1 = startJ + 5;
40 float minWave, maxWave;
42 double*
x = (
double*) (calloc(nbMax,
sizeof (
double)));
43 double*
y = (
double*) (calloc(nbMax,
sizeof (
double)));
45 while (i0 >= 0 && i1 < nbMax) {
49 for (
j = i0;
j < i1;
j++) {
50 if (
data->Lt[
j * npixels +
k] > 0) {
52 y[n] =
data->Lt[
j * npixels +
k];
54 if (minWave >
data->wave[
j]) minWave =
data->wave[
j];
55 if (maxWave < data->wave[
j]) maxWave =
data->wave[
j];
59 if (n > 2 && minWave <= ociaWavelength && maxWave >= ociaWavelength)
break;
60 if (minWave > ociaWavelength || n < 3)
62 if (maxWave < ociaWavelength || n < 3)
68 gsl_spline*
spline = gsl_spline_alloc(gsl_interp_cspline, n);
69 gsl_sort2(
x, 1,
y, 1, n);
70 if (ociaWavelength >
x[0]) {
72 gsl_sort2(
x, 1,
y, 1, n);
76 double yi = gsl_spline_eval(
spline, ociaWavelength, acc);
77 Lt[iwave * npixels +
k] = yi;
79 Lt[iwave * npixels +
k] =
FILL;
98 int main(
int argc,
char* argv[]) {
100 size_t sline = 0, eline = 0;
101 char filename[FILENAME_MAX],
hdrfile[FILENAME_MAX], imgfile[FILENAME_MAX],
102 navfile[FILENAME_MAX], gainfile[FILENAME_MAX];
105 double scantime_first, scantime_last;
106 static int first_good_scantime = 0;
107 cout <<
"avirisbil2oci " <<
VERSION <<
" ("
108 << __DATE__ <<
" " << __TIME__ <<
")" << endl;
112 "avirisbil2oci input_AVIRIS_file output_OCIA_file <sline (default=0)> <eline (default=last row) <img file(optional)> <nav file(optional)> <gain file(optional)>>"
118 sscanf(argv[3],
"%ld", &sline);
119 if (sline < 0) sline = 0;
123 sscanf(argv[4],
"%ld", &eline);
124 if (eline < 0) eline = 0;
127 sscanf(argv[5],
"%s", imgfile);
128 if (eline < 0) eline = 0;
131 sscanf(argv[6],
"%s", navfile);
132 if (eline < 0) eline = 0;
135 sscanf(argv[7],
"%s", gainfile);
136 if (eline < 0) eline = 0;
140 if ((filedir = getenv(
"OCDATAROOT")) ==
NULL) {
141 printf(
"-E- %s: OCDATAROOT env variable undefined.\n", __FILE__);
155 aviris4ocia_t **
data, *temp;
157 data = (aviris4ocia_t **) malloc(
sizeof (aviris4ocia_t *));
159 size_t nscans, ip, npixels = temp->npix;
161 if (eline <= 0) eline = temp->nscans;
163 if (eline == sline && sline > 0) sline--;
164 nscans = eline - sline;
168 const char *dimNames[] = {
"number_of_scans",
"number_of_pixels",
"number_of_bands"};
169 size_t dimSize[] = {nscans, npixels,
NBANDS};
183 size_t nbands_av = temp->numBands;
184 size_t nbands_ocia =
NBANDS;
186 size_t n = 0, iwave = 0;
189 char isodatetime_first[30], isodatetime_last[30];
195 gsl_interp_accel *acc = gsl_interp_accel_alloc();
197 float *Lt = (
float *) calloc(npixels*nbands_ocia,
sizeof (
float));
198 float *ociaWavelength = (
float *) calloc(nbands_ocia,
sizeof (
float));
199 double* utc = (
double*) (calloc(nscans,
sizeof (
double)));
200 float* alt = (
float*) (calloc(nscans,
sizeof (
float)));
203 grpID = ociafile.
getGid(
"observation_data");
211 cout <<
"Can't read file " << argv[1] << endl;
215 for (ip = 0; ip < npixels; ip++)
for (iwave = 0; iwave < nbands_ocia; iwave++) Lt[iwave * npixels + ip] =
FILL;
217 if ((
iscan % 100) == 0) {
218 cout <<
"Processing scan: " <<
iscan <<
" out of " << nscans << endl;
222 for (
size_t k = 0;
k < npixels;
k++) {
227 for (
j = 0;
j < nbands_av;
j++) {
228 if (temp->Lt[
j * npixels +
k] > 0) n++;
232 if (n == 0)
continue;
239 for (
j = 0;
j < 31;
j++) {
240 if (temp->Lt[
j * npixels +
k] > 0) {
241 ociaWavelength[iwave] = temp->wave[
j];
242 Lt[iwave * npixels +
k] = temp->Lt[
j * npixels +
k];
243 fwhm[iwave] = temp->fwhm[
j];
247 for (
j = 33;
j < 57;
j++) {
248 if (temp->Lt[
j * npixels +
k] > 0) {
249 ociaWavelength[iwave] = temp->wave[
j];
250 Lt[iwave * npixels +
k] = temp->Lt[
j * npixels +
k];
251 fwhm[iwave] = temp->fwhm[
j];
256 ociaWavelength[iwave] = 936.646;
257 fwhm[iwave] = 32.4702967;
258 Lt[iwave * npixels +
k] = (11.9269624 * temp->Lt[60 * npixels +
k] +
259 10.78153 * temp->Lt[61 * npixels +
k] +
260 9.76180425 * temp->Lt[62 * npixels +
k]) /
fwhm[iwave];
263 ociaWavelength[iwave] = 1238.750;
264 fwhm[iwave] = 20.3179033;
265 Lt[iwave * npixels +
k] = (10.1448143 * temp->Lt[92 * npixels +
k] +
266 10.173089 * temp->Lt[93 * npixels +
k]) /
fwhm[iwave];
269 Lt[iwave * npixels +
k] = temp->Lt[109 * npixels +
k];
270 fwhm[iwave] = temp->fwhm[109];
271 ociaWavelength[iwave] = temp->wave[109];
274 ociaWavelength[iwave] = 1641.530;
275 fwhm[iwave] = 53.6097915;
276 Lt[iwave * npixels +
k] = (10.7227049 * temp->Lt[133 * npixels +
k] +
277 10.7221941 * temp->Lt[134 * npixels +
k] +
278 10.7218208 * temp->Lt[135 * npixels +
k] +
279 10.721585 * temp->Lt[136 * npixels +
k] +
280 10.7214867 * temp->Lt[137 * npixels +
k]) /
fwhm[iwave];
283 ociaWavelength[iwave] = 2126.795;
284 fwhm[iwave] = 54.1850639;
285 Lt[iwave * npixels +
k] = (10.8702638 * temp->Lt[184 * npixels +
k] +
286 10.8539551 * temp->Lt[185 * npixels +
k] +
287 10.8373296 * temp->Lt[186 * npixels +
k] +
288 10.8203873 * temp->Lt[187 * npixels +
k] +
289 10.8031281 * temp->Lt[188 * npixels +
k]) /
fwhm[iwave];
292 ociaWavelength[iwave] = 2246.658;
293 fwhm[iwave] = 53.0639591;
294 Lt[iwave * npixels +
k] = (10.6536474 * temp->Lt[196 * npixels +
k] +
295 10.6335365 * temp->Lt[197 * npixels +
k] +
296 10.6131087 * temp->Lt[198 * npixels +
k] +
297 10.592364 * temp->Lt[199 * npixels +
k] +
298 10.5713025 * temp->Lt[200 * npixels +
k]) /
fwhm[iwave];
306 printf(
"Oops, something's wrong iwave (%d) != nbands (%d) \n", (
int) iwave,
NBANDS);
314 status = nc_inq_varid(grpID,
"Lt", &varID);
318 size_t count[3] = {nbands_ocia, 1, npixels};
325 utc[
iscan] = temp->scantime;
326 if (temp->scantime > 0) {
327 scantime_last = temp->scantime;
328 if (!first_good_scantime) {
329 first_good_scantime = 1;
330 scantime_first = temp->scantime;
343 if (scantime_first < scantime_last) {
350 status = nc_put_att_text(ncid, NC_GLOBAL,
"time_coverage_start", strlen(isodatetime_first) + 1, isodatetime_first);
352 printf(
"-E- %s %d: %s for %s\n",
353 __FILE__, __LINE__, nc_strerror(
status),
"time_coverage_start");
356 status = nc_put_att_text(ncid, NC_GLOBAL,
"time_coverage_end", strlen(isodatetime_last) + 1, isodatetime_last);
358 printf(
"-E- %s %d: %s for %s\n",
359 __FILE__, __LINE__, nc_strerror(
status),
"time_coverage_end");
363 const char *navfieldsAVIRIS[] = {
"to-sensor_azimuth",
"to-sensor_zenith",
"to-sun_azimuth",
"to-sun_zenith",
"lat",
"lon"};
364 const char *navfieldsOCIA[] = {
"sensor_azimuth",
"sensor_zenith",
"solar_azimuth",
"solar_zenith",
"latitude",
"longitude"};
366 grpID = ociafile.
getGid(
"geolocation_data");
368 size_t startOCIA[2] = {0, 0};
369 size_t countOCIA[2] = {nscans, npixels};
372 for (
i = 0;
i < 6;
i++) {
373 cout <<
"Copying " << navfieldsAVIRIS[
i] <<
" to " <<
374 navfieldsOCIA[
i] << endl;
376 status = nc_inq_varid(grpID, navfieldsOCIA[
i], &varID);
381 status = nc_put_vara_float(grpID, varID, startOCIA, countOCIA, &temp->sena[sline * npixels]);
385 status = nc_put_vara_float(grpID, varID, startOCIA, countOCIA, &temp->senz[sline * npixels]);
389 status = nc_put_vara_float(grpID, varID, startOCIA, countOCIA, &temp->sola[sline * npixels]);
393 status = nc_put_vara_float(grpID, varID, startOCIA, countOCIA, &temp->solz[sline * npixels]);
397 status = nc_put_vara_double(grpID, varID, startOCIA, countOCIA, &temp->lat[sline * npixels]);
401 status = nc_put_vara_double(grpID, varID, startOCIA, countOCIA, &temp->lon[sline * npixels]);
409 gsl_interp_accel_free(acc);
411 size_t startw[2] = {0, 0};
412 size_t countw[2] = {nbands_ocia, 0};
414 grpID = ociafile.
getGid(
"sensor_band_parameters");
416 status = nc_inq_varid(grpID,
"wavelength", &varID);
418 status = nc_put_vara_float(grpID, varID, startw, countw, ociaWavelength);
421 status = nc_inq_varid(grpID,
"fwhm", &varID);
423 status = nc_put_vara_float(grpID, varID, startw, countw,
fwhm);
426 size_t starts[2] = {0, 0};
427 size_t counts[2] = {nscans, 0};
429 const char *nscanfieldsAVIRIS[] = {
"utc",
"alt"};
430 const char *nscanfieldsOCIA[] = {
"scan_start_time",
"altitude"};
432 for (
i = 0;
i < nscans;
i++) {
436 grpID = ociafile.
getGid(
"scan_line_attributes");
438 for (
i = 0;
i < 2;
i++) {
439 cout <<
"Copying " << nscanfieldsAVIRIS[
i] <<
" to " <<
440 nscanfieldsOCIA[
i] << endl;
442 status = nc_inq_varid(grpID, nscanfieldsOCIA[
i], &varID);
447 status = nc_put_vara_double(grpID, varID, starts,
counts, utc);
451 status = nc_put_vara_float(grpID, varID, starts,
counts, alt);