@@ -428,6 +428,12 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
428428 const auto &edge = edges[edge_index];
429429 const auto geometry_id = get_geometry_id (edge);
430430
431+ // Get coordinates for start/end nodes of segment (NodeIDs u and v)
432+ const auto a = facade.GetCoordinateOfNode (edge.u );
433+ const auto b = facade.GetCoordinateOfNode (edge.v );
434+ // Calculate the length in meters
435+ const double length = osrm::util::coordinate_calculation::haversineDistance (a, b);
436+
431437 // Weight values
432438 const auto forward_weight_vector =
433439 facade.GetUncompressedForwardWeights (geometry_id);
@@ -439,6 +445,14 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
439445 use_line_value (forward_weight);
440446 use_line_value (reverse_weight);
441447
448+ std::uint32_t forward_rate =
449+ static_cast <std::uint32_t >(round (length / forward_weight * 10 .));
450+ std::uint32_t reverse_rate =
451+ static_cast <std::uint32_t >(round (length / reverse_weight * 10 .));
452+
453+ use_line_value (forward_rate);
454+ use_line_value (reverse_rate);
455+
442456 // Duration values
443457 const auto forward_duration_vector =
444458 facade.GetUncompressedForwardDurations (geometry_id);
@@ -489,9 +503,9 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
489503 const auto reverse_duration =
490504 reverse_duration_vector[reverse_duration_vector.size () -
491505 edge.fwd_segment_position - 1 ];
492- const auto forward_datasource =
506+ const auto forward_datasource_idx =
493507 forward_datasource_vector[edge.fwd_segment_position ];
494- const auto reverse_datasource =
508+ const auto reverse_datasource_idx =
495509 reverse_datasource_vector[reverse_datasource_vector.size () -
496510 edge.fwd_segment_position - 1 ];
497511
@@ -516,14 +530,16 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
516530 &component_id,
517531 &id,
518532 &max_datasource_id,
519- &used_line_ints](const FixedLine &tile_line,
520- const std::uint32_t speed_kmh,
521- const std::size_t weight,
522- const std::size_t duration,
523- const DatasourceID datasource,
524- const std::size_t name_idx,
525- std::int32_t &start_x,
526- std::int32_t &start_y) {
533+ &used_line_ints](
534+ const FixedLine &tile_line,
535+ const std::uint32_t speed_kmh_idx,
536+ const std::uint32_t rate_idx,
537+ const std::size_t weight_idx,
538+ const std::size_t duration_idx,
539+ const DatasourceID datasource_idx,
540+ const std::size_t name_idx,
541+ std::int32_t &start_x,
542+ std::int32_t &start_y) {
527543 // Here, we save the two attributes for our feature: the speed and
528544 // the is_small boolean. We only serve up speeds from 0-139, so all we
529545 // do is save the first
@@ -547,23 +563,27 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
547563 feature_writer, util::vector_tile::FEATURE_ATTRIBUTES_TAG);
548564
549565 field.add_element (0 ); // "speed" tag key offset
566+ field.add_element (std::min (
567+ speed_kmh_idx, 127u )); // save the speed value, capped at 127
568+ field.add_element (1 ); // "is_small" tag key offset
550569 field.add_element (
551- std::min (speed_kmh, 127u )); // save the speed value, capped at 127
552- field.add_element (1 ); // "is_small" tag key offset
553- field.add_element (128 +
554- (component_id.is_tiny ? 0 : 1 )); // is_small feature
555- field.add_element (2 ); // "datasource" tag key offset
556- field.add_element (130 + datasource); // datasource value offset
557- field.add_element (3 ); // "weight" tag key offset
570+ 128 + (component_id.is_tiny ? 0 : 1 )); // is_small feature offset
571+ field.add_element (2 ); // "datasource" tag key offset
572+ field.add_element (130 + datasource_idx); // datasource value offset
573+ field.add_element (3 ); // "weight" tag key offset
558574 field.add_element (130 + max_datasource_id + 1 +
559- weight ); // weight value offset
560- field.add_element (4 ); // "duration" tag key offset
575+ weight_idx ); // weight value offset
576+ field.add_element (4 ); // "duration" tag key offset
561577 field.add_element (130 + max_datasource_id + 1 +
562- duration ); // duration value offset
563- field.add_element (5 ); // "name" tag key offset
578+ duration_idx ); // duration value offset
579+ field.add_element (5 ); // "name" tag key offset
564580
565581 field.add_element (130 + max_datasource_id + 1 + used_line_ints.size () +
566582 name_idx); // name value offset
583+
584+ field.add_element (6 ); // rate tag key offset
585+ field.add_element (130 + max_datasource_id + 1 +
586+ rate_idx); // rate goes in used_line_ints
567587 }
568588 {
569589
@@ -581,17 +601,26 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
581601 std::int32_t start_y = 0 ;
582602
583603 // Calculate the speed for this line
584- std::uint32_t speed_kmh =
604+ // Speeds are looked up in a simple 1:1 table, so the speed value == lookup
605+ // table index
606+ std::uint32_t speed_kmh_idx =
585607 static_cast <std::uint32_t >(round (length / forward_duration * 10 * 3.6 ));
586608
609+ // Rate values are in meters per weight-unit - and similar to speeds, we
610+ // present 1 decimal place of precision (these values are added as
611+ // double/10) lower down
612+ std::uint32_t forward_rate =
613+ static_cast <std::uint32_t >(round (length / forward_weight * 10 .));
614+
587615 auto tile_line = coordinatesToTileLine (a, b, tile_bbox);
588616 if (!tile_line.empty ())
589617 {
590618 encode_tile_line (tile_line,
591- speed_kmh,
619+ speed_kmh_idx,
620+ line_int_offsets[forward_rate],
592621 line_int_offsets[forward_weight],
593622 line_int_offsets[forward_duration],
594- forward_datasource ,
623+ forward_datasource_idx ,
595624 name_offset,
596625 start_x,
597626 start_y);
@@ -606,17 +635,26 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
606635 std::int32_t start_y = 0 ;
607636
608637 // Calculate the speed for this line
609- std::uint32_t speed_kmh =
638+ // Speeds are looked up in a simple 1:1 table, so the speed value == lookup
639+ // table index
640+ std::uint32_t speed_kmh_idx =
610641 static_cast <std::uint32_t >(round (length / reverse_duration * 10 * 3.6 ));
611642
643+ // Rate values are in meters per weight-unit - and similar to speeds, we
644+ // present 1 decimal place of precision (these values are added as
645+ // double/10) lower down
646+ std::uint32_t reverse_rate =
647+ static_cast <std::uint32_t >(round (length / reverse_weight * 10 .));
648+
612649 auto tile_line = coordinatesToTileLine (b, a, tile_bbox);
613650 if (!tile_line.empty ())
614651 {
615652 encode_tile_line (tile_line,
616- speed_kmh,
653+ speed_kmh_idx,
654+ line_int_offsets[reverse_rate],
617655 line_int_offsets[reverse_weight],
618656 line_int_offsets[reverse_duration],
619- reverse_datasource ,
657+ reverse_datasource_idx ,
620658 name_offset,
621659 start_x,
622660 start_y);
@@ -634,6 +672,7 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
634672 line_layer_writer.add_string (util::vector_tile::KEY_TAG, " weight" );
635673 line_layer_writer.add_string (util::vector_tile::KEY_TAG, " duration" );
636674 line_layer_writer.add_string (util::vector_tile::KEY_TAG, " name" );
675+ line_layer_writer.add_string (util::vector_tile::KEY_TAG, " rate" );
637676
638677 // Now, we write out the possible speed value arrays and possible is_tiny
639678 // values. Field type 4 is the "values" field. It's a variable type field,
@@ -695,19 +734,21 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
695734 {
696735 // we need to pre-encode all values here because we need the full offsets later
697736 // for encoding the actual features.
698- std::vector<std::tuple<util::Coordinate, unsigned , unsigned , unsigned >>
737+ std::vector<std::tuple<util::Coordinate, unsigned , unsigned , unsigned , unsigned >>
699738 encoded_turn_data (all_turn_data.size ());
700- std::transform (
701- all_turn_data.begin (),
702- all_turn_data.end (),
703- encoded_turn_data.begin (),
704- [&](const routing_algorithms::TurnData &t) {
705- auto angle_idx = use_point_int_value (t.in_angle );
706- auto turn_idx = use_point_int_value (t.turn_angle );
707- auto duration_idx =
708- use_point_float_value (t.duration / 10.0 ); // Note conversion to float here
709- return std::make_tuple (t.coordinate , angle_idx, turn_idx, duration_idx);
710- });
739+ std::transform (all_turn_data.begin (),
740+ all_turn_data.end (),
741+ encoded_turn_data.begin (),
742+ [&](const routing_algorithms::TurnData &t) {
743+ auto angle_idx = use_point_int_value (t.in_angle );
744+ auto turn_idx = use_point_int_value (t.turn_angle );
745+ auto duration_idx = use_point_float_value (
746+ t.duration / 10.0 ); // Note conversion to float here
747+ auto weight_idx = use_point_float_value (
748+ t.weight / 10.0 ); // Note conversion to float here
749+ return std::make_tuple (
750+ t.coordinate , angle_idx, turn_idx, duration_idx, weight_idx);
751+ });
711752
712753 // Now write the points layer for turn penalty data:
713754 // Add a layer object to the PBF stream. 3=='layer' from the vector tile spec
@@ -734,7 +775,7 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
734775 util::vector_tile::GEOMETRY_TYPE_POINT); // geometry type
735776 feature_writer.add_uint64 (util::vector_tile::ID_TAG, id++); // id
736777 {
737- // Write out the 3 properties we want on the feature. These
778+ // Write out the 4 properties we want on the feature. These
738779 // refer to indexes in the properties lookup table, which we
739780 // add to the tile after we add all features.
740781 protozero::packed_field_uint32 field (
@@ -745,6 +786,8 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
745786 field.add_element (std::get<2 >(point_turn_data));
746787 field.add_element (2 ); // "cost" tag key offset
747788 field.add_element (used_point_ints.size () + std::get<3 >(point_turn_data));
789+ field.add_element (3 ); // "weight" tag key offset
790+ field.add_element (used_point_ints.size () + std::get<4 >(point_turn_data));
748791 }
749792 {
750793 // Add the geometry as the last field in this feature
@@ -772,6 +815,7 @@ void encodeVectorTile(const datafacade::ContiguousInternalMemoryDataFacadeBase &
772815 point_layer_writer.add_string (util::vector_tile::KEY_TAG, " bearing_in" );
773816 point_layer_writer.add_string (util::vector_tile::KEY_TAG, " turn_angle" );
774817 point_layer_writer.add_string (util::vector_tile::KEY_TAG, " cost" );
818+ point_layer_writer.add_string (util::vector_tile::KEY_TAG, " weight" );
775819
776820 // Now, save the lists of integers and floats that our features refer to.
777821 for (const auto &value : used_point_ints)
0 commit comments