| 9 | using namespace strings; |
| 10 | |
| 11 | void ParseGeometry(std::string_view s, std::vector<ms::LatLon> & geom) |
| 12 | { |
| 13 | std::string_view constexpr prefix = "LINESTRING("; |
| 14 | if (!s.ends_with(')') || !s.starts_with(prefix)) |
| 15 | return; |
| 16 | |
| 17 | s.remove_prefix(prefix.size()); |
| 18 | s.remove_suffix(1); |
| 19 | |
| 20 | ms::LatLon last; |
| 21 | auto const skipPoint = [&last, &geom]() |
| 22 | { |
| 23 | // Check simple distance (meters) threshold. |
| 24 | return !geom.empty() && ms::DistanceOnEarth(geom.back(), last) < 10.0; |
| 25 | }; |
| 26 | |
| 27 | Tokenize(s, ",", [&](std::string_view s) |
| 28 | { |
| 29 | auto i = s.find(' '); |
| 30 | CHECK(i != std::string_view::npos, (s)); |
| 31 | |
| 32 | CHECK(to_double(s.substr(0, i), last.m_lon), (s)); |
| 33 | CHECK(to_double(s.substr(i + 1), last.m_lat), (s)); |
| 34 | |
| 35 | if (!skipPoint()) |
| 36 | geom.push_back(last); |
| 37 | }); |
| 38 | |
| 39 | if (skipPoint()) |
| 40 | { |
| 41 | auto & back = geom.back(); |
| 42 | if (geom.size() == 1) |
| 43 | { |
| 44 | // Set one middle point address. |
| 45 | back = ms::LatLon{(back.m_lat + last.m_lat) / 2.0, (back.m_lon + last.m_lon) / 2.0}; |
| 46 | } |
| 47 | else |
| 48 | { |
| 49 | // Replace last point. |
| 50 | back = last; |
| 51 | } |
| 52 | } |
| 53 | } |
| 54 | |
| 55 | feature::InterpolType ParseInterpolation(std::string_view s) |
| 56 | { |
no test coverage detected