/******************************************************** * ██████╗ ██████╗████████╗██╗ * ██╔════╝ ██╔════╝╚══██╔══╝██║ * ██║ ███╗██║ ██║ ██║ * ██║ ██║██║ ██║ ██║ * ╚██████╔╝╚██████╗ ██║ ███████╗ * ╚═════╝ ╚═════╝ ╚═╝ ╚══════╝ * Geophysical Computational Tools & Library (GCTL) * * Copyright (c) 2022 Yi Zhang (yizhang-geo@zju.edu.cn) * * GCTL is distributed under a dual licensing scheme. You can redistribute * it and/or modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation, either version 2 * of the License, or (at your option) any later version. You should have * received a copy of the GNU Lesser General Public License along with this * program. If not, see . * * If the terms and conditions of the LGPL v.2. would prevent you from using * the GCTL, please consider the option to obtain a commercial license for a * fee. These licenses are offered by the GCTL's original author. As a rule, * licenses are provided "as-is", unlimited in time for a one time fee. Please * send corresponding requests to: yizhang-geo@zju.edu.cn. Please do not forget * to include some description of your company and the realm of its activities. * Also add information on how to contact you by electronic and paper mail. ******************************************************/ #include "gctl/core.h" #include "gctl/io.h" #include "gctl/utility.h" int main(int argc, char *argv[]) try { gctl::flags_parser fp; fp.set_proname("xyz2sph"); fp.set_proinfo("Convert coordinates of 3-D points from the Cartesian \ coordinates to the spherical coordinates, or the other way around. This program \ is a toolkit of the GCTL package. The GCTL comes with ABSOLUTE NO WARRANTY. \ Please see instructions or contact the author for more information. The program \ takes inputs from the standard input and display the results on screen. The coordinates \ should be separated by spaces and different points should be placed on different lines. \ The inputting continues until encounter a blank line or 'EOF'. Any lines start with '#' will be skipped."); fp.add_opt('c', "cartesian", no_argument, NULL, "The input points are under the Cartesian coordinates. Point format is .", 0, false); fp.add_opt('s', "spherical", no_argument, NULL, "The input points are under the spherical coordinates (default). Point format is .", 0, false); fp.add_opt('p', "precision", required_argument, NULL, "Set the precision of the outputs (the default is 12).", "", false); fp.add_opt('r', "reference", required_argument, NULL, "Set a reference system for converting coordinates to the given spherical or ellipsoidal surface.", "/|,|WGS84|Earth|Moon", false); fp.add_opt('v', "verbose", no_argument, NULL, "Show full outputs.", 0, false); fp.add_opt('h', "help", no_argument, NULL, "Show help information.", 0, false); fp.configure(argc, argv); if(fp.set_opt('h')) { fp.show_help_page(); return 0; } bool verbose = false; if (fp.set_opt('v')) { verbose = true; } double ref_r, ref_R; std::string err_str, pre_str, ref_str; std::stringstream tmp_ss; fp.get_argv({'p', 'r'}, {&pre_str, &ref_str}); if (pre_str == "NULL") pre_str = "12"; if (ref_str != "NULL") { if (ref_str == "WGS84") { ref_r = GCTL_WGS84_PoleRadius; ref_R = GCTL_WGS84_EquatorRadius; } else if (ref_str == "Earth") { ref_r = GCTL_Earth_Radius; ref_R = GCTL_Earth_Radius; } else if (ref_str == "Moon") { ref_r = GCTL_Moon_Radius; ref_R = GCTL_Moon_Radius; } else if (2 != sscanf(ref_str.c_str(), "%lf/%lf", &ref_r, &ref_R)) { if (2 == sscanf(ref_str.c_str(), "%lf,%lf", &ref_r, &ref_R)) { ref_r = (1.0-ref_r)*ref_R; } else { err_str = "Wrong entrance: " + ref_str; throw err_str; } } } int pre_int; gctl::str2type(pre_str, pre_int); std::string line; std::vector line_arr; gctl::point3dc pc; gctl::point3ds ps; while (true) { std::getline(std::cin, line); if (line[0] == '#') continue; if (line.empty() || line == "EOF") break; else line_arr.push_back(line); } std::cout << "# Outputs from the xyz2sph. Use -h to see the help information." << std::endl; if (verbose) std::cout << "# reference system: " << ref_str << std::endl; if (fp.set_opt('c')) { if (verbose) std::cout << "x,y,z,rad,lon,lat" << std::endl; for (int i = 0; i < line_arr.size(); i++) { tmp_ss.clear(); tmp_ss.str(line_arr[i]); tmp_ss >> pc.x >> pc.y >> pc.z; if (tmp_ss.fail()) { err_str = "Wrong entrance: " + line_arr[i]; throw err_str; } ps = pc.c2s(); if (ref_str != "NULL") { ps.rad = gctl::ellipse_radius_2d(ref_R, ref_r, ps.lat*GCTL_Pi/180.0); pc = ps.s2c(); } if (verbose) std::cout << std::setprecision(pre_int) << pc.x << "," << pc.y << "," << pc.z << ","; std::cout << std::setprecision(pre_int) << ps.rad << "," << ps.lon << "," << ps.lat << std::endl; } } else { if (verbose) std::cout << "rad,lon,lat,x,y,z" << std::endl; for (int i = 0; i < line_arr.size(); i++) { tmp_ss.clear(); tmp_ss.str(line_arr[i]); tmp_ss >> ps.rad >> ps.lon >> ps.lat; if (tmp_ss.fail()) { err_str = "Wrong entrance: " + line_arr[i]; throw err_str; } if (ref_str != "NULL") { ps.rad = gctl::ellipse_radius_2d(ref_R, ref_r, ps.lat*GCTL_Pi/180.0); } pc = ps.s2c(); if (verbose) std::cout << std::setprecision(pre_int) << ps.rad << "," << ps.lon << "," << ps.lat << ","; std::cout << std::setprecision(pre_int) << pc.x << "," << pc.y << "," << pc.z << std::endl; } } return 0; } catch(std::exception &e) { GCTL_ShowWhatError(e.what(), GCTL_ERROR_ERROR, 0, 0, 0); }