From: Torsten Dreyer Date: Tue, 13 May 2014 09:20:11 +0000 (+0200) Subject: More AtisSpeaker variations X-Git-Url: https://git.mxchange.org/?a=commitdiff_plain;h=ffe6c39a1dc2aa0874401613c4b5a8d62166e2ff;p=flightgear.git More AtisSpeaker variations Also hide the voice installation path from the user of the VoiceSynthesizer --- diff --git a/src/Instrumentation/commradio.cxx b/src/Instrumentation/commradio.cxx index 899e8f73a..e392b0fd4 100644 --- a/src/Instrumentation/commradio.cxx +++ b/src/Instrumentation/commradio.cxx @@ -75,27 +75,14 @@ public: _stationId = stationId; } - void setVoice(const string & voice) - { - _voice = voice; - } - - const string & getVoice() const - { - return _voice; - } private: SynthesizeRequest _synthesizeRequest; SGLockedQueue > _spokenAtis; string _stationId; - string _voice; }; AtisSpeaker::AtisSpeaker() - : - _voice("/ATC/cmu_us_arctic_slt.htsvoice") -// _voice("/ATC/cstr_uk_female-1.0.htsvoice") { _synthesizeRequest.listener = this; } @@ -107,29 +94,42 @@ AtisSpeaker::~AtisSpeaker() void AtisSpeaker::valueChanged(SGPropertyNode * node) { if (!fgGetBool("/sim/sound/working", false)) - return; + return; string newText = node->getStringValue(); if (_synthesizeRequest.text == newText) return; _synthesizeRequest.text = newText; + string voice = "cmu_us_arctic_slt"; + if (!_stationId.empty()) { // lets play a bit with the voice so not every airports atis sounds alike // but every atis of an airport has the same voice + // create a simple hash from the last two letters of the airport's id + unsigned char hash = 0; string::iterator i = _stationId.end() - 1; - if( i != _stationId.begin() ) + hash += *i; + + if( i != _stationId.begin() ) { --i; + hash += *i; + } - _synthesizeRequest.speed = ((*i) % 16) / 16.0; - _synthesizeRequest.pitch = ((*i) % 16) / 16.0; + _synthesizeRequest.speed = (hash % 16) / 16.0; + _synthesizeRequest.pitch = (hash % 16) / 16.0; + + // pick a voice + voice = FLITEVoiceSynthesizer::getVoicePath( + static_cast(hash % FLITEVoiceSynthesizer::VOICE_UNKNOWN) ); } + FGSoundManager * smgr = dynamic_cast(globals->get_soundmgr()); assert(smgr != NULL); - string voice = globals->get_fg_root() + _voice; + SG_LOG(SG_INSTR,SG_INFO,"AtisSpeaker voice is " << voice ); FLITEVoiceSynthesizer * synthesizer = dynamic_cast(smgr->getSynthesizer(voice)); synthesizer->synthesize(_synthesizeRequest); diff --git a/src/Sound/VoiceSynthesizer.cxx b/src/Sound/VoiceSynthesizer.cxx index 2a8aafee7..fb40b439c 100644 --- a/src/Sound/VoiceSynthesizer.cxx +++ b/src/Sound/VoiceSynthesizer.cxx @@ -26,6 +26,13 @@ #include #include +using std::string; + +static const char * VOICE_FILES[] = { + "cmu_us_arctic_slt.htsvoice", + "cstr_uk_female-1.0.htsvoice" +}; + class FLITEVoiceSynthesizer::WorkerThread: public OpenThreads::Thread { public: WorkerThread(FLITEVoiceSynthesizer * synthesizer) @@ -48,6 +55,21 @@ void FLITEVoiceSynthesizer::WorkerThread::run() } } +string FLITEVoiceSynthesizer::getVoicePath( voice_t voice ) +{ + if( voice < 0 || voice >= VOICE_UNKNOWN ) return string(""); + string voicePath = globals->get_fg_root() + "/ATC/" + VOICE_FILES[voice]; + return voicePath; +} + +string FLITEVoiceSynthesizer::getVoicePath( const string & voice ) +{ + if( voice == "cmu_us_arctic_slt" ) return getVoicePath(CMU_US_ARCTIC_SLT); + if( voice == "cstr_uk_female" ) return getVoicePath(CSTR_UK_FEMALE); + return getVoicePath(VOICE_UNKNOWN); +} + + void FLITEVoiceSynthesizer::synthesize( SynthesizeRequest & request) { _requests.push(request); diff --git a/src/Sound/VoiceSynthesizer.hxx b/src/Sound/VoiceSynthesizer.hxx index 1b8648a21..17fb4bc1f 100644 --- a/src/Sound/VoiceSynthesizer.hxx +++ b/src/Sound/VoiceSynthesizer.hxx @@ -76,6 +76,17 @@ struct SynthesizeRequest { */ class FLITEVoiceSynthesizer : public VoiceSynthesizer { public: + + typedef enum { + CMU_US_ARCTIC_SLT = 0, + CSTR_UK_FEMALE, + + VOICE_UNKNOWN // keep this at the end + } voice_t; + + static std::string getVoicePath( voice_t voice ); + static std::string getVoicePath( const std::string & voice ); + FLITEVoiceSynthesizer( const std::string & voice ); ~FLITEVoiceSynthesizer(); virtual SGSoundSample * synthesize( const std::string & text, double volume, double speed, double pitch );