Welcome to mirror list, hosted at ThFree Co, Russian Federation.

turns_sound_settings.hpp « routing - github.com/mapsme/omim.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: d53370856389441b8412316a450ea5123435be78 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
#pragma once

#include "routing/turns.hpp"

#include "platform/measurement_utils.hpp"

#include "std/vector.hpp"

namespace routing
{
namespace turns
{
namespace sound
{
/// \brief The Settings struct is a structure for gathering information about turn sound
/// notifications settings.
/// Part distance parameters shall be set in m_lengthUnits. (Meters of feet for the time being.)
/// Another part in meters. See the suffix to understand which units are used.
class Settings
{
  friend void UnitTest_TurnNotificationSettingsMetersTest();
  friend void UnitTest_TurnNotificationSettingsFeetTest();
  friend void UnitTest_TurnNotificationSettingsNotValidTest();

  uint32_t m_timeSeconds;
  uint32_t m_minDistanceUnits;
  uint32_t m_maxDistanceUnits;

  /// To inform an end user about the next turn with the help of an voice information message
  /// an operation system needs:
  /// - to launch TTS subsystem;
  /// - to pronounce the message.
  /// So to inform the user in time it's necessary to start
  /// m_startBeforeSeconds before the time. It is used in the following way:
  /// we start playing voice notice in m_startBeforeSeconds * TurnsSound::m_speedMetersPerSecond
  /// meters before the turn (for the second voice notification).
  /// When m_startBeforeSeconds * TurnsSound::m_speedMetersPerSecond is too small or too large
  /// we use m_{min|max}StartBeforeMeters to clamp the value.
  uint32_t m_startBeforeSeconds;
  uint32_t m_minStartBeforeMeters;
  uint32_t m_maxStartBeforeMeters;

  /// m_minDistToSayNotificationMeters is minimum distance between two turns
  /// when pronouncing the first notification about the second turn makes sense.
  uint32_t m_minDistToSayNotificationMeters;

  /// \brief m_distancesToPronounce is a list of distances in m_lengthUnits
  ///  which are ready to be pronounced.
  vector<uint32_t> m_soundedDistancesUnits;
  measurement_utils::Units m_lengthUnits;

  // This constructor is for testing only.
  Settings(uint32_t notificationTimeSeconds, uint32_t minNotificationDistanceUnits,
           uint32_t maxNotificationDistanceUnits, uint32_t startBeforeSeconds,
           uint32_t minStartBeforeMeters, uint32_t maxStartBeforeMeters,
           uint32_t minDistToSayNotificationMeters, vector<uint32_t> const & soundedDistancesUnits,
           measurement_utils::Units lengthUnits)
    : m_timeSeconds(notificationTimeSeconds)
    , m_minDistanceUnits(minNotificationDistanceUnits)
    , m_maxDistanceUnits(maxNotificationDistanceUnits)
    , m_startBeforeSeconds(startBeforeSeconds)
    , m_minStartBeforeMeters(minStartBeforeMeters)
    , m_maxStartBeforeMeters(maxStartBeforeMeters)
    , m_minDistToSayNotificationMeters(minDistToSayNotificationMeters)
    , m_soundedDistancesUnits(soundedDistancesUnits)
    , m_lengthUnits(lengthUnits)
  {
    ASSERT(!m_soundedDistancesUnits.empty(), ());
  }

public:
  Settings(uint32_t startBeforeSeconds, uint32_t minStartBeforeMeters,
           uint32_t maxStartBeforeMeters, uint32_t minDistToSayNotificationMeters)
    : m_timeSeconds(0)
    , m_minDistanceUnits(0)
    , m_maxDistanceUnits(0)
    , m_startBeforeSeconds(startBeforeSeconds)
    , m_minStartBeforeMeters(minStartBeforeMeters)
    , m_maxStartBeforeMeters(maxStartBeforeMeters)
    , m_minDistToSayNotificationMeters(minDistToSayNotificationMeters)
    , m_lengthUnits(measurement_utils::Units::Metric)
  {
  }

  void SetState(uint32_t notificationTimeSeconds, uint32_t minNotificationDistanceUnits,
                uint32_t maxNotificationDistanceUnits,
                vector<uint32_t> const & soundedDistancesUnits,
                measurement_utils::Units lengthUnits);

  /// \brief IsValid checks if Settings data is consistent.
  /// \warning The complexity is up to linear in size of m_soundedDistancesUnits.
  /// \note For any instance created by default constructor IsValid() returns false.
  bool IsValid() const;

