4 * Created on: Apr 24, 2014
8 #include "VoiceSynthesizer.hxx"
9 #include <Main/globals.hxx>
10 #include <simgear/debug/logstream.hxx>
11 #include <simgear/sound/readwav.hxx>
12 #include <simgear/misc/sg_path.hxx>
13 #include <OpenThreads/Thread>
14 #include <flite_hts_engine.h>
16 class ScopedTempfile {
20 _name = ::tempnam(globals->get_fg_home().c_str(), "fgvox");
25 if (_name) ::unlink(_name);
29 const char * getName() const
41 class FLITEVoiceSynthesizer::WorkerThread: public OpenThreads::Thread {
43 WorkerThread(FLITEVoiceSynthesizer * synthesizer)
44 : _synthesizer(synthesizer)
49 FLITEVoiceSynthesizer * _synthesizer;
52 void FLITEVoiceSynthesizer::WorkerThread::run()
55 SynthesizeRequest request = _synthesizer->_requests.pop();
56 if ( NULL != request.listener) {
57 SGSharedPtr<SGSoundSample> sample = _synthesizer->synthesize(request.text);
58 request.listener->SoundSampleReady( sample );
63 void FLITEVoiceSynthesizer::synthesize( SynthesizeRequest & request)
65 _requests.push(request);
68 FLITEVoiceSynthesizer::FLITEVoiceSynthesizer(const std::string & voice)
69 : _engine(new Flite_HTS_Engine), _worker(new FLITEVoiceSynthesizer::WorkerThread(this))
71 Flite_HTS_Engine_initialize(_engine);
72 Flite_HTS_Engine_load(_engine, voice.c_str());
76 FLITEVoiceSynthesizer::~FLITEVoiceSynthesizer()
80 Flite_HTS_Engine_clear(_engine);
83 SGSoundSample * FLITEVoiceSynthesizer::synthesize(const std::string & text)
85 ScopedTempfile scratch;
86 if ( FALSE == Flite_HTS_Engine_synthesize(_engine, text.c_str(), scratch.getName())) return NULL;
88 SG_LOG(SG_SOUND, SG_ALERT, "created wav at " << scratch.getPath());
93 ALvoid * data = simgear::loadWAVFromFile(scratch.getPath(), format, size, freqf);
94 SG_LOG(SG_ALL, SG_ALERT, "loaded wav at " << freqf << "Hz size=" << size << " format=" << format);
97 SG_LOG(SG_SOUND, SG_ALERT, "Failed to load wav file " << scratch.getPath());
100 if (format == AL_FORMAT_STEREO8 || format == AL_FORMAT_STEREO16) {
102 SG_LOG(SG_SOUND, SG_ALERT, "Warning: STEREO files are not supported for 3D audio effects: " << scratch.getPath());
105 return new SGSoundSample(&data, size, (ALsizei) freqf, format);