00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080 #include <jsoc_main.h>
00081 #include "fstats.c"
00082 #include "/homee/yliu/cvs/JSOC/proj/myproj/apps/rickmaproj/cartography.c"
00083 #include "/homee/yliu/cvs/JSOC/proj/myproj/apps/rickmaproj/imginfo.c"
00084 #include "/homee/yliu/cvs/JSOC/proj/myproj/apps/rickmaproj/keystuff.c"
00085 #include "/homee/yliu/cvs/JSOC/proj/myproj/apps/rickmaproj/mdistuff.c"
00086
00087 #define RECTANGULAR (0)
00088 #define CASSINI (1)
00089 #define MERCATOR (2)
00090 #define CYLEQA (3)
00091 #define SINEQA (4)
00092 #define GNOMONIC (5)
00093 #define POSTEL (6)
00094 #define STEREOGRAPHIC (7)
00095 #define ORTHOGRAPHIC (8)
00096 #define LAMBERT (9)
00097
00098 #define RSUNM (6.96e8)
00099 #define INTERP_NEAREST_NEIGHBOR (1)
00100 #define INTERP_BILINEAR (2)
00101
00102 char *module_name = "maprojbrfromblos";
00103 char *module_desc = "mapping from solar images";
00104 char *version_id = "0.9";
00105
00106 ModuleArgs_t module_args[] = {
00107 {ARG_DATASET, "in", "", "input data set"},
00108 {ARG_DATASERIES, "out", "", "output data series"},
00109 {ARG_DOUBLE, "clat", "0.0", "heliographic latitude of map center [deg]"},
00110 {ARG_DOUBLE, "clon", "0.0", "Carrington longitude of map center [deg]"},
00111 {ARG_DOUBLE, "scale", "Not specified", "map scale at center [deg/pxl]"},
00112 {ARG_NUME, "map", "orthographic", "map projection",
00113 "carree, Cassini, Mercator, cyleqa, sineqa, gnomonic, Postel, stereographic, orthographic, Lambert"},
00114 {ARG_NUME, "interp", "cubiconv", "interpolation option",
00115 "cubiconv, nearest, bilinear"},
00116 {ARG_FLOAT, "grid", "Not Specified",
00117 "if specified, spacing of grid overlay [deg]"},
00118 {ARG_INT, "cols", "0", "columns in output map"},
00119 {ARG_INT, "rows", "0", "rows in output map"},
00120 {ARG_INT, "blos2br", "0", "Blos converts to Br: 0 = not convert; 1 = convert"},
00121 {ARG_FLOAT, "map_pa", "0.0", "position angle of north on output map [deg]"},
00122 {ARG_FLOAT, "bscale", "0.0", "output scaling factor"},
00123 {ARG_FLOAT, "bzero", "Default", "output offset"},
00124 {ARG_STRING, "clon_key", "CRLN_OBS", "keyname for image central longitude"},
00125 {ARG_STRING, "clat_key", "CRLT_OBS", "keyname for image central latitude"},
00126 {ARG_STRING, "rsun_key", "R_SUN", "keyname for image semi-diameter (pixel)"},
00127 {ARG_STRING, "apsd_key", "RSUN_OBS", "keyname for apparent solar semi-diameter (arcsec)"},
00128 {ARG_STRING, "dsun_key", "DSUN_OBS", "keyname for observer distance"},
00129 {ARG_FLAG, "c", "", "center map at center of image"},
00130 {ARG_FLAG, "s", "", "clon is Stonyhurst longitude"},
00131 {ARG_FLAG, "v", "", "verbose mode"},
00132 {}
00133 };
00134
00135
00136 float missing_val;
00137
00138
00139 void ccker (double *u, double s) {
00140 double s2, s3;
00141
00142 s2= s * s;
00143 s3= s2 * s;
00144 u[0] = s2 - 0.5 * (s3 + s);
00145 u[1] = 1.5*s3 - 2.5*s2 + 1.0;
00146 u[2] = -1.5*s3 + 2.0*s2 + 0.5*s;
00147 u[3] = 0.5 * (s3 - s2);
00148 }
00149
00150 float ccint2 (float *f, int nx, int ny, double x, double y) {
00151 double ux[4], uy[4];
00152 double sum;
00153 int ix, iy, ix1, iy1, i, j;
00154
00155 if (x < 1.0 || x >= (float)(nx-2) || y < 1.0 || y >= (float)(ny-2))
00156 return missing_val;
00157
00158 ix = (int)x;
00159 ccker (ux, x - (double)ix);
00160 iy = (int)y;
00161 ccker (uy, y - (double)iy);
00162
00163 ix1 = ix - 1;
00164 iy1 = iy - 1;
00165 sum = 0.;
00166 for (i = 0; i < 4; i++)
00167 for (j = 0; j < 4; j++)
00168 sum = sum + f[(iy1+i) * nx + ix1 + j] * uy[i] * ux[j];
00169 return (float)sum;
00170 }
00171
00172 float linint2 (float *f, int cols, int rows, double x, double y) {
00173 double p, q, val;
00174 int col = (int)x, row = (int)y;
00175 int onerow = cols * row;
00176 int colp1 = col + 1, onerowp1 = onerow + cols;
00177
00178 if (x < 0.0 || x > cols || y < 0.0 || y >= rows)
00179 return missing_val;
00180 p = x - col;
00181 q = y - row;
00182 val = (1 - p) * (1 - q) * f[col + onerow]
00183 + p * (1 - q) * f[colp1 + onerow]
00184 + (1 - p) * q * f[col + onerowp1]
00185 + p * q * f[colp1 + onerowp1];
00186 return val;
00187 }
00188
00189 float nearest_val (float *f, int cols, int rows, double x, double y) {
00190 int col, row;
00191 if (x < -0.5 || x >= (cols - 0.5) || y < -0.5 || y >= (rows - 0.5))
00192 return missing_val;
00193 col = x + 0.5;
00194 row = y + 0.5;
00195 return f[col + row * cols];
00196 }
00197
00198
00199 float array_imaginterp (DRMS_Array_t *img, double x, double y,
00200 int schema) {
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225 double xs, ys;
00226 int cols, rows, mdim;
00227
00228 cols = img->axis[0];
00229 rows = img->axis[1];
00230 mdim = (cols > rows) ? cols : rows;
00231 xs = 0.5 * (x + 1.0) * mdim - 0.5;
00232 ys = 0.5 * (y + 1.0) * mdim - 0.5;
00233 if (schema == INTERP_NEAREST_NEIGHBOR)
00234 return nearest_val (img->data, cols, rows, xs, ys);
00235 else if (schema == INTERP_BILINEAR)
00236 return linint2 (img->data, cols, rows, xs, ys);
00237 else return ccint2 (img->data, cols, rows, xs, ys);
00238 }
00239
00240 void perform_mapping (DRMS_Array_t *img, float *map,
00241 double *maplat, double *maplon, double *map_coslat, double *map_sinlat,
00242 int pixct, unsigned char *offsun, double latc, double lonc,
00243 double xc, double yc, double radius, double pa, double ellipse_e,
00244 double ellipse_pa, int x_invrt, int y_invrt, int interpolator,
00245 int MDI_correct_distort) {
00246
00247
00248
00249
00250
00251 static double sin_asd = 0.004660, cos_asd = 0.99998914;
00252
00253 double r, cos_cang, xr, yr;
00254 double cos_lat, sin_lat, lon, cos_lat_lon;
00255 double xx, yy;
00256 float interpval;
00257 int n;
00258
00259 double cos_pa = cos (pa);
00260 double sin_pa = sin (pa);
00261 double cos_latc = cos (latc);
00262 double sin_latc = sin (latc);
00263 int plate_cols = img->axis[0];
00264 int plate_rows = img->axis[1];
00265 double plate_width = (plate_cols > plate_rows) ? plate_cols : plate_rows;
00266
00267 xc *= 2.0 / plate_width;
00268 yc *= 2.0 / plate_width;
00269 radius *= 2.0 / plate_width;
00270
00271 for (n = 0; n < pixct; n++) {
00272
00273 if (offsun[n]) {
00274 map[n] = missing_val;
00275 continue;
00276 }
00277 sin_lat = map_sinlat[n];
00278 cos_lat = map_coslat[n];
00279 lon = maplon[n];
00280 cos_lat_lon = cos_lat * cos (lon - lonc);
00281 cos_cang = sin_lat * sin_latc + cos_latc * cos_lat_lon;
00282 if (cos_cang < 0.0) {
00283 map[n] = missing_val;
00284 continue;
00285 }
00286 r = radius * cos_asd / (1.0 - cos_cang * sin_asd);
00287 xr = r * cos_lat * sin (lon - lonc);
00288 yr = r * (sin_lat * cos_latc - sin_latc * cos_lat_lon);
00289 xx = xr * cos_pa - yr * sin_pa;
00290 yy = xr * sin_pa + yr * cos_pa;
00291 yy += yc;
00292 xx += xc;
00293
00294 if (plate_cols > plate_rows) yy -= 1.0 - plate_rows / plate_width;
00295 if (plate_rows > plate_cols) xx -= 1.0 - plate_cols / plate_width;
00296 interpval = array_imaginterp (img, xx, yy, interpolator);
00297
00298
00299 if (MDI_correct_distort) {
00300 mtrack_MDI_image_tip (&xx, &yy, 1, 1);
00301 mtrack_MDI_image_stretch (&xx, &yy, 1, 1);
00302 }
00303 map[n] = (isnan (interpval)) ? missing_val : interpval;
00304 }
00305 }
00306
00307 int near_grid_line (double lon, double lat, double grid, double near) {
00308
00309
00310
00311
00312 static double degrad = 180.0 / M_PI;
00313 double g2 = 0.5 * grid;
00314
00315 lon *= degrad;
00316 lat *= degrad;
00317
00318 while (lon < 0.0) lon += grid;
00319 while (lon > g2) lon -= grid;
00320 if (fabs (lon) < near) return 1;
00321 while (lat < 0.0) lat += grid;
00322 while (lat > g2) lat -= grid;
00323 if (fabs (lat) < near) return 1;
00324 return 0;
00325 }
00326
00327 void convertblos2br(DRMS_Array_t *img, float xcen, float ycen, float rsun_obs) {
00328
00329 int jy, yOff, iData, status;
00330 double yDist, yDist2, xDist, xDist2, xDist2PlusyDist2, dToDiskCenter, sinrho, cosrho;
00331 int xDim = img->axis[0]; int yDim = img->axis[1], axes[2];
00332 float *bLos;
00333 bLos = (float *)img->data;
00334
00335 for (jy = 0; jy < yDim; jy++)
00336 {
00337 int ix = 0;
00338 yDist = (double)jy - ycen;
00339 yDist2 = yDist * yDist;
00340 yOff = jy * xDim;
00341
00342 for (ix = 0; ix < xDim; ix++)
00343 {
00344 iData = yOff + ix;
00345 xDist = (double)ix - xcen;
00346 xDist2 = xDist * xDist;
00347 xDist2PlusyDist2 = xDist2 + yDist2;
00348 dToDiskCenter = sqrt(xDist2PlusyDist2);
00349
00350 if (dToDiskCenter >= rsun_obs) continue;
00351 if (isnan(bLos[iData])) continue;
00352
00353 sinrho = dToDiskCenter / rsun_obs;
00354 cosrho = sqrt(1 - sinrho * sinrho);
00355 if (cosrho > 0) bLos[iData] /= cosrho;
00356 else bLos[iData] = DRMS_MISSING_FLOAT;
00357 }
00358 }
00359
00360 }
00361
00362 int DoIt (void) {
00363 CmdParams_t *params = &cmdparams;
00364 DRMS_RecordSet_t *ids, *ods;
00365 DRMS_Record_t *irec, *orec;
00366 DRMS_Segment_t *iseg, *oseg;
00367 DRMS_Array_t *image = NULL, *map = NULL;
00368 double *maplat, *maplon, *map_coslat, *map_sinlat;
00369 double x, y, x0, y0, xstp, ystp, xrot, yrot;
00370 double lat, lon, cos_phi, sin_phi;
00371 double img_lat, img_lon;
00372 double img_xscl, img_yscl, img_xc, img_yc, img_radius, img_pa;
00373 double grid_width;
00374 double ellipse_e, ellipse_pa;
00375 float *data;
00376 int axes[2];
00377 int img, imgct, pixct, segct;
00378 int isegnum, osegnum;
00379 int found, kstat, status;
00380 int need_ephem;
00381 int x_invrt, y_invrt;
00382 int n, col, row;
00383 int MDI_correct, MDI_correct_distort;
00384 unsigned char *offsun, *ongrid;
00385 char *input, *isegname, *osegname;
00386 char source[DRMS_MAXQUERYLEN], recid[DRMS_MAXQUERYLEN];
00387 char module_ident[64], key[64], tbuf[64];
00388
00389 double raddeg = M_PI / 180.0;
00390 double degrad = 1.0 / raddeg;
00391 int scaling_override = 0;
00392 char *mapname[] = {"PlateCarree", "Cassini-Soldner", "Mercator",
00393 "LambertCylindrical", "Sanson-Flamsteed", "gnomonic", "Postel",
00394 "stereographic", "orthographic", "LambertAzimuthal"};
00395 char *interpname[] = {"Cubic Convolution", "Nearest Neighbor", "Bilinear"};
00396 char *wcscode[] = {"CAR", "CAS", "MER", "CEA", "GLS", "TAN", "ARC", "STG",
00397 "SIN", "ZEA"};
00398 missing_val = 0.0 / 0.0;
00399 float bblank = -1.0 / 0.0;
00400 float wblank = 1.0 / 0.0;
00401
00402 char *inset = strdup (params_get_str (params, "in"));
00403 char *outser = strdup (params_get_str (params, "out"));
00404 double clat = params_get_double (params, "clat") * raddeg;
00405 double clon = params_get_double (params, "clon") * raddeg;
00406 double map_scale = params_get_double (params, "scale");
00407 double map_pa = params_get_double (params, "map_pa") * raddeg;
00408 float bscale = params_get_float (params, "bscale");
00409 float bzero = params_get_float (params, "bzero");
00410 float grid_spacing = params_get_float (params, "grid");
00411 int map_cols = params_get_int (params, "cols");
00412 int map_rows = params_get_int (params, "rows");
00413 int map_blos2br = params_get_int (params, "blos2br");
00414 int proj = params_get_int (params, "map");
00415 int intrpopt = params_get_int (params, "interp");
00416 char *clon_key = strdup (params_get_str (params, "clon_key"));
00417 char *clat_key = strdup (params_get_str (params, "clat_key"));
00418 char *rsun_key = strdup (params_get_str (params, "rsun_key"));
00419 char *apsd_key = strdup (params_get_str (params, "apsd_key"));
00420 char *dsun_key = strdup (params_get_str (params, "dsun_key"));
00421 int center = params_isflagset (params, "c");
00422 int stonyhurst = params_isflagset (params, "s");
00423 int verbose = params_isflagset (params, "v");
00424 int overlay = (isfinite (grid_spacing));
00425 int MDI_proc = params_isflagset (params, "M");
00426
00427 TIME trec, tnow, UNIX_epoch = -220924792.000;
00428
00429 snprintf (module_ident, 64, "%s v %s", module_name, version_id);
00430 if (verbose) printf ("%s: JSOC version %s\n", module_ident, jsoc_version);
00431
00432 if (map_cols < 1) map_cols = map_rows;
00433 if (map_rows < 1) map_rows = map_cols;
00434 if (map_rows < 1) {
00435 fprintf (stderr, "Error: at least one of \"cols\" or \"rows\" must be set\n");
00436 return 1;
00437 }
00438 if (isnan (map_scale) || map_scale == 0.0) {
00439 fprintf (stderr,
00440 "Error: auto scaling from image resolution not implemented;\n");
00441 fprintf (stderr, " scale parameter must be set.\n");
00442 return 1;
00443 }
00444 MDI_correct = MDI_correct_distort = MDI_proc;
00445 cos_phi = cos (map_pa);
00446 sin_phi = sin (map_pa);
00447 xstp = ystp = map_scale * raddeg;
00448 x0 = 0.5 * (1.0 - map_cols) * xstp;
00449 y0 = 0.5 * (1.0 - map_rows) * ystp;
00450 grid_width = 0.01 * grid_spacing;
00451
00452 if (!(ids = drms_open_records (drms_env, inset, &status))) {
00453 fprintf (stderr, "Error: (%s) unable to open input data set \"%s\"\n",
00454 module_ident, inset);
00455 fprintf (stderr, " status = %d\n", status);
00456 return 1;
00457 }
00458 if ((imgct = ids->n) < 1) {
00459 fprintf (stderr, "Error: (%s) no records in selected input set\n",
00460 module_ident);
00461 fprintf (stderr, " %s\n", inset);
00462 drms_close_records (ids, DRMS_FREE_RECORD);
00463 return 1;
00464 }
00465 input = strdup (inset);
00466
00467 irec = ids->records[0];
00468 segct = drms_record_numsegments (irec);
00469 isegnum = 0;
00470 if (segct) {
00471 found = 0;
00472 for (n = 0; n < segct; n++) {
00473 iseg = drms_segment_lookupnum (irec, n);
00474 if (iseg->info->naxis != 2) continue;
00475 if (!found) {
00476 isegname = strdup (iseg->info->name);
00477 isegnum = n;
00478 }
00479 found++;
00480 }
00481 if (found > 1) {
00482 fprintf (stderr,
00483 "Warning: multiple data segments of dimension 2 in input series %s\n",
00484 input);
00485 fprintf (stderr, " using \"%s\"\n", isegname);
00486 }
00487 iseg = drms_segment_lookupnum (irec, isegnum);
00488 } else {
00489 fprintf (stderr, "Error: no data segments in input series %s\n", input);
00490 drms_close_records (ids, DRMS_FREE_RECORD);
00491 return 1;
00492 }
00493 if (found < 1 || iseg->info->naxis != 2) {
00494 fprintf (stderr,
00495 "Error: no data segment of dimension 2 in input series %s\n", input);
00496 drms_close_records (ids, DRMS_FREE_RECORD);
00497 return 1;
00498 }
00499
00500 if (verbose) printf ("creating %d records in series %s\n", imgct, outser);
00501 if (!(ods = drms_create_records (drms_env, imgct, outser, DRMS_PERMANENT,
00502 &status))) {
00503 fprintf (stderr, "Error: unable to create %d records in series %s\n",
00504 imgct, outser);
00505 fprintf (stderr, " drms_create_records() returned status %d\n",
00506 status);
00507 return 1;
00508 }
00509
00510 orec = ods->records[0];
00511 segct = drms_record_numsegments (orec);
00512 found = 0;
00513 for (n = 0; n < segct; n++) {
00514 oseg = drms_segment_lookupnum (orec, n);
00515 if (oseg->info->naxis != 2) continue;
00516 if (oseg->info->scope == DRMS_CONSTANT) continue;
00517 if (oseg->info->scope == DRMS_VARIABLE) {
00518 if (oseg->axis[0] != map_cols ||
00519 oseg->axis[1] != map_rows) continue;
00520 }
00521 if (!found) {
00522 osegname = strdup (oseg->info->name);
00523 osegnum = n;
00524 }
00525 found++;
00526 }
00527 if (found < 1) {
00528 fprintf (stderr,
00529 "Error: no data segment of dimension 2 and appropriate size in output series %s\n", outser);
00530 drms_close_records (ods, DRMS_FREE_RECORD);
00531 return 1;
00532 }
00533 if (found > 1) {
00534 fprintf (stderr,
00535 "Warning: multiple data segments of dimension 2 and appropriate size in output series %s\n",
00536 outser);
00537 fprintf (stderr, " using \"%s\"\n", osegname);
00538 }
00539
00540 axes[0] = map_cols;
00541 axes[1] = map_rows;
00542 map = drms_array_create (DRMS_TYPE_FLOAT, 2, axes, NULL, &status);
00543 if (status) {
00544 fprintf (stderr, "Error: couldn't create output array\n");
00545 return 1;
00546 }
00547 pixct = map_cols * map_rows;
00548 maplat = (double *)malloc (pixct * sizeof (double));
00549 maplon = (double *)malloc (pixct * sizeof (double));
00550 map_coslat = (double *)malloc (pixct * sizeof (double));
00551 map_sinlat = (double *)malloc (pixct * sizeof (double));
00552 offsun = (unsigned char *)malloc (pixct * sizeof (char));
00553 if (overlay) ongrid = (unsigned char *)malloc (pixct * sizeof (char));
00554
00555 scaling_override = 0;
00556 if (bscale == 0.0) {
00557 bscale = oseg->bscale;
00558 scaling_override = 1;
00559 if (verbose) printf ("bscale set to output default: %g\n", bscale);
00560 }
00561 if (isnan (bzero)) {
00562 bzero = oseg->bzero;
00563 scaling_override = 1;
00564 if (verbose) printf ("bzero set to output default: %g\n", bzero);
00565 }
00566 map->bscale = bscale;
00567 map->bzero = bzero;
00568
00569
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582
00583
00584
00585 data = (float *)map->data;
00586
00587 for (img = 0; img < imgct; img++) {
00588
00589 irec = ids->records[img];
00590 drms_sprint_rec_query (source, irec);
00591 iseg = drms_segment_lookupnum (irec, isegnum);
00592 image = drms_segment_read (iseg, DRMS_TYPE_FLOAT, &status);
00593
00594
00595 img_lon = drms_getkey_double (irec, clon_key, &status);
00596 img_lat = drms_getkey_double (irec, clat_key, &status);
00597
00598 status = solar_image_info (irec, &img_xscl, &img_yscl, &img_xc, &img_yc,
00599 &img_radius, rsun_key, apsd_key, &img_pa, &ellipse_e, &ellipse_pa,
00600 &x_invrt, &y_invrt, &need_ephem, 0);
00601 if (status & NO_SEMIDIAMETER) {
00602 int keystat = 0;
00603 double dsun_obs = drms_getkey_double (irec, dsun_key, &keystat);
00604 if (keystat) {
00605 fprintf (stderr, "Error: one or more essential keywords or values missing; skipped\n");
00606 fprintf (stderr, "solar_image_info() returned %08x\n", status);
00607 continue;
00608 }
00609
00610 img_radius = asin (RSUNM / dsun_obs);
00611 img_radius *= 3600.0 * degrad;
00612 img_radius /= (img_xscl <= img_yscl) ? img_xscl : img_yscl;
00613 status &= ~NO_SEMIDIAMETER;
00614 }
00615 if (status == KEYSCOPE_VARIABLE) {
00616 fprintf (stderr, "Warning: one or more keywords expected constant are variable\n");
00617 } else if (status) {
00618 fprintf (stderr, "Error: one or more essential keywords or values missing; skipped\n");
00619 fprintf (stderr, "solar_image_info() returned %08x\n", status);
00620 continue;
00621 }
00622 if (MDI_correct) {
00623 mtrack_MDI_correct_imgctr (&img_xc, &img_yc, img_radius);
00624 mtrack_MDI_correct_pa (&img_pa);
00625 }
00626 img_xc -= 0.5 * (image->axis[0] - 1);
00627 img_yc -= 0.5 * (image->axis[1] - 1);
00628
00629 img_lon *= raddeg; clon = img_lon;
00630 img_lat *= raddeg;
00631
00632
00633
00634 for (n=0, row=0, y=y0; row < map_rows; row++, y += ystp) {
00635 for (col=0, x=x0; col < map_cols; col++, x += xstp, n++) {
00636 xrot = x * cos_phi - y * sin_phi;
00637 yrot = y * cos_phi + x * sin_phi;
00638 offsun[n] = plane2sphere (xrot, yrot, clat, clon, &lat, &lon, proj);
00639 maplat[n] = lat;
00640 maplon[n] = lon;
00641 map_coslat[n] = cos (lat);
00642 map_sinlat[n] = sin (lat);
00643 if (overlay) ongrid[n] =
00644 near_grid_line (maplon[n], maplat[n], grid_spacing, grid_width);
00645 }
00646 }
00647
00648
00649
00650
00651 float xcen, ycen, rsun_obs;
00652 xcen = drms_getkey_float(irec, "CRPIX1", &status) - 1.0;
00653 ycen = drms_getkey_float(irec, "CRPIX2", &status) - 1.0;
00654 if (map_blos2br == 1) convertblos2br(image, xcen, ycen, img_radius);
00655
00656
00657 orec = ods->records[img];
00658 oseg = drms_segment_lookup (orec, osegname);
00659
00660 perform_mapping (image, data, maplat, maplon, map_coslat, map_sinlat,
00661 pixct, offsun, img_lat, img_lon, img_xc, img_yc, img_radius, img_pa,
00662 ellipse_e, ellipse_pa, x_invrt, y_invrt, intrpopt, MDI_correct_distort);
00663 if (overlay) {
00664 for (n = 0; n < pixct; n++)
00665 if (ongrid[n]) data[n] = (isfinite (data[n])) ? bblank : wblank;
00666 }
00667
00668 status = drms_segment_write (oseg, map, 0);
00669 if (status) {
00670 drms_sprint_rec_query (recid, orec);
00671 fprintf (stderr, "Error writing data to record %s\n", recid);
00672 fprintf (stderr, " series may not have appropriate structure\n");
00673 return 1;
00674 }
00675
00676
00677 drms_copykey(orec, irec, "T_REC");
00678 drms_copykey(orec, irec, "T_OBS");
00679 drms_copykey(orec, irec, "CADENCE");
00680 drms_copykey(orec, irec, "DATASIGN");
00681 drms_copykey(orec, irec, "OBS_VR");
00682 drms_copykey(orec, irec, "OBS_VW");
00683 drms_copykey(orec, irec, "OBS_VN");
00684 drms_copykey(orec, irec, "DATE__OBS");
00685 drms_copykey(orec, irec, "QUALITY");
00686 drms_copykey(orec, irec, "CAMERA");
00687 drms_copykey(orec, irec, "CRLN_OBS");
00688 drms_copykey(orec, irec, "CRLT_OBS");
00689 drms_copykey(orec, irec, "CAR_ROT");
00690
00691 double statMin, statMax, statMedn, statMean, statSig, statSkew, statKurt;
00692 int statNgood, ipixels;
00693 if (fstats(axes[0] * axes[1], data, &statMin, &statMax, &statMedn, &statMean, &statSig,
00694 &statSkew, &statKurt, &statNgood)) printf("\n Statistics computation failed\n");
00695
00696
00697 ipixels = axes[0] * axes[1];
00698 drms_setkey_int(orec, "TOTVALS", ipixels);
00699 drms_setkey_int(orec, "DATAVALS", statNgood);
00700 ipixels = axes[0] * axes[1]-statNgood;
00701 drms_setkey_int(orec, "MISSVALS", ipixels);
00702 drms_setkey_double(orec, "DATAMIN", statMin);
00703 drms_setkey_double(orec, "DATAMAX", statMax);
00704 drms_setkey_double(orec, "DATAMEDN", statMedn);
00705 drms_setkey_double(orec, "DATAMEAN", statMean);
00706 drms_setkey_double(orec, "DATARMS", statSig);
00707 drms_setkey_double(orec, "DATASKEW", statSkew);
00708 drms_setkey_double(orec, "DATAKURT", statKurt);
00709 drms_setkey_int(orec, "BLOS2BR", map_blos2br);
00710
00711 kstat = 0;
00712 kstat += check_and_set_key_str (orec, "WCSNAME", "Carrington Heliographic");
00713 kstat += check_and_set_key_int (orec, "WCSAXES", 2);
00714 snprintf (key, 64, "CRLN-%s", wcscode[proj]);
00715 kstat += check_and_set_key_str (orec, "CTYPE1", key);
00716 snprintf (key, 64, "CRLT-%s", wcscode[proj]);
00717 kstat += check_and_set_key_str (orec, "CTYPE2", key);
00718 kstat += check_and_set_key_str (orec, "CUNIT1", "deg");
00719 kstat += check_and_set_key_str (orec, "CUNIT2", "deg");
00720 kstat += check_and_set_key_float (orec, "CRPIX1", 0.5 * map_cols + 0.5);
00721 kstat += check_and_set_key_float (orec, "CRPIX2", 0.5 * map_rows + 0.5);
00722 kstat += check_and_set_key_float (orec, "CRVAL1", clon * degrad);
00723 kstat += check_and_set_key_float (orec, "CRVAL2", clat * degrad);
00724 kstat += check_and_set_key_float (orec, "CDELT1", map_scale);
00725 kstat += check_and_set_key_float (orec, "CDELT2", map_scale);
00726 if (map_pa != 0.0) {
00727 kstat += check_and_set_key_float (orec, "PC1_1", cos (map_pa));
00728
00729 kstat += check_and_set_key_float (orec, "PC1_2", sin (map_pa));
00730
00731 kstat += check_and_set_key_float (orec, "PC2_1", sin (map_pa));
00732 kstat += check_and_set_key_float (orec, "PC2_2", cos (map_pa));
00733 }
00734
00735
00736
00737 kstat += check_and_set_key_str (orec, "MapProj", mapname[proj]);
00738 kstat += check_and_set_key_float (orec, "MapScale", map_scale);
00739 kstat += check_and_set_key_float (orec, "Width", map_cols * map_scale);
00740 kstat += check_and_set_key_float (orec, "Height", map_rows * map_scale);
00741 kstat += check_and_set_key_float (orec, "Size", sqrt (map_rows * map_cols) * map_scale);
00742 kstat += check_and_set_key_float (orec, "Map_PA", map_pa / raddeg);
00743 kstat += check_and_set_key_float (orec, "RSunRef", 1.0e-6 * RSUNM);
00744 kstat += check_and_set_key_str (orec, "Interp", interpname[intrpopt]);
00745
00746 kstat += check_and_set_key_str (orec, "Module", module_ident);
00747 kstat += check_and_set_key_str (orec, "BLD_VERS", jsoc_version);
00748
00749 kstat += check_and_set_key_str (orec, "Source", source);
00750 kstat += check_and_set_key_str (orec, "Input", input);
00751
00752 if (kstat) {
00753 fprintf (stderr, "Error writing key value(s) to record %d in series %s\n",
00754 img, outser);
00755 fprintf (stderr, " series may not have appropriate structure\n");
00756 drms_close_records (ods, DRMS_FREE_RECORD);
00757 return 1;
00758 }
00759 tnow = (double)time(NULL);
00760 tnow += UNIX_epoch;
00761 drms_setkey_time(orec, "DATE", tnow);
00762 }
00763 drms_close_records (ods, DRMS_INSERT_RECORD);
00764 drms_free_array (map);
00765 return 0;
00766 }
00767
00768
00769
00770
00771
00772
00773
00774
00775
00776
00777
00778
00779
00780
00781