  /// \brief computes the distance an end user shall be informed about the future turn.
  /// \param speedMetersPerSecond is a speed. For example it could be a current speed of an end
  /// user.
  /// \return distance in meters.
  uint32_t ComputeTurnDistanceM(double speedMetersPerSecond) const;

  /// \brief computes the distance which will be passed at the |speedMetersPerSecond|
  /// while pronouncing turn sound notification.
  uint32_t ComputeDistToPronounceDistM(double speedMetersPerSecond) const;

  /// @return true if distToTurnMeters is too short to start pronouncing first turn notification.
  bool TooCloseForFisrtNotification(double distToTurnMeters) const;

  /// \brief RoundByPresetSoundedDistancesUnits rounds off its parameter by
  /// m_soundedDistancesUnits.
  /// \param turnNotificationDistance is a distance in m_lengthUnits.
  /// \return the distance which will be used (will be pronounced) in the next turn sound
  /// notification in m_lengthUnits units. (Meters of feet for the time being.)
  /// The result will be one of the m_soundedDistancesUnits values.
  uint32_t RoundByPresetSoundedDistancesUnits(uint32_t turnNotificationUnits) const;

  inline measurement_utils::Units GetLengthUnits() const { return m_lengthUnits; }
  inline void SetLengthUnits(measurement_utils::Units units) { m_lengthUnits = units; }
  double ConvertMetersPerSecondToUnitsPerSecond(double speedInMetersPerSecond) const;
  double ConvertUnitsToMeters(double distanceInUnits) const;
  double ConvertMetersToUnits(double distanceInMeters) const;
  void ForTestingSetNotificationTimeSecond(uint32_t time) { m_timeSeconds = time; }
};

/// \brief The Notification struct contains all the information about the next sound
/// notification to pronounce.
struct Notification
{
  /// m_distanceUnits is a distance to the turn in m_lengthUnits (meters or feet).
  /// If m_distanceUnits == 0 then the information about distance to the turn shall
  /// not be pronounced.
  uint32_t m_distanceUnits;
  uint8_t m_exitNum;
  /// if m_useThenInsteadOfDistance == true the m_distanceUnits is ignored.
  /// The word "Then" shall be pronounced intead of the distance.
  bool m_useThenInsteadOfDistance;
  TurnDirection m_turnDir;
  measurement_utils::Units m_lengthUnits;

  Notification(uint32_t distanceUnits, uint8_t exitNum, bool useThenInsteadOfDistance,
               TurnDirection turnDir, measurement_utils::Units lengthUnits)
    : m_distanceUnits(distanceUnits)
    , m_exitNum(exitNum)
    , m_useThenInsteadOfDistance(useThenInsteadOfDistance)
    , m_turnDir(turnDir)
    , m_lengthUnits(lengthUnits)
  {
  }
  bool operator==(Notification const & rhv) const
  {
    return m_distanceUnits == rhv.m_distanceUnits && m_exitNum == rhv.m_exitNum &&
           m_useThenInsteadOfDistance == rhv.m_useThenInsteadOfDistance &&
           m_turnDir == rhv.m_turnDir && m_lengthUnits == rhv.m_lengthUnits;
  }
};

string DebugPrint(Notification const & turnGeom);

using PairDist = pair<uint32_t, char const *>;
using VecPairDist = vector<PairDist>;

/// @return a reference to a vector of pairs of a distance in meters and a text id.
/// All the distances are translated in supported languages and can be pronounced.
VecPairDist const & GetAllSoundedDistMeters();
/// @return a reference to a vector of pairs of a distance in feet and a text id.
/// All the distances are translated in supported languages and can be pronounced.
VecPairDist const & GetAllSoundedDistFeet();

// @TODO(vbykoianko) Now GetSoundedDistMeters/Feet() functions returns a subset of
// the result of GetAllSoundedDistMeters/Feet() functions. So GetAllSoundedDistMeters/Feet()
// returns more distances.
// After the tuning of turn sound notification is finished to do
// * remove all unnecessary distances from GetAllSoundedDistMeters/Feet().
// * remove all unnecessary string form resources. It let us to reduce the size of apk/ipa by
// 10-20KB.
// * remove GetSoundedDistMeters/Feet() and use lambda in TurnsSound::SetLengthUnits
// to convert from vector<pair<uint32_t, char const *>> to vector<uint32_t>.

/// @return distance in meters which are used for turn sound generation.
vector<uint32_t> const & GetSoundedDistMeters();
/// @return distance in feet which are used for turn sound generation.
vector<uint32_t> const & GetSoundedDistFeet();

}  // namespace sound
}  // namespace turns
}  // namespace routing