int main(int argc, char** argv) { int status = 0; oskar::OptionParser opt("oskar_convert_geodetic_to_ecef", oskar_version_string()); opt.set_description("Converts geodetic longitude/latitude/altitude to " "Cartesian ECEF coordinates. Assumes WGS84 ellipsoid."); opt.add_required("input file", "Path to file containing input coordinates. " "Angles must be in degrees."); if (!opt.check_options(argc, argv)) return OSKAR_FAIL; const char* filename = opt.get_arg(); // Load the input file. oskar_Mem *lon = oskar_mem_create(OSKAR_DOUBLE, OSKAR_CPU, 0, &status); oskar_Mem *lat = oskar_mem_create(OSKAR_DOUBLE, OSKAR_CPU, 0, &status); oskar_Mem *alt = oskar_mem_create(OSKAR_DOUBLE, OSKAR_CPU, 0, &status); size_t num_points = oskar_mem_load_ascii(filename, 3, &status, lon, "", lat, "", alt, "0.0"); oskar_mem_scale_real(lon, M_PI / 180.0, &status); oskar_mem_scale_real(lat, M_PI / 180.0, &status); // Convert coordinates. oskar_Mem *x = oskar_mem_create(OSKAR_DOUBLE, OSKAR_CPU, num_points, &status); oskar_Mem *y = oskar_mem_create(OSKAR_DOUBLE, OSKAR_CPU, num_points, &status); oskar_Mem *z = oskar_mem_create(OSKAR_DOUBLE, OSKAR_CPU, num_points, &status); oskar_convert_geodetic_spherical_to_ecef(num_points, oskar_mem_double_const(lon, &status), oskar_mem_double_const(lat, &status), oskar_mem_double_const(alt, &status), oskar_mem_double(x, &status), oskar_mem_double(y, &status), oskar_mem_double(z, &status)); // Print converted coordinates. oskar_mem_save_ascii(stdout, 3, num_points, &status, x, y, z); // Clean up. oskar_mem_free(lon, &status); oskar_mem_free(lat, &status); oskar_mem_free(alt, &status); oskar_mem_free(x, &status); oskar_mem_free(y, &status); oskar_mem_free(z, &status); if (status) { oskar_log_error(0, oskar_get_error_string(status)); return status; } return 0; }
double oskar_evaluate_diurnal_aberration(double lon_rad, double lat_rad, double height_m, double era_rad, double pm_x_rad, double pm_y_rad, double s_prime) { double sin_sp, cos_sp, sin_xp, cos_xp, sin_yp, cos_yp, sin_era, cos_era; double a, b, x, y, z, vx, vy; /* Earth rotation rate in rad per second of UT1. */ const double omega_earth = 1.00273781191135448 * 2.0 * M_PI / 86400.0; /* Transform geodetic (longitude, latitude, altitude) to geocentric XYZ. */ oskar_convert_geodetic_spherical_to_ecef(1, &lon_rad, &lat_rad, &height_m, &x, &y, &z); /* Calculate elements of polar motion matrix. */ sin_sp = sin(s_prime); cos_sp = cos(s_prime); sin_xp = sin(pm_x_rad); cos_xp = cos(pm_x_rad); sin_yp = sin(pm_y_rad); cos_yp = cos(pm_y_rad); /* Matrix-vector multiplication. */ a = x * cos_sp * cos_xp + y * (cos_yp * sin_sp + cos_sp * sin_xp * sin_yp) + z * (cos_sp * cos_yp * sin_xp - sin_sp * sin_yp); b = x * -cos_xp * sin_sp + y * (cos_sp * cos_yp - sin_sp * sin_xp * sin_yp) + z * (-cos_sp * sin_yp - cos_yp * sin_sp * sin_xp); /* Get velocity components. */ sin_era = sin(era_rad); cos_era = cos(era_rad); vx = omega_earth * (-sin_era * a - cos_era * b); vy = omega_earth * ( cos_era * a - sin_era * b); /* Return magnitude of diurnal aberration vector. */ return sqrt(vx*vx + vy*vy) / 299792458.0; }