| 659 | } |
| 660 | |
| 661 | double CalcSegmentWeight(Segment const & segment, RoadGeometry const & road, Purpose purpose) const override |
| 662 | { |
| 663 | return CalcClimbSegment(purpose, segment, road, |
| 664 | [purpose, this](double speedMpS, double tangent, geometry::Altitude altitude) |
| 665 | { |
| 666 | auto const factor = GetBicycleClimbPenalty(purpose, tangent, altitude); |
| 667 | ASSERT_GREATER(factor, 0.0, ()); |
| 668 | |
| 669 | /// @todo Take out "bad" bicycle road (path, track, footway, ...) check into BicycleModel? |
| 670 | static double constexpr badBicycleRoadSpeed = KmphToMps(9); |
| 671 | if (speedMpS <= badBicycleRoadSpeed) |
| 672 | { |
| 673 | if (factor > 1) |
| 674 | speedMpS /= factor; |
| 675 | } |
| 676 | else if (factor > 1) |
| 677 | { |
| 678 | // Calculate uphill speed according to the average bicycle speed, because "good-roads" like |
| 679 | // residential, secondary, cycleway are "equal-low-speed" uphill and road type doesn't matter. |
| 680 | static double constexpr avgBicycleSpeed = KmphToMps(20); |
| 681 | double const upperBound = avgBicycleSpeed / factor; |
| 682 | if (speedMpS > upperBound) |
| 683 | { |
| 684 | // Add small weight to distinguish roads by class (10 is a max factor value). |
| 685 | speedMpS = upperBound + (purpose == Purpose::Weight ? speedMpS / (10 * avgBicycleSpeed) : 0); |
| 686 | } |
| 687 | } |
| 688 | else |
| 689 | speedMpS /= factor; |
| 690 | |
| 691 | return std::min(speedMpS, GetMaxWeightSpeedMpS()); |
| 692 | }); |
| 693 | } |
| 694 | }; |
| 695 | |
| 696 | double BicycleEstimator::GetTurnPenalty(Purpose purpose, double angle, RoadGeometry const & from_road, |
nothing calls this directly
no test coverage detected