Merge ca320f7cc1 into 50f5a753ea
This commit is contained in:
commit
3fdcd104ae
@ -1,5 +1,9 @@
|
||||
# Unreleased
|
||||
- Changes from 5.24.0
|
||||
- Features:
|
||||
- ADDED: a new `ways` subsection in the `annotations` section containing way IDs along the found path, with sign meaning direction [#5325](https://github.com/Project-OSRM/osrm-backend/issues/5325)
|
||||
- API:
|
||||
- FIXED: item type for `nodes` section of the `annotations` flatbuffers output format [#5970](https://github.com/Project-OSRM/osrm-backend/issues/5970)
|
||||
- Misc:
|
||||
- FIXED: Upgrade to @mapbox/node-pre-gyp fix various bugs with Node 12/14 [#5991](https://github.com/Project-OSRM/osrm-backend/pull/5991)
|
||||
- FIXED: `valid` type in documentation examples [#5990](https://github.com/Project-OSRM/osrm-backend/issues/5990)
|
||||
|
||||
@ -242,7 +242,7 @@ endif()
|
||||
|
||||
if(CMAKE_CXX_COMPILER_ID MATCHES "GNU")
|
||||
set(CMAKE_C_FLAGS_RELWITHDEBINFO "${CMAKE_C_FLAGS_RELWITHDEBINFO} -ggdb")
|
||||
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -Og -ggdb")
|
||||
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -O0 -ggdb")
|
||||
endif()
|
||||
|
||||
|
||||
|
||||
@ -208,7 +208,7 @@ In addition to the [general options](#general-options) the following options are
|
||||
|------------|---------------------------------------------|-------------------------------------------------------------------------------|
|
||||
|alternatives|`true`, `false` (default), or Number |Search for alternative routes. Passing a number `alternatives=n` searches for up to `n` alternative routes.\* |
|
||||
|steps |`true`, `false` (default) |Returned route steps for each route leg |
|
||||
|annotations |`true`, `false` (default), `nodes`, `distance`, `duration`, `datasources`, `weight`, `speed` |Returns additional metadata for each coordinate along the route geometry. |
|
||||
|annotations |`true`, `false` (default), `nodes`, `ways`, `distance`, `duration`, `datasources`, `weight`, `speed` |Returns additional metadata for each coordinate along the route geometry. |
|
||||
|geometries |`polyline` (default), `polyline6`, `geojson` |Returned route geometry format (influences overview and per step) |
|
||||
|overview |`simplified` (default), `full`, `false` |Add overview geometry either full, simplified according to highest zoom level it could be display on, or not at all.|
|
||||
|continue\_straight |`default` (default), `true`, `false` |Forces the route to keep going straight at waypoints constraining uturns there even if it would be faster. Default value depends on the profile. |
|
||||
@ -430,7 +430,7 @@ In addition to the [general options](#general-options) the following options are
|
||||
|------------|------------------------------------------------|------------------------------------------------------------------------------------------|
|
||||
|steps |`true`, `false` (default) |Returned route steps for each route |
|
||||
|geometries |`polyline` (default), `polyline6`, `geojson` |Returned route geometry format (influences overview and per step) |
|
||||
|annotations |`true`, `false` (default), `nodes`, `distance`, `duration`, `datasources`, `weight`, `speed` |Returns additional metadata for each coordinate along the route geometry. |
|
||||
|annotations |`true`, `false` (default), `nodes`, `ways`, `distance`, `duration`, `datasources`, `weight`, `speed` |Returns additional metadata for each coordinate along the route geometry. |
|
||||
|overview |`simplified` (default), `full`, `false` |Add overview geometry either full, simplified according to highest zoom level it could be display on, or not at all.|
|
||||
|timestamps |`{timestamp};{timestamp}[;{timestamp} ...]` |Timestamps for the input locations in seconds since UNIX epoch. Timestamps need to be monotonically increasing. |
|
||||
|radiuses |`{radius};{radius}[;{radius} ...]` |Standard deviation of GPS precision used for map matching. If applicable use GPS accuracy.|
|
||||
@ -486,7 +486,7 @@ In addition to the [general options](#general-options) the following options are
|
||||
|source |`any` (default), `first` |Returned route starts at `any` or `first` coordinate |
|
||||
|destination |`any` (default), `last` |Returned route ends at `any` or `last` coordinate |
|
||||
|steps |`true`, `false` (default) |Returned route instructions for each trip |
|
||||
|annotations |`true`, `false` (default), `nodes`, `distance`, `duration`, `datasources`, `weight`, `speed` |Returns additional metadata for each coordinate along the route geometry. |
|
||||
|annotations |`true`, `false` (default), `nodes`, `ways`, `distance`, `duration`, `datasources`, `weight`, `speed` |Returns additional metadata for each coordinate along the route geometry. |
|
||||
|geometries |`polyline` (default), `polyline6`, `geojson` |Returned route geometry format (influences overview and per step) |
|
||||
|overview |`simplified` (default), `full`, `false` |Add overview geometry either full, simplified according to highest zoom level it could be display on, or not at all.|
|
||||
|
||||
@ -700,6 +700,7 @@ Annotation of the whole route leg with fine-grained information about each segme
|
||||
- `duration`: The duration between each pair of coordinates, in seconds. Does not include the duration of any turns.
|
||||
- `datasources`: The index of the datasource for the speed between each pair of coordinates. `0` is the default profile, other values are supplied via `--segment-speed-file` to `osrm-contract` or `osrm-customize`. String-like names are in the `metadata.datasource_names` array.
|
||||
- `nodes`: The OSM node ID for each coordinate along the route, excluding the first/last user-supplied coordinates
|
||||
- `ways`: The OSM way ID for each pair of neighbor nodes in the list of nodes, with a sign. The sign means direction. A positive sign means moving in the direction of the way, while negative means moving in the opposite direction.
|
||||
- `weight`: The weights between each pair of coordinates. Does not include any turn costs.
|
||||
- `speed`: Convenience field, calculation of `distance / duration` rounded to one decimal place
|
||||
- `metadata`: Metadata related to other annotations
|
||||
@ -714,6 +715,7 @@ Annotation of the whole route leg with fine-grained information about each segme
|
||||
"datasources": [1,0,0,0,1],
|
||||
"metadata": { "datasource_names": ["traffic","lua profile","lua profile","lua profile","traffic"] },
|
||||
"nodes": [49772551,49772552,49786799,49786800,49786801,49786802],
|
||||
"ways": [130764281,130764281,-6056749,-6056749,-6056749],
|
||||
"weight": [15,15,40,15,15]
|
||||
}
|
||||
```
|
||||
|
||||
@ -55,7 +55,7 @@ Returns the fastest route between two or more coordinates while visiting the way
|
||||
- `options.alternatives` **[Number](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number)** Search for up to this many alternative routes.
|
||||
_Please note that even if alternative routes are requested, a result cannot be guaranteed._ (optional, default `0`)
|
||||
- `options.steps` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)** Return route steps for each route leg. (optional, default `false`)
|
||||
- `options.annotations` **([Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array) \| [Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean))** An array with strings of `duration`, `nodes`, `distance`, `weight`, `datasources`, `speed` or boolean for enabling/disabling all. (optional, default `false`)
|
||||
- `options.annotations` **([Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array) \| [Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean))** An array with strings of `duration`, `nodes`, `ways`, `distance`, `weight`, `datasources`, `speed` or boolean for enabling/disabling all. (optional, default `false`)
|
||||
- `options.geometries` **[String](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String)** Returned route geometry format (influences overview and per step). Can also be `geojson`. (optional, default `polyline`)
|
||||
- `options.overview` **[String](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String)** Add overview geometry either `full`, `simplified` according to highest zoom level it could be display on, or not at all (`false`). (optional, default `simplified`)
|
||||
- `options.continue_straight` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)?** Forces the route to keep going straight at waypoints and don't do a uturn even if it would be faster. Default value depends on the profile.
|
||||
@ -215,7 +215,7 @@ if they can not be matched successfully.
|
||||
- `options.hints` **[Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array)?** Hints for the coordinate snapping. Array of base64 encoded strings.
|
||||
- `options.generate_hints` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)?** Whether or not adds a Hint to the response which can be used in subsequent requests. (optional, default `true`)
|
||||
- `options.steps` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)** Return route steps for each route. (optional, default `false`)
|
||||
- `options.annotations` **([Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array) \| [Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean))** An array with strings of `duration`, `nodes`, `distance`, `weight`, `datasources`, `speed` or boolean for enabling/disabling all. (optional, default `false`)
|
||||
- `options.annotations` **([Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array) \| [Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean))** An array with strings of `duration`, `nodes`, `ways`, `distance`, `weight`, `datasources`, `speed` or boolean for enabling/disabling all. (optional, default `false`)
|
||||
- `options.geometries` **[String](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String)** Returned route geometry format (influences overview and per step). Can also be `geojson`. (optional, default `polyline`)
|
||||
- `options.overview` **[String](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String)** Add overview geometry either `full`, `simplified` according to highest zoom level it could be display on, or not at all (`false`). (optional, default `simplified`)
|
||||
- `options.timestamps` **[Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array)<[Number](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Number)>?** Timestamp of the input location (integers, UNIX-like timestamp).
|
||||
@ -282,7 +282,7 @@ Right now, the following combinations are possible:
|
||||
- `options.hints` **[Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array)?** Hints for the coordinate snapping. Array of base64 encoded strings.
|
||||
- `options.generate_hints` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)?** Whether or not adds a Hint to the response which can be used in subsequent requests. (optional, default `true`)
|
||||
- `options.steps` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)** Return route steps for each route. (optional, default `false`)
|
||||
- `options.annotations` **([Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array) \| [Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean))** An array with strings of `duration`, `nodes`, `distance`, `weight`, `datasources`, `speed` or boolean for enabling/disabling all. (optional, default `false`)
|
||||
- `options.annotations` **([Array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array) \| [Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean))** An array with strings of `duration`, `nodes`, `ways`, `distance`, `weight`, `datasources`, `speed` or boolean for enabling/disabling all. (optional, default `false`)
|
||||
- `options.geometries` **[String](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String)** Returned route geometry format (influences overview and per step). Can also be `geojson`. (optional, default `polyline`)
|
||||
- `options.overview` **[String](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String)** Add overview geometry either `full`, `simplified` (optional, default `simplified`)
|
||||
- `options.roundtrip` **[Boolean](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Boolean)** Return route is a roundtrip. (optional, default `true`)
|
||||
|
||||
3
include/engine/api/flatbuffers/compile.sh
Executable file
3
include/engine/api/flatbuffers/compile.sh
Executable file
@ -0,0 +1,3 @@
|
||||
#!/bin/sh
|
||||
|
||||
../../../../build/flatbuffers-build/flatc --cpp --no-includes --gen-all --gen-object-api fbresult.fbs
|
||||
@ -461,7 +461,8 @@ struct AnnotationT : public flatbuffers::NativeTable {
|
||||
std::vector<uint32_t> distance;
|
||||
std::vector<uint32_t> duration;
|
||||
std::vector<uint32_t> datasources;
|
||||
std::vector<uint32_t> nodes;
|
||||
std::vector<uint64_t> nodes;
|
||||
std::vector<int64_t> ways;
|
||||
std::vector<uint32_t> weight;
|
||||
std::vector<float> speed;
|
||||
std::unique_ptr<osrm::engine::api::fbresult::MetadataT> metadata;
|
||||
@ -476,9 +477,10 @@ struct Annotation FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
|
||||
VT_DURATION = 6,
|
||||
VT_DATASOURCES = 8,
|
||||
VT_NODES = 10,
|
||||
VT_WEIGHT = 12,
|
||||
VT_SPEED = 14,
|
||||
VT_METADATA = 16
|
||||
VT_WAYS = 12,
|
||||
VT_WEIGHT = 14,
|
||||
VT_SPEED = 16,
|
||||
VT_METADATA = 18
|
||||
};
|
||||
const flatbuffers::Vector<uint32_t> *distance() const {
|
||||
return GetPointer<const flatbuffers::Vector<uint32_t> *>(VT_DISTANCE);
|
||||
@ -489,8 +491,11 @@ struct Annotation FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
|
||||
const flatbuffers::Vector<uint32_t> *datasources() const {
|
||||
return GetPointer<const flatbuffers::Vector<uint32_t> *>(VT_DATASOURCES);
|
||||
}
|
||||
const flatbuffers::Vector<uint32_t> *nodes() const {
|
||||
return GetPointer<const flatbuffers::Vector<uint32_t> *>(VT_NODES);
|
||||
const flatbuffers::Vector<uint64_t> *nodes() const {
|
||||
return GetPointer<const flatbuffers::Vector<uint64_t> *>(VT_NODES);
|
||||
}
|
||||
const flatbuffers::Vector<int64_t> *ways() const {
|
||||
return GetPointer<const flatbuffers::Vector<int64_t> *>(VT_WAYS);
|
||||
}
|
||||
const flatbuffers::Vector<uint32_t> *weight() const {
|
||||
return GetPointer<const flatbuffers::Vector<uint32_t> *>(VT_WEIGHT);
|
||||
@ -511,6 +516,8 @@ struct Annotation FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
|
||||
verifier.VerifyVector(datasources()) &&
|
||||
VerifyOffset(verifier, VT_NODES) &&
|
||||
verifier.VerifyVector(nodes()) &&
|
||||
VerifyOffset(verifier, VT_WAYS) &&
|
||||
verifier.VerifyVector(ways()) &&
|
||||
VerifyOffset(verifier, VT_WEIGHT) &&
|
||||
verifier.VerifyVector(weight()) &&
|
||||
VerifyOffset(verifier, VT_SPEED) &&
|
||||
@ -536,9 +543,12 @@ struct AnnotationBuilder {
|
||||
void add_datasources(flatbuffers::Offset<flatbuffers::Vector<uint32_t>> datasources) {
|
||||
fbb_.AddOffset(Annotation::VT_DATASOURCES, datasources);
|
||||
}
|
||||
void add_nodes(flatbuffers::Offset<flatbuffers::Vector<uint32_t>> nodes) {
|
||||
void add_nodes(flatbuffers::Offset<flatbuffers::Vector<uint64_t>> nodes) {
|
||||
fbb_.AddOffset(Annotation::VT_NODES, nodes);
|
||||
}
|
||||
void add_ways(flatbuffers::Offset<flatbuffers::Vector<int64_t>> ways) {
|
||||
fbb_.AddOffset(Annotation::VT_WAYS, ways);
|
||||
}
|
||||
void add_weight(flatbuffers::Offset<flatbuffers::Vector<uint32_t>> weight) {
|
||||
fbb_.AddOffset(Annotation::VT_WEIGHT, weight);
|
||||
}
|
||||
@ -565,7 +575,8 @@ inline flatbuffers::Offset<Annotation> CreateAnnotation(
|
||||
flatbuffers::Offset<flatbuffers::Vector<uint32_t>> distance = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<uint32_t>> duration = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<uint32_t>> datasources = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<uint32_t>> nodes = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<uint64_t>> nodes = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<int64_t>> ways = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<uint32_t>> weight = 0,
|
||||
flatbuffers::Offset<flatbuffers::Vector<float>> speed = 0,
|
||||
flatbuffers::Offset<osrm::engine::api::fbresult::Metadata> metadata = 0) {
|
||||
@ -573,6 +584,7 @@ inline flatbuffers::Offset<Annotation> CreateAnnotation(
|
||||
builder_.add_metadata(metadata);
|
||||
builder_.add_speed(speed);
|
||||
builder_.add_weight(weight);
|
||||
builder_.add_ways(ways);
|
||||
builder_.add_nodes(nodes);
|
||||
builder_.add_datasources(datasources);
|
||||
builder_.add_duration(duration);
|
||||
@ -585,14 +597,16 @@ inline flatbuffers::Offset<Annotation> CreateAnnotationDirect(
|
||||
const std::vector<uint32_t> *distance = nullptr,
|
||||
const std::vector<uint32_t> *duration = nullptr,
|
||||
const std::vector<uint32_t> *datasources = nullptr,
|
||||
const std::vector<uint32_t> *nodes = nullptr,
|
||||
const std::vector<uint64_t> *nodes = nullptr,
|
||||
const std::vector<int64_t> *ways = nullptr,
|
||||
const std::vector<uint32_t> *weight = nullptr,
|
||||
const std::vector<float> *speed = nullptr,
|
||||
flatbuffers::Offset<osrm::engine::api::fbresult::Metadata> metadata = 0) {
|
||||
auto distance__ = distance ? _fbb.CreateVector<uint32_t>(*distance) : 0;
|
||||
auto duration__ = duration ? _fbb.CreateVector<uint32_t>(*duration) : 0;
|
||||
auto datasources__ = datasources ? _fbb.CreateVector<uint32_t>(*datasources) : 0;
|
||||
auto nodes__ = nodes ? _fbb.CreateVector<uint32_t>(*nodes) : 0;
|
||||
auto nodes__ = nodes ? _fbb.CreateVector<uint64_t>(*nodes) : 0;
|
||||
auto ways__ = ways ? _fbb.CreateVector<int64_t>(*ways) : 0;
|
||||
auto weight__ = weight ? _fbb.CreateVector<uint32_t>(*weight) : 0;
|
||||
auto speed__ = speed ? _fbb.CreateVector<float>(*speed) : 0;
|
||||
return osrm::engine::api::fbresult::CreateAnnotation(
|
||||
@ -601,6 +615,7 @@ inline flatbuffers::Offset<Annotation> CreateAnnotationDirect(
|
||||
duration__,
|
||||
datasources__,
|
||||
nodes__,
|
||||
ways__,
|
||||
weight__,
|
||||
speed__,
|
||||
metadata);
|
||||
@ -1974,6 +1989,7 @@ inline void Annotation::UnPackTo(AnnotationT *_o, const flatbuffers::resolver_fu
|
||||
{ auto _e = duration(); if (_e) { _o->duration.resize(_e->size()); for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->duration[_i] = _e->Get(_i); } } };
|
||||
{ auto _e = datasources(); if (_e) { _o->datasources.resize(_e->size()); for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->datasources[_i] = _e->Get(_i); } } };
|
||||
{ auto _e = nodes(); if (_e) { _o->nodes.resize(_e->size()); for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->nodes[_i] = _e->Get(_i); } } };
|
||||
{ auto _e = ways(); if (_e) { _o->ways.resize(_e->size()); for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->ways[_i] = _e->Get(_i); } } };
|
||||
{ auto _e = weight(); if (_e) { _o->weight.resize(_e->size()); for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->weight[_i] = _e->Get(_i); } } };
|
||||
{ auto _e = speed(); if (_e) { _o->speed.resize(_e->size()); for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->speed[_i] = _e->Get(_i); } } };
|
||||
{ auto _e = metadata(); if (_e) _o->metadata = std::unique_ptr<osrm::engine::api::fbresult::MetadataT>(_e->UnPack(_resolver)); };
|
||||
@ -1991,6 +2007,7 @@ inline flatbuffers::Offset<Annotation> CreateAnnotation(flatbuffers::FlatBufferB
|
||||
auto _duration = _o->duration.size() ? _fbb.CreateVector(_o->duration) : 0;
|
||||
auto _datasources = _o->datasources.size() ? _fbb.CreateVector(_o->datasources) : 0;
|
||||
auto _nodes = _o->nodes.size() ? _fbb.CreateVector(_o->nodes) : 0;
|
||||
auto _ways = _o->ways.size() ? _fbb.CreateVector(_o->ways) : 0;
|
||||
auto _weight = _o->weight.size() ? _fbb.CreateVector(_o->weight) : 0;
|
||||
auto _speed = _o->speed.size() ? _fbb.CreateVector(_o->speed) : 0;
|
||||
auto _metadata = _o->metadata ? CreateMetadata(_fbb, _o->metadata.get(), _rehasher) : 0;
|
||||
@ -2000,6 +2017,7 @@ inline flatbuffers::Offset<Annotation> CreateAnnotation(flatbuffers::FlatBufferB
|
||||
_duration,
|
||||
_datasources,
|
||||
_nodes,
|
||||
_ways,
|
||||
_weight,
|
||||
_speed,
|
||||
_metadata);
|
||||
|
||||
@ -9,7 +9,8 @@ table Annotation {
|
||||
distance: [uint];
|
||||
duration: [uint];
|
||||
datasources: [uint];
|
||||
nodes: [uint];
|
||||
nodes: [ulong];
|
||||
ways: [long];
|
||||
weight: [uint];
|
||||
speed: [float];
|
||||
metadata: Metadata;
|
||||
|
||||
@ -494,7 +494,7 @@ class RouteAPI : public BaseAPI
|
||||
return anno.datasource;
|
||||
});
|
||||
}
|
||||
std::vector<uint32_t> nodes;
|
||||
std::vector<uint64_t> nodes;
|
||||
if (requested_annotations & RouteParameters::AnnotationsType::Nodes)
|
||||
{
|
||||
nodes.reserve(leg_geometry.osm_node_ids.size());
|
||||
@ -503,7 +503,18 @@ class RouteAPI : public BaseAPI
|
||||
nodes.emplace_back(static_cast<uint64_t>(node_id));
|
||||
}
|
||||
}
|
||||
std::vector<int64_t> ways;
|
||||
if (requested_annotations & RouteParameters::AnnotationsType::Ways &&
|
||||
leg_geometry.osm_way_ids.size())
|
||||
{
|
||||
ways.reserve(leg_geometry.osm_way_ids.size());
|
||||
for (const auto way_id : leg_geometry.osm_way_ids)
|
||||
{
|
||||
ways.emplace_back(static_cast<int64_t>(way_id));
|
||||
}
|
||||
}
|
||||
auto nodes_vector = fb_result.CreateVector(nodes);
|
||||
auto ways_vector = fb_result.CreateVector(ways);
|
||||
// Add any supporting metadata, if needed
|
||||
bool use_metadata = requested_annotations & RouteParameters::AnnotationsType::Datasources;
|
||||
flatbuffers::Offset<fbresult::Metadata> metadata_buffer;
|
||||
@ -529,6 +540,7 @@ class RouteAPI : public BaseAPI
|
||||
annotation.add_weight(weight);
|
||||
annotation.add_datasources(datasources);
|
||||
annotation.add_nodes(nodes_vector);
|
||||
annotation.add_ways(ways_vector);
|
||||
if (use_metadata)
|
||||
{
|
||||
annotation.add_metadata(metadata_buffer);
|
||||
@ -832,6 +844,17 @@ class RouteAPI : public BaseAPI
|
||||
}
|
||||
annotation.values["nodes"] = std::move(nodes);
|
||||
}
|
||||
if (requested_annotations & RouteParameters::AnnotationsType::Ways &&
|
||||
leg_geometry.osm_way_ids.size())
|
||||
{
|
||||
util::json::Array ways;
|
||||
ways.values.reserve(leg_geometry.osm_way_ids.size());
|
||||
for (const auto way_id : leg_geometry.osm_way_ids)
|
||||
{
|
||||
ways.values.push_back(static_cast<std::int64_t>(way_id));
|
||||
}
|
||||
annotation.values["ways"] = std::move(ways);
|
||||
}
|
||||
// Add any supporting metadata, if needed
|
||||
if (requested_annotations & RouteParameters::AnnotationsType::Datasources)
|
||||
{
|
||||
|
||||
@ -76,7 +76,8 @@ struct RouteParameters : public BaseParameters
|
||||
Weight = 0x08,
|
||||
Datasources = 0x10,
|
||||
Speed = 0x20,
|
||||
All = Duration | Nodes | Distance | Weight | Datasources | Speed
|
||||
Ways = 0x40,
|
||||
All = Duration | Nodes | Distance | Weight | Datasources | Speed | Ways
|
||||
};
|
||||
|
||||
RouteParameters() = default;
|
||||
|
||||
@ -251,6 +251,19 @@ class ContiguousInternalMemoryDataFacadeBase : public BaseDataFacade
|
||||
return segment_data.GetReverseGeometry(id);
|
||||
}
|
||||
|
||||
OSMWayForwardRange GetUncompressedForwardWayIDs(const EdgeID id) const override final
|
||||
{
|
||||
return segment_data.GetForwardOSMWayIDs(id);
|
||||
}
|
||||
OSMWayReverseRange GetUncompressedReverseWayIDs(const EdgeID id) const override final
|
||||
{
|
||||
return segment_data.GetReverseOSMWayIDs(id);
|
||||
}
|
||||
bool GetUncompressedWayIDsSkipped() const override final
|
||||
{
|
||||
return segment_data.GetOSMWaysSkipped();
|
||||
}
|
||||
|
||||
DurationForwardRange GetUncompressedForwardDurations(const EdgeID id) const override final
|
||||
{
|
||||
return segment_data.GetForwardDurations(id);
|
||||
|
||||
@ -57,6 +57,12 @@ class BaseDataFacade
|
||||
boost::iterator_range<extractor::SegmentDataView::SegmentNodeVector::const_iterator>;
|
||||
using NodeReverseRange = boost::reversed_range<const NodeForwardRange>;
|
||||
|
||||
using OSMWayForwardRange =
|
||||
boost::iterator_range<extractor::SegmentDataView::SegmentOSMWayVector::const_iterator>;
|
||||
using OSMWayNegateForwardRange =
|
||||
boost::transformed_range<std::negate<OSMWayIDDir>, const OSMWayForwardRange>;
|
||||
using OSMWayReverseRange = boost::reversed_range<const OSMWayNegateForwardRange>;
|
||||
|
||||
using WeightForwardRange =
|
||||
boost::iterator_range<extractor::SegmentDataView::SegmentWeightVector::const_iterator>;
|
||||
using WeightReverseRange = boost::reversed_range<const WeightForwardRange>;
|
||||
@ -85,6 +91,10 @@ class BaseDataFacade
|
||||
|
||||
virtual ComponentID GetComponentID(const NodeID id) const = 0;
|
||||
|
||||
virtual OSMWayForwardRange GetUncompressedForwardWayIDs(const EdgeID id) const = 0;
|
||||
virtual OSMWayReverseRange GetUncompressedReverseWayIDs(const EdgeID id) const = 0;
|
||||
virtual bool GetUncompressedWayIDsSkipped() const = 0;
|
||||
|
||||
virtual NodeForwardRange GetUncompressedForwardGeometry(const EdgeID id) const = 0;
|
||||
virtual NodeReverseRange GetUncompressedReverseGeometry(const EdgeID id) const = 0;
|
||||
|
||||
|
||||
@ -100,6 +100,8 @@ inline LegGeometry assembleGeometry(const datafacade::BaseDataFacade &facade,
|
||||
path_point.datasource_id});
|
||||
geometry.locations.push_back(std::move(coordinate));
|
||||
geometry.osm_node_ids.push_back(osm_node_id);
|
||||
if (!facade.GetUncompressedWayIDsSkipped())
|
||||
geometry.osm_way_ids.push_back(path_point.osm_way_id);
|
||||
}
|
||||
}
|
||||
current_distance =
|
||||
@ -160,7 +162,20 @@ inline LegGeometry assembleGeometry(const datafacade::BaseDataFacade &facade,
|
||||
const auto target_geometry = facade.GetUncompressedForwardGeometry(target_geometry_id);
|
||||
geometry.osm_node_ids.push_back(
|
||||
facade.GetOSMNodeIDOfNode(target_geometry(target_segment_end_coordinate)));
|
||||
|
||||
if (!facade.GetUncompressedWayIDsSkipped())
|
||||
{
|
||||
if (reversed_target)
|
||||
{
|
||||
const auto target_osm_way_ids = facade.GetUncompressedReverseWayIDs(target_geometry_id);
|
||||
geometry.osm_way_ids.push_back(target_osm_way_ids(
|
||||
target_osm_way_ids.size() - target_node.fwd_segment_position - 1));
|
||||
}
|
||||
else
|
||||
{
|
||||
const auto target_osm_way_ids = facade.GetUncompressedForwardWayIDs(target_geometry_id);
|
||||
geometry.osm_way_ids.push_back(target_osm_way_ids(target_node.fwd_segment_position));
|
||||
}
|
||||
}
|
||||
BOOST_ASSERT(geometry.segment_distances.size() == geometry.segment_offsets.size() - 1);
|
||||
BOOST_ASSERT(geometry.locations.size() > geometry.segment_distances.size());
|
||||
BOOST_ASSERT(geometry.annotations.size() == geometry.locations.size() - 1);
|
||||
|
||||
@ -33,6 +33,8 @@ struct LegGeometry
|
||||
std::vector<double> segment_distances;
|
||||
// original OSM node IDs for each coordinate
|
||||
std::vector<OSMNodeID> osm_node_ids;
|
||||
// original OSM way IDs between every pair of nodes
|
||||
std::vector<OSMWayIDDir> osm_way_ids;
|
||||
|
||||
// Per-coordinate metadata
|
||||
struct Annotation
|
||||
|
||||
@ -26,6 +26,8 @@ struct PathData
|
||||
{
|
||||
// from edge-based-node id
|
||||
NodeID from_edge_based_node;
|
||||
// OSM Way ID of the edge immediately followed by via node
|
||||
OSMWayIDDir osm_way_id;
|
||||
// the internal OSRM id of the OSM node id that is the via node of the turn
|
||||
NodeID turn_via_node;
|
||||
// name of the street that leads to the turn
|
||||
|
||||
@ -144,6 +144,7 @@ void annotatePath(const FacadeT &facade,
|
||||
|
||||
// datastructures to hold extracted data from geometry
|
||||
std::vector<NodeID> id_vector;
|
||||
std::vector<OSMWayIDDir> osm_way_id_vector;
|
||||
std::vector<SegmentWeight> weight_vector;
|
||||
std::vector<SegmentDuration> duration_vector;
|
||||
std::vector<DatasourceID> datasource_vector;
|
||||
@ -157,6 +158,8 @@ void annotatePath(const FacadeT &facade,
|
||||
if (geometry_index.forward)
|
||||
{
|
||||
copy(id_vector, facade.GetUncompressedForwardGeometry(geometry_index.id));
|
||||
copy(osm_way_id_vector, facade.GetUncompressedForwardWayIDs(geometry_index.id));
|
||||
|
||||
copy(weight_vector, facade.GetUncompressedForwardWeights(geometry_index.id));
|
||||
copy(duration_vector, facade.GetUncompressedForwardDurations(geometry_index.id));
|
||||
copy(datasource_vector, facade.GetUncompressedForwardDatasources(geometry_index.id));
|
||||
@ -164,6 +167,8 @@ void annotatePath(const FacadeT &facade,
|
||||
else
|
||||
{
|
||||
copy(id_vector, facade.GetUncompressedReverseGeometry(geometry_index.id));
|
||||
copy(osm_way_id_vector, facade.GetUncompressedReverseWayIDs(geometry_index.id));
|
||||
|
||||
copy(weight_vector, facade.GetUncompressedReverseWeights(geometry_index.id));
|
||||
copy(duration_vector, facade.GetUncompressedReverseDurations(geometry_index.id));
|
||||
copy(datasource_vector, facade.GetUncompressedReverseDatasources(geometry_index.id));
|
||||
@ -189,6 +194,7 @@ void annotatePath(const FacadeT &facade,
|
||||
BOOST_ASSERT(datasource_vector.size() > 0);
|
||||
BOOST_ASSERT(weight_vector.size() + 1 == id_vector.size());
|
||||
BOOST_ASSERT(duration_vector.size() + 1 == id_vector.size());
|
||||
BOOST_ASSERT(!osm_way_id_vector.size() || osm_way_id_vector.size() + 1 == id_vector.size());
|
||||
|
||||
const bool is_first_segment = unpacked_path.empty();
|
||||
|
||||
@ -213,6 +219,7 @@ void annotatePath(const FacadeT &facade,
|
||||
{
|
||||
unpacked_path.push_back(
|
||||
PathData{*node_from,
|
||||
osm_way_id_vector.size() ? osm_way_id_vector[segment_idx] : 0,
|
||||
id_vector[segment_idx + 1],
|
||||
name_index,
|
||||
is_segregated,
|
||||
@ -288,6 +295,7 @@ void annotatePath(const FacadeT &facade,
|
||||
BOOST_ASSERT(facade.GetTravelMode(target_node_id) > 0);
|
||||
unpacked_path.push_back(
|
||||
PathData{target_node_id,
|
||||
osm_way_id_vector.size() ? osm_way_id_vector[segment_idx] : 0,
|
||||
id_vector[start_index < end_index ? segment_idx + 1 : segment_idx - 1],
|
||||
facade.GetNameIndex(target_node_id),
|
||||
facade.IsSegregated(target_node_id),
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
#ifndef GEOMETRY_COMPRESSOR_HPP_
|
||||
#define GEOMETRY_COMPRESSOR_HPP_
|
||||
|
||||
#include "extractor/node_based_edge.hpp"
|
||||
#include "extractor/segment_data_container.hpp"
|
||||
|
||||
#include "util/typedefs.hpp"
|
||||
@ -48,7 +49,9 @@ class CompressedEdgeContainer
|
||||
const SegmentWeight duration);
|
||||
|
||||
void InitializeBothwayVector();
|
||||
unsigned ZipEdges(const unsigned f_edge_pos, const unsigned r_edge_pos);
|
||||
unsigned ZipEdges(const unsigned f_edge_pos,
|
||||
const unsigned r_edge_pos,
|
||||
const OSMWayIDMap &osm_way_id_map);
|
||||
|
||||
bool HasEntryForID(const EdgeID edge_id) const;
|
||||
bool HasZippedEntryForForwardID(const EdgeID edge_id) const;
|
||||
|
||||
@ -63,6 +63,7 @@ class Extractor
|
||||
ExtractorConfig config;
|
||||
|
||||
std::tuple<LaneDescriptionMap,
|
||||
OSMWayIDMap,
|
||||
std::vector<TurnRestriction>,
|
||||
std::vector<UnresolvedManeuverOverride>>
|
||||
ParseOSMData(ScriptingEnvironment &scripting_environment, const unsigned number_of_threads);
|
||||
|
||||
@ -2,6 +2,7 @@
|
||||
#define EXTRACTOR_CALLBACKS_HPP
|
||||
|
||||
#include "extractor/class_data.hpp"
|
||||
#include "extractor/node_based_edge.hpp"
|
||||
#include "extractor/turn_lane_types.hpp"
|
||||
#include "util/typedefs.hpp"
|
||||
|
||||
|
||||
@ -70,7 +70,8 @@ struct ExtractorConfig final : storage::IOConfig
|
||||
".osrm.cnbg",
|
||||
".osrm.cnbg_to_ebg",
|
||||
".osrm.maneuver_overrides"}),
|
||||
requested_num_threads(0), parse_conditionals(false), use_locations_cache(true)
|
||||
requested_num_threads(0), parse_conditionals(false), use_locations_cache(true),
|
||||
skip_osm_ways(false)
|
||||
{
|
||||
}
|
||||
|
||||
@ -92,6 +93,7 @@ struct ExtractorConfig final : storage::IOConfig
|
||||
bool use_metadata;
|
||||
bool parse_conditionals;
|
||||
bool use_locations_cache;
|
||||
bool skip_osm_ways;
|
||||
};
|
||||
} // namespace extractor
|
||||
} // namespace osrm
|
||||
|
||||
@ -206,7 +206,9 @@ inline void readSegmentData(const boost::filesystem::path &path, SegmentDataT &s
|
||||
|
||||
// writes .osrm.geometry
|
||||
template <typename SegmentDataT>
|
||||
inline void writeSegmentData(const boost::filesystem::path &path, const SegmentDataT &segment_data)
|
||||
inline void writeSegmentData(const boost::filesystem::path &path,
|
||||
bool skip_osm_ways,
|
||||
const SegmentDataT &segment_data)
|
||||
{
|
||||
static_assert(std::is_same<SegmentDataContainer, SegmentDataT>::value ||
|
||||
std::is_same<SegmentDataView, SegmentDataT>::value,
|
||||
@ -214,7 +216,7 @@ inline void writeSegmentData(const boost::filesystem::path &path, const SegmentD
|
||||
const auto fingerprint = storage::tar::FileWriter::GenerateFingerprint;
|
||||
storage::tar::FileWriter writer{path, fingerprint};
|
||||
|
||||
serialization::write(writer, "/common/segment_data", segment_data);
|
||||
serialization::write(writer, "/common/segment_data", skip_osm_ways, segment_data);
|
||||
}
|
||||
|
||||
// reads .osrm.ebg_nodes
|
||||
|
||||
@ -60,10 +60,11 @@ struct InternalExtractorEdge
|
||||
|
||||
explicit InternalExtractorEdge(OSMNodeID source,
|
||||
OSMNodeID target,
|
||||
OSMWayID way,
|
||||
WeightData weight_data,
|
||||
DurationData duration_data,
|
||||
util::Coordinate source_coordinate)
|
||||
: result(source, target, 0, 0, 0, {}, -1, {}), weight_data(std::move(weight_data)),
|
||||
: result(source, target, way, 0, 0, 0, {}, -1, {}), weight_data(std::move(weight_data)),
|
||||
duration_data(std::move(duration_data)), source_coordinate(std::move(source_coordinate))
|
||||
{
|
||||
}
|
||||
|
||||
@ -2,6 +2,7 @@
|
||||
#define NODE_BASED_EDGE_HPP
|
||||
|
||||
#include <cstdint>
|
||||
#include <map>
|
||||
#include <tuple>
|
||||
|
||||
#include "extractor/class_data.hpp"
|
||||
@ -15,6 +16,12 @@ namespace osrm
|
||||
namespace extractor
|
||||
{
|
||||
|
||||
// Intermediate map to lookup OSMWayID by neighbor nbg node pair
|
||||
// while CompressedEdgeContainer::ZipEdges and store it in the segment data
|
||||
// to use when building found path annotations
|
||||
using OSMWayIDMapKey = std::pair<NodeID, NodeID>;
|
||||
using OSMWayIDMap = std::map<OSMWayIDMapKey, OSMWayIDDir>;
|
||||
|
||||
// Flags describing the class of the road. This data is used during creation of graphs/guidance
|
||||
// generation but is not available in annotation/navigation
|
||||
struct NodeBasedEdgeClassification
|
||||
@ -120,6 +127,7 @@ struct NodeBasedEdgeWithOSM : NodeBasedEdge
|
||||
|
||||
NodeBasedEdgeWithOSM(OSMNodeID source,
|
||||
OSMNodeID target,
|
||||
OSMWayID way,
|
||||
EdgeWeight weight,
|
||||
EdgeDuration duration,
|
||||
EdgeDistance distance,
|
||||
@ -129,6 +137,7 @@ struct NodeBasedEdgeWithOSM : NodeBasedEdge
|
||||
|
||||
OSMNodeID osm_source_id;
|
||||
OSMNodeID osm_target_id;
|
||||
OSMWayID osm_way_id;
|
||||
};
|
||||
|
||||
// Impl.
|
||||
@ -178,6 +187,7 @@ inline bool NodeBasedEdge::operator<(const NodeBasedEdge &other) const
|
||||
|
||||
inline NodeBasedEdgeWithOSM::NodeBasedEdgeWithOSM(OSMNodeID source,
|
||||
OSMNodeID target,
|
||||
OSMWayID way,
|
||||
EdgeWeight weight,
|
||||
EdgeDuration duration,
|
||||
EdgeDistance distance,
|
||||
@ -192,12 +202,12 @@ inline NodeBasedEdgeWithOSM::NodeBasedEdgeWithOSM(OSMNodeID source,
|
||||
geometry_id,
|
||||
annotation_data,
|
||||
flags),
|
||||
osm_source_id(std::move(source)), osm_target_id(std::move(target))
|
||||
osm_source_id(std::move(source)), osm_target_id(std::move(target)), osm_way_id(std::move(way))
|
||||
{
|
||||
}
|
||||
|
||||
inline NodeBasedEdgeWithOSM::NodeBasedEdgeWithOSM()
|
||||
: osm_source_id(MIN_OSM_NODEID), osm_target_id(MIN_OSM_NODEID)
|
||||
: osm_source_id(MIN_OSM_NODEID), osm_target_id(MIN_OSM_NODEID), osm_way_id(MIN_OSM_WAYID)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
@ -39,6 +39,7 @@ class NodeBasedGraphFactory
|
||||
// turn the graph into the routing graph to be used with the navigation algorithms.
|
||||
NodeBasedGraphFactory(const boost::filesystem::path &input_file,
|
||||
ScriptingEnvironment &scripting_environment,
|
||||
OSMWayIDMap &osm_way_id_map,
|
||||
std::vector<TurnRestriction> &turn_restrictions,
|
||||
std::vector<UnresolvedManeuverOverride> &maneuver_overrides);
|
||||
|
||||
@ -73,7 +74,7 @@ class NodeBasedGraphFactory
|
||||
// Most ways are bidirectional, making the geometry in forward and backward direction the same,
|
||||
// except for reversal. We make use of this fact by keeping only one representation of the
|
||||
// geometry around
|
||||
void CompressGeometry();
|
||||
void CompressGeometry(const OSMWayIDMap &osm_way_id_map);
|
||||
|
||||
// After graph compression, some of the annotation entries might not be referenced anymore. We
|
||||
// compress the annotation data by relabeling the node-based graph references and removing all
|
||||
|
||||
@ -10,10 +10,12 @@
|
||||
|
||||
#include <boost/filesystem/path.hpp>
|
||||
#include <boost/range/adaptor/reversed.hpp>
|
||||
#include <boost/range/adaptor/transformed.hpp>
|
||||
#include <boost/range/iterator_range.hpp>
|
||||
|
||||
#include <unordered_map>
|
||||
|
||||
#include <functional>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
@ -38,6 +40,7 @@ inline void read(storage::tar::FileReader &reader,
|
||||
template <storage::Ownership Ownership>
|
||||
inline void write(storage::tar::FileWriter &writer,
|
||||
const std::string &name,
|
||||
const bool skip_osm_ways,
|
||||
const detail::SegmentDataContainerImpl<Ownership> &segment_data);
|
||||
} // namespace serialization
|
||||
|
||||
@ -56,6 +59,7 @@ template <storage::Ownership Ownership> class SegmentDataContainerImpl
|
||||
using DirectionalGeometryID = std::uint32_t;
|
||||
using SegmentOffset = std::uint32_t;
|
||||
using SegmentNodeVector = Vector<NodeID>;
|
||||
using SegmentOSMWayVector = Vector<OSMWayIDDir>;
|
||||
using SegmentWeightVector = PackedVector<SegmentWeight, SEGMENT_WEIGHT_BITS>;
|
||||
using SegmentDurationVector = PackedVector<SegmentDuration, SEGMENT_DURATION_BITS>;
|
||||
using SegmentDatasourceVector = Vector<DatasourceID>;
|
||||
@ -64,16 +68,17 @@ template <storage::Ownership Ownership> class SegmentDataContainerImpl
|
||||
|
||||
SegmentDataContainerImpl(Vector<std::uint32_t> index_,
|
||||
SegmentNodeVector nodes_,
|
||||
SegmentOSMWayVector osm_ways_,
|
||||
SegmentWeightVector fwd_weights_,
|
||||
SegmentWeightVector rev_weights_,
|
||||
SegmentDurationVector fwd_durations_,
|
||||
SegmentDurationVector rev_durations_,
|
||||
SegmentDatasourceVector fwd_datasources_,
|
||||
SegmentDatasourceVector rev_datasources_)
|
||||
: index(std::move(index_)), nodes(std::move(nodes_)), fwd_weights(std::move(fwd_weights_)),
|
||||
rev_weights(std::move(rev_weights_)), fwd_durations(std::move(fwd_durations_)),
|
||||
rev_durations(std::move(rev_durations_)), fwd_datasources(std::move(fwd_datasources_)),
|
||||
rev_datasources(std::move(rev_datasources_))
|
||||
: index(std::move(index_)), nodes(std::move(nodes_)), osm_ways(std::move(osm_ways_)),
|
||||
fwd_weights(std::move(fwd_weights_)), rev_weights(std::move(rev_weights_)),
|
||||
fwd_durations(std::move(fwd_durations_)), rev_durations(std::move(rev_durations_)),
|
||||
fwd_datasources(std::move(fwd_datasources_)), rev_datasources(std::move(rev_datasources_))
|
||||
{
|
||||
}
|
||||
|
||||
@ -90,6 +95,20 @@ template <storage::Ownership Ownership> class SegmentDataContainerImpl
|
||||
return boost::adaptors::reverse(GetForwardGeometry(id));
|
||||
}
|
||||
|
||||
auto GetForwardOSMWayIDs(const DirectionalGeometryID id)
|
||||
{
|
||||
const auto begin = osm_ways.begin() + index[id];
|
||||
const auto end = osm_ways.begin() + index[id + 1] - 1;
|
||||
|
||||
return boost::make_iterator_range(begin, end);
|
||||
}
|
||||
|
||||
auto GetReverseOSMWayIDs(const DirectionalGeometryID id)
|
||||
{
|
||||
return boost::adaptors::reverse(
|
||||
boost::adaptors::transform(GetForwardOSMWayIDs(id), std::negate<OSMWayIDDir>()));
|
||||
}
|
||||
|
||||
auto GetForwardDurations(const DirectionalGeometryID id)
|
||||
{
|
||||
const auto begin = fwd_durations.begin() + index[id] + 1;
|
||||
@ -151,6 +170,22 @@ template <storage::Ownership Ownership> class SegmentDataContainerImpl
|
||||
return boost::adaptors::reverse(GetForwardGeometry(id));
|
||||
}
|
||||
|
||||
auto GetForwardOSMWayIDs(const DirectionalGeometryID id) const
|
||||
{
|
||||
if (GetOSMWaysSkipped())
|
||||
return boost::make_iterator_range(osm_ways.cend(), osm_ways.cend());
|
||||
const auto begin = osm_ways.cbegin() + index[id];
|
||||
const auto end = osm_ways.cbegin() + index[id + 1] - 1;
|
||||
|
||||
return boost::make_iterator_range(begin, end);
|
||||
}
|
||||
|
||||
auto GetReverseOSMWayIDs(const DirectionalGeometryID id) const
|
||||
{
|
||||
return boost::adaptors::reverse(
|
||||
boost::adaptors::transform(GetForwardOSMWayIDs(id), std::negate<OSMWayIDDir>()));
|
||||
}
|
||||
|
||||
auto GetForwardDurations(const DirectionalGeometryID id) const
|
||||
{
|
||||
const auto begin = fwd_durations.cbegin() + index[id] + 1;
|
||||
@ -201,6 +236,7 @@ template <storage::Ownership Ownership> class SegmentDataContainerImpl
|
||||
|
||||
auto GetNumberOfGeometries() const { return index.size() - 1; }
|
||||
auto GetNumberOfSegments() const { return fwd_weights.size(); }
|
||||
auto GetOSMWaysSkipped() const { return osm_ways.size() == 0; }
|
||||
|
||||
friend void
|
||||
serialization::read<Ownership>(storage::tar::FileReader &reader,
|
||||
@ -209,11 +245,13 @@ template <storage::Ownership Ownership> class SegmentDataContainerImpl
|
||||
friend void serialization::write<Ownership>(
|
||||
storage::tar::FileWriter &writer,
|
||||
const std::string &name,
|
||||
const bool skip_osm_ways,
|
||||
const detail::SegmentDataContainerImpl<Ownership> &segment_data);
|
||||
|
||||
private:
|
||||
Vector<std::uint32_t> index;
|
||||
SegmentNodeVector nodes;
|
||||
SegmentOSMWayVector osm_ways;
|
||||
SegmentWeightVector fwd_weights;
|
||||
SegmentWeightVector rev_weights;
|
||||
SegmentDurationVector fwd_durations;
|
||||
|
||||
@ -84,6 +84,7 @@ inline void read(storage::tar::FileReader &reader,
|
||||
{
|
||||
storage::serialization::read(reader, name + "/index", segment_data.index);
|
||||
storage::serialization::read(reader, name + "/nodes", segment_data.nodes);
|
||||
storage::serialization::read(reader, name + "/osm_ways", segment_data.osm_ways);
|
||||
util::serialization::read(reader, name + "/forward_weights", segment_data.fwd_weights);
|
||||
util::serialization::read(reader, name + "/reverse_weights", segment_data.rev_weights);
|
||||
util::serialization::read(reader, name + "/forward_durations", segment_data.fwd_durations);
|
||||
@ -97,10 +98,18 @@ inline void read(storage::tar::FileReader &reader,
|
||||
template <storage::Ownership Ownership>
|
||||
inline void write(storage::tar::FileWriter &writer,
|
||||
const std::string &name,
|
||||
const bool skip_osm_ways,
|
||||
const detail::SegmentDataContainerImpl<Ownership> &segment_data)
|
||||
{
|
||||
storage::serialization::write(writer, name + "/index", segment_data.index);
|
||||
storage::serialization::write(writer, name + "/nodes", segment_data.nodes);
|
||||
if (!skip_osm_ways)
|
||||
storage::serialization::write(writer, name + "/osm_ways", segment_data.osm_ways);
|
||||
else
|
||||
storage::serialization::write(
|
||||
writer,
|
||||
name + "/osm_ways",
|
||||
osrm::util::ViewOrVector<OSMWayIDDir, osrm::storage::Ownership::Container>());
|
||||
util::serialization::write(writer, name + "/forward_weights", segment_data.fwd_weights);
|
||||
util::serialization::write(writer, name + "/reverse_weights", segment_data.rev_weights);
|
||||
util::serialization::write(writer, name + "/forward_durations", segment_data.fwd_durations);
|
||||
|
||||
@ -762,6 +762,11 @@ inline bool parseCommonParameters(const v8::Local<v8::Object> &obj, ParamType &p
|
||||
params->annotations_type =
|
||||
params->annotations_type | osrm::RouteParameters::AnnotationsType::Nodes;
|
||||
}
|
||||
else if (annotations_str == "ways")
|
||||
{
|
||||
params->annotations_type =
|
||||
params->annotations_type | osrm::RouteParameters::AnnotationsType::Ways;
|
||||
}
|
||||
else if (annotations_str == "distance")
|
||||
{
|
||||
params->annotations_type =
|
||||
|
||||
@ -73,8 +73,8 @@ struct RouteParametersGrammar : public BaseParametersGrammar<Iterator, Signature
|
||||
"full", engine::api::RouteParameters::OverviewType::Full)(
|
||||
"false", engine::api::RouteParameters::OverviewType::False);
|
||||
|
||||
annotations_type.add("duration", AnnotationsType::Duration)("nodes",
|
||||
AnnotationsType::Nodes)(
|
||||
annotations_type.add("duration", AnnotationsType::Duration)(
|
||||
"nodes", AnnotationsType::Nodes)("ways", AnnotationsType::Ways)(
|
||||
"distance", AnnotationsType::Distance)("weight", AnnotationsType::Weight)(
|
||||
"datasources", AnnotationsType::Datasources)("speed", AnnotationsType::Speed);
|
||||
|
||||
|
||||
@ -134,6 +134,8 @@ inline auto make_segment_data_view(const SharedDataIndex &index, const std::stri
|
||||
|
||||
auto num_entries = index.GetBlockEntries(name + "/nodes");
|
||||
|
||||
auto osm_way_list = make_vector_view<OSMWayIDDir>(index, name + "/osm_ways");
|
||||
|
||||
extractor::SegmentDataView::SegmentWeightVector fwd_weight_list(
|
||||
make_vector_view<extractor::SegmentDataView::SegmentWeightVector::block_type>(
|
||||
index, name + "/forward_weights/packed"),
|
||||
@ -162,6 +164,7 @@ inline auto make_segment_data_view(const SharedDataIndex &index, const std::stri
|
||||
|
||||
return extractor::SegmentDataView{std::move(geometry_begin_indices),
|
||||
std::move(node_list),
|
||||
std::move(osm_way_list),
|
||||
std::move(fwd_weight_list),
|
||||
std::move(rev_weight_list),
|
||||
std::move(fwd_duration_list),
|
||||
|
||||
@ -53,6 +53,7 @@ using OSMNodeID = osrm::Alias<std::uint64_t, tag::osm_node_id>;
|
||||
static_assert(std::is_pod<OSMNodeID>(), "OSMNodeID is not a valid alias");
|
||||
using OSMWayID = osrm::Alias<std::uint64_t, tag::osm_way_id>;
|
||||
static_assert(std::is_pod<OSMWayID>(), "OSMWayID is not a valid alias");
|
||||
using OSMWayIDDir = std::int64_t;
|
||||
|
||||
using DuplicatedNodeID = std::uint64_t;
|
||||
using RestrictionID = std::uint64_t;
|
||||
|
||||
@ -281,6 +281,8 @@ void trimShortSegments(std::vector<RouteStep> &steps, LegGeometry &geometry)
|
||||
geometry.annotations.begin() + offset);
|
||||
geometry.osm_node_ids.erase(geometry.osm_node_ids.begin(),
|
||||
geometry.osm_node_ids.begin() + offset);
|
||||
geometry.osm_way_ids.erase(geometry.osm_way_ids.begin(),
|
||||
geometry.osm_way_ids.begin() + offset);
|
||||
}
|
||||
|
||||
auto const first_bearing = steps.front().maneuver.bearing_after;
|
||||
@ -378,6 +380,7 @@ void trimShortSegments(std::vector<RouteStep> &steps, LegGeometry &geometry)
|
||||
geometry.locations.resize(geometry.segment_offsets.back() + 1);
|
||||
geometry.annotations.resize(geometry.segment_offsets.back());
|
||||
geometry.osm_node_ids.resize(geometry.segment_offsets.back() + 1);
|
||||
geometry.osm_way_ids.resize(geometry.segment_offsets.back());
|
||||
|
||||
BOOST_ASSERT(geometry.segment_distances.back() <= 1);
|
||||
geometry.segment_distances.pop_back();
|
||||
@ -415,6 +418,7 @@ void trimShortSegments(std::vector<RouteStep> &steps, LegGeometry &geometry)
|
||||
geometry.locations.pop_back();
|
||||
geometry.annotations.pop_back();
|
||||
geometry.osm_node_ids.pop_back();
|
||||
geometry.osm_way_ids.pop_back();
|
||||
geometry.segment_offsets.back()--;
|
||||
// since the last geometry includes the location of arrival, the arrival instruction
|
||||
// geometry overlaps with the previous segment
|
||||
|
||||
@ -262,7 +262,9 @@ void CompressedEdgeContainer::InitializeBothwayVector()
|
||||
segment_data->rev_datasources.reserve(m_compressed_oneway_geometries.size());
|
||||
}
|
||||
|
||||
unsigned CompressedEdgeContainer::ZipEdges(const EdgeID f_edge_id, const EdgeID r_edge_id)
|
||||
unsigned CompressedEdgeContainer::ZipEdges(const EdgeID f_edge_id,
|
||||
const EdgeID r_edge_id,
|
||||
const OSMWayIDMap &osm_way_id_map)
|
||||
{
|
||||
if (!segment_data)
|
||||
InitializeBothwayVector();
|
||||
@ -279,7 +281,8 @@ unsigned CompressedEdgeContainer::ZipEdges(const EdgeID f_edge_id, const EdgeID
|
||||
segment_data->index.emplace_back(segment_data->nodes.size());
|
||||
|
||||
const auto &first_node = reverse_bucket.back();
|
||||
|
||||
auto prev_node_id = first_node.node_id;
|
||||
OSMWayIDDir osm_way_id = 0;
|
||||
constexpr DatasourceID LUA_SOURCE = 0;
|
||||
|
||||
segment_data->nodes.emplace_back(first_node.node_id);
|
||||
@ -290,6 +293,31 @@ unsigned CompressedEdgeContainer::ZipEdges(const EdgeID f_edge_id, const EdgeID
|
||||
segment_data->fwd_datasources.emplace_back(LUA_SOURCE);
|
||||
segment_data->rev_datasources.emplace_back(LUA_SOURCE);
|
||||
|
||||
auto store_way_id = [&](const NodeID prev_node_id, const NodeID node_id) {
|
||||
if (node_id != prev_node_id)
|
||||
{
|
||||
auto find_way_id = osm_way_id_map.find(OSMWayIDMapKey(prev_node_id, node_id));
|
||||
if (find_way_id != osm_way_id_map.cend())
|
||||
{
|
||||
segment_data->osm_ways.emplace_back(osm_way_id = find_way_id->second);
|
||||
util::Log(logDEBUG) << "zipped_geometry_id: " << zipped_geometry_id << " "
|
||||
<< prev_node_id << "->" << node_id << " = " << osm_way_id;
|
||||
}
|
||||
else
|
||||
{
|
||||
util::Log(logERROR)
|
||||
<< "OSM Way ID not found for (nbg) nodes, it should never be happened: "
|
||||
<< prev_node_id << "<-x->" << node_id;
|
||||
segment_data->osm_ways.emplace_back(osm_way_id);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Special case (artificial lighting signal edge)
|
||||
segment_data->osm_ways.emplace_back(osm_way_id);
|
||||
}
|
||||
};
|
||||
|
||||
for (std::size_t i = 0; i < forward_bucket.size() - 1; ++i)
|
||||
{
|
||||
const auto &fwd_node = forward_bucket.at(i);
|
||||
@ -297,6 +325,10 @@ unsigned CompressedEdgeContainer::ZipEdges(const EdgeID f_edge_id, const EdgeID
|
||||
|
||||
BOOST_ASSERT(fwd_node.node_id == rev_node.node_id);
|
||||
|
||||
auto node_id = fwd_node.node_id;
|
||||
|
||||
store_way_id(prev_node_id, node_id);
|
||||
|
||||
segment_data->nodes.emplace_back(fwd_node.node_id);
|
||||
segment_data->fwd_weights.emplace_back(fwd_node.weight);
|
||||
segment_data->rev_weights.emplace_back(rev_node.weight);
|
||||
@ -304,9 +336,16 @@ unsigned CompressedEdgeContainer::ZipEdges(const EdgeID f_edge_id, const EdgeID
|
||||
segment_data->rev_durations.emplace_back(rev_node.duration);
|
||||
segment_data->fwd_datasources.emplace_back(LUA_SOURCE);
|
||||
segment_data->rev_datasources.emplace_back(LUA_SOURCE);
|
||||
prev_node_id = node_id;
|
||||
}
|
||||
|
||||
const auto &last_node = forward_bucket.back();
|
||||
auto node_id = last_node.node_id;
|
||||
store_way_id(prev_node_id, node_id);
|
||||
|
||||
// Make osm_ways vector size the same as
|
||||
// nodes vector size to use index vector for the both
|
||||
segment_data->osm_ways.emplace_back(osm_way_id);
|
||||
|
||||
segment_data->nodes.emplace_back(last_node.node_id);
|
||||
segment_data->fwd_weights.emplace_back(last_node.weight);
|
||||
|
||||
@ -215,9 +215,10 @@ int Extractor::run(ScriptingEnvironment &scripting_environment)
|
||||
#endif
|
||||
|
||||
LaneDescriptionMap turn_lane_map;
|
||||
OSMWayIDMap osm_way_id_map;
|
||||
std::vector<TurnRestriction> turn_restrictions;
|
||||
std::vector<UnresolvedManeuverOverride> unresolved_maneuver_overrides;
|
||||
std::tie(turn_lane_map, turn_restrictions, unresolved_maneuver_overrides) =
|
||||
std::tie(turn_lane_map, osm_way_id_map, turn_restrictions, unresolved_maneuver_overrides) =
|
||||
ParseOSMData(scripting_environment, number_of_threads);
|
||||
|
||||
// Transform the node-based graph that OSM is based on into an edge-based graph
|
||||
@ -238,6 +239,7 @@ int Extractor::run(ScriptingEnvironment &scripting_environment)
|
||||
// Create a node-based graph from the OSRM file
|
||||
NodeBasedGraphFactory node_based_graph_factory(config.GetPath(".osrm"),
|
||||
scripting_environment,
|
||||
osm_way_id_map,
|
||||
turn_restrictions,
|
||||
unresolved_maneuver_overrides);
|
||||
|
||||
@ -319,6 +321,7 @@ int Extractor::run(ScriptingEnvironment &scripting_environment)
|
||||
// output the geometry of the node-based graph, needs to be done after the last usage, since it
|
||||
// destroys internal containers
|
||||
files::writeSegmentData(config.GetPath(".osrm.geometry"),
|
||||
config.skip_osm_ways,
|
||||
*node_based_graph_factory.GetCompressedEdges().ToSegmentData());
|
||||
|
||||
util::Log() << "Saving edge-based node weights to file.";
|
||||
@ -368,10 +371,12 @@ int Extractor::run(ScriptingEnvironment &scripting_environment)
|
||||
return 0;
|
||||
}
|
||||
|
||||
std::
|
||||
tuple<LaneDescriptionMap, std::vector<TurnRestriction>, std::vector<UnresolvedManeuverOverride>>
|
||||
Extractor::ParseOSMData(ScriptingEnvironment &scripting_environment,
|
||||
const unsigned number_of_threads)
|
||||
std::tuple<LaneDescriptionMap,
|
||||
OSMWayIDMap,
|
||||
std::vector<TurnRestriction>,
|
||||
std::vector<UnresolvedManeuverOverride>>
|
||||
Extractor::ParseOSMData(ScriptingEnvironment &scripting_environment,
|
||||
const unsigned number_of_threads)
|
||||
{
|
||||
TIMER_START(extracting);
|
||||
|
||||
@ -420,6 +425,7 @@ std::
|
||||
ExtractionContainers extraction_containers;
|
||||
ExtractorCallbacks::ClassesMap classes_map;
|
||||
LaneDescriptionMap turn_lane_map;
|
||||
OSMWayIDMap osm_way_id_map;
|
||||
auto extractor_callbacks =
|
||||
std::make_unique<ExtractorCallbacks>(extraction_containers,
|
||||
classes_map,
|
||||
@ -626,10 +632,42 @@ std::
|
||||
SetExcludableClasses(classes_map, excludable_classes, profile_properties);
|
||||
files::writeProfileProperties(config.GetPath(".osrm.properties").string(), profile_properties);
|
||||
|
||||
// Fill OSM Way ID Lookup Map to use it later
|
||||
for (auto edge : extraction_containers.all_edges_list)
|
||||
{
|
||||
OSMWayIDDir way_id = edge.result.osm_way_id.__value;
|
||||
OSMNodeID osm_source_id = edge.result.osm_source_id;
|
||||
OSMNodeID osm_target_id = edge.result.osm_target_id;
|
||||
if ((edge.result.source < edge.result.target && osm_source_id > osm_target_id) ||
|
||||
(edge.result.source > edge.result.target && osm_source_id < osm_target_id))
|
||||
{
|
||||
// Bogus criteria?
|
||||
way_id = -way_id;
|
||||
std::swap(osm_source_id, osm_target_id);
|
||||
}
|
||||
if (edge.result.flags.forward)
|
||||
{
|
||||
osm_way_id_map[OSMWayIDMapKey(edge.result.source, edge.result.target)] = way_id;
|
||||
util::Log(logDEBUG)
|
||||
<< "osm_way_id_map: " << edge.result.source << "->" << edge.result.target << " = "
|
||||
<< osm_way_id_map[OSMWayIDMapKey(edge.result.source, edge.result.target)] << " ("
|
||||
<< osm_source_id << "->" << osm_target_id << ")";
|
||||
}
|
||||
if (edge.result.flags.backward)
|
||||
{
|
||||
osm_way_id_map[OSMWayIDMapKey(edge.result.target, edge.result.source)] = -way_id;
|
||||
util::Log(logDEBUG)
|
||||
<< "osm_way_id_map: " << edge.result.target << "->" << edge.result.source << " = "
|
||||
<< osm_way_id_map[OSMWayIDMapKey(edge.result.target, edge.result.source)] << " ("
|
||||
<< osm_target_id << "->" << osm_source_id << ")";
|
||||
}
|
||||
}
|
||||
|
||||
TIMER_STOP(extracting);
|
||||
util::Log() << "extraction finished after " << TIMER_SEC(extracting) << "s";
|
||||
|
||||
return std::make_tuple(std::move(turn_lane_map),
|
||||
std::move(osm_way_id_map),
|
||||
std::move(extraction_containers.turn_restrictions),
|
||||
std::move(extraction_containers.internal_maneuver_overrides));
|
||||
}
|
||||
|
||||
@ -409,6 +409,7 @@ void ExtractorCallbacks::ProcessWay(const osmium::Way &input_way, const Extracti
|
||||
NodeBasedEdgeWithOSM edge = {
|
||||
OSMNodeID{static_cast<std::uint64_t>(first_node.ref())},
|
||||
OSMNodeID{static_cast<std::uint64_t>(last_node.ref())},
|
||||
OSMWayID{static_cast<std::uint64_t>(input_way.id())},
|
||||
0, // weight
|
||||
0, // duration
|
||||
0, // distance
|
||||
@ -445,6 +446,7 @@ void ExtractorCallbacks::ProcessWay(const osmium::Way &input_way, const Extracti
|
||||
NodeBasedEdgeWithOSM edge = {
|
||||
OSMNodeID{static_cast<std::uint64_t>(first_node.ref())},
|
||||
OSMNodeID{static_cast<std::uint64_t>(last_node.ref())},
|
||||
OSMWayID{static_cast<std::uint64_t>(input_way.id())},
|
||||
0, // weight
|
||||
0, // duration
|
||||
0, // distance
|
||||
|
||||
@ -18,12 +18,13 @@ namespace extractor
|
||||
NodeBasedGraphFactory::NodeBasedGraphFactory(
|
||||
const boost::filesystem::path &input_file,
|
||||
ScriptingEnvironment &scripting_environment,
|
||||
OSMWayIDMap &osm_way_id_map,
|
||||
std::vector<TurnRestriction> &turn_restrictions,
|
||||
std::vector<UnresolvedManeuverOverride> &maneuver_overrides)
|
||||
{
|
||||
LoadDataFromFile(input_file);
|
||||
Compress(scripting_environment, turn_restrictions, maneuver_overrides);
|
||||
CompressGeometry();
|
||||
CompressGeometry(osm_way_id_map);
|
||||
CompressAnnotationData();
|
||||
}
|
||||
|
||||
@ -93,7 +94,7 @@ void NodeBasedGraphFactory::Compress(ScriptingEnvironment &scripting_environment
|
||||
compressed_edge_container);
|
||||
}
|
||||
|
||||
void NodeBasedGraphFactory::CompressGeometry()
|
||||
void NodeBasedGraphFactory::CompressGeometry(const OSMWayIDMap &osm_way_id_map)
|
||||
{
|
||||
for (const auto nbg_node_u : util::irange(0u, compressed_output_graph.GetNumberOfNodes()))
|
||||
{
|
||||
@ -126,7 +127,8 @@ void NodeBasedGraphFactory::CompressGeometry()
|
||||
const EdgeID edge_id_2 = compressed_output_graph.FindEdge(to, from);
|
||||
BOOST_ASSERT(edge_id_2 != SPECIAL_EDGEID);
|
||||
|
||||
auto packed_geometry_id = compressed_edge_container.ZipEdges(edge_id_1, edge_id_2);
|
||||
auto packed_geometry_id =
|
||||
compressed_edge_container.ZipEdges(edge_id_1, edge_id_2, osm_way_id_map);
|
||||
|
||||
// remember the geometry ID for both edges in the node-based graph
|
||||
compressed_output_graph.GetEdgeData(edge_id_1).geometry_id = {packed_geometry_id, true};
|
||||
|
||||
@ -74,7 +74,12 @@ return_code parseArguments(int argc,
|
||||
boost::program_options::bool_switch(&extractor_config.use_locations_cache)
|
||||
->implicit_value(false)
|
||||
->default_value(true),
|
||||
"Use internal nodes locations cache for location-dependent data lookups");
|
||||
"Use internal nodes locations cache for location-dependent data lookups")(
|
||||
"skip-osm-ways",
|
||||
boost::program_options::bool_switch(&extractor_config.skip_osm_ways)
|
||||
->implicit_value(true)
|
||||
->default_value(false),
|
||||
"Skip OSM Way IDs in annotations");
|
||||
|
||||
bool dummy;
|
||||
// hidden options, will be allowed on command line, but will not be
|
||||
|
||||
@ -623,7 +623,8 @@ Updater::LoadAndUpdateEdgeExpandedGraph(std::vector<extractor::EdgeBasedEdge> &e
|
||||
coordinates,
|
||||
osm_node_ids);
|
||||
// Now save out the updated compressed geometries
|
||||
extractor::files::writeSegmentData(config.GetPath(".osrm.geometry"), segment_data);
|
||||
extractor::files::writeSegmentData(
|
||||
config.GetPath(".osrm.geometry"), segment_data.GetOSMWaysSkipped(), segment_data);
|
||||
TIMER_STOP(segment);
|
||||
util::Log() << "Updating segment data took " << TIMER_MSEC(segment) << "ms.";
|
||||
}
|
||||
|
||||
@ -19,8 +19,8 @@ BOOST_AUTO_TEST_CASE(unchanged_collapse_route_result)
|
||||
PhantomNode target;
|
||||
source.forward_segment_id = {1, true};
|
||||
target.forward_segment_id = {6, true};
|
||||
PathData pathy{0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData pathy{0, 0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
InternalRouteResult one_leg_result;
|
||||
one_leg_result.unpacked_path_segments = {{pathy, kathy}};
|
||||
one_leg_result.segment_end_coordinates = {PhantomNodes{source, target}};
|
||||
@ -41,9 +41,9 @@ BOOST_AUTO_TEST_CASE(two_legs_to_one_leg)
|
||||
// weight_of_turn,
|
||||
// duration_until_turn, duration_of_turn, turn_instruction, lane_data, travel_mode, classes,
|
||||
// entry_class, datasource_id, pre_turn_bearing, post_turn_bearing, left_hand
|
||||
PathData pathy{0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData cathy{0, 3, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData pathy{0, 0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData cathy{0, 0, 3, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PhantomNode node_1;
|
||||
PhantomNode node_2;
|
||||
PhantomNode node_3;
|
||||
@ -73,11 +73,11 @@ BOOST_AUTO_TEST_CASE(two_legs_to_one_leg)
|
||||
|
||||
BOOST_AUTO_TEST_CASE(three_legs_to_two_legs)
|
||||
{
|
||||
PathData pathy{0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData qathy{0, 5, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData cathy{0, 3, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData mathy{0, 4, 18, false, 8, 9, 13, 4, 2, {}, 4, 2, {}, 2, {3.0}, {1.0}, false};
|
||||
PathData pathy{0, 0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData qathy{0, 0, 5, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData cathy{0, 0, 3, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData mathy{0, 0, 4, 18, false, 8, 9, 13, 4, 2, {}, 4, 2, {}, 2, {3.0}, {1.0}, false};
|
||||
PhantomNode node_1;
|
||||
PhantomNode node_2;
|
||||
PhantomNode node_3;
|
||||
@ -117,9 +117,9 @@ BOOST_AUTO_TEST_CASE(three_legs_to_two_legs)
|
||||
|
||||
BOOST_AUTO_TEST_CASE(two_legs_to_two_legs)
|
||||
{
|
||||
PathData pathy{0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData cathy{0, 3, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData pathy{0, 0, 2, 17, false, 2, 3, 4, 5, 0, {}, 4, 2, {}, 2, {1.0}, {1.0}, false};
|
||||
PathData kathy{0, 0, 1, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PathData cathy{0, 0, 3, 16, false, 1, 2, 3, 4, 1, {}, 3, 1, {}, 1, {2.0}, {3.0}, false};
|
||||
PhantomNode node_1;
|
||||
PhantomNode node_2;
|
||||
PhantomNode node_3;
|
||||
|
||||
@ -166,6 +166,18 @@ class ContiguousInternalMemoryDataFacade<routing_algorithms::offline::Algorithm>
|
||||
return NodeReverseRange(NodeForwardRange());
|
||||
}
|
||||
|
||||
OSMWayForwardRange GetUncompressedForwardWayIDs(const EdgeID /*id*/) const override
|
||||
{
|
||||
return {};
|
||||
}
|
||||
bool GetUncompressedWayIDsSkipped() const override { return true; }
|
||||
|
||||
OSMWayReverseRange GetUncompressedReverseWayIDs(const EdgeID id) const override
|
||||
{
|
||||
return boost::adaptors::reverse(boost::adaptors::transform(GetUncompressedForwardWayIDs(id),
|
||||
std::negate<OSMWayIDDir>()));
|
||||
}
|
||||
|
||||
TurnPenalty GetWeightPenaltyForEdgeID(const unsigned /*id*/) const override
|
||||
{
|
||||
return INVALID_TURN_PENALTY;
|
||||
|
||||
@ -14,6 +14,12 @@
|
||||
#include "osrm/osrm.hpp"
|
||||
#include "osrm/route_parameters.hpp"
|
||||
#include "osrm/status.hpp"
|
||||
#include <osmium/handler.hpp>
|
||||
#include <osmium/io/pbf_input.hpp>
|
||||
#include <osmium/io/reader.hpp>
|
||||
#include <osmium/osm/node.hpp>
|
||||
#include <osmium/osm/way.hpp>
|
||||
#include <osmium/visitor.hpp>
|
||||
|
||||
osrm::Status run_route_json(const osrm::OSRM &osrm,
|
||||
const osrm::RouteParameters ¶ms,
|
||||
@ -584,7 +590,7 @@ void test_manual_setting_of_annotations_property(bool use_json_only_api)
|
||||
.values["annotation"]
|
||||
.get<json::Object>()
|
||||
.values;
|
||||
BOOST_CHECK_EQUAL(annotations.size(), 6);
|
||||
BOOST_CHECK_EQUAL(annotations.size(), 7);
|
||||
}
|
||||
BOOST_AUTO_TEST_CASE(test_manual_setting_of_annotations_property_old_api)
|
||||
{
|
||||
@ -595,6 +601,158 @@ BOOST_AUTO_TEST_CASE(test_manual_setting_of_annotations_property_new_api)
|
||||
test_manual_setting_of_annotations_property(false);
|
||||
}
|
||||
|
||||
using NodePair = std::pair<osmium::unsigned_object_id_type, osmium::unsigned_object_id_type>;
|
||||
using NodePairToWayIDMap = std::map<NodePair, int64_t>;
|
||||
|
||||
NodePairToWayIDMap read_node_pair_to_way_id_map(osmium::io::Reader &osm)
|
||||
{
|
||||
struct H : public osmium::handler::Handler
|
||||
{
|
||||
NodePairToWayIDMap ret;
|
||||
void way(const osmium::Way &way)
|
||||
{
|
||||
osmium::unsigned_object_id_type first = 0;
|
||||
for (const auto &n : way.nodes())
|
||||
{
|
||||
const auto second = n.positive_ref();
|
||||
if (first != 0)
|
||||
{
|
||||
ret[{first, second}] = way.id();
|
||||
}
|
||||
first = second;
|
||||
}
|
||||
}
|
||||
} handler;
|
||||
osmium::apply(osm, handler);
|
||||
return std::move(handler.ret);
|
||||
}
|
||||
|
||||
using LonLat = std::pair<float, float>;
|
||||
using LonLatVector = std::vector<LonLat>;
|
||||
|
||||
LonLatVector check_route_annotated_ways(std::vector<osrm::util::Coordinate> &coordinates,
|
||||
osrm::OSRM &osrm,
|
||||
NodePairToWayIDMap &node_pair_to_way_id_map,
|
||||
bool use_steps)
|
||||
{
|
||||
LonLatVector ret;
|
||||
using namespace osrm;
|
||||
(void)node_pair_to_way_id_map;
|
||||
RouteParameters params{};
|
||||
params.annotations_type =
|
||||
RouteParameters::AnnotationsType::Nodes | RouteParameters::AnnotationsType::Ways;
|
||||
params.steps = use_steps;
|
||||
params.geometries = engine::api::RouteParameters::GeometriesType::GeoJSON;
|
||||
params.coordinates = coordinates;
|
||||
|
||||
json::Object json_result;
|
||||
const auto rc = run_route_json(osrm, params, json_result, true);
|
||||
BOOST_CHECK(rc == Status::Ok);
|
||||
|
||||
const auto code = json_result.values.at("code").get<json::String>().value;
|
||||
BOOST_CHECK_EQUAL(code, "Ok");
|
||||
|
||||
auto routes = json_result.values["routes"].get<json::Array>().values;
|
||||
BOOST_CHECK_EQUAL(routes.size(), 1);
|
||||
auto route = routes[0];
|
||||
|
||||
auto geom = route.get<json::Object>()
|
||||
.values["geometry"]
|
||||
.get<json::Object>()
|
||||
.values["coordinates"]
|
||||
.get<json::Array>()
|
||||
.values;
|
||||
|
||||
auto legs = route.get<json::Object>().values["legs"].get<json::Array>().values;
|
||||
for (auto leg : legs)
|
||||
{
|
||||
if (use_steps)
|
||||
{
|
||||
auto steps = leg.get<json::Object>().values["steps"].get<json::Array>().values;
|
||||
for (auto step : steps)
|
||||
{
|
||||
auto geom = step.get<json::Object>()
|
||||
.values["geometry"]
|
||||
.get<json::Object>()
|
||||
.values["coordinates"]
|
||||
.get<json::Array>()
|
||||
.values;
|
||||
for (auto gleg : geom)
|
||||
{
|
||||
auto p = gleg.get<json::Array>().values;
|
||||
auto lon = p[0].get<json::Number>().value;
|
||||
auto lat = p[1].get<json::Number>().value;
|
||||
ret.push_back(LonLat{lon, lat});
|
||||
}
|
||||
}
|
||||
}
|
||||
auto annotations = leg.get<json::Object>().values["annotation"].get<json::Object>().values;
|
||||
BOOST_CHECK_EQUAL(annotations.size(), 2);
|
||||
|
||||
auto nodes = annotations["nodes"].get<json::Array>().values;
|
||||
auto ways = annotations["ways"].get<json::Array>().values;
|
||||
|
||||
BOOST_CHECK_GT(nodes.size(), 1);
|
||||
BOOST_CHECK_EQUAL(nodes.size() - 1, ways.size());
|
||||
auto nodes_it = nodes.cbegin();
|
||||
auto ways_it = ways.cbegin();
|
||||
osmium::unsigned_object_id_type first = nodes_it->get<json::Number>().value;
|
||||
for (nodes_it++; nodes_it != nodes.cend(); nodes_it++, ways_it++)
|
||||
{
|
||||
osmium::unsigned_object_id_type second = nodes_it->get<json::Number>().value;
|
||||
int64_t way_id = ways_it->get<json::Number>().value;
|
||||
auto found = node_pair_to_way_id_map.find(NodePair(first, second));
|
||||
auto reverse = false;
|
||||
if (found == node_pair_to_way_id_map.end())
|
||||
{
|
||||
reverse = true;
|
||||
found = node_pair_to_way_id_map.find(NodePair(second, first));
|
||||
}
|
||||
BOOST_CHECK_MESSAGE(found != node_pair_to_way_id_map.end(),
|
||||
"The node pair not found: " << first << "<->" << second);
|
||||
int64_t found_way_id = reverse ? -found->second : found->second;
|
||||
BOOST_CHECK_MESSAGE(found_way_id == way_id,
|
||||
"The node pair way doesn't correspond: " << first << "<->" << second
|
||||
<< "=" << found_way_id
|
||||
<< "=?=" << way_id);
|
||||
first = second;
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE(test_route_annotated_ways)
|
||||
{
|
||||
auto osrm = getOSRM(OSRM_TEST_DATA_DIR "/ch/monaco.osrm");
|
||||
osmium::io::Reader osm(OSRM_TEST_DATA_DIR "/monaco.osm.pbf");
|
||||
NodePairToWayIDMap node_pair_to_way_id_map = read_node_pair_to_way_id_map(osm);
|
||||
|
||||
auto coordinates = get_split_trace_locations();
|
||||
BOOST_TEST_MESSAGE("split_trace_locations without steps");
|
||||
check_route_annotated_ways(coordinates, osrm, node_pair_to_way_id_map, false);
|
||||
BOOST_TEST_MESSAGE("split_trace_locations with steps");
|
||||
check_route_annotated_ways(coordinates, osrm, node_pair_to_way_id_map, true);
|
||||
coordinates = get_locations_in_big_component();
|
||||
BOOST_TEST_MESSAGE("locations_in_big_component without steps");
|
||||
check_route_annotated_ways(coordinates, osrm, node_pair_to_way_id_map, false);
|
||||
BOOST_TEST_MESSAGE("locations_in_big_component with steps");
|
||||
auto coords = check_route_annotated_ways(coordinates, osrm, node_pair_to_way_id_map, true);
|
||||
auto c1 = coords.cbegin(), c2 = coords.cend();
|
||||
for (c1++, c2--; c1 != coords.cend() && c2 != coords.cbegin(); c1++, c2--)
|
||||
{
|
||||
if (c1 == c2)
|
||||
continue;
|
||||
coordinates = Locations{{Longitude{c1->first}, Latitude{c1->second}},
|
||||
{Longitude{c2->first}, Latitude{c2->second}}};
|
||||
BOOST_TEST_MESSAGE("Checking: <" << osrm::util::toFloating(coordinates[0].lat) << ":"
|
||||
<< osrm::util::toFloating(coordinates[0].lon) << "> -> <"
|
||||
<< osrm::util::toFloating(coordinates[1].lat) << ":"
|
||||
<< osrm::util::toFloating(coordinates[1].lon) << ">");
|
||||
check_route_annotated_ways(coordinates, osrm, node_pair_to_way_id_map, false);
|
||||
check_route_annotated_ways(coordinates, osrm, node_pair_to_way_id_map, true);
|
||||
}
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE(test_route_serialize_fb)
|
||||
{
|
||||
auto osrm = getOSRM(OSRM_TEST_DATA_DIR "/ch/monaco.osrm");
|
||||
|
||||
@ -64,6 +64,18 @@ class MockBaseDataFacade : public engine::datafacade::BaseDataFacade
|
||||
{
|
||||
return NodeReverseRange(GetUncompressedForwardGeometry(id));
|
||||
}
|
||||
OSMWayForwardRange GetUncompressedForwardWayIDs(const EdgeID /* id */) const override
|
||||
{
|
||||
static OSMWayIDDir data[] = {0, 1, 2, 3};
|
||||
static extractor::SegmentDataView::SegmentOSMWayVector ways(data, 4);
|
||||
return boost::make_iterator_range(ways.cbegin(), ways.cend());
|
||||
}
|
||||
bool GetUncompressedWayIDsSkipped() const override { return false; }
|
||||
OSMWayReverseRange GetUncompressedReverseWayIDs(const EdgeID id) const override
|
||||
{
|
||||
return boost::adaptors::reverse(boost::adaptors::transform(GetUncompressedForwardWayIDs(id),
|
||||
std::negate<OSMWayIDDir>()));
|
||||
}
|
||||
WeightForwardRange GetUncompressedForwardWeights(const EdgeID /* id */) const override
|
||||
{
|
||||
static std::uint64_t data[] = {1, 2, 3};
|
||||
|
||||
Loading…
Reference in New Issue
Block a user