diff --git a/src/mbgl/geometry/pbf_geometry.hpp b/src/mbgl/geometry/pbf_geometry.hpp deleted file mode 100644 index 84e15d101..000000000 --- a/src/mbgl/geometry/pbf_geometry.hpp +++ /dev/null @@ -1,77 +0,0 @@ -#ifndef MBGL_GEOMETRY_PBF_GEOMETRY -#define MBGL_GEOMETRY_PBF_GEOMETRY - -#include -#include - -#include - -namespace mbgl { - -class PBFGeometry : private util::noncopyable { - -public: - inline explicit PBFGeometry(pbf data); - - enum command : uint8_t { - end = 0, - move_to = 1, - line_to = 2, - close = 7 - }; - - inline command next(int32_t &rx, int32_t &ry); - -private: - pbf data; - uint8_t cmd; - uint32_t length; - int32_t x, y; - int32_t ox, oy; -}; - -PBFGeometry::PBFGeometry(pbf data_) - : data(data_), - cmd(1), - length(0), - x(0), y(0), - ox(0), oy(0) {} - -PBFGeometry::command PBFGeometry::next(int32_t &rx, int32_t &ry) { - if (data.data < data.end) { - if (length == 0) { - uint32_t cmd_length = static_cast(data.varint()); - cmd = cmd_length & 0x7; - length = cmd_length >> 3; - } - - --length; - - if (cmd == move_to || cmd == line_to) { - rx = (x += data.svarint()); - ry = (y += data.svarint()); - - if (cmd == move_to) { - ox = x; - oy = y; - return move_to; - } else { - return line_to; - } - } else if (cmd == close) { - rx = ox; - ry = oy; - return close; - } else { - fprintf(stderr, "unknown command: %d\n", cmd); - // TODO: gracefully handle geometry parse failures - return end; - } - } else { - return end; - } -} - -} - -#endif diff --git a/src/mbgl/map/vector_tile.cpp b/src/mbgl/map/vector_tile.cpp index 501ae4ff6..9ea57f4f6 100644 --- a/src/mbgl/map/vector_tile.cpp +++ b/src/mbgl/map/vector_tile.cpp @@ -1,10 +1,4 @@ #include -#include -#include -#include - -#include -#include using namespace mbgl; @@ -52,29 +46,48 @@ mapbox::util::optional VectorTileFeature::getValue(const std::string& key } GeometryCollection VectorTileFeature::getGeometries() const { - GeometryCollection result; + pbf data(geometry_pbf); + uint8_t cmd = 1; + uint32_t length = 0; + int32_t x = 0; + int32_t y = 0; - PBFGeometry geometry(geometry_pbf); - PBFGeometry::command cmd; - int32_t x, y; + GeometryCollection lines; - std::vector line; + lines.emplace_back(); + std::vector* line = &lines.back(); - while ((cmd = geometry.next(x, y)) != PBFGeometry::end) { - if (cmd == PBFGeometry::move_to) { - if (!line.empty()) { - result.push_back(line); - line.clear(); - } + while (data.data < data.end) { + if (length == 0) { + uint32_t cmd_length = data.varint(); + cmd = cmd_length & 0x7; + length = cmd_length >> 3; + } + + --length; + + if (cmd == 1 || cmd == 2) { + x += data.svarint(); + y += data.svarint(); + + if (cmd == 1 && !line->empty()) { // moveTo + lines.emplace_back(); + line = &lines.back(); + } + + line->emplace_back(x, y); + + } else if (cmd == 7) { // closePolygon + if (!line->empty()) { + line->push_back((*line)[0]); + } + + } else { + throw std::runtime_error("unknown command"); } - line.emplace_back(x, y); } - if (!line.empty()) { - result.push_back(line); - } - - return std::move(result); + return lines; } VectorTile::VectorTile(pbf tile_pbf) {