Skip to content

Commit

Permalink
Include backward compat for proj v4
Browse files Browse the repository at this point in the history
  • Loading branch information
pietern committed May 5, 2023
1 parent 3a15b3a commit 1bbe828
Show file tree
Hide file tree
Showing 3 changed files with 113 additions and 12 deletions.
12 changes: 6 additions & 6 deletions src/goesproc/map_drawer.cc
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,12 @@ using namespace nlohmann;
namespace {

Proj longitudeToProj(float longitude) {
std::stringstream args;
args << "+proj=geos ";
args << "+h=35786023.0 ";
args << "+lon_0=" << std::to_string(longitude) << " ";
args << "+sweep=x";
return Proj(args.str());
std::map<std::string, std::string> args;
args["proj"] = "geos";
args["h"] = "35786023.0";
args["lon_0"] = std::to_string(longitude);
args["sweep"] = "x";
return Proj(args);
}

} // namespace
Expand Down
88 changes: 87 additions & 1 deletion src/goesproc/proj.cc
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,85 @@

namespace {

std::vector<std::string> toVector(const std::map<std::string, std::string>& args) {
std::vector<std::string> vargs;
vargs.reserve(args.size());
for (const auto& arg : args) {
std::stringstream ss;
ss << arg.first << "=" << arg.second;
vargs.push_back(ss.str());
}
return vargs;
}

}

#if PROJ_VERSION_MAJOR == 4

namespace {

std::string pj_error(std::string prefix = "proj: ") {
std::stringstream ss;
ss << prefix << pj_strerrno(pj_errno);
return ss.str();
}

} // namespace

// Forward compatibility.
double proj_torad (double angle_in_degrees) {
return angle_in_degrees * DEG_TO_RAD;
}

Proj::Proj(const std::vector<std::string>& args) {
std::vector<char*> argv;
for (const auto& arg : args) {
argv.push_back(strdup(arg.c_str()));
}
proj_ = pj_init(argv.size(), argv.data());
if (!proj_) {
throw std::runtime_error(pj_error("proj initialization error: "));
}
for (auto& arg : argv) {
free(arg);
}
}

Proj::Proj(const std::map<std::string, std::string>& args)
: Proj(toVector(args)) {
}

Proj::~Proj() {
pj_free(proj_);
}

std::tuple<double, double> Proj::fwd(double lon, double lat) {
projUV in = { lon, lat };
projXY out = pj_fwd(in, proj_);
return std::make_tuple<double, double>(std::move(out.u), std::move(out.v));
}

std::tuple<double, double> Proj::inv(double x, double y) {
projXY in = { x, y };
projUV out = pj_inv(in, proj_);
return std::make_tuple<double, double>(std::move(out.u), std::move(out.v));
}

#elif PROJ_VERSION_MAJOR >= 5

namespace {

std::string toString(const std::vector<std::string>& vargs) {
std::stringstream ss;
for (auto it = vargs.begin(); it != vargs.end(); it++) {
ss << "+" << *it;
if (std::next(it) != std::end(vargs)) {
ss << " ";
}
}
return ss.str();
}

std::string pj_error(std::string prefix = "proj: ") {
std::stringstream ss;
ss << prefix << proj_errno_string(proj_errno(NULL));
Expand All @@ -13,13 +92,18 @@ std::string pj_error(std::string prefix = "proj: ") {

} // namespace

Proj::Proj(const std::string& args) {
Proj::Proj(const std::vector<std::string>& vargs) {
const auto args = toString(vargs);
proj_ = proj_create(NULL, args.c_str());
if (!proj_) {
throw std::runtime_error(pj_error("proj initialization error: "));
}
}

Proj::Proj(const std::map<std::string, std::string>& args)
: Proj(toVector(args)) {
}

Proj::~Proj() {
proj_destroy(proj_);
}
Expand All @@ -37,3 +121,5 @@ std::tuple<double, double> Proj::inv(double x, double y) {
PJ_COORD out = proj_trans(proj_, PJ_INV, in);
return std::make_tuple<double, double>(std::move(out.uv.u), std::move(out.uv.v));
}

#endif
25 changes: 20 additions & 5 deletions src/goesproc/proj.h
Original file line number Diff line number Diff line change
@@ -1,17 +1,28 @@
#pragma once

#if PROJ_VERSION_MAJOR < 5
#error "proj version >= 5 required"
#if PROJ_VERSION_MAJOR == 4
#include <proj_api.h>
#elif PROJ_VERSION_MAJOR >= 5
#include <proj.h>
#else
#error "proj version >= 4 required"
#endif

#if PROJ_VERSION_MAJOR == 4
// Forward compatibility.
double proj_torad (double angle_in_degrees);
#endif

#include <map>
#include <string>
#include <tuple>

#include <proj.h>
#include <vector>

class Proj {
public:
explicit Proj(const std::string& args);
explicit Proj(const std::vector<std::string>& args);

explicit Proj(const std::map<std::string, std::string>& args);

~Proj();

Expand All @@ -20,5 +31,9 @@ class Proj {
std::tuple<double, double> inv(double x, double y);

protected:
#if PROJ_VERSION_MAJOR == 4
projPJ proj_;
#elif PROJ_VERSION_MAJOR >= 5
PJ *proj_;
#endif
};

0 comments on commit 1bbe828

Please sign in to comment